* 16649 general contrast issues (#16759)
* fixes#16647: navigation contrast issues updated
* fixes#16651: table contrast issues new
* fixed#16649: general contrast issues
* fixes#16649: feedback changes
---------
Co-authored-by: Andrew Gormley <Andrew@MacBook-Pro-3.local>
Co-authored-by: Andrew Gormley <Andrew@MacBook-Pro-3.broadband>
* 16648 dashboard contrast issues (#16824)
* fixed#16648: dashboard contrast issues
* reinstate amendment to 16649
* fixed#16648: created gridstack override and removed inline bug fix
---------
Co-authored-by: Andrew Gormley <Andrew@MacBook-Pro-3.local>
* fixed#16853: accessibility issues
* fixed#16847: updated font (#16848)
* fixed#16847: updated font
* fixed#16847: changed font to local and added current font as fallback
* fixed#16847: removed inter and added padding to page header
---------
Co-authored-by: Andrew Gormley <Andrew@MacBook-Pro-3.local>
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* 16849 document hierarchy issues (#16875)
* fixed#16849: h elements not in sequential order
* fixed#16849: Lists do not contain only li elements
* fixed#16849: fixed h hierarchy on rack object pages
* Remove standalone h5 classes
* Remove unnecessary line breaks
---------
Co-authored-by: Andrew Gormley <Andrew@MacBook-Pro-3.local>
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* 16650 button contrast issues (#16845)
* fixed#16650: button contrast issues
* fixed#16650: green bg text contrast issue
* Revert errant JS resource updates
* Revert custom button colors
* Fix indentation
---------
Co-authored-by: Andrew Gormley <Andrew@MacBook-Pro-3.local>
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* 16907 web UI refresh (#16915)
* closes#16907: web ui refresh
* closes#16907: changed default widget color to primary color
* closes#16907: removed comma
* Revert dashboard widget color changes
* Rename logo images for consistency
* Restore original dashboard widget config
* Remove .navbar-brand-autodark from logo
* Restore logo file names
---------
Co-authored-by: Andrew Gormley <Andrew@MacBook-Pro-3.local>
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* 16394 distinguish product edition (#16924)
* closes#16907: web ui refresh
* closes#16907: changed default widget color to primary color
* closes#16907: removed comma
* closes#16394: distinguish product edition
* Revert dashboard changes
* Clean up redundant styling (merge error)
* removed labs logo and added sub text for all editions
* fixed motif bug
* Fix "flashing" of side nav under dark mode
* Use title case for edition label
* altered edition text style
---------
Co-authored-by: Andrew Gormley <Andrew@MacBook-Pro-3.local>
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Query release features to toggle commercial theme
* fixes dark mode primary button contrast issue
* fixes#16913: hidden admin nav link (#16978)
Co-authored-by: Andrew Gormley <Andrew@MacBook-Pro-3.local>
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* fixed 16852: misc accessbility problems (#16977)
* fixed 16852: misc accessbility problems
* Restore tooltip text
* Add translation support
* Add missing i18n
---------
Co-authored-by: Andrew Gormley <Andrew@MacBook-Pro-3.local>
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* fixes issues in #16850 (#16986)
* fixes issues in #16850: issue 3 and 5
* Add link text for 'clear' button on table column
* Translate aria label
---------
Co-authored-by: Andrew Gormley <Andrew@MacBook-Pro-3.local>
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Use alternate footer links for commercial releases
* Remove Inter font
* Adjust base font weight to 500
* Retain default text color for hyperlinks inside tables
* Logo & edition cleanup
* Move dashboard styling
* Misc cleanup
* Remove unused styles
* Misc cleanup & refactoring
---------
Co-authored-by: Andrew Gormley <andrewgormley91@gmail.com>
Co-authored-by: Andrew Gormley <Andrew@MacBook-Pro-3.local>
Co-authored-by: Andrew Gormley <Andrew@MacBook-Pro-3.broadband>
* Introduce reusable BackgroundJob framework
A new abstract class can be used to implement job function classes. It
handles the necessary logic for starting and stopping jobs, including
exception handling and rescheduling of recurring jobs.
This commit also includes the migration of data source jobs to the new
framework.
* Restore using import_string for jobs
Using the 'import_string()' utility from Django allows the job script
class to be simplified, as module imports no longer need to avoid loops.
This should make it easier to queue and maintain jobs.
* Use SyncDataSourceJob for management command
Instead of maintaining two separate job execution logics, the same job
is now used for both background and interactive execution.
* Implement BackgroundJob for running scripts
The independent implementations of interactive and background script
execution have been merged into a single BackgroundJob implementation.
* Fix documentation of model features
* Ensure consitent code style
* Introduce reusable ScheduledJob
A new abstract class can be used to implement job function classes that
specialize in scheduling. These use the same logic as regular
BackgroundJobs, but ensure that they are only scheduled once at any given
time.
* Introduce reusable SystemJob
A new abstract class can be used to implement job function classes that
specialize in system background tasks (e.g. synchronization or
housekeeping). In addition to the features of the BackgroundJob and
ScheduledJob classes, these implement additional logic to not need to be
bound to an existing NetBox object and to setup job schedules on plugin
load instead of an interactive request.
* Add documentation for jobs framework
* Revert "Use SyncDataSourceJob for management"
This partially reverts commit db591d4. The 'run_now' parameter of
'enqueue()' remains, as its being used by following commits.
* Merge enqueued status into JobStatusChoices
* Fix logger for ScriptJob
* Remove job name for scripts
Because scripts are already linked through the Job Instance field, the
name is displayed twice. Removing this reduces redundancy and opens up
the possibility of simplifying the BackgroundJob framework in future
commits.
* Merge ScheduledJob into BackgroundJob
Instead of using separate classes, the logic of ScheduledJob is now
merged into the generic BackgroundJob class. This allows reusing the
same logic, but dynamically deciding whether to enqueue the same job
once or multiple times.
* Add name attribute for BackgroundJob
Instead of defining individual names on enqueue, BackgroundJob classes
can now set a job name in their meta class. This is equivalent to other
Django classes and NetBox scripts.
* Drop enqueue_sync_job() method from DataSource
* Import ScriptJob directly
* Relax requirement for Jobs to reference a specific object
* Rename 'run_now' arg on Job.enqueue() to 'immediate'
* Fix queue lookup in Job enqueue
* Collapse SystemJob into BackgroundJob
* Remove legacy JobResultStatusChoices
ChoiceSet was moved to core in 40572b5.
* Use queue 'low' for system jobs by default
System jobs usually perform low-priority background tasks and therefore
can use a different queue than 'default', which is used for regular jobs
related to specific objects.
* Add test cases for BackgroundJob handling
* Fix enqueue interval jobs
As the job's name is set by enqueue(), it must not be passed in handle()
to avoid duplicate kwargs with the same name.
* Honor schedule_at for job's enqueue_once
Not only can a job's interval change, but so can the time at which it is
scheduled to run. If a specific scheduled time is set, it will also be
checked against the current job schedule. If there are any changes, the
job is rescheduled with the new time.
* Switch BackgroundJob to regular methods
Instead of using a class method for run(), a regular method is used for
this purpose. This gives the possibility to add more convenience methods
in the future, e.g. for interacting with the job object or for logging,
as implemented for scripts.
* Fix background tasks documentation
* Test enqueue in combination with enqueue_once
* Rename background jobs to tasks (to differentiate from RQ)
* Touch up docs
* Revert "Use queue 'low' for system jobs by default"
This reverts commit b17b2050df.
* Remove system background job
This commit reverts commits 4880d81 and 0b15ecf. Using the database
'connection_created' signal for job registration feels a little wrong at
this point, as it would trigger registration very often. However, the
background job framework is prepared for this use case and can be used
by plugins once the auto-registration of jobs is solved.
* Fix runscript management command
Defining names for background jobs was disabled with fb75389. The
preceeding changes in 257976d did forget the management command.
* Use regular imports for ScriptJob
* Rename BackgroundJob to JobRunner
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Closes#16964: Validate password when creating a new user or updating password for an existing user
* Add serializer validation & tests
---------
Co-authored-by: Nishant Gaglani <nishantgaglani@gmail.com>
The GitHub reactions icon has been moved from the top right to the bottom left of messages in Issues - I was going insane trying to find it, so this might help someone in the future ; )
* Fixes 16536 - Fix filtering of device component by device role
Rename role and role_id fields to device_role and device_role_id in
DeviceComponentFilterSet
* Update tests for DeviceComponentFilterSet
* Use device_role filter name for DeviceComponentFilterSetTests
* Add test_device_role test in InventoryItemTestCase
* Added CS, DA, IT, NL, and PL, minus the .po and .mo starting point files
* Add initial PO files for new languages
* Revert updates to EN django.po
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Fixes#16760: datasource git on local file system fails
* Fixes#16760: datasource git on local file system fails
* Set depth & quiet parameters only if using a remote URL
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Closes#16964: Validate password when creating a new user or updating password for an existing user
* Add serializer validation & tests
---------
Co-authored-by: Nishant Gaglani <nishantgaglani@gmail.com>
The GitHub reactions icon has been moved from the top right to the bottom left of messages in Issues - I was going insane trying to find it, so this might help someone in the future ; )
* 12826 add RackType
* 12826 add forms, filters, tables
* 12826 add to menu
* 12826 remove role
* 12826 add api/serializers
* 12826 add tests and fixes
* 12826 fix tests
* 12826 fix tests
* 12826 fix tests
* 12826 fix tests
* 12826 add device_type to device and instantiation
* 12826 test device creation
* 12826 add slug
* 12826 fix tests
* 12826 fix slug field
* 12826 prevent modification of rack fields if rack_type set
* 12826 update rack fields on rack_type edit
* Misc cleanup
* Update model docs
* Add manufacturer field to RackType
* Add test for mounting_depth
* Rename 'type' to 'form_factor'
* Create base classes for Rack & RackType models, serializers
* Hide RackType-defined fields on RackForm when a rack type is set
* Establish a base filter form for Rack & RackType
* Clean up RackType attr inheritance
* Clean up templates
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Initial work on #15621
* Signal receiver should ignore models which don't support notifications
* Flesh out NotificationGroup functionality
* Add NotificationGroup filters for users & groups
* Separate read & dimiss actions
* Enable one-click dismissals from notifications list
* Include total notification count in dropdown
* Drop 'kind' field from Notification model
* Register event types in the registry; add colors & icons
* Enable event rules to target notification groups
* Define dynamic choices for Notification.event_name
* Move event registration to core
* Add more job events
* Misc cleanup
* Misc cleanup
* Correct absolute URLs for notifications & subscriptions
* Optimize subscriber notifications
* Use core event types when queuing events
* Standardize queued event attribute to event_type; change content_type to object_type
* Rename Notification.event_name to event_type
* Restore NotificationGroupBulkEditView
* Add API tests
* Add view & filterset tests
* Add model documentation
* Fix tests
* Update notification bell when notifications have been cleared
* Ensure subscribe button appears only on relevant models
* Notifications/subscriptions cannot be ordered by object
* Misc cleanup
* Add event icon & type to notifications table
* Adjust icon sizing
* Mute color of read notifications
* Misc cleanup
* Fixes 16536 - Fix filtering of device component by device role
Rename role and role_id fields to device_role and device_role_id in
DeviceComponentFilterSet
* Update tests for DeviceComponentFilterSet
* Use device_role filter name for DeviceComponentFilterSetTests
* Add test_device_role test in InventoryItemTestCase
* Added CS, DA, IT, NL, and PL, minus the .po and .mo starting point files
* Add initial PO files for new languages
* Revert updates to EN django.po
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Fixes#16760: datasource git on local file system fails
* Fixes#16760: datasource git on local file system fails
* Set depth & quiet parameters only if using a remote URL
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in fr [Manual Sync]
12% of minimum 1% reviewed source file: 'django.po'
on 'fr'.
Sync of partially translated files:
untranslated content is included with an empty translation
or source language content depending on file format
* Translate django.po in pt [Manual Sync]
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in de [Manual Sync]
78% of minimum 1% reviewed source file: 'django.po'
on 'de'.
Sync of partially translated files:
untranslated content is included with an empty translation
or source language content depending on file format
* Translate django.po in tr [Manual Sync]
7% of minimum 1% reviewed source file: 'django.po'
on 'tr'.
Sync of partially translated files:
untranslated content is included with an empty translation
or source language content depending on file format
* Translate django.po in ru [Manual Sync]
30% of minimum 1% reviewed source file: 'django.po'
on 'ru'.
Sync of partially translated files:
untranslated content is included with an empty translation
or source language content depending on file format
* Translate django.po in zh [Manual Sync]
16% of minimum 1% reviewed source file: 'django.po'
on 'zh'.
Sync of partially translated files:
untranslated content is included with an empty translation
or source language content depending on file format
---------
Co-authored-by: transifex-integration[bot] <43880903+transifex-integration[bot]@users.noreply.github.com>
* Allowed configuration of Sentry send_default_pii parameter.
Also changed default value of send_default_pii to False to avoid sending sensitive data to Sentry.
Closes#16802
* Order alphabetically & link to Sentry parameter documentation
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Extend STORAGE_BACKEND config to support Swift
Requires django-storage-swift >= 1.4.0 when used.
Bug: T310717
Change-Id: I67cf439e9152608cbba3a3de4173d54ba5fbddc2
* Update system.md from suggestions
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Update settings.py from suggestions
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Update system.md from suggestions 2
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Remove SWIFT storage from configuration_example.py
* Load swift config as global instead of monkey path
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Do not delete all search indexes when reindexing specific models
* Clear all indexes only if neither --lazy nor a list of models are
specified for "manage.py reindex"
* Otherwise, clear the index for a model immediately before rebuilding
it
* Separated clearing from re-indexing the search cache
* I replaced `append` with `insert` into menu.py to make the admin section appear last in the navigation menu.
* Clean up ordering logic
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Was added to searching support languages other than English for object types(s).
* Fix SearchForm field label translation
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Added `help_text` to ColorField.
* Addressed PR comment to remove the redundant help_text from all the forms where ColorField was used.
* Add space before example value
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in pt
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in fr [Manual Sync]
12% of minimum 1% reviewed source file: 'django.po'
on 'fr'.
Sync of partially translated files:
untranslated content is included with an empty translation
or source language content depending on file format
* Translate django.po in pt [Manual Sync]
100% reviewed source file: 'django.po'
on 'pt'.
* Translate django.po in ru [Manual Sync]
30% of minimum 1% reviewed source file: 'django.po'
on 'ru'.
Sync of partially translated files:
untranslated content is included with an empty translation
or source language content depending on file format
* Translate django.po in de [Manual Sync]
75% of minimum 1% reviewed source file: 'django.po'
on 'de'.
Sync of partially translated files:
untranslated content is included with an empty translation
or source language content depending on file format
* Translate django.po in tr [Manual Sync]
7% of minimum 1% reviewed source file: 'django.po'
on 'tr'.
Sync of partially translated files:
untranslated content is included with an empty translation
or source language content depending on file format
---------
Co-authored-by: transifex-integration[bot] <43880903+transifex-integration[bot]@users.noreply.github.com>
* Fixes#15717: Allow VM with Site to Cluster without Site
* Fixes#15717: Allow VM with Site to Cluster without Site
* Fixes#15717: Allow VM with Site to Cluster without Site
* Fixes#15717: Allow VM with Site to Cluster without Site
* Fixes#15717: Allow VM with Site to Cluster without Site
* Added dropdown for Saved Filters.
* Added dropdown for Saved Filters.
* Added dropdown for Saved Filters.
* Fixed linter issues in savedFiltersSelect.ts
* Fixed linter issues in netbox.ts
* Fixed linter issues in netbox.ts
* Removed the blue tag with the filters when saved filters is selected.
* Adjusts in table_controls_htmx.html to vertical height of the Quick Search match to the dropdown.
* Adjusts in table_controls_htmx.html to vertical height of the Quick Search match to the dropdown.
* Adjusts in table_controls_htmx.html to vertical height of the Quick Search match to the dropdown.
* Minor adjusts in savedFiltersSelect.ts
* Addressed PR comment.
* Addressed PR comment.
* Addressed PR comment.
* Omit saved filters from 'applied filters'; clean up form widget
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* 7537 add serial number to virtual machines
* 7537 add migration
* 7537 add sn to search
* 7537 add to model documentation
* 8984 move serializer field
* 8984 add to detail view and search index
* 7537 serial_number -> serial
* 7537 fix migration
* Add missing serial field
* Give serial field higher precedence for search
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Closes#15794: Make "related objects" dynamic
Instead of hardcoding relationships between models for the detail view,
they are now dynamically generated.
* Fix related models call
* Remove extra related models hook
Instead of providing a rarely used hook method, additional related
models can now be passed directly to the lookup method.
* Fix relations view for ASNs
ASNs have ManyToMany relationships and therefore can't used automatic
resolving. Explicit relations have been restored as before.
* Add method call keywords for clarification
* Cleanup related models
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Translate django.po in de [Manual Sync]
74% of minimum 1% reviewed source file: 'django.po'
on 'de'.
Sync of partially translated files:
untranslated content is included with an empty translation
or source language content depending on file format
* Translate django.po in de [Manual Sync]
74% of minimum 1% reviewed source file: 'django.po'
on 'de'.
Sync of partially translated files:
untranslated content is included with an empty translation
or source language content depending on file format
* Translate django.po in ru [Manual Sync]
30% of minimum 1% reviewed source file: 'django.po'
on 'ru'.
Sync of partially translated files:
untranslated content is included with an empty translation
or source language content depending on file format
* Translate django.po in pt [Manual Sync]
2% of minimum 1% reviewed source file: 'django.po'
on 'pt'.
Sync of partially translated files:
untranslated content is included with an empty translation
or source language content depending on file format
* Translate django.po in fr [Manual Sync]
12% of minimum 1% reviewed source file: 'django.po'
on 'fr'.
Sync of partially translated files:
untranslated content is included with an empty translation
or source language content depending on file format
* Translate django.po in tr [Manual Sync]
7% of minimum 1% reviewed source file: 'django.po'
on 'tr'.
Sync of partially translated files:
untranslated content is included with an empty translation
or source language content depending on file format
---------
Co-authored-by: transifex-integration[bot] <43880903+transifex-integration[bot]@users.noreply.github.com>
* Created "convert_byte_size" method to convert the memory and disk size according to unit informed.
Changed "get_extra_context" method from "ClusterView" to use the method above and convert all the disks and memories from VMs to normalize the units.
* Changed decimal size for memory_sum and disk_sum
* Added test for convert_byte_size.
* Fixed
* Addressed PR comments.
Changed humanize_megabytes in helpers.py
* Addressed PR comments.
Changed humanize_megabytes in helpers.py
* Linter issues for helpers.py
* Changed humanize_megabytes
* Changed humanize_megabytes
* Changed humanize_megabytes
* Added the title to display the value in MB when mouseover.
* Addressed PR comment.
* Addressed PR comment.
* Rewrite sizing logic
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* 16050 Show script python_class name and description
* 16050 change to use Meta.description
* 16050 change to use Meta.description
* 16050 remove module name customization from docs
* Fixes: #16083 - Add font-variant-ligatures setting to disable ligatures on chromium
* Fix comment
* Disable ligatures on input fields
* Condense rules & apply to all elements
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Fix row highlighting
* Minor fix for VMInterfaces
* Move duplicated dicts into inheritable meta class
* Add CableTerminationTable.Meta class for inheritance of the row_attrs to each descendant Meta class.
* 16145 script api use module.script name instead of pk
* 16145 fix test
* 16145 allow both pk and script name
* 16145 update doc string
* Simplify retrieval logic
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Fixes#15962: support Redis Unix sockets
* Clean up language & remove obsolete note
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* 14953 fix serializers when using add_related_count
* 14953 update comments
* Set default=0 for annotated count fields
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Translate django.po in ja
100% translated source file: 'django.po'
on 'ja'.
* Translate django.po in uk
100% translated source file: 'django.po'
on 'uk'.
* Translate django.po in de
100% translated source file: 'django.po'
on 'de'.
* Translate django.po in zh
100% translated source file: 'django.po'
on 'zh'.
---------
Co-authored-by: transifex-integration[bot] <43880903+transifex-integration[bot]@users.noreply.github.com>
* add USE_I18N setting
* change setting name to ENABLE_TRANSLATION
* raise a warning in the UI when translation is disabled
* Misc cleanup
* Rename to TRANSLATION_ENABLED for consistency with other settings
---------
Co-authored-by: Anton Myasnikov <anton.myasnikov@nordigy.ru>
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Closes#16090: Show NetBox version if plugin validation fails
* Shorten error message
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* slim-select-pagination-bug-fix : fixed several bugs related to slim
select search box gui element
1. If user enters a search text in the filter text box, the user will
not be able to scroll to the next page. That is the user will only be
able to see the first page of returned item with a none empty search
string.
2. User will not be able to select an item returned from search query
if user clicks reload after a dynami search. When the user is able
to load a second page, the user will be able to select an item from
the third+ page if previous bug is fixed.
* Recompile static assets
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* slim-select-pagination-bug-fix : fixed several bugs related to slim
select search box gui element
1. If user enters a search text in the filter text box, the user will
not be able to scroll to the next page. That is the user will only be
able to see the first page of returned item with a none empty search
string.
2. User will not be able to select an item returned from search query
if user clicks reload after a dynami search. When the user is able
to load a second page, the user will be able to select an item from
the third+ page if previous bug is fixed.
* Recompile static assets
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* 15802 change table anchor color
* 15802 make link color lighter
* 15802 lighten table color
* 15802 add comment
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* 15831 monkeypatch LDAP _mirror_group function for NB4
* 15831 monkeypatch LDAP _mirror_group function for NB4
* 15831 monkeypatch LDAP _mirror_group function for NB4
* Move the modified _mirror_groups() method to a separate module to retain license
* 15831 fix import
* 15831 fix import
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Fix cable edit form with single unterminated cable
* Minor tweaks
* Instead of skipping HTMX, override the template & move form template to an "htmx" template
* Use HTMXSelect widget for A/B type selection
* Infer A/B termination types from POST data
* Fix saving cable which results in resetting of the termination type fields
* Condense view logic
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Fixes#15812: Add Date(Time)Var for scripts to allow much easier date input
* Extend tests for invalid data
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Closes#14690: Pretty-format JSON fields in the config form
* Revert changes
* Use our own JSONField for config parameters for pretty editor outputs
* Compare identity instead of equality
* 15761 filter IKEAProposals on IKEAPolicy detail view
* Add test for ike_policy filter
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* 5509 add content type data to model tests create and update
* 5509 update use cf form data
* 5509 update tests to use CustomFieldTypeChoices
* 5509 update tests to check custom fields
* Simplify custom fields used for testing
* Move custom field data functions to testing.utils
* Move validate_custom_field_data() into assertInstanceEqual()
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Introduce the isodate(), isotime(), and isodatetime() template filters
* Display the relative time on mouse hover
* Render journal entry times in ISO 8601 format
* Use ISO 8601 format when displaying dates & times in a table
* Standardize the use of DateTimeColumn across all tables
* Fix typos in migration-v4.md
* Replace typing.List with list
typing.List is deprecated since Python 3.9
* Also replace typing.List with list in graphql-api.md
* Added SECURE_HSTS_SECONDSm SECURE_HSTS_INCLUDE_SUBDOMAINS, and SECURE_HSTS_PRELOAD to settings.py
* Addressed some PR comments.
* Apply suggestions from code review
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Enable HTMX boosting
* Refactor HTMX properties for tables
* Fix dashboard object list widget
* Disable scrolling to page content
* Fix initialization of TomSelect dropdowns after HTMX loading
* Replace formaction properties with hx-post
* Fix quick search field on object list view
* Reinitialize copy-to-clipboard buttons upon HTMX load
* Disable scrolling effect for intra-page navigation
* Introduce user preference for toggling HTMX navigation
* Enable HTMX navigation only when selected by user
* Pass htmx_navigation context
* Fix display of confirmation form when deleting an object
* Disable HTMX boosting for rack elevation SVG downloads
* Fix dyanmic form rendering
* Introduce htmx_boost template tag; enable HTMX for user menu
* Use out-of-band sap to update footer stamp
* Fix display of toasts after form submission
* Fix user preference selection
* Misc cleanup
* Rename render_partial() to htmx_partial()
* Add docstring to htmx_boost template tag
* Disable HTMX for user preferences form to force a full page refresh on changes
* Fix left padding of login button in top menu
* Relocate "add" buttons for embedded object tables
* Remove unused data template block & getNetboxData() utility function
* Remove bottom margin from last <p> element in rendered Markdown inside a table cell
* Prevent TomSelect from initializing on <select> elements with a size
* Fix styling of dropdown menu button for circuit commit rate
* Change .color-block to display: inline-block
* Delete unused static asset
* Improve contrast between menu group headings & items
* Remove custom color for attr-table row headings
* Fix border color of copy-to-clipboard button
* Fix toast text color in dark mode
* Fix rack elevation label/image toggles
* Increase border radius for small buttons
* Fix object selector
* Rename sequences & indexes after renaming users table
* Migrate from auth.Group to a custom group model
* Delete original groups from auth_group table
* Update object & multi-object custom fields referencing the Group model
* Fix ContentType resolution
* Clean up obsolete logic for view/serializer resolution
- Introduces the Script model to represent individual Python classes within a ScriptModule file
- Automatically migrates jobs & event rules
---------
Co-authored-by: Jeremy Stretch <jstretch@netboxlabs.com>
* Introduce RelatedObjectCountField
* Introduce get_annotations_for_serializer() and enable dynamic annotations
* Add RelatedObjectCountFields to serializers; remove static annotations from querysets
* Remove annotations cleanup logic from BriefModeMixin
* Annotate type for RelatedObjectCountField
* Remove redundant field on TagSerializer
* Add missing reverse relationship for power feeds to rack
* Refactor RelatedObjectCountField to take a single relationship name
* Enable dynamic field inclusion for REST API serializers
* Recurse through nested serializer when resolving prefetches
* Remove obsolete calls to prefetch_related() for API views
* Remove support for brief_prefetch_fields viewset attribute
* Rename query parameter
* Fixes#15133: Fix FHRP group representation on assignments endpoint under brief mode (#15134)
* Fixes#15133: Fix FHRP group representation on assignments endpoint under brief mode
* Update API test
* Restore get_queryset() on BriefModeMixin, minus prefetch logic
* get_prefetches_for_serializer() should reference serializer field source if set
* Initial work on #13283
* Enable passing TomSelect HTML template attibutes on DynamicModelChoiceField
* Merge disabled_indicator into option_attrs
* Add support for annotating a numeric count on dropdown options
* Annotate parent object on relevant fields
* Improve rendering of color options
* Improve rendering of color options
* Rename option_attrs to context
* Expose option context on ObjectVar for custom scripts
* Document dropdown context variables
* Experimenting
* Remove testing resources
* Replace ApiSelect with TomSelect
* Add color support
* Add clear button
* Clear cached options when searching dynamic selects
* Add support for static parameters
* Refactor TomSelect implementation
* Add dynamic parameter support
* Limit number of options to 100
* Remove redundant api_url definitions for user model
* Add support for disabled indicator
* Remove obsolete value-field attr on dynamic select widgets
* Remove obsolete fetch_trigger kwarg from dynamic model choice widgets
* Remove obsolete empty_label kwarg from dynamic model choice widgets
* Add support for API path variables
* Add support for setting a 'null' option
* Annotate depth for recursive hierarchies
* Misc cleanup
* Remove obsolete APISelect code
* Remove slim-select & just-debounce-it
* Clean up type validation
* Closes#14237: Clear child selections on change to parent selection
* Use an MD icon for the clear button
* Use an MD icon for the clear button
* Explain why noUnusedParameters is disabled
Clean up spacing for nav pills
Markdown fields should default to using monospace font
Wrap action buttons in object page header
Fix page link style for non-HTMX paginators
Clean up styling of Markdown preview widget
Fix spacing around placeholder text for empty panel tables
Remove obsolete templates
Tweak checkbox input spacing
Fix toggling of clear button for quick search
Fix positioning of quick search filter dropdown
Fix positioning of 'highlight device' button
Fix styling for custom field group names
Widen buttons on nav menu items
Restyle the login page
Fix active nav-pill background color in dark mode
Fix spacing around 'map' button for sites
* Introduce custom form widget templates to apply CSS classes
* Apply both mandatory and optional CSS classes to form widgets
* Omit required & placeholder attrs
* Move annotation of field validation failures to CSS
* Remove BootstrapMixin class
* Remove obsolete ComponentTemplateImportForm class
* Remove obsolete custom forms for login & password change
* Clean up obsolete accommodations for 'required' widget attr
* Remove dark mode styling
* Condense & rename light mode stylesheet
* Upgrade to Bootstrap 5.3.2
* Swap out Bootstrap for Tabler; remove custom styling
* Update base page layout for Tabler
* Update login page
* Bump node to v18
* Update button styles
* Update object list view
* Tweak navbar size
* Clean up dashboard widgets
* Ditch separate stylesheet for print media
* Remove simplebar
* Remove obsolete sidebar styling
* Clean up object view template
* Clean up object edit template
* Standardize primary button sizing
* Clean up object list styling
* Add buttons for add & import to navigation menu
* Fix global search bar
* Fix slim-select form widget styling
* Fix toast styling
* Set base fonts
* Clean up paginator styling
* Clean up navigation menu group headings
* Clean up footer links
* Clean up card styles
* Move SVG styles to a designated directory
* Restructure SCSS files
* Remove obsolete/redundant dependencies
* Fix icon spacing
* Update background color classes
* Tweak banner & footer styling and spacing
* Fix badge background colors in table content
* Bump @types/bootstrap to 5.2.10
* Clean up form layouts
* Fix object selector button style
* Fix icon padding inside small buttons
* Fix icon & badge spacing inside buttons and tabs
* Hide paginator for empty pages
* Fix hover color for list items (Tabler bug #1694)
* Fix width of checkbox column in empty tables
* Clean up bulk edit template
* Fix border color of reslug button
* Package & serve Google fonts locally
* Fix tab styling
* Reduce vetical space at top of dashboard
* Remove obsolete content-wrapper template block
* Fix icon spacing in dropdown menu items
* Fix color label sizing
* Separate bulk delete form & object list into tabs
* Fix styling of filter group headings
* Fix styling for object changelog & journal views
* Standardize ordering & styling of action buttons
* Fix designation of active menu item
* Automatically expand menu section containing the active link
* Clean up nav menu styling
* Remove button colors; hide buttons except on hover/active
* Highlight menu group containing the active item
* Update & standardize alert styling
* Refactor base templates to ensure consistent display of header content
* Tweak styling for links inside badges
* Clean up top menu
* Fix JSON/YAML toggles for config context data
* Fix object template header
* Constrain tabs to container-xl; tweak header margins
* Fix object identifier styling
* Fix positioning of card header buttons
* Remove padding from HTMX tables inside cards
* Ensure consistent use of row headings in attribute tables
* Remove padding surrounding tables inside cards
* Remove obsolete CSS classes
* Misc cleanup of old styling
* Refactor 'controls' template block; ditch old classes
* Fix login button sizing
* Limit object edit form width
* Append asterisk to required form field labels
* Remove obsolete styling
* Remove obsolete styling
* Fix position of progress bar outside label
* Fix alignment of delete button in report/script lists
* Fix <pre> styling
* Clean up page headers
* Replace SVG icons with Material Design icons
* Restore dark mode togle functionality
* Fix top navbar background color under dark mode
* Rebuild static assets
This commit updates the cable rendering logic to fix
both issue #14722 and #13922. Before, objects, terminations
and cables where drawn in the svg without context of each
other.
Now the following changes are applied:
- Hosts and Terminations are where possible sorted alphabetically
- Terminations and Cables are visually connected, and if necessary not in a vertical line
- Terminations and Hosts are visually aligning
- Cable Tooltips contain more information
@@ -40,7 +40,7 @@ NetBox users are welcome to participate in either role, on stage or in the crowd
* First, ensure that you're running the [latest stable version](https://github.com/netbox-community/netbox/releases) of NetBox. If you're running an older version, it's likely that the bug has already been fixed.
* Next, search our [issues list](https://github.com/netbox-community/netbox/issues?q=is%3Aissue) to see if the bug you've found has already been reported. If you come across a bug report that seems to match, please click "add a reaction" in the top right corner of the issue and add a thumbs up (:thumbsup:). This will help draw more attention to it. Any comments you can add to provide additional information or context would also be much appreciated.
* Next, search our [issues list](https://github.com/netbox-community/netbox/issues?q=is%3Aissue) to see if the bug you've found has already been reported. If you come across a bug report that seems to match, please click "add a reaction" in the bottom left corner of the issue and add a thumbs up (:thumbsup:). This will help draw more attention to it. Any comments you can add to provide additional information or context would also be much appreciated.
* If you can't find any existing issues (open or closed) that seem to match yours, you're welcome to [submit a new bug report](https://github.com/netbox-community/netbox/issues/new?label=type%3A+bug&template=bug_report.yaml). Be sure to complete the entire report template, including detailed steps that someone triaging your issue can follow to confirm the reported behavior. (If we're not able to replicate the bug based on the information provided, we'll ask for additional detail.)
@@ -17,7 +17,6 @@ NetBox exists to empower network engineers. Since its release in 2016, it has be
<a href="#why-netbox">Why NetBox?</a> |
<a href="#getting-started">Getting Started</a> |
<a href="#get-involved">Get Involved</a> |
<a href="#project-stats">Project Stats</a> |
<a href="#screenshots">Screenshots</a>
</p>
@@ -95,16 +94,6 @@ NetBox automatically logs the creation, modification, and deletion of all manage
* Contributions from the community are encouraged and appreciated! Check out our [contributing guide](CONTRIBUTING.md) to get started.
* [Share your idea](https://plugin-ideas.netbox.dev/) for a new plugin, or [learn how to build one](https://github.com/netbox-community/netbox-plugin-tutorial) yourself!
@@ -16,7 +16,7 @@ Administrators are encouraged to adhere to industry best practices concerning th
## Reporting a Suspected Vulnerability
If you believe you've uncovered a security vulnerability and wish to report it confidentially, you may do so via email. Please note that any reported vulnerabilities **MUST** meet all the following conditions:
If you believe you've uncovered a security vulnerability and wish to report it confidentially, you may do so by emailing `security@netboxlabs.com`. Please ensure that your report meets all the following conditions:
* Affects the most recent stable release of NetBox, or a current beta release
* Affects a NetBox instance installed and configured per the official documentation
@@ -24,7 +24,7 @@ If you believe you've uncovered a security vulnerability and wish to report it c
Please note that we **DO NOT** accept reports generated by automated tooling which merely suggest that a file or file(s) _may_ be vulnerable under certain conditions, as these are most often innocuous.
If you believe that you've found a vulnerability which meets all of these conditions, please [submit a draft security advisory](https://github.com/netbox-community/netbox/security/advisories/new) on GitHub, or email a brief description of the suspected bug and instructions for reproduction to **security@netbox.dev**. For any security concerns regarding NetBox deployed via Docker, please see the [netbox-docker](https://github.com/netbox-community/netbox-docker) project.
For any security concerns regarding the community-maintained Docker image for NetBox, please see the [netbox-docker](https://github.com/netbox-community/netbox-docker) project.
@@ -73,7 +73,7 @@ You should be redirected to Microsoft's authentication portal. Enter the usernam
If successful, you will be redirected back to the NetBox UI, and will be logged in as the AD user. You can verify this by navigating to your profile (using the button at top right).
This user account has been replicated locally to NetBox, and can now be assigned groups and permissions by navigating to Admin > Permissions.
This user account has been replicated locally to NetBox, and can now be assigned groups and permissions.
@@ -67,4 +67,4 @@ You should be redirected to Okta's authentication portal. Enter the username/ema
If successful, you will be redirected back to the NetBox UI, and will be logged in as the Okta user. You can verify this by navigating to your profile (using the button at top right).
This user account has been replicated locally to NetBox, and can now be assigned groups and permissions by navigating to Admin > Permissions.
This user account has been replicated locally to NetBox, and can now be assigned groups and permissions.
Local user accounts and groups can be created in NetBox under the "Authentication" section in the "Admin" menu. This section is available only to users with the "staff" permission enabled.
At a minimum, each user account must have a username and password set. User accounts may also denote a first name, last name, and email address. [Permissions](../permissions.md) may also be assigned to users and/or groups under Admin > Permissions.
At a minimum, each user account must have a username and password set. User accounts may also denote a first name, last name, and email address. [Permissions](../permissions.md) may also be assigned to individual users and/or groups as needed.
Another option for remote authentication in NetBox is to enable HTTP header-based user assignment. The front end HTTP server (e.g. nginx or Apache) performs client authentication as a process external to NetBox, and passes information about the authenticated user via HTTP headers. By default, the user is assigned via the `REMOTE_USER` header, but this can be customized via the `REMOTE_AUTH_HEADER` configuration parameter.
Optionally, user profile information can be supplied by `REMOTE_USER_FIRST_NAME`, `REMOTE_USER_LAST_NAME` and `REMOTE_USER_EMAIL` headers. These are saved to the users profile during the authentication process. These headers can be customized like the `REMOTE_USER` header.
Optionally, user profile information can be supplied by `REMOTE_USER_FIRST_NAME`, `REMOTE_USER_LAST_NAME` and `REMOTE_USER_EMAIL` headers. These are saved to the user's profile during the authentication process. These headers can be customized like the `REMOTE_USER` header.
!!! warning Verify Header Compatibility
Some WSGI servers may drop headers which contain unsupported characters. For instance, gunicorn v22.0 and later silently drops HTTP headers containing underscores. This behavior can be disabled by changing gunicorn's [`header_map`](https://docs.gunicorn.org/en/stable/settings.html#header-map) setting to `dangerous`.
NetBox supports single sign-on authentication via the [python-social-auth](https://github.com/python-social-auth) library. To enable SSO, specify the path to the desired authentication backend within the `social_core` Python package. Please see the complete list of [supported authentication backends](https://github.com/python-social-auth/social-core/tree/master/social_core/backends) for the available options.
Most remote authentication backends require some additional configuration through settings prefixed with `SOCIAL_AUTH_`. These will be automatically imported from NetBox's `configuration.py` file. Additionally, the [authentication pipeline](https://python-social-auth.readthedocs.io/en/latest/pipeline.html) can be customized via the `SOCIAL_AUTH_PIPELINE` parameter. (NetBox's default pipeline is defined in `netbox/settings.py` for your reference.)
#### Configuring the SSO module's appearance
The way a remote authentication backend is displayed to the user on the login
page may be adjusted via the `SOCIAL_AUTH_BACKEND_ATTRS` parameter, defaulting
to an empty dictionary. This dictionary maps a `social_core` module's name (ie.
`REMOTE_AUTH_BACKEND.name`) to a couple of parameters, `(display_name, icon)`.
The `display_name` is the name displayed to the user on the login page. The
icon may either be the URL of an icon; refer to a [Material Design
Icons](https://github.com/google/material-design-icons) icon's name; or be
`None` for no icon.
For instance, the OIDC backend may be customized with
@@ -70,8 +70,6 @@ The `$user` token can be used only as a constraint value, or as an item within a
### Default Permissions
!!! info "This feature was introduced in NetBox v3.6."
While permissions are typically assigned to specific groups and/or users, it is also possible to define a set of default permissions that are applied to _all_ authenticated users. This is done using the [`DEFAULT_PERMISSIONS`](../configuration/security.md#default_permissions) configuration parameter. Note that statically configuring permissions for specific users or groups is **not** supported.
The time zone NetBox will use when dealing with dates and times. It is recommended to use UTC time unless you have a specific need to use a local time zone. Please see the [list of available time zones](https://en.wikipedia.org/wiki/List_of_tz_database_time_zones).
## Date and Time Formatting
You may define custom formatting for date and times. For detailed instructions on writing format strings, please see [the Django documentation](https://docs.djangoproject.com/en/stable/ref/templates/builtins/#date). Default formats are listed below.
!!! note
These system defaults will be overridden by a user's selected language/locale when [localization](./system.md#enable_localization) is enabled.
```python
DATE_FORMAT='N j, Y'# June 26, 2016
SHORT_DATE_FORMAT='Y-m-d'# 2016-06-26
TIME_FORMAT='g:i a'# 1:23 p.m.
SHORT_TIME_FORMAT='H:i:s'# 13:23:00
DATETIME_FORMAT='N j, Y g:i a'# June 26, 2016 1:23 p.m.
@@ -31,6 +31,17 @@ The sampling rate for errors. Must be a value between 0 (disabled) and 1.0 (repo
---
## SENTRY_SEND_DEFAULT_PII
Default: False
Maps to the Sentry SDK's [`send_default_pii`](https://docs.sentry.io/platforms/python/configuration/options/#send-default-pii) parameter. If enabled, certain personally identifiable information (PII) is added.
!!! warning "Sensitive data"
If you enable this option, be aware that sensitive data such as cookies and authentication tokens will be logged.
---
## SENTRY_TAGS
An optional dictionary of tag names and values to apply to Sentry error reports.For example:
@@ -33,9 +33,6 @@ This defines custom content to be displayed on the login page above the login fo
!!! tip "Dynamic Configuration Parameter"
!!! note
This parameter was added in NetBox v3.5.
This adds a banner to the top of every page when maintenance mode is enabled. HTML is allowed.
---
@@ -99,6 +96,14 @@ The maximum size (in bytes) of an incoming HTTP request (i.e. `GET` or `POST` da
---
## DJANGO_ADMIN_ENABLED
Default: False
Setting this to True installs the `django.contrib.admin` app and enables the [Django admin UI](https://docs.djangoproject.com/en/5.0/ref/contrib/admin/). This may be necessary to support older plugins which do not integrate with the native NetBox interface.
---
## ENFORCE_GLOBAL_UNIQUE
!!! tip "Dynamic Configuration Parameter"
@@ -107,9 +112,6 @@ Default: True
By default, NetBox will prevent the creation of duplicate prefixes and IP addresses in the global table (that is, those which are not assigned to any VRF). This validation can be disabled by setting `ENFORCE_GLOBAL_UNIQUE` to False.
!!! info "Changed in v3.7"
The default value for this parameter was changed from False to True in NetBox v3.7.
---
## FILE_UPLOAD_MAX_MEMORY_SIZE
@@ -134,9 +136,6 @@ Setting this to False will disable the GraphQL API.
!!! tip "Dynamic Configuration Parameter"
!!! note
This parameter was renamed from `JOBRESULT_RETENTION` in NetBox v3.5.
Default: 90
The number of days to retain job results (scripts and reports). Set this to `0` to retain job results in the database indefinitely.
@@ -231,9 +230,6 @@ The maximum execution time of a background task (such as running a custom script
## RQ_RETRY_INTERVAL
!!! note
This parameter was added in NetBox v3.5.
Default: `60`
This parameter controls how frequently a failed job is retried, up to the maximum number of times specified by `RQ_RETRY_MAX`. This must be either an integer specifying the number of seconds to wait between successive attempts, or a list of such values. For example, `[60, 300, 3600]` will retry the task after 1 minute, 5 minutes, and 1 hour.
@@ -242,9 +238,6 @@ This parameter controls how frequently a failed job is retried, up to the maximu
## RQ_RETRY_MAX
!!! note
This parameter was added in NetBox v3.5.
Default: `0` (retries disabled)
The maximum number of times a background task will be retried before being marked as failed.
When remote user authentication is in use, this is the name of the HTTP header which informs NetBox of the currently authenticated user. For example, to use the request header `X-Remote-User` it needs to be set to `HTTP_X_REMOTE_USER`. (Requires `REMOTE_AUTH_ENABLED`.)
!!! warning Verify Header Compatibility
Some WSGI servers may drop headers which contain unsupported characters. For instance, gunicorn v22.0 and later silently drops HTTP headers containing underscores. This behavior can be disabled by changing gunicorn's [`header_map`](https://docs.gunicorn.org/en/stable/settings.html#header-map) setting to `dangerous`.
If you are upgrading from a NetBox release older than v2.7.0, please note that the Redis connection configuration
settings have changed. Manual modification to bring the `REDIS` section inline with the above specification is
necessary
!!! warning
It is highly recommended to keep the task and cache databases separate. Using the same database number on the
same Redis instance for both may result in queued background tasks being lost during cache flushing events.
### UNIX Socket Support
Redis may alternatively be configured by specifying a complete URL instead of individual components. This approach supports the use of a UNIX socket connection. For example:
```python
REDIS={
'tasks':{
'URL':'unix:///run/redis-netbox/redis.sock?db=0'
},
'caching':{
'URL':'unix:///run/redis-netbox/redis.sock?db=1'
},
}
```
### Using Redis Sentinel
If you are using [Redis Sentinel](https://redis.io/topics/sentinel) for high-availability purposes, there is minimal
!!! info "This parameter was introduced in NetBox v3.6."
Default:
```python
@@ -161,9 +159,12 @@ Note that enabling this setting causes NetBox to update a user's session in the
## LOGIN_REQUIRED
Default: False
Default: True
Setting this to True will permit only authenticated users to access any part of NetBox. By default, anonymous users are permitted to access most data in NetBox but not make any changes.
When enabled, only authenticated users are permitted to access any part of NetBox. Disabling this will allow unauthenticated users to access most areas of NetBox (but not make any changes).
!!! info "Changed in NetBox v4.0.2"
Prior to NetBox v4.0.2, this setting was disabled by default.
---
@@ -183,6 +184,30 @@ The view name or URL to which a user is redirected after logging out.
---
## SECURE_HSTS_INCLUDE_SUBDOMAINS
Default: False
If true, the `includeSubDomains` directive will be included in the HTTP Strict Transport Security (HSTS) header. This directive instructs the browser to apply the HSTS policy to all subdomains of the current domain.
---
## SECURE_HSTS_PRELOAD
Default: False
If true, the `preload` directive will be included in the HTTP Strict Transport Security (HSTS) header. This directive instructs the browser to preload the site in HTTPS. Browsers that use the HSTS preload list will force the site to be accessed via HTTPS even if the user types HTTP in the address bar.
---
## SECURE_HSTS_SECONDS
Default: 0
If set to a non-zero integer value, the SecurityMiddleware sets the HTTP Strict Transport Security (HSTS) header on all responses that do not already have it. This will instruct the browser that the website must be accessed via HTTPS, blocking any HTTP request.
Defines the default preferred language/locale for requests that do not specify one. This is used to alter e.g. the display of dates and numbers to fit the user's locale. See [this list](http://www.i18nguy.com/unicode/language-identifiers.html) of standard language codes. (This parameter maps to Django's [`LANGUAGE_CODE`](https://docs.djangoproject.com/en/stable/ref/settings/#language-code) internal setting.)
!!! note
Altering this parameter will *not* change the language used in NetBox. We hope to provide translation support in a future NetBox release.
Defines the default preferred language/locale for requests that do not specify one. (This parameter maps to Django's [`LANGUAGE_CODE`](https://docs.djangoproject.com/en/stable/ref/settings/#language-code) internal setting.)
---
@@ -65,14 +62,6 @@ Email is sent from NetBox only for critical events or if configured for [logging
---
## ENABLE_LOCALIZATION
Default: False
Determines if localization features are enabled or not. This should only be enabled for development or testing purposes as netbox is not yet fully localized. Turning this on will localize numeric and date formats (overriding any configured [system defaults](./date-time.md#date-and-time-formatting)) based on the browser locale as well as translate certain strings from third party modules.
---
## HTTP_PROXIES
Default: None
@@ -98,6 +87,17 @@ addresses (and [`DEBUG`](#debug) is true).
---
## ISOLATED_DEPLOYMENT
Default: False
Set this configuration parameter to True for NetBox deployments which do not have Internet access. This will disable miscellaneous functionality which depends on access to the Internet.
!!! note
If Internet access is available via a proxy, set [`HTTP_PROXIES`](#http_proxies) instead.
---
## JINJA2_FILTERS
Default: `{}`
@@ -154,7 +154,7 @@ LOGGING = {
## MEDIA_ROOT
Default: $INSTALL_ROOT/netbox/media/
Default: `$INSTALL_ROOT/netbox/media/`
The file path to the location where media files (such as image attachments) are stored. By default, this is the `netbox/media/` directory within the base NetBox installation path.
@@ -188,7 +188,7 @@ The dotted path to the desired search backend class. `CachedValueSearchBackend`
Default: None (local storage)
The backend storage engine for handling uploaded files (e.g. image attachments). NetBox supports integration with the [`django-storages`](https://django-storages.readthedocs.io/en/stable/) package, which provides backends for several popular file storage services. If not configured, local filesystem storage will be used.
The backend storage engine for handling uploaded files (e.g. image attachments). NetBox supports integration with the [`django-storages`](https://django-storages.readthedocs.io/en/stable/) and [`django-storage-swift`](https://github.com/dennisv/django-storage-swift) packages, which provide backends for several popular file storage services. If not configured, local filesystem storage will be used.
The configuration parameters for the specified storage backend are defined under the `STORAGE_CONFIG` setting.
@@ -198,8 +198,22 @@ The configuration parameters for the specified storage backend are defined under
Default: Empty
A dictionary of configuration parameters for the storage backend configured as `STORAGE_BACKEND`. The specific parameters to be used here are specific to each backend; see the [`django-storages` documentation](https://django-storages.readthedocs.io/en/stable/) for more detail.
A dictionary of configuration parameters for the storage backend configured as `STORAGE_BACKEND`. The specific parameters to be used here are specific to each backend; see the documentation for your selected backend ([`django-storages`](https://django-storages.readthedocs.io/en/stable/) or [`django-storage-swift`](https://github.com/dennisv/django-storage-swift)) for more detail.
If `STORAGE_BACKEND` is not defined, this setting will be ignored.
---
## TIME_ZONE
Default: UTC
The time zone NetBox will use when dealing with dates and times. It is recommended to use UTC time unless you have a specific need to use a local time zone. Please see the [list of available time zones](https://en.wikipedia.org/wiki/List_of_tz_database_time_zones).
---
## TRANSLATION_ENABLED
Default: True
Enables language translation for the user interface. (This parameter maps to Django's [USE_I18N](https://docs.djangoproject.com/en/stable/ref/settings/#std-setting-USE_I18N) setting.)
@@ -42,8 +42,6 @@ This parameter has no effect on the API representation of custom field data.
### Visibility & Editing
!!! info "This feature was improved in NetBox v3.7."
When creating a custom field, users can control the conditions under which it may be displayed and edited within the NetBox user interface. The following choices are available for controlling the display of a custom field on an object:
* **Always** (default): The custom field is included when viewing an object.
@@ -76,6 +74,8 @@ If a default value is specified for a selection field, it must exactly match one
An object or multi-object custom field can be used to refer to a particular NetBox object or objects as the "value" for a custom field. These custom fields must define an `object_type`, which determines the type of object to which custom field instances point.
By default, an object choice field will make all objects of that type available for selection in the drop-down. The list choices can be filtered to show only objects with certain values by providing a `query_params` dict in the Related Object Filter field, as a JSON value. More information about `query_params` can be found [here](./custom-scripts.md#objectvar).
## Custom Fields in Templates
Several features within NetBox, such as export templates and webhooks, utilize Jinja2 templating. For convenience, objects which support custom field assignment expose custom field data through the `cf` property. This is a bit cleaner than accessing custom field data through the actual field (`custom_field_data`).
@@ -5,8 +5,17 @@ Custom scripting was introduced to provide a way for users to execute custom log
* Automatically populate new devices and cables in preparation for a new site deployment
* Create a range of new reserved prefixes or IP addresses
* Fetch data from an external source and import it to NetBox
* Update objects with invalid or incomplete data
Custom scripts are Python code and exist outside of the official NetBox code base, so they can be updated and changed without interfering with the core NetBox installation. And because they're completely custom, there is no inherent limitation on what a script can accomplish.
They can also be used as a mechanism for validating the integrity of data within NetBox. Script authors can define test to check object against specific rules and conditions. For example, you can write script to check that:
* All top-of-rack switches have a console connection
* Every router has a loopback interface with an IP address assigned
* Each interface description conforms to a standard format
* Every site has a minimum set of VLANs defined
* All IP addresses have a parent prefix
Custom scripts are Python code which exists outside the NetBox code base, so they can be updated and changed without interfering with the core NetBox installation. And because they're completely custom, there is no inherent limitation on what a script can accomplish.
## Writing Custom Scripts
@@ -56,12 +65,6 @@ class AnotherCustomScript(Script):
script_order=(MyCustomScript,AnotherCustomScript)
```
## Module Attributes
### `name`
You can define `name` within a script module (the Python file which contains one or more scripts) to set the module name. If `name` is not defined, the module's file name will be used.
## Script Attributes
Script attributes are defined under a class named `Meta` within the script. These are optional, but encouraged.
@@ -135,13 +138,75 @@ These two methods will load data in YAML or JSON format, respectively, from file
The Script object provides a set of convenient functions for recording messages at different severity levels:
*`log_debug`
*`log_success`
*`log_info`
*`log_warning`
*`log_failure`
*`log_debug(message=None, obj=None)`
*`log_success(message=None, obj=None)`
*`log_info(message=None, obj=None)`
*`log_warning(message=None, obj=None)`
*`log_failure(message=None, obj=None)`
Log messages are returned to the user upon execution of the script. Markdown rendering is supported for log messages.
Log messages are returned to the user upon execution of the script. Markdown rendering is supported for log messages. A message may optionally be associated with a particular object by passing it as the second argument to the logging method.
## Test Methods
A script can define one or more test methods to report on certain conditions. All test methods must have a name beginning with `test_` and accept no arguments beyond `self`.
These methods are detected and run automatically when the script is executed, unless its `run()` method has been overridden. (When overriding `run()`, `run_tests()` can be called to run all test methods present in the script.)
Calling any of these logging methods without a message will increment the relevant counter, but will not generate an output line in the script's log.
!!! info
This functionality was ported from [legacy reports](./reports.md) in NetBox v4.0.
### Example
```
from dcim.choices import DeviceStatusChoices
from dcim.models import ConsolePort, Device, PowerPort
from extras.scripts import Script
class DeviceConnectionsReport(Script):
description = "Validate the minimum physical connections for each device"
def test_console_connection(self):
# Check that every console port for every active device has a connection defined.
active = DeviceStatusChoices.STATUS_ACTIVE
for console_port in ConsolePort.objects.prefetch_related('device').filter(device__status=active):
if not console_port.connected_endpoints:
self.log_failure(
f"No console connection defined for {console_port.name}",
console_port.device,
)
elif not console_port.connection_status:
self.log_warning(
f"Console connection for {console_port.name} marked as planned",
console_port.device,
)
else:
self.log_success("Passed", console_port.device)
def test_power_connections(self):
# Check that every active device has at least two connected power supplies.
for device in Device.objects.filter(status=DeviceStatusChoices.STATUS_ACTIVE):
connected_ports = 0
for power_port in PowerPort.objects.filter(device=device):
if power_port.connected_endpoints:
connected_ports += 1
if not power_port.path.is_active:
self.log_warning(
f"Power connection for {power_port.name} marked as planned",
device,
)
if connected_ports < 2:
self.log_failure(
f"{connected_ports} connected power supplies found (2 needed)",
device,
)
else:
self.log_success("Passed", device)
```
## Change Logging
@@ -235,6 +300,7 @@ A particular object within NetBox. Each ObjectVar must specify a particular mode
*`model` - The model class
*`query_params` - A dictionary of query parameters to use when retrieving available options (optional)
*`context` - A custom dictionary mapping template context variables to fields, used when rendering `<option>` elements within the dropdown menu (optional; see below)
*`null_option` - A label representing a "null" or empty choice (optional)
To limit the selections available within the list, additional query parameters can be passed as the `query_params` dictionary. For example, to show only devices with an "active" status:
@@ -262,6 +328,22 @@ site = ObjectVar(
)
```
#### Context Variables
Custom context variables can be passed to override the default attribute names or to display additional information, such as a parent object.
@@ -4,7 +4,7 @@ NetBox validates every object prior to it being written to the database to ensur
## Custom Validation Rules
Custom validation rules are expressed as a mapping of model attributes to a set of rules to which that attribute must conform. For example:
Custom validation rules are expressed as a mapping of object attributes to a set of rules to which that attribute must conform. For example:
```json
{
@@ -17,6 +17,8 @@ Custom validation rules are expressed as a mapping of model attributes to a set
This defines a custom validator which checks that the length of the `name` attribute for an object is at least five characters long, and no longer than 30 characters. This validation is executed _after_ NetBox has performed its own internal validation.
### Validation Types
The `CustomValidator` class supports several validation types:
*`min`: Minimum value
@@ -36,14 +38,14 @@ The `min` and `max` types should be defined for numeric values, whereas `min_len
### Custom Validation Logic
There may be instances where the provided validation types are insufficient. NetBox provides a `CustomValidator` class which can be extended to enforce arbitrary validation logic by overriding its `validate()` method, and calling `fail()` when an unsatisfactory condition is detected.
There may be instances where the provided validation types are insufficient. NetBox provides a `CustomValidator` class which can be extended to enforce arbitrary validation logic by overriding its `validate()` method, and calling `fail()` when an unsatisfactory condition is detected. The `validate()` method should accept an instance (the object being saved) as well as the current request effecting the change.
self.fail("Active sites must have a description set!",field='status')
```
@@ -82,7 +84,38 @@ CUSTOM_VALIDATORS = {
}
```
### Dotted Path
#### Referencing Related Object Attributes
The attributes of a related object can be referenced by specifying a dotted path. For example, to reference the name of a region to which a site is assigned, use `region.name`:
```python
CUSTOM_VALIDATORS={
"dcim.site":[
{
"region.name":{
"neq":"New York"
}
}
]
}
```
#### Validating Request Parameters
In addition to validating object attributes, custom validators can also match against parameters of the current request (where available). For example, the following rule will permit only the user named "admin" to modify an object:
```json
{
"request.user.username":{
"eq":"admin"
}
}
```
!!! tip
Custom validation should generally not be used to enforce permissions. NetBox provides a robust [object-based permissions](../administration/permissions.md) mechanism which should be used for this purpose.
### Dotted Path to Class
In instances where a custom validator class is needed, it can be referenced by its Python path (relative to NetBox's working directory):
A NetBox report is a mechanism for validating the integrity of data within NetBox. Running a report allows the user to verify that the objects defined within NetBox meet certain arbitrary conditions. For example, you can write reports to check that:
* All top-of-rack switches have a console connection
* Every router has a loopback interface with an IP address assigned
* Each interface description conforms to a standard format
* Every site has a minimum set of VLANs defined
* All IP addresses have a parent prefix
...and so on. Reports are completely customizable, so there's practically no limit to what you can test for.
## Writing Reports
Reports must be saved as files in the [`REPORTS_ROOT`](../configuration/system.md#reports_root) path (which defaults to `netbox/reports/`). Each file created within this path is considered a separate module. Each module holds one or more reports (Python classes), each of which performs a certain function. The logic of each report is broken into discrete test methods, each of which applies a small portion of the logic comprising the overall test.
!!! warning
The reports path includes a file named `__init__.py`, which registers the path as a Python module. Do not delete this file.
Reports are deprecated beginning with NetBox v4.0, and their functionality has been merged with [custom scripts](./custom-scripts.md). While backward compatibility has been maintained, users are advised to convert legacy reports into custom scripts soon, as support for legacy reports will be removed in a future release.
For example, we can create a module named `devices.py` to hold all of our reports which pertain to devices in NetBox. Within that module, we might define several reports. Each report is defined as a Python class inheriting from `extras.reports.Report`.
## Converting Reports to Scripts
```
### Step 1: Update Class Definition
Change the parent class from `Report` to `Script`:
```python title="Old code"
from extras.reports import Report
class DeviceConnectionsReport(Report):
description = "Validate the minimum physical connections for each device"
class DeviceIPsReport(Report):
description = "Check that every device has a primary IP address assigned"
class MyReport(Report):
```
Within each report class, we'll create a number of test methods to execute our report's logic. In DeviceConnectionsReport, for instance, we want to ensure that every live device has a console connection, an out-of-band management connection, and two power connections.
```python title="New code"
from extras.scripts import Script
```
from dcim.choices import DeviceStatusChoices
from dcim.models import ConsolePort, Device, PowerPort
from extras.reports import Report
class DeviceConnectionsReport(Report):
description = "Validate the minimum physical connections for each device"
def test_console_connection(self):
# Check that every console port for every active device has a connection defined.
active = DeviceStatusChoices.STATUS_ACTIVE
for console_port in ConsolePort.objects.prefetch_related('device').filter(device__status=active):
if not console_port.connected_endpoints:
self.log_failure(
console_port.device,
"No console connection defined for {}".format(console_port.name)
)
elif not console_port.connection_status:
self.log_warning(
console_port.device,
"Console connection for {} marked as planned".format(console_port.name)
)
else:
self.log_success(console_port.device)
def test_power_connections(self):
# Check that every active device has at least two connected power supplies.
for device in Device.objects.filter(status=DeviceStatusChoices.STATUS_ACTIVE):
connected_ports = 0
for power_port in PowerPort.objects.filter(device=device):
if power_port.connected_endpoints:
connected_ports += 1
if not power_port.path.is_active:
self.log_warning(
device,
"Power connection for {} marked as planned".format(power_port.name)
)
if connected_ports < 2:
self.log_failure(
device,
"{} connected power supplies found (2 needed)".format(connected_ports)
)
else:
self.log_success(device)
class MyReport(Script):
```
As you can see, reports are completely customizable. Validation logic can be as simple or as complex as needed. Also note that the `description` attribute support markdown syntax. It will be rendered in the report list page.
### Step 2: Update Logging Calls
!!! warning
Reports should never alter data: If you find yourself using the `create()`, `save()`, `update()`, or `delete()` methods on objects within reports, stop and re-evaluate what you're trying to accomplish. Note that there are no safeguards against the accidental alteration or destruction of data.
Reports and scripts both provide logging methods, however their signatures differ. All script logging methods accept a message as the first parameter, and accept an object as an optional second parameter.
## Report Attributes
Additionally, the Report class' generic `log()` method is **not** available on Script. Users are advised to replace calls of this method with `log_info()`.
### `description`
Use the table below as a reference when updating these methods.
A human-friendly description of what your report does.
[^1]: `log_debug()` was added to the Report class in v4.0 to avoid confusion with the same method on Script
By default, a report can be scheduled for execution at a later time. Setting `scheduling_enabled` to False disables this ability: Only immediate execution will be possible. (This also disables the ability to set a recurring execution interval.)
### `job_timeout`
Set the maximum allowed runtime for the report. If not set, `RQ_DEFAULT_TIMEOUT` will be used.
## Logging
The following methods are available to log results within a report:
* log(message)
* log_success(object, message=None)
* log_info(object, message)
* log_warning(object, message)
* log_failure(object, message)
The recording of one or more failure messages will automatically flag a report as failed. It is advised to log a success for each object that is evaluated so that the results will reflect how many objects are being reported on. (The inclusion of a log message is optional for successes.) Messages recorded with `log()` will appear in a report's results but are not associated with a particular object or status. Log messages also support using markdown syntax and will be rendered on the report result page.
To perform additional tasks, such as sending an email or calling a webhook, before or after a report is run, extend the `pre_run()` and/or `post_run()` methods, respectively.
By default, reports within a module are ordered alphabetically in the reports list page. To return reports in a specific order, you can define the `report_order` variable at the end of your module. The `report_order` variable is a tuple which contains each Report class in the desired order. Any reports that are omitted from this list will be listed last.
f"No console connection defined for {console_port.name}"
)
```
Once you have created a report, it will appear in the reports list. Initially, reports will have no results associated with them. To generate results, run the report.
## Running Reports
!!! note
To run a report, a user must be assigned permissions for `Extras > Report`, `Extras > Report Module`, and `Core > Managed File` objects. They must also be assigned the `extras.run_report` permission. This is achieved by assigning the user (or group) a permission on the Report object and specifying the `run` action in "Permissions" as shown below.

### Via the Web UI
Reports can be run via the web UI by navigating to the report and clicking the "run report" button at top right. Once a report has been run, its associated results will be included in the report view. It is possible to schedule a report to be executed at specified time in the future. A scheduled report can be canceled by deleting the associated job result object.
### Via the API
To run a report via the API, simply issue a POST request to its `run` endpoint. Reports are identified by their module and class name.
```
POST /api/extras/reports/<module>.<name>/run/
```python title="New code"
self.log_failure(
f"No console connection defined for {console_port.name}",
obj=console_port.device,
)
```
Our example report above would be called as:
### Other Notes
```
POST /api/extras/reports/devices.DeviceConnectionsReport/run/
```
Existing reports will be converted to scripts automatically upon upgrading to NetBox v4.0, and previous job history will be retained. However, users are advised to convert legacy reports into custom scripts at the earliest opportunity, as support for legacy reports will be removed in a future release.
Optionally `schedule_at` can be passed in the form data with a datetime string to schedule a script at the specified date and time.
The `pre_run()` and `post_run()` Report methods have been carried over to Script. These are called automatically by Script's `run()` method. (Note that if you opt to override this method, you are responsible for calling `pre_run()` and `post_run()` where applicable.)
### Via the CLI
Reports can be run on the CLI by invoking the management command:
```
python3 manage.py runreport <module>
```
where ``<module>`` is the name of the python file in the ``reports`` directory without the ``.py`` extension. One or more report modules may be specified.
The `is_valid()` method on Report is no longer needed and has been removed.
@@ -18,7 +18,7 @@ Depending on its classification, each NetBox model may support various features
| [Custom links](../customization/custom-links.md) | `CustomLinksMixin` | `custom_links` | These models support the assignment of custom links |
| [Custom validation](../customization/custom-validation.md) | `CustomValidationMixin` | - | Supports the enforcement of custom validation rules |
| [Export templates](../customization/export-templates.md) | `ExportTemplatesMixin` | `export_templates` | Users can create custom export templates for these models |
| [Job results](../features/background-jobs.md) | `JobsMixin` | `jobs` | Users can create custom export templates for these models |
| [Job results](../features/background-jobs.md) | `JobsMixin` | `jobs` | Background jobs can be scheduled for these models |
| [Journaling](../features/journaling.md) | `JournalingMixin` | `journaling` | These models support persistent historical commentary |
| [Synchronized data](../integrations/synchronized-data.md) | `SyncedDataMixin` | `synced_data` | Certain model data can be automatically synchronized from a remote data source |
| [Tagging](../models/extras/tag.md) | `TagsMixin` | `tags` | The models can be tagged with user-defined tags |
@@ -34,7 +34,9 @@ These are considered the "core" application models which are used to model netwo
@@ -59,7 +59,7 @@ Notify the [`netbox-docker`](https://github.com/netbox-community/netbox-docker)
* Increases in minimum versions for service dependencies (PostgreSQL, Redis, etc.)
* Any changes to the reference installation
### Update Requirements
### Update Python Dependencies
Before each release, update each of NetBox's Python dependencies to its most recent stable version. These are defined in `requirements.txt`, which is updated from `base_requirements.txt` using `pip`. To do this:
@@ -70,6 +70,10 @@ Before each release, update each of NetBox's Python dependencies to its most rec
In cases where upgrading a dependency to its most recent release is breaking, it should be constrained to its current minor version in `base_requirements.txt` with an explanatory comment and revisited for the next major NetBox release (see the [Address Constrained Dependencies](#address-constrained-dependencies) section above).
### Update UI Dependencies
Check whether any UI dependencies (JavaScript packages, fonts, etc.) need to be updated by running `yarn outdated` from within the `project-static/` directory. [Upgrade these dependencies](./web-ui.md#updating-dependencies) as necessary, then run `yarn bundle` to generate the necessary files for distribution.
### Rebuild the Device Type Definition Schema
Run the following command to update the device type definition validation schema:
@@ -82,15 +86,7 @@ This will automatically update the schema file at `contrib/generated_schema.json
### Update & Compile Translations
Log into [Transifex](https://app.transifex.com/netbox-community/netbox/dashboard/) to download the updated string maps. Download the resource (portable object, or `.po`) file for each language and save them to `netbox/translations/$lang/LC_MESSAGES/django.po`, overwriting the current files. (Be sure to click the **Download for use** link.)
Once the resource files for all languages have been updated, compile the machine object (`.mo`) files using the `compilemessages` management command:
```nohighlight
./manage.py compilemessages
```
Updated language translations should be pulled from [Transifex](https://app.transifex.com/netbox-community/netbox/dashboard/) and re-compiled for each new release. Follow the documented process for [updating translated strings](./translations.md#updating-translated-strings) to do this.
### Update Version and Changelog
@@ -117,7 +113,7 @@ Create a [new release](https://github.com/netbox-community/netbox/releases/new)
* **Tag:** Current version (e.g. `v3.3.1`)
* **Target:** `master`
* **Title:** Version and date (e.g. `v3.3.1 - 2022-08-25`)
* **Description:** Copy from the pull request body
* **Description:** Copy from the pull request body, then promote the `###` headers to `##` ones
Once created, the release will become available for users to install.
@@ -130,3 +126,15 @@ VERSION = 'v3.3.2-dev'
```
Commit this change with the comment "PRVB" (for _post-release version bump_) and push the commit upstream.
### Update the Public Documentation
After a release has been published, the public NetBox documentation needs to be updated. This is accomplished by running two actions on the [netboxlabs-docs](https://github.com/netboxlabs/netboxlabs-docs) repository.
First, run the `build-site` action, by navigating to Actions > build-site > Run workflow. This process compiles the documentation along with an overlay for integration with the documentation portal at <https://netboxlabs.com/docs>. The job should take about two minutes.
Once the documentation files have been compiled, they must be published by running the `deploy-kinsta` action. Select the desired deployment environment (staging or production) and specify `latest` as the deploy tag.
Clear the CDN cache from the [Kinsta](https://my.kinsta.com/) portal. Navigate to _Sites_ / _NetBox Labs_ / _Live_, select _Cache_ in the left-nav, click the _Clear Cache_ button, and confirm the clear operation.
Finally, verify that the documentation at <https://netboxlabs.com/docs/netbox/en/stable/> has been updated.
@@ -6,17 +6,40 @@ All language translations in NetBox are generated from the source file found at
Reviewers log into Transifex and navigate to their designated language(s) to translate strings. The initial translation for most strings will be machine-generated via the AWS Translate service. Human reviewers are responsible for reviewing these translations and making corrections where necessary.
Immediately prior to each NetBox release, the translation maps for all completed languages will be downloaded from Transifex, compiled, and checked into the NetBox code base by a maintainer.
## Updating Translation Sources
To update the English `.po` file from which all translations are derived, use the `makemessages` management command:
To update the English `.po` file from which all translations are derived, use the `makemessages` management command (ignoring the `project-static/` directory):
```nohighlight
./manage.py makemessages -l en
./manage.py makemessages -l en -i "project-static/*"
```
Then, commit the change and push to the `develop` branch on GitHub. After some time, any new strings will appear for translation on Transifex automatically.
Then, commit the change and push to the `develop` branch on GitHub. Any new strings will appear for translation on Transifex automatically.
## Updating Translated Strings
Typically, translated strings need to be updated only as part of the NetBox [release process](./release-checklist.md).
Check the Transifex dashboard for languages that are not marked _ready for use_, being sure to click _Show all languages_ if it appears at the bottom of the list. Use machine translation to round out any not-ready languages. It's not necessary to review the machine translation immediately as the translation teams will handle that aspect; the goal at this stage is to get translations included in the Transifex pull request.
To update translated strings, start by initiating a sync from Transifex. From the Transifex dashboard, navigate to Settings > Integrations > GitHub > Manage, and click the **Manual Sync** button at top right.
Enter a threshold percentage of 1 (to ensure all translations are captured) and select the `develop` branch, then click **Sync**. This will initiate a pull request to GitHub to update any newly modified translation (`.po`) files.
!!! tip
The new PR should appear within a few minutes. If it does not, check that there are in fact new translations to be added.
Once the PR has been merged, the updated strings need to be compiled into new `.mo` files so they can be used by the application. Update the `develop` branch locally to pull in the changes from the Transifex PR, then run Django's [`compilemessages`](https://docs.djangoproject.com/en/stable/ref/django-admin/#django-admin-compilemessages) management command:
```nohighlight
./manage.py compilemessages
```
Once any new `.mo` files have been generated, they need to be committed and pushed back up to GitHub. (Again, this is typically done as part of publishing a new NetBox release.)
| `dist/` | Destination path for installed dependencies |
| `docs/` | Local build path for documentation |
| `img/` | Image files |
| `js/` | Miscellaneous JavaScript resources served directly |
| `src/` | TypeScript resources (to be compiled into JS) |
| `styles/` | Sass resources (to be compiled into CSS) |
## Front End Technologies
The NetBox UI is built on languages and frameworks:
Front end scripting is written in [TypeScript](https://www.typescriptlang.org/), which is a strongly-typed extension to JavaScript. TypeScript is "transpiled" into JavaScript resources which are served to and executed by the client web browser.
### Styling & HTML Elements
All UI styling is written in [Sass](https://sass-lang.com/), which is an extension to browser-native [Cascading Stylesheets (CSS)](https://developer.mozilla.org/en-US/docs/Web/CSS). Similar to how TypeScript content is transpiled to JavaScript, Sass resources (`.scss` files) are compiled to CSS.
#### [Bootstrap](https://getbootstrap.com/) 5
## Dependencies
The majority of the NetBox UI is made up of stock Bootstrap components, with some styling modifications and custom components added on an as-needed basis. Bootstrap uses [Sass](https://sass-lang.com/), and NetBox extends Bootstrap's core Sass files for theming and customization.
The following software is employed by the NetBox user interface.
All client-side scripting is transpiled from TypeScript to JavaScript and served by Django. In development, TypeScript is an _extremely_ effective tool for accurately describing and checking the code, which leads to significantly fewer bugs, a better development experience, and more predictable/readable code.
As part of the [bundling](#bundling) process, Bootstrap's JavaScript plugins are imported and bundled alongside NetBox's front-end code.
!!! danger "NetBox is jQuery-free"
Following the Bootstrap team's deprecation of jQuery in Bootstrap 5, NetBox also no longer uses jQuery in front-end code.
* [Bootstrap 5](https://getbootstrap.com/) - A popular CSS & JS framework
* [clipboard.js](https://clipboardjs.com/) - A lightweight package for enabling copy-to-clipboard functionality
* [flatpickr](https://flatpickr.js.org/) - A lightweight date & time selection widget
* [gridstack.js](https://gridstackjs.com/) - Enables interactive grid layouts (for the dashboard)
* [HTMX](https://htmx.org/) - Enables dynamic web interfaces through the use of HTML element attributes
* [Material Design Icons](https://pictogrammers.com/library/mdi/) - An extensive open source collection of graphical icons, delivered as a web font
* [query-string](https://www.npmjs.com/package/query-string) - Assists with parsing URL query strings
* [Tabler](https://tabler.io/) - A web application UI toolkit & theme based on Bootstrap 5
* [Tom Select](https://tom-select.js.org/) - Provides dynamic selection form fields
## Guidance
@@ -54,6 +66,41 @@ $ yarn
!!! warning "Check Your Working Directory"
You need to be in the `netbox/project-static` directory to run the below `yarn` commands.
### Updating Dependencies
Run `yarn outdated` to identify outdated dependencies.
```
$ yarn outdated
yarn outdated v1.22.19
info Color legend :
"<red>" : Major Update backward-incompatible updates
"<yellow>" : Minor Update backward-compatible features
Run `yarn upgrade --latest` to automatically upgrade these packages to their most recent versions.
```
$ yarn upgrade bootstrap --latest
yarn upgrade v1.22.19
[1/4] Resolving packages...
[2/4] Fetching packages...
[3/4] Linking dependencies...
[4/4] Rebuilding all packages...
success Saved lockfile.
success Saved 1 new dependency.
info Direct dependencies
└─ bootstrap@5.3.3
info All dependencies
└─ bootstrap@5.3.3
Done in 0.95s.
```
`package.json` will be updated to reflect the new package versions automatically.
### Bundling
In order for the TypeScript and Sass (SCSS) source files to be usable by a browser, they must first be transpiled (TypeScript → JavaScript, Sass → CSS), bundled, and minified. After making changes to TypeScript or Sass source files, run `yarn bundle`.
@@ -20,8 +20,6 @@ GET /api/dcim/devices/?tag=monitored&tag=deprecated
## Bookmarks
!!! info "This feature was introduced in NetBox v3.6."
Users can bookmark their most commonly visited objects for convenient access. Bookmarks are listed under a user's profile, and can be displayed with custom filtering and ordering on the user's personal dashboard.
For example, suppose you want to automatically configure a monitoring system to start monitoring a device when its operational status is changed to active, and remove it from monitoring for any other status. You can create a webhook in NetBox for the device model and craft its content and destination URL to effect the desired change on the receiving system. You can then associate an event rule with this webhook and the webhook will be sent automatically by NetBox whenever the configured constraints are met.
@@ -28,4 +29,4 @@ For more detail, see the reference documentation for NetBox's [conditional logic
## Event Rule Processing
When a change is detected, any resulting events are placed into a Redis queue for processing. This allows the user's request to complete without needing to wait for the outgoing event(s) to be processed. The events are then extracted from the queue by the `rqworker` process. The current event queue and any failed events can be inspected in the admin UI under System > Background Tasks.
When a change is detected, any resulting events are placed into a Redis queue for processing. This allows the user's request to complete without needing to wait for the outgoing event(s) to be processed. The events are then extracted from the queue by the `rqworker` process. The current event queue and any failed events can be inspected under System > Background Tasks.
@@ -56,6 +56,10 @@ A site typically represents a building within a region and/or site group. Each s
A location can be any logical subdivision within a building, such as a floor or room. Like regions and site groups, locations can be nested into a self-recursive hierarchy for maximum flexibility. And like sites, each location has an operational status assigned to it.
## Rack Types
A rack type represents a unique specification of a rack which exists in the real world. Each rack type can be setup with weight, height, and unit ordering. New racks of this type can then be created in NetBox, and any associated specifications will be automatically replicated from the device type.
## Racks
Finally, NetBox models each equipment rack as a discrete object within a site and location. These are physical objects into which devices are installed. Each rack can be assigned an operational status, type, facility ID, and other attributes related to inventory tracking. Each rack also must define a height (in rack units) and width, and may optionally specify its physical dimensions.
!!! info "This feature was introduced in NetBox v4.1."
NetBox includes a system for generating user notifications, which can be marked as read or deleted by individual users. There are two built-in mechanisms for generating a notification:
* A user can subscribe to an object. When that object is modified, a notification is created to inform the user of the change.
* An [event rule](./event-rules.md) can be defined to automatically generate a notification for one or more users in response to specific system events.
Additionally, NetBox plugins can generate notifications for their own purposes.
Before continuing, check that your installed Python version is at least 3.8:
Before continuing, check that your installed Python version is at least 3.10:
```no-highlight
python3 -V
@@ -255,10 +255,10 @@ Once NetBox has been configured, we're ready to proceed with the actual installa
sudo /opt/netbox/upgrade.sh
```
Note that **Python 3.8 or later is required** for NetBox v3.2 and later releases. If the default Python installation on your server is set to a lesser version, pass the path to the supported installation as an environment variable named `PYTHON`. (Note that the environment variable must be passed _after_ the `sudo` command.)
Note that **Python 3.10 or later is required** for NetBox v4.0 and later releases. If the default Python installation on your server is set to a lesser version, pass the path to the supported installation as an environment variable named `PYTHON`. (Note that the environment variable must be passed _after_ the `sudo` command.)
Like most Django applications, NetBox runs as a [WSGI application](https://en.wikipedia.org/wiki/Web_Server_Gateway_Interface) behind an HTTP server. This documentation shows how to install and configure [gunicorn](http://gunicorn.org/) (which is automatically installed with NetBox) for this role, however other WSGI servers are available and should work similarly well. [uWSGI](https://uwsgi-docs.readthedocs.io/en/latest/) is a popular alternative.
!!! tip
This page provides instructions for setting up the [gunicorn](http://gunicorn.org/) WSGI server. If you plan to use [uWSGI](https://uwsgi-docs.readthedocs.io/en/latest/) instead, go [here](./4b-uwsgi.md).
NetBox runs as a [WSGI application](https://en.wikipedia.org/wiki/Web_Server_Gateway_Interface) behind an HTTP server. This documentation shows how to install and configure [gunicorn](http://gunicorn.org/) (which is automatically installed with NetBox) for this role, however other WSGI servers are available and should work similarly well.
## Configuration
NetBox ships with a default configuration file for gunicorn. To use it, copy `/opt/netbox/contrib/gunicorn.py` to `/opt/netbox/gunicorn.py`. (We make a copy of this file rather than pointing to it directly to ensure that any local changes to it do not get overwritten by a future upgrade.)
NetBox ships with a default configuration file for gunicorn. To use it, copy `/opt/netbox/contrib/gunicorn.py` to `/opt/netbox/gunicorn.py`. (We make a copy of this file rather than pointing to it directly to ensure that any local changes to it do not get overwritten during a future NetBox upgrade.)
This page provides instructions for setting up the [uWSGI](https://uwsgi-docs.readthedocs.io/) WSGI server. If you plan to use [gunicorn](http://gunicorn.org/) instead, go [here](./4a-gunicorn.md).
NetBox runs as a [WSGI application](https://en.wikipedia.org/wiki/Web_Server_Gateway_Interface) behind an HTTP server. This documentation shows how to install and configure [uWSGI](https://uwsgi-docs.readthedocs.io/en/latest/) for this role, however other WSGI servers are available and should work similarly well.
## Installation
Activate the Python virtual environment and install the `pyuwsgi` package using pip:
```no-highlight
source /opt/netbox/venv/bin/activate
pip3 install pyuwsgi
```
Once installed, add the package to `local_requirements.txt` to ensure it is re-installed during future rebuilds of the virtual environment:
```no-highlight
sudo sh -c "echo 'pyuwsgi' >> /opt/netbox/local_requirements.txt"
```
## Configuration
NetBox ships with a default configuration file for uWSGI. To use it, copy `/opt/netbox/contrib/uwsgi.ini` to `/opt/netbox/uwsgi.ini`. (We make a copy of this file rather than pointing to it directly to ensure that any local changes to it do not get overwritten during a future NetBox upgrade.)
While the provided configuration should suffice for most initial installations, you may wish to edit this file to change the bound IP address and/or port number, or to make performance-related adjustments. See [the uWSGI documentation](https://uwsgi-docs-additions.readthedocs.io/en/latest/Options.html) for the available configuration parameters and take a minute to review the [Things to know](https://uwsgi-docs.readthedocs.io/en/latest/ThingsToKnow.html) page. Django also provides [additional documentation](https://docs.djangoproject.com/en/5.0/howto/deployment/wsgi/uwsgi/) on configuring uWSGI with a Django app.
## systemd Setup
We'll use systemd to control both uWSGI and NetBox's background worker process. First, copy `contrib/netbox.service` and `contrib/netbox-rq.service` to the `/etc/systemd/system/` directory.
The reference configuration assumes that gunicorn is in use, so we need to update it. Edit the `netbox.service` file to remove the line beginning with `ExecStart=/opt/netbox/venv/bin/gunicorn` and uncomment the line below it.
!!! warning "Check user & group assignment"
The stock service configuration files packaged with NetBox assume that the service will run with the `netbox` user and group names. If these differ on your installation, be sure to update the service files accordingly.
Once the configuration file has been saved, reload the service:
```no-highlight
sudo systemctl daemon-reload
```
Then, start the `netbox` and `netbox-rq` services and enable them to initiate at boot time:
```no-highlight
sudo systemctl enable --now netbox netbox-rq
```
You can use the command `systemctl status netbox` to verify that the WSGI service is running:
If the NetBox service fails to start, issue the command `journalctl -eu netbox` to check for log messages that may indicate the problem.
Once you've verified that the WSGI workers are up and running, move on to HTTP server setup.
## HTTP Server Installation
For server installation, you will want to follow the NetBox [HTTP Server Setup](5-http-server.md) guide, however after copying the configuration file, you will need to edit the file and change the `location` section to uncomment the uWSGI parameters:
```no-highlight
location / {
# proxy_pass http://127.0.0.1:8001;
# proxy_set_header X-Forwarded-Host $http_host;
# proxy_set_header X-Real-IP $remote_addr;
# proxy_set_header X-Forwarded-Proto $scheme;
# comment the lines above and uncomment the lines below if using uWSGI
The reference nginx configuration file assumes that gunicorn is in use. If using uWSGI instead, you'll need to remove the gunicorn-specific configuration (lines beginning with `proxy_pass` and `proxy_set_header`) and uncomment the uWSGI section below them before proceeding.
Then, delete `/etc/nginx/sites-enabled/default` and create a symlink in the `sites-enabled` directory to the configuration file you just created.
@@ -17,11 +17,11 @@ Prior to upgrading your NetBox instance, be sure to carefully review all [releas
NetBox requires the following dependencies:
| Dependency | Minimum Version |
|------------|-----------------|
| Python | 3.8 |
| PostgreSQL | 12 |
| Redis | 4.0 |
| Dependency | Supported Versions |
|------------|--------------------|
| Python | 3.10, 3.11, 3.12 |
| PostgreSQL | 12+ |
| Redis | 4.0+ |
## 3. Install the Latest Release
@@ -108,10 +108,10 @@ sudo ./upgrade.sh
```
!!! warning
If the default version of Python is not at least 3.8, you'll need to pass the path to a supported Python version as an environment variable when calling the upgrade script. For example:
If the default version of Python is not at least 3.10, you'll need to pass the path to a supported Python version as an environment variable when calling the upgrade script. For example:
NetBox provides a read-only [GraphQL](https://graphql.org/) API to complement its REST API. This API is powered by the [Graphene](https://graphene-python.org/) library and [Graphene-Django](https://docs.graphene-python.org/projects/django/en/latest/).
NetBox provides a read-only [GraphQL](https://graphql.org/) API to complement its REST API. This API is powered by [Strawberry Django](https://strawberry-graphql.github.io/strawberry-django/).
## Queries
@@ -47,14 +47,18 @@ NetBox provides both a singular and plural query field for each object type:
For example, query `device(id:123)` to fetch a specific device (identified by its unique ID), and query `device_list` (with an optional set of filters) to fetch all devices.
For more detail on constructing GraphQL queries, see the [Graphene documentation](https://docs.graphene-python.org/en/latest/) as well as the [GraphQL queries documentation](https://graphql.org/learn/queries/).
For more detail on constructing GraphQL queries, see the [GraphQL queries documentation](https://graphql.org/learn/queries/). For filtering and lookup syntax, please refer to the [Strawberry Django documentation](https://strawberry-graphql.github.io/strawberry-django/guide/filters/).
## Filtering
The GraphQL API employs the same filtering logic as the UI and REST API. Filters can be specified as key-value pairs within parentheses immediately following the query name. For example, the following will return only sites within the North Carolina region with a status of active:
@@ -73,9 +73,9 @@ If no body template is specified, the request body will be populated with a JSON
## Webhook Processing
Using [Event Rules](../features/event-rules.md), when a change is detected, any resulting webhooks are placed into a Redis queue for processing. This allows the user's request to complete without needing to wait for the outgoing webhook(s) to be processed. The webhooks are then extracted from the queue by the `rqworker` process and HTTP requests are sent to their respective destinations. The current webhook queue and any failed webhooks can be inspected in the admin UI under System > Background Tasks.
Using [Event Rules](../features/event-rules.md), when a change is detected, any resulting webhooks are placed into a Redis queue for processing. This allows the user's request to complete without needing to wait for the outgoing webhook(s) to be processed. The webhooks are then extracted from the queue by the `rqworker` process and HTTP requests are sent to their respective destinations. The current webhook queue and any failed webhooks can be inspected under System > Background Tasks.
A request is considered successful if the response has a 2XX status code; otherwise, the request is marked as having failed. Failed requests may be retried manually via the admin UI.
A request is considered successful if the response has a 2XX status code; otherwise, the request is marked as having failed. Failed requests may be requeued manually under System > Background Tasks.
Circuits can be assigned to [circuit groups](./circuitgroup.md) for correlation purposes. For instance, three circuits, each belonging to a different provider, may each be assigned to the same circuit group. Each assignment may optionally include a priority designation.
## Fields
### Group
The [circuit group](./circuitgroup.md) being assigned.
### Circuit
The [circuit](./circuit.md) that is being assigned to the group.
### Priority
The circuit's operation priority relative to its peers within the group. The assignment of a priority is optional. Choices include:
* Primary
* Secondary
* Tertiary
* Inactive
!!! tip
Additional priority choices may be defined by setting `CircuitGroupAssignment.priority` under the [`FIELD_CHOICES`](../../configuration/data-validation.md#field_choices) configuration parameter.
@@ -18,9 +18,9 @@ When a device has one or more interfaces with IP addresses assigned, a primary I
The device's configured name. This field is optional; devices can be unnamed. However, if set, the name must be unique to the assigned site and tenant.
### Device Role
### Role
The functional [role](./devicerole.md) assigned to this device.
The functional [device role](./devicerole.md) assigned to this device.
@@ -26,3 +26,7 @@ The location's operational status.
!!! tip
Additional statuses may be defined by setting `Location.status` under the [`FIELD_CHOICES`](../../configuration/data-validation.md#field_choices) configuration parameter.
### Facility
Data center or facility designation for identifying the location.
@@ -20,6 +20,10 @@ The [location](./location.md) within a site where the rack has been installed (o
The rack's name or identifier. Must be unique to the rack's location, if assigned.
### Rack Type
The [physical type](./racktype.md) of this rack. The rack type defines physical attributes such as height and weight.
### Status
Operational status.
@@ -43,44 +47,5 @@ The unique physical serial number assigned to this rack.
A unique, locally-administered label used to identify hardware resources.
### Type
A rack can be designated as one of the following types:
* 2-post frame
* 4-post frame
* 4-post cabinet
* Wall-mounted frame
* Wall-mounted cabinet
### Width
The canonical distance between the two vertical rails on a face. (This is typically 19 inches, however other standard widths exist.)
### Height
The height of the rack, measured in units.
### Starting Unit
The number of the numerically lowest unit in the rack. This value defaults to one, but may be higher in certain situations. For example, you may want to model only a select range of units within a shared physical rack (e.g. U13 through U24).
### Outer Dimensions
The external width and depth of the rack can be tracked to aid in floorplan calculations. These measurements must be designated in either millimeters or inches.
### Mounting Depth
The maximum depth of a mounted device that the rack can accommodate, in millimeters. For four-post frames or cabinets, this is the horizontal distance between the front and rear vertical rails. (Note that this measurement does _not_ include space between the rails and the cabinet doors.)
### Weight
The numeric weight of the rack, including a unit designation (e.g. 10 kilograms or 20 pounds).
### Maximum Weight
The maximum total weight capacity for all installed devices, inclusive of the rack itself.
### Descending Units
If selected, the rack's elevation will display unit 1 at the top of the rack. (Most racks use ascending numbering, with unit 1 assigned to the bottommost position.)
!!! note
Some additional fields pertaining to physical attributes such as height and weight can also be defined on each rack, but should generally be defined instead on the [rack type](./racktype.md).
!!! info "This feature was introduced in NetBox v4.1."
A rack type defines the physical characteristics of a particular model of [rack](./rack.md).
## Fields
### Manufacturer
The [manufacturer](./manufacturer.md) which produces this type of rack.
### Model
The model number assigned to this rack type by its manufacturer. Must be unique to the manufacturer.
### Slug
A unique URL-friendly representation of the model identifier. (This value can be used for filtering.)
### Form Factor
A rack can be designated as one of the following form factors:
* 2-post frame
* 4-post frame
* 4-post cabinet
* Wall-mounted frame
* Wall-mounted cabinet
### Width
The canonical distance between the two vertical rails on a face. (This is typically 19 inches, however other standard widths exist.)
### Height
The height of the rack, measured in units.
### Starting Unit
The number of the numerically lowest unit in the rack. This value defaults to one, but may be higher in certain situations. For example, you may want to model only a select range of units within a shared physical rack (e.g. U13 through U24).
### Outer Dimensions
The external width and depth of the rack can be tracked to aid in floorplan calculations. These measurements must be designated in either millimeters or inches.
### Mounting Depth
The maximum depth of a mounted device that the rack can accommodate, in millimeters. For four-post frames or cabinets, this is the horizontal distance between the front and rear vertical rails. (Note that this measurement does _not_ include space between the rails and the cabinet doors.)
### Weight
The numeric weight of the rack, including a unit designation (e.g. 10 kilograms or 20 pounds).
### Maximum Weight
The maximum total weight capacity for all installed devices, inclusive of the rack itself.
### Descending Units
If selected, the rack's elevation will display unit 1 at the top of the rack. (Most racks use ascending numbering, with unit 1 assigned to the bottommost position.)
### Airflow
The direction in which air circulates through the rack for cooling.
!!! info "This feature was introduced in NetBox v3.6."
A user can bookmark individual objects for convenient access. Bookmarks are listed under a user's profile and can be displayed using a dashboard widget.
@@ -38,10 +38,19 @@ The type of data this field holds. This must be one of the following:
| Object | A single NetBox object of the type defined by `object_type` |
| Multiple object | One or more NetBox objects of the type defined by `object_type` |
### Object Type
### Related Object Type
For object and multiple-object fields only. Designates the type of NetBox object being referenced.
### Related Object Filter
!!! info "This field was introduced in NetBox v4.1."
For object and multi-object custom fields, a filter may be defined to limit the available objects when populating a field value. This filter maps object attributes to values. For example, `{"status": "active"}` will include only objects with a status of "active."
!!! warning
This setting is employed for convenience only, and should not be relied upon to enforce data integrity.
### Weight
A numeric weight used to override alphabetic ordering of fields by name. Custom fields with a lower weight will be listed before those with a higher weight. (Note that weight applies within the context of a custom field group, if defined.)
@@ -107,3 +116,7 @@ For numeric custom fields only. The maximum valid value (optional).
### Validation Regex
For string-based custom fields only. A regular expression used to validate the field's value (optional).
### Uniqueness Validation
If enabled, each object must have a unique value set for this custom field (per object type).
!!! info "This feature was introduced in NetBox v3.6."
Single- and multi-selection [custom fields](../../customization/custom-fields.md) must define a set of valid choices from which the user may choose when defining the field value. These choices are defined as sets that may be reused among multiple custom fields.
A choice set must define a base choice set and/or a set of arbitrary extra choices.
A notification alerts a user that a specific action has taken place in NetBox, such as an object being modified or a background job completing. A notification may be generated via a user's [subscription](./subscription.md) to a particular object, or by an event rule targeting a [notification group](./notificationgroup.md) of which the user is a member.
A record indicating that a user is to be notified of any changes to a particular NetBox object. A notification maps exactly one user to exactly one object.
When an object to which a user is subscribed changes, a [notification](./notification.md) is generated for the user.
@@ -18,8 +18,6 @@ The color to use when displaying the tag in the NetBox UI.
### Object Types
!!! info "This feature was introduced in NetBox v3.6."
The assignment of a tag may be limited to a prescribed set of objects. For example, it may be desirable to limit the application of a specific tag to only devices and virtual machines.
If no object types are specified, the tag will be assignable to any type of object.
A unique URL-friendly identifier. (This value can be used for filtering.)
### Minimum & Maximum VLAN IDs
### VLAN ID Ranges
A minimum and maximum child VLAN ID must be set for each group. (These default to 1 and 4094 respectively.) VLANs created within a group must have a VID that falls between these values (inclusive).
!!! info "This field replaced the legacy `min_vid` and `max_vid` fields in NetBox v4.1."
The set of VLAN IDs which are encompassed by the group. By default, this will be the entire range of valid IEEE 802.1Q VLAN IDs (1 to 4094, inclusive). VLANs created within a group must have a VID that falls within one of these ranges. Ranges may not overlap.
@@ -50,4 +50,13 @@ The amount of running memory provisioned, in megabytes.
### Disk
The amount of disk storage provisioned, in gigabytes.
The amount of disk storage provisioned, in megabytes.
!!! warning
This field may be directly modified only on virtual machines which do not define discrete [virtual disks](./virtualdisk.md). Otherwise, it will report the sum of all attached disks.
### Serial Number
!!! info "This field was introduced in NetBox v4.1."
Optional serial number assigned to this virtual machine. Unlike devices, uniqueness is not enforced for virtual machine serial numbers.
!!! info "This feature was introduced in NetBox v4.1."
NetBox plugins can defer certain operations by enqueuing [background jobs](../../features/background-jobs.md), which are executed asynchronously by background workers. This is helpful for decoupling long-running processes from the user-facing request-response cycle.
For example, your plugin might need to fetch data from a remote system. Depending on the amount of data and the responsiveness of the remote server, this could take a few minutes. Deferring this task to a queued job ensures that it can be completed in the background, without interrupting the user. The data it fetches can be made available once the job has completed.
## Job Runners
A background job implements a basic [Job](../../models/core/job.md) executor for all kinds of tasks. It has logic implemented to handle the management of the associated job object, rescheduling of periodic jobs in the given interval and error handling. Adding custom jobs is done by subclassing NetBox's `JobRunner` class.
::: netbox.jobs.JobRunner
#### Example
```python title="jobs.py"
from netbox.jobs import JobRunner
class MyTestJob(JobRunner):
class Meta:
name = "My Test Job"
def run(self, *args, **kwargs):
obj = self.job.object
# your logic goes here
```
You can schedule the background job from within your code (e.g. from a model's `save()` method or a view) by calling `MyTestJob.enqueue()`. This method passes through all arguments to `Job.enqueue()`. However, no `name` argument must be passed, as the background job name will be used instead.
### Attributes
`JobRunner` attributes are defined under a class named `Meta` within the job. These are optional, but encouraged.
#### `name`
This is the human-friendly names of your background job. If omitted, the class name will be used.
### Scheduled Jobs
As described above, jobs can be scheduled for immediate execution or at any later time using the `enqueue()` method. However, for management purposes, the `enqueue_once()` method allows a job to be scheduled exactly once avoiding duplicates. If a job is already scheduled for a particular instance, a second one won't be scheduled, respecting thread safety. An example use case would be to schedule a periodic task that is bound to an instance in general, but not to any event of that instance (such as updates). The parameters of the `enqueue_once()` method are identical to those of `enqueue()`.
!!! tip
It is not forbidden to `enqueue()` additional jobs while an interval schedule is active. An example use of this would be to schedule a periodic daily synchronization, but also trigger additional synchronizations on demand when the user presses a button.
#### Example
```python title="jobs.py"
from netbox.jobs import JobRunner
class MyHousekeepingJob(JobRunner):
class Meta:
name = "Housekeeping"
def run(self, *args, **kwargs):
# your logic goes here
```
```python title="__init__.py"
from netbox.plugins import PluginConfig
class MyPluginConfig(PluginConfig):
def ready(self):
from .jobs import MyHousekeepingJob
MyHousekeepingJob.setup(interval=60)
```
## Task queues
Three task queues of differing priority are defined by default:
* High
* Default
* Low
Any tasks in the "high" queue are completed before the default queue is checked, and any tasks in the default queue are completed before those in the "low" queue.
Plugins can also add custom queues for their own needs by setting the `queues` attribute under the PluginConfig class. An example is included below:
```python
class MyPluginConfig(PluginConfig):
name = 'myplugin'
...
queues = [
'foo',
'bar',
]
```
The `PluginConfig` above creates two custom queues with the following names `my_plugin.foo` and `my_plugin.bar`. (The plugin's name is prepended to each queue to avoid conflicts between plugins.)
!!! warning "Configuring the RQ worker process"
By default, NetBox's RQ worker process only services the high, default, and low queues. Plugins which introduce custom queues should advise users to either reconfigure the default worker, or run a dedicated worker specifying the necessary queues. For example:
NetBox supports the queuing of tasks that need to be performed in the background, decoupled from the request-response cycle, using the [Python RQ](https://python-rq.org/) library. Three task queues of differing priority are defined by default:
* High
* Default
* Low
Any tasks in the "high" queue are completed before the default queue is checked, and any tasks in the default queue are completed before those in the "low" queue.
Plugins can also add custom queues for their own needs by setting the `queues` attribute under the PluginConfig class. An example is included below:
```python
classMyPluginConfig(PluginConfig):
name='myplugin'
...
queues=[
'foo',
'bar',
]
```
The PluginConfig above creates two custom queues with the following names `my_plugin.foo` and `my_plugin.bar`. (The plugin's name is prepended to each queue to avoid conflicts between plugins.)
!!! warning "Configuring the RQ worker process"
By default, NetBox's RQ worker process only services the high, default, and low queues. Plugins which introduce custom queues should advise users to either reconfigure the default worker, or run a dedicated worker specifying the necessary queues. For example:
!!! info "This feature was introduced in NetBox v4.1."
Plugins can register their own custom event types for use with NetBox [event rules](../../models/extras/eventrule.md). This is accomplished by calling the `register()` method on an instance of the `EventType` class. This can be done anywhere within the plugin. An example is provided below.
@@ -115,10 +120,10 @@ class MyModelEditForm(NetBoxModelImportForm):
This form class is used to render a form expressly for filtering a list of objects. Its fields should correspond to filters defined on the model's filter set.
A plugin can extend NetBox's GraphQL API by registering its own schema class. By default, NetBox will attempt to import `graphql.schema` from the plugin, if it exists. This path can be overridden by defining `graphql_schema` on the PluginConfig instance as the dotted path to the desired Python class. This class must be a subclass of `graphene.ObjectType`.
A plugin can extend NetBox's GraphQL API by registering its own schema class. By default, NetBox will attempt to import `graphql.schema` from the plugin, if it exists. This path can be overridden by defining `graphql_schema` on the PluginConfig instance as the dotted path to the desired Python class.
Just getting started with plugins? Check out our [**NetBox Plugin Tutorial**](https://github.com/netbox-community/netbox-plugin-tutorial) on GitHub! This in-depth guide will walk you through the process of creating an entire plugin from scratch. It even includes a companion [demo plugin repo](https://github.com/netbox-community/netbox-plugin-demo) to ensure you can jump in at any step along the way. This will get you up and running with plugins in no time!
!!! tip "Plugin Certification Program"
NetBox Labs offers a [**Plugin Certification Program**](https://github.com/netbox-community/netbox/wiki/Plugin-Certification-Program) for plugin developers interested in establishing a co-maintainer relationship. The program aims to assure ongoing compatibility, maintainability, and commercial supportability of key plugins.
NetBox can be extended to support additional data models and functionality through the use of plugins. A plugin is essentially a self-contained [Django app](https://docs.djangoproject.com/en/stable/) which gets installed alongside NetBox to provide custom functionality. Multiple plugins can be installed in a single NetBox instance, and each plugin can be enabled and configured independently.
!!! info "Django Development"
@@ -44,6 +47,7 @@ project-name/
- __init__.py
- filtersets.py
- graphql.py
- jobs.py
- models.py
- middleware.py
- navigation.py
@@ -52,18 +56,20 @@ project-name/
- template_content.py
- urls.py
- views.py
- pyproject.toml
- README.md
- setup.py
```
The top level is the project root, which can have any name that you like. Immediately within the root should exist several items:
* `setup.py` - This is a standard installation script used to install the plugin package within the Python environment.
* `pyproject.toml` - is a standard configuration file used to install the plugin package within the Python environment.
* `README.md` - A brief introduction to your plugin, how to install and configure it, where to find help, and any other pertinent information. It is recommended to write `README` files using a markup language such as Markdown to enable human-friendly display.
* The plugin source directory. This must be a valid Python package name, typically comprising only lowercase letters, numbers, and underscores.
The plugin source directory contains all the actual Python code and other resources used by your plugin. Its structure is left to the author's discretion, however it is recommended to follow best practices as outlined in the [Django documentation](https://docs.djangoproject.com/en/stable/intro/reusable-apps/). At a minimum, this directory **must** contain an `__init__.py` file containing an instance of NetBox's `PluginConfig` class, discussed below.
**Note:** The [Cookiecutter NetBox Plugin](https://github.com/netbox-community/cookiecutter-netbox-plugin) can be used to auto-generate all the needed directories and files for a new plugin.
## PluginConfig
The `PluginConfig` class is a NetBox-specific wrapper around Django's built-in [`AppConfig`](https://docs.djangoproject.com/en/stable/ref/applications/) class. It is used to declare NetBox plugin functionality within a Python package. Each plugin should provide its own subclass, defining its name, metadata, and default and required configuration parameters. An example is below:
@@ -133,31 +139,48 @@ Apps from this list are inserted *before* the plugin's `PluginConfig` in the ord
Any additional apps must be installed within the same Python environment as NetBox or `ImproperlyConfigured` exceptions will be raised when loading the plugin.
## Create setup.py
## Create pyproject.toml
`setup.py` is the [setup script](https://docs.python.org/3.8/distutils/setupscript.html) used to package and install our plugin once it's finished. The primary function of this script is to call the setuptools library's `setup()` function to create a Python distribution package. We can pass a number of keyword arguments to control the package creation as well as to provide metadata about the plugin. An example `setup.py` is below:
`pyproject.toml` is the [configuration file](https://packaging.python.org/en/latest/guides/writing-pyproject-toml/) used to package and install our plugin once it's finished. It is used by packaging tools, as well as other tools. The primary function of this file is to call the build system to create a Python distribution package. We can pass a number of keyword arguments to control the package creation as well as to provide metadata about the plugin. There are three possible TOML tables in this file:
```python
from setuptools import find_packages, setup
* `[build-system]` allows you to declare which build backend you use and which other dependencies (if any) are needed to build your project.
* `[project]` is the format that most build backends use to specify your project’s basic metadata, such as the author's name, project URL, etc.
* `[tool]` has tool-specific subtables, e.g., `[tool.black]`, `[tool.mypy]`. Consult the particular tool’s documentation for reference.
Many of these are self-explanatory, but for more information, see the [setuptools documentation](https://setuptools.readthedocs.io/en/latest/setuptools.html).
!!! info
`zip_safe=False` is **required** as the current plugin iteration is not zip safe due to upstream python issue [issue19699](https://bugs.python.org/issue19699)
Many of these are self-explanatory, but for more information, see the [pyproject.toml documentation](https://packaging.python.org/en/latest/specifications/pyproject-toml/).
You can make NetBox available within this environment by creating a path file pointing to its location. This will add NetBox to the Python path upon activation. (Be sure to adjust the command below to specify your actual virtual environment path, Python version, and NetBox installation.)
To ease development, it is recommended to go ahead and install the plugin at this point using setuptools' `develop` mode. This will create symbolic links within your Python environment to the plugin development directory. Call `setup.py` from the plugin's root directory with the `develop` argument (instead of `install`):
To ease development, it is recommended to go ahead and install the plugin at this point using setuptools' `develop` mode. This will create symbolic links within your Python environment to the plugin development directory. Call `pip` from the plugin's root directory with the `-e` flag:
```no-highlight
$ python setup.py develop
$ pip install -e .
```
More information on editable builds can be found at [Editable installs for pyproject.toml ](https://peps.python.org/pep-0660/).
This document serves as a handbook for maintainers of plugins that were written prior to the release of NetBox v4.0. It serves to capture all the changes recommended to ensure a plugin is compatible with NetBox v4.0 and later releases.
## General
### Python support
NetBox v4.0 drops support for Python 3.8 and 3.9, and introduces support for Python 3.12. You may need to update your CI/CD processes and/or packaging to reflect this.
### Plugin resources relocated
All plugin Python resources were moved from `extras.plugins` to `netbox.plugins` in NetBox v3.7 (see [#14036](https://github.com/netbox-community/netbox/issues/14036)), and support for importing these resources from their old locations has been removed.
```python title="Old"
from extras.plugins import PluginConfig
```
```python title="New"
from netbox.plugins import PluginConfig
```
### ContentType renamed to ObjectType
NetBox's proxy model for Django's [ContentType model](https://docs.djangoproject.com/en/5.0/ref/contrib/contenttypes/#the-contenttype-model) has been renamed to ObjectType for clarity. In general, plugins should use the ObjectType proxy when referencing content types, as it includes several custom manager methods. The one exception to this is when defining [generic foreign keys](https://docs.djangoproject.com/en/5.0/ref/contrib/contenttypes/#generic-relations): The ForeignKey field used for a GFK should point to Django's native ContentType.
Additionally, plugin maintainers are strongly encouraged to adopt the "object type" terminology for field and filter names wherever feasible to be consistent with NetBox core (however this is not required for compatibility).
```python title="Old"
content_types = models.ManyToManyField(
to='contenttypes.ContentType',
related_name='event_rules'
)
```
```python title="New"
object_types = models.ManyToManyField(
to='core.ObjectType',
related_name='event_rules'
)
```
## Views
### View actions must be dictionaries
The format for declaring view actions & permissions was updated in NetBox v3.7 (see [#13550](https://github.com/netbox-community/netbox/issues/13550)), and NetBox v4.0 drops support for the old format. Views which inherit `ActionsMixin` must declare a single `actions` map.
The `BootstrapMixin` class is no longer available or needed and can be removed from all forms.
```python title="Old"
from django import forms
from utilities.forms import BootstrapMixin
class MyForm(BootstrapMixin, forms.Form):
```
```python title="New"
from django import forms
class MyForm(forms.Form):
```
### Update Fieldset definitions
NetBox v4.0 introduces [several new classes](./forms.md#form-rendering) for advanced form rendering, including FieldSet. Fieldset definitions on forms should use this new class instead of a tuple or list.
Notably, the name of a fieldset is now optional, and passed as a keyword argument rather than as the first item in the set.
```python title="Old"
from django.utils.translation import gettext_lazy as _
NetBox no longer applies color to buttons within navigation menu items. Although this functionality is still supported, you might want to remove color from any buttons to ensure consistency with the updated design.
```python title="Old"
PluginMenuButton(
link='myplugin:foo_add',
title='Add a new Foo',
icon_class='mdi mdi-plus-thick',
color=ButtonColorChoices.GREEN
)
```
```python title="New"
PluginMenuButton(
link='myplugin:foo_add',
title='Add a new Foo',
icon_class='mdi mdi-plus-thick'
)
```
## UI Layout
### Renamed template blocks
The following template blocks have been renamed or removed:
Ditch any legacy "float" controls (e.g. `float-end`) in favor of Bootstrap's new [flex behaviors](https://getbootstrap.com/docs/5.3/utilities/flex/) for controlling the layout and sizing of elements horizontally. For example, the following will align two items against the left and right sides of the parent element:
```html
<div class="d-flex justify-content-between">
<h3>Title text</h3>
<i class="mdi mdi-close"></i>
</div>
```
### Check column offsets
When using [offset columns](https://getbootstrap.com/docs/5.3/layout/columns/#offsetting-columns) (e.g. `class="col-offset-3"`), be sure to also set the column width (e.g. `class="col-9 col-offset-3"`) to avoid horizontal scrolling.
### Tables inside cards
Tables inside cards should be embedded directly, not nested inside a `card-body` element.
```html title="Old"
<div class="card">
<div class="card-body">
<table class="table table-hover attr-table">
...
</table>
</div>
</div>
```
```html title="New"
<div class="card">
<table class="table table-hover attr-table">
...
</table>
</div>
```
### Remove `btn-sm` class from buttons
The `btn-sm` (small) class is no longer typically needed on general-purpose buttons.
Foreground (text) color is no longer automatically adjusted by `bg-$color` classes. To ensure sufficient contrast with the background color, use the [`text-bg-$color`](https://getbootstrap.com/docs/5.3/helpers/color-background/) form of the class instead, or set the text color separately with `text-$color`.
```html title="Old"
<span class="badge bg-primary">Text</span>
```
```html title="New"
<span class="badge text-bg-primary">Text</span>
```
### Obsolete custom CSS classes
The following custom CSS classes have been removed:
NetBox now uses a single API serializer for both normal and "brief" modes (i.e. `GET /api/dcim/sites/?brief=true`); nested serializer classes are no longer required. Two changes to API serializers are necessary to support brief mode:
1. Define `brief_fields` under its `Meta` class. These are the fields which will be included when brief mode is used.
2. For any nested objects, switch to using the primary serializer and pass `nested=True`.
Any nested serializers which are no longer needed can be removed.
```python title="Old"
class SiteSerializer(NetBoxModelSerializer):
region = NestedRegionSerializer(required=False, allow_null=True)
NetBox now includes the `description` field in "brief" mode for all models which have one. This is not required for plugins, but you may opt to do the same for consistency.
## GraphQL
NetBox has replaced [Graphene-Django](https://github.com/graphql-python/graphene-django) with [Strawberry](https://strawberry.rocks/) which requires any GraphQL code to be updated.
### Change schema.py
Strawberry uses [Python typing](https://docs.python.org/3/library/typing.html) and generally only requires a small refactoring of the schema definition to update:
```python title="Old"
import graphene
from netbox.graphql.fields import ObjectField, ObjectListField
from utilities.graphql_optimizer import gql_query_optimizer
Strawberry currently doesn't directly support django-filter, so an explicit filters.py file will need to be created. NetBox includes a new `autotype_decorator` used to automatically wrap FilterSets to reduce the required code to a minimum.
```python title="New"
import strawberry
import strawberry_django
from circuits import filtersets, models
from netbox.graphql.filter_mixins import autotype_decorator, BaseFilterMixin
Each menu item represents a link and (optionally) a set of buttons comprising one entry in NetBox's navigation menu. Menu items are defined as PluginMenuItem instances. An example is shown below.
```python title="navigation.py"
from netbox.choices import ButtonColorChoices
from netbox.plugins import PluginMenuButton, PluginMenuItem
from utilities.choices import ButtonColorChoices
item1 = PluginMenuItem(
link='plugins:myplugin:myview',
@@ -72,8 +72,6 @@ A `PluginMenuItem` has the following attributes:
| `staff_only` | - | Display only for users who have `is_staff` set to true (any specified permissions will also be required) |
| `buttons` | - | An iterable of PluginMenuButton instances to include |
!!! info "The `staff_only` attribute was introduced in NetBox v3.6.1."
## Menu Buttons
Each menu item can include a set of buttons. These can be handy for providing shortcuts related to the menu item. For instance, most items in NetBox's navigation menu include buttons to create and import new objects.
@@ -27,7 +27,7 @@ Serializers are responsible for converting Python objects to JSON data suitable
#### Example
To create a serializer for a plugin model, subclass `NetBoxModelSerializer` in `api/serializers.py`. Specify the model class and the fields to include within the serializer's `Meta` class. It is generally advisable to include a `url` attribute on each serializer. This will render the direct link to access the object being rendered.
To create a serializer for a plugin model, subclass `NetBoxModelSerializer` in `api/serializers.py`. Specify the model class and the fields to include within the serializer's `Meta` class.
```python
# api/serializers.py
@@ -36,9 +36,7 @@ from netbox.api.serializers import NetBoxModelSerializer
@@ -90,8 +90,6 @@ The table column classes listed below are supported for use in plugins. These cl
## Extending Core Tables
!!! info "This feature was introduced in NetBox v3.7."
Plugins can register their own custom columns on core tables using the `register_table_column()` utility function. This allows a plugin to attach additional information, such as relationships to its own models, to built-in object lists.
@@ -157,7 +157,7 @@ These views are provided to enable or enhance certain NetBox model features, suc
### Additional Tabs
Plugins can "attach" a custom view to a core NetBox model by registering it with `register_model_view()`. To include a tab for this view within the NetBox UI, declare a TabView instance named `tab`:
Plugins can "attach" a custom view to a core NetBox model by registering it with `register_model_view()`. To include a tab for this view within the NetBox UI, declare a TabView instance named `tab`, and add it to the template context dict:
```python
fromdcim.modelsimportSite
@@ -173,6 +173,16 @@ class MyView(generic.ObjectView):
@@ -181,19 +191,25 @@ class MyView(generic.ObjectView):
### Extra Template Content
Plugins can inject custom content into certain areas of core NetBox views. This is accomplished by subclassing `PluginTemplateExtension`, designating a particular NetBox model, and defining the desired method(s) to render custom content. Five methods are available:
Plugins can inject custom content into certain areas of core NetBox views. This is accomplished by subclassing `PluginTemplateExtension`, optionally designating one or more particular NetBox models, and defining the desired method(s) to render custom content. Five methods are available:
| `navbar()` | All | Inject content inside the top navigation bar |
| `list_buttons()` | List view | Add buttons to the top of the page |
| `buttons()` | Object view | Add buttons to the top of the page |
| `alerts()` | Object view | Inject content at the top of the page |
| `left_page()` | Object view | Inject content on the left side of the page |
| `right_page()` | Object view | Inject content on the right side of the page |
| `full_width_page()` | Object view | Inject content across the entire bottom of the page |
| `buttons()` | Object view | Add buttons to the top of the page |
| `list_buttons()` | List view | Add buttons to the top of the page |
!!! info "The `navbar()` and `alerts()` methods were introduced in NetBox v4.1."
Additionally, a `render()` method is available for convenience. This method accepts the name of a template to render, and any additional context data you want to pass. Its use is optional, however.
When a PluginTemplateExtension is instantiated, context data is assigned to `self.context`. Available data include:
To control where the custom content is injected, plugin authors can specify an iterable of models by overriding the `models` attribute on the subclass. Extensions which do not specify a set of models will be invoked on every view, where supported.
When a PluginTemplateExtension is instantiated, context data is assigned to `self.context`. Available data includes:
*`object` - The object being viewed (object views only)
*`model` - The model of the list view (list views only)
@@ -210,7 +226,7 @@ from netbox.plugins import PluginTemplateExtension
Plugins are packaged [Django](https://docs.djangoproject.com/) apps that can be installed alongside NetBox to provide custom functionality not present in the core application. Plugins can introduce their own models and views, but cannot interfere with existing components. A NetBox user may opt to install plugins provided by the community or build his or her own.
Please see the documented instructions for [installing a plugin](./installation.md) to get started.
## Capabilities
The NetBox plugin architecture allows for the following:
@@ -23,122 +25,3 @@ Either by policy or by technical limitation, the interaction of plugins with Net
* **Override core templates.** Plugins can inject additional content where supported, but may not manipulate or remove core content.
* **Modify core settings.** A configuration registry is provided for plugins, however they cannot alter or delete the core configuration.
* **Disable core components.** Plugins are not permitted to disable or hide core NetBox components.
## Installing Plugins
The instructions below detail the process for installing and enabling a NetBox plugin.
### Install Package
Download and install the plugin package per its installation instructions. Plugins published via PyPI are typically installed using pip. Be sure to install the plugin within NetBox's virtual environment.
```no-highlight
$ source /opt/netbox/venv/bin/activate
(venv) $ pip install <package>
```
Alternatively, you may wish to install the plugin manually by running `python setup.py install`. If you are developing a plugin and want to install it only temporarily, run `python setup.py develop` instead.
### Enable the Plugin
In `configuration.py`, add the plugin's name to the `PLUGINS` list:
```python
PLUGINS = [
'plugin_name',
]
```
### Configure Plugin
If the plugin requires any configuration, define it in `configuration.py` under the `PLUGINS_CONFIG` parameter. The available configuration parameters should be detailed in the plugin's README file.
```no-highlight
PLUGINS_CONFIG = {
'plugin_name': {
'foo': 'bar',
'buzz': 'bazz'
}
}
```
### Run Database Migrations
If the plugin introduces new database models, run the provided schema migrations:
```no-highlight
(venv) $ cd /opt/netbox/netbox/
(venv) $ python3 manage.py migrate
```
### Collect Static Files
Plugins may package static files to be served directly by the HTTP front end. Ensure that these are copied to the static root directory with the `collectstatic` management command:
```no-highlight
(venv) $ cd /opt/netbox/netbox/
(venv) $ python3 manage.py collectstatic
```
### Restart WSGI Service
Restart the WSGI service and RQ workers to load the new plugin:
```no-highlight
# sudo systemctl restart netbox netbox-rq
```
## Removing Plugins
Follow these steps to completely remove a plugin.
### Update Configuration
Remove the plugin from the `PLUGINS` list in `configuration.py`. Also remove any relevant configuration parameters from `PLUGINS_CONFIG`.
### Remove the Python Package
Use `pip` to remove the installed plugin:
```no-highlight
$ source /opt/netbox/venv/bin/activate
(venv) $ pip uninstall <package>
```
### Restart WSGI Service
Restart the WSGI service:
```no-highlight
# sudo systemctl restart netbox
```
### Drop Database Tables
!!! note
This step is necessary only for plugin which have created one or more database tables (generally through the introduction of new models). Check your plugin's documentation if unsure.
Enter the PostgreSQL database shell to determine if the plugin has created any SQL tables. Substitute `pluginname` in the example below for the name of the plugin being removed. (You can also run the `\dt` command without a pattern to list _all_ tables.)
```no-highlight
netbox=> \dt pluginname_*
List of relations
List of relations
Schema | Name | Type | Owner
--------+----------------+-------+--------
public | pluginname_foo | table | netbox
public | pluginname_bar | table | netbox
(2 rows)
```
!!! warning
Exercise extreme caution when removing tables. Users are strongly encouraged to perform a backup of their database immediately before taking these actions.
Drop each of the listed tables to remove it from the database:
The instructions below detail the general process for installing and configuring a NetBox plugin. However, each plugin is different and may require additional tasks or modifications to the steps below. Always consult the documentation for a specific plugin **before** attempting to install it.
## Install the Python Package
Download and install the plugin's Python package per its installation instructions. Plugins published via PyPI are typically installed using the [`pip`](https://packaging.python.org/en/latest/tutorials/installing-packages/) command line utility. Be sure to install the plugin within NetBox's virtual environment.
```no-highlight
$ source /opt/netbox/venv/bin/activate
(venv) $ pip install <package>
```
Alternatively, you may wish to install the plugin manually by running `python setup.py install`. If you are developing a plugin and want to install it only temporarily, run `python setup.py develop` instead.
## Enable the Plugin
In `configuration.py`, add the plugin's name to the `PLUGINS` list:
```python
PLUGINS = [
# ...
'plugin_name',
]
```
## Configure the Plugin
If the plugin requires any configuration, define it in `configuration.py` under the `PLUGINS_CONFIG` parameter. The available configuration parameters should be detailed in the plugin's `README` file or other documentation.
```no-highlight
PLUGINS_CONFIG = {
'plugin_name': {
'foo': 'bar',
'buzz': 'bazz'
}
}
```
## Run Database Migrations
If the plugin introduces new database models, run the provided schema migrations:
```no-highlight
(venv) $ cd /opt/netbox/netbox/
(venv) $ python3 manage.py migrate
```
!!! tip
It's okay to run the `migrate` management command even if the plugin does not include any migration files.
## Collect Static Files
Plugins may package static resources like images or scripts to be served directly by the HTTP front end. Ensure that these are copied to the static root directory with the `collectstatic` management command:
```no-highlight
(venv) $ cd /opt/netbox/netbox/
(venv) $ python3 manage.py collectstatic
```
### Restart WSGI Service
Finally, restart the WSGI service and RQ workers to load the new plugin:
The instructions below detail the general process for removing a NetBox plugin. However, each plugin is different and may require additional tasks or modifications to the steps below. Always consult the documentation for a specific plugin **before** attempting to remove it.
## Disable the Plugin
Disable the plugin by removing it from the `PLUGINS` list in `configuration.py`.
## Remove its Configuration
Delete the plugin's entry (if any) in the `PLUGINS_CONFIG` dictionary in `configuration.py`.
!!! tip
If there's a chance you may reinstall the plugin, consider commenting out any configuration parameters instead of deleting them.
## Re-index Search Entries
Run the `reindex` management command to reindex the global search engine. This will remove any stale entries pertaining to objects provided by the plugin.
```no-highlight
$ cd /opt/netbox/netbox/
$ source /opt/netbox/venv/bin/activate
(venv) $ python3 manage.py reindex
```
## Uninstall its Python Package
Use `pip` to remove the installed plugin:
```no-highlight
$ source /opt/netbox/venv/bin/activate
(venv) $ pip uninstall <package>
```
## Restart WSGI Service
Restart the WSGI service:
```no-highlight
# sudo systemctl restart netbox
```
## Drop Database Tables
!!! note
This step is necessary only for plugins which have created one or more database tables (generally through the introduction of new models). Check your plugin's documentation if unsure.
Enter the PostgreSQL database shell (`manage.py dbshell`) to determine if the plugin has created any SQL tables. Substitute `pluginname` in the example below for the name of the plugin being removed. (You can also run the `\dt` command without a pattern to list _all_ tables.)
```no-highlight
netbox=> \dt pluginname_*
List of relations
List of relations
Schema | Name | Type | Owner
--------+----------------+-------+--------
public | pluginname_foo | table | netbox
public | pluginname_bar | table | netbox
(2 rows)
```
!!! warning
Exercise extreme caution when removing tables. Users are strongly encouraged to perform a backup of their database immediately before taking these actions.
Drop each of the listed tables to remove it from the database:
```no-highlight
netbox=> DROP TABLE pluginname_foo;
DROP TABLE
netbox=> DROP TABLE pluginname_bar;
DROP TABLE
```
### Remove the Django Migration Records
After removing the tables created by a plugin, the migrations that created the tables need to be removed from Django's migration history as well. This is necessary to make it possible to reinstall the plugin at a later time. If the migration history were left in place, Django would skip all migrations that were executed in the course of a previous installation, which would cause the plugin to fail after reinstallation.
```no-highlight
netbox=> SELECT * FROM django_migrations WHERE app='pluginname';
netbox=> DELETE FROM django_migrations WHERE app='pluginname';
```
!!! warning
Exercise extreme caution when altering Django system tables. Users are strongly encouraged to perform a backup of their database immediately before taking these actions.
Some files were not shown because too many files have changed in this diff
Show More
Reference in New Issue
Block a user
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.