nautobot 2.4.8__py3-none-any.whl → 2.4.9__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of nautobot might be problematic. Click here for more details.
- nautobot/circuits/templates/circuits/circuittype.html +1 -1
- nautobot/circuits/templates/circuits/circuittype_retrieve.html +1 -39
- nautobot/circuits/views.py +18 -23
- nautobot/cloud/templates/cloud/cloudresourcetype_retrieve.html +4 -111
- nautobot/cloud/views.py +56 -25
- nautobot/core/celery/schedulers.py +1 -0
- nautobot/core/filters.py +1 -1
- nautobot/core/graphql/schema.py +1 -0
- nautobot/core/jobs/__init__.py +14 -3
- nautobot/core/tables.py +13 -6
- nautobot/core/testing/views.py +27 -2
- nautobot/core/tests/test_jobs.py +113 -0
- nautobot/core/tests/test_ui.py +53 -1
- nautobot/core/tests/test_utils.py +11 -0
- nautobot/core/ui/object_detail.py +19 -12
- nautobot/core/utils/filtering.py +3 -0
- nautobot/core/views/renderers.py +1 -1
- nautobot/dcim/forms.py +10 -0
- nautobot/dcim/templates/dcim/devicefamily_retrieve.html +1 -43
- nautobot/dcim/templates/dcim/deviceredundancygroup_retrieve.html +1 -59
- nautobot/dcim/templates/dcim/devicetype.html +2 -217
- nautobot/dcim/templates/dcim/devicetype_edit.html +2 -32
- nautobot/dcim/templates/dcim/devicetype_retrieve.html +217 -0
- nautobot/dcim/templates/dcim/devicetype_update.html +32 -0
- nautobot/dcim/templates/dcim/inc/rack_elevation.html +1 -1
- nautobot/dcim/templates/dcim/modulebay_retrieve.html +1 -84
- nautobot/dcim/templates/dcim/rack_elevation.html +14 -0
- nautobot/dcim/templates/dcim/rackreservation_retrieve.html +0 -68
- nautobot/dcim/tests/integration/test_fileinputpicker.py +1 -1
- nautobot/dcim/urls.py +1 -36
- nautobot/dcim/views.py +133 -81
- nautobot/extras/api/views.py +4 -6
- nautobot/extras/migrations/0024_job_data_migration.py +1 -1
- nautobot/extras/models/jobs.py +78 -62
- nautobot/extras/tables.py +11 -1
- nautobot/extras/templates/extras/computedfield_retrieve.html +1 -55
- nautobot/extras/templates/extras/inc/job_tiles.html +1 -1
- nautobot/extras/templates/extras/jobresult.html +1 -1
- nautobot/extras/templates/extras/metadatatype_retrieve.html +1 -66
- nautobot/extras/templates/extras/scheduledjob.html +25 -9
- nautobot/extras/tests/test_api.py +1 -1
- nautobot/extras/tests/test_views.py +15 -2
- nautobot/extras/utils.py +18 -16
- nautobot/extras/views.py +65 -26
- nautobot/ipam/tables.py +3 -4
- nautobot/project-static/docs/404.html +4 -4
- nautobot/project-static/docs/apps/index.html +4 -4
- nautobot/project-static/docs/apps/nautobot-apps.html +4 -4
- nautobot/project-static/docs/assets/javascripts/{bundle.c8b220af.min.js → bundle.13a4f30d.min.js} +4 -4
- nautobot/project-static/docs/assets/javascripts/{bundle.c8b220af.min.js.map → bundle.13a4f30d.min.js.map} +2 -2
- nautobot/project-static/docs/assets/javascripts/workers/{search.f8cc74c7.min.js → search.d50fe291.min.js} +2 -2
- nautobot/project-static/docs/assets/javascripts/workers/{search.f8cc74c7.min.js.map → search.d50fe291.min.js.map} +1 -1
- nautobot/project-static/docs/assets/stylesheets/{main.2afb09e1.min.css → main.342714a4.min.css} +1 -1
- nautobot/project-static/docs/assets/stylesheets/{main.2afb09e1.min.css.map → main.342714a4.min.css.map} +1 -1
- nautobot/project-static/docs/code-reference/nautobot/apps/__init__.html +4 -4
- nautobot/project-static/docs/code-reference/nautobot/apps/admin.html +4 -4
- nautobot/project-static/docs/code-reference/nautobot/apps/api.html +4 -4
- nautobot/project-static/docs/code-reference/nautobot/apps/change_logging.html +4 -4
- nautobot/project-static/docs/code-reference/nautobot/apps/choices.html +4 -4
- nautobot/project-static/docs/code-reference/nautobot/apps/config.html +4 -4
- nautobot/project-static/docs/code-reference/nautobot/apps/constants.html +4 -4
- nautobot/project-static/docs/code-reference/nautobot/apps/datasources.html +4 -4
- nautobot/project-static/docs/code-reference/nautobot/apps/events.html +4 -4
- nautobot/project-static/docs/code-reference/nautobot/apps/exceptions.html +4 -4
- nautobot/project-static/docs/code-reference/nautobot/apps/factory.html +4 -4
- nautobot/project-static/docs/code-reference/nautobot/apps/filters.html +4 -4
- nautobot/project-static/docs/code-reference/nautobot/apps/forms.html +4 -4
- nautobot/project-static/docs/code-reference/nautobot/apps/graphql.html +4 -4
- nautobot/project-static/docs/code-reference/nautobot/apps/jobs.html +4 -4
- nautobot/project-static/docs/code-reference/nautobot/apps/models.html +4 -4
- nautobot/project-static/docs/code-reference/nautobot/apps/querysets.html +4 -4
- nautobot/project-static/docs/code-reference/nautobot/apps/secrets.html +4 -4
- nautobot/project-static/docs/code-reference/nautobot/apps/tables.html +4 -4
- nautobot/project-static/docs/code-reference/nautobot/apps/testing.html +4 -4
- nautobot/project-static/docs/code-reference/nautobot/apps/ui.html +6 -8
- nautobot/project-static/docs/code-reference/nautobot/apps/urls.html +4 -4
- nautobot/project-static/docs/code-reference/nautobot/apps/utils.html +36 -6
- nautobot/project-static/docs/code-reference/nautobot/apps/views.html +4 -4
- nautobot/project-static/docs/development/apps/api/configuration-view.html +4 -4
- nautobot/project-static/docs/development/apps/api/database-backend-config.html +4 -4
- nautobot/project-static/docs/development/apps/api/models/django-admin.html +4 -4
- nautobot/project-static/docs/development/apps/api/models/global-search.html +4 -4
- nautobot/project-static/docs/development/apps/api/models/graphql.html +4 -4
- nautobot/project-static/docs/development/apps/api/models/index.html +4 -4
- nautobot/project-static/docs/development/apps/api/nautobot-app-config.html +4 -4
- nautobot/project-static/docs/development/apps/api/platform-features/custom-validators.html +4 -4
- nautobot/project-static/docs/development/apps/api/platform-features/filter-extensions.html +4 -4
- nautobot/project-static/docs/development/apps/api/platform-features/git-repository-content.html +4 -4
- nautobot/project-static/docs/development/apps/api/platform-features/index.html +4 -4
- nautobot/project-static/docs/development/apps/api/platform-features/jinja2-filters.html +4 -4
- nautobot/project-static/docs/development/apps/api/platform-features/jobs.html +4 -4
- nautobot/project-static/docs/development/apps/api/platform-features/populating-extensibility-features.html +4 -4
- nautobot/project-static/docs/development/apps/api/platform-features/secrets-providers.html +4 -4
- nautobot/project-static/docs/development/apps/api/platform-features/table-extensions.html +4 -4
- nautobot/project-static/docs/development/apps/api/platform-features/uniquely-identify-objects.html +4 -4
- nautobot/project-static/docs/development/apps/api/prometheus.html +4 -4
- nautobot/project-static/docs/development/apps/api/setup.html +4 -4
- nautobot/project-static/docs/development/apps/api/testing.html +4 -4
- nautobot/project-static/docs/development/apps/api/ui-extensions/banners.html +4 -4
- nautobot/project-static/docs/development/apps/api/ui-extensions/home-page.html +4 -4
- nautobot/project-static/docs/development/apps/api/ui-extensions/index.html +4 -4
- nautobot/project-static/docs/development/apps/api/ui-extensions/navigation.html +4 -4
- nautobot/project-static/docs/development/apps/api/ui-extensions/object-views.html +4 -4
- nautobot/project-static/docs/development/apps/api/views/base-template.html +4 -4
- nautobot/project-static/docs/development/apps/api/views/core-view-overrides.html +4 -4
- nautobot/project-static/docs/development/apps/api/views/django-generic-views.html +4 -4
- nautobot/project-static/docs/development/apps/api/views/help-documentation.html +4 -4
- nautobot/project-static/docs/development/apps/api/views/index.html +4 -4
- nautobot/project-static/docs/development/apps/api/views/nautobot-generic-views.html +4 -4
- nautobot/project-static/docs/development/apps/api/views/nautobotuiviewset.html +4 -4
- nautobot/project-static/docs/development/apps/api/views/nautobotuiviewsetrouter.html +4 -4
- nautobot/project-static/docs/development/apps/api/views/notes.html +4 -4
- nautobot/project-static/docs/development/apps/api/views/rest-api.html +4 -4
- nautobot/project-static/docs/development/apps/api/views/urls.html +4 -4
- nautobot/project-static/docs/development/apps/index.html +4 -4
- nautobot/project-static/docs/development/apps/migration/code-updates.html +4 -4
- nautobot/project-static/docs/development/apps/migration/dependency-updates.html +4 -4
- nautobot/project-static/docs/development/apps/migration/from-v1.html +4 -4
- nautobot/project-static/docs/development/apps/migration/model-updates/dcim.html +4 -4
- nautobot/project-static/docs/development/apps/migration/model-updates/extras.html +4 -4
- nautobot/project-static/docs/development/apps/migration/model-updates/global.html +4 -4
- nautobot/project-static/docs/development/apps/migration/model-updates/ipam.html +4 -4
- nautobot/project-static/docs/development/apps/migration/ui-component-framework/best-practices.html +4 -4
- nautobot/project-static/docs/development/apps/migration/ui-component-framework/custom-content.html +4 -4
- nautobot/project-static/docs/development/apps/migration/ui-component-framework/index.html +4 -4
- nautobot/project-static/docs/development/apps/migration/ui-component-framework/migration-steps.html +4 -4
- nautobot/project-static/docs/development/apps/porting-from-netbox.html +4 -4
- nautobot/project-static/docs/development/core/application-registry.html +4 -4
- nautobot/project-static/docs/development/core/best-practices.html +4 -4
- nautobot/project-static/docs/development/core/bootstrap-ui.html +4 -4
- nautobot/project-static/docs/development/core/caching.html +4 -4
- nautobot/project-static/docs/development/core/controllers.html +4 -4
- nautobot/project-static/docs/development/core/docker-compose-advanced-use-cases.html +41 -55
- nautobot/project-static/docs/development/core/generic-views.html +4 -4
- nautobot/project-static/docs/development/core/getting-started.html +4 -4
- nautobot/project-static/docs/development/core/homepage.html +4 -4
- nautobot/project-static/docs/development/core/index.html +4 -4
- nautobot/project-static/docs/development/core/minikube-dev-environment-for-k8s-jobs.html +4 -4
- nautobot/project-static/docs/development/core/model-checklist.html +4 -4
- nautobot/project-static/docs/development/core/model-features.html +4 -4
- nautobot/project-static/docs/development/core/natural-keys.html +4 -4
- nautobot/project-static/docs/development/core/navigation-menu.html +4 -4
- nautobot/project-static/docs/development/core/release-checklist.html +4 -4
- nautobot/project-static/docs/development/core/role-internals.html +4 -4
- nautobot/project-static/docs/development/core/settings.html +4 -4
- nautobot/project-static/docs/development/core/style-guide.html +4 -4
- nautobot/project-static/docs/development/core/templates.html +4 -4
- nautobot/project-static/docs/development/core/testing.html +4 -4
- nautobot/project-static/docs/development/core/ui-component-framework.html +4 -4
- nautobot/project-static/docs/development/core/user-preferences.html +4 -4
- nautobot/project-static/docs/development/index.html +4 -4
- nautobot/project-static/docs/development/jobs/getting-started.html +4 -4
- nautobot/project-static/docs/development/jobs/index.html +4 -4
- nautobot/project-static/docs/development/jobs/installation.html +4 -4
- nautobot/project-static/docs/development/jobs/job-extensions.html +4 -4
- nautobot/project-static/docs/development/jobs/job-logging.html +4 -4
- nautobot/project-static/docs/development/jobs/job-patterns.html +4 -4
- nautobot/project-static/docs/development/jobs/job-structure.html +4 -4
- nautobot/project-static/docs/development/jobs/migration/from-v1.html +4 -4
- nautobot/project-static/docs/development/jobs/testing.html +4 -4
- nautobot/project-static/docs/index.html +4 -4
- nautobot/project-static/docs/overview/application_stack.html +4 -4
- nautobot/project-static/docs/overview/design_philosophy.html +4 -4
- nautobot/project-static/docs/release-notes/index.html +4 -4
- nautobot/project-static/docs/release-notes/version-1.0.html +4 -4
- nautobot/project-static/docs/release-notes/version-1.1.html +4 -4
- nautobot/project-static/docs/release-notes/version-1.2.html +4 -4
- nautobot/project-static/docs/release-notes/version-1.3.html +4 -4
- nautobot/project-static/docs/release-notes/version-1.4.html +4 -4
- nautobot/project-static/docs/release-notes/version-1.5.html +4 -4
- nautobot/project-static/docs/release-notes/version-1.6.html +4 -4
- nautobot/project-static/docs/release-notes/version-2.0.html +4 -4
- nautobot/project-static/docs/release-notes/version-2.1.html +4 -4
- nautobot/project-static/docs/release-notes/version-2.2.html +4 -4
- nautobot/project-static/docs/release-notes/version-2.3.html +4 -4
- nautobot/project-static/docs/release-notes/version-2.4.html +190 -4
- nautobot/project-static/docs/requirements.txt +1 -1
- nautobot/project-static/docs/search/search_index.json +1 -1
- nautobot/project-static/docs/sitemap.xml +298 -298
- nautobot/project-static/docs/sitemap.xml.gz +0 -0
- nautobot/project-static/docs/user-guide/administration/configuration/authentication/ldap.html +4 -4
- nautobot/project-static/docs/user-guide/administration/configuration/authentication/remote.html +4 -4
- nautobot/project-static/docs/user-guide/administration/configuration/authentication/sso.html +4 -4
- nautobot/project-static/docs/user-guide/administration/configuration/index.html +4 -4
- nautobot/project-static/docs/user-guide/administration/configuration/redis.html +4 -4
- nautobot/project-static/docs/user-guide/administration/configuration/settings.html +4 -4
- nautobot/project-static/docs/user-guide/administration/configuration/time-zones.html +4 -4
- nautobot/project-static/docs/user-guide/administration/guides/celery-queues.html +4 -4
- nautobot/project-static/docs/user-guide/administration/guides/docker.html +4 -4
- nautobot/project-static/docs/user-guide/administration/guides/health-checks.html +4 -4
- nautobot/project-static/docs/user-guide/administration/guides/permissions.html +4 -4
- nautobot/project-static/docs/user-guide/administration/guides/prometheus-metrics.html +4 -4
- nautobot/project-static/docs/user-guide/administration/guides/replicating-nautobot.html +4 -4
- nautobot/project-static/docs/user-guide/administration/guides/request-profiling.html +4 -4
- nautobot/project-static/docs/user-guide/administration/guides/s3-django-storage.html +4 -4
- nautobot/project-static/docs/user-guide/administration/guides/selinux-troubleshooting.html +4 -4
- nautobot/project-static/docs/user-guide/administration/installation/app-install.html +4 -4
- nautobot/project-static/docs/user-guide/administration/installation/external-authentication.html +4 -4
- nautobot/project-static/docs/user-guide/administration/installation/http-server.html +4 -4
- nautobot/project-static/docs/user-guide/administration/installation/index.html +4 -4
- nautobot/project-static/docs/user-guide/administration/installation/install_system.html +4 -4
- nautobot/project-static/docs/user-guide/administration/installation/nautobot.html +4 -4
- nautobot/project-static/docs/user-guide/administration/installation/services.html +4 -4
- nautobot/project-static/docs/user-guide/administration/migration/migrating-from-netbox.html +4 -4
- nautobot/project-static/docs/user-guide/administration/migration/migrating-from-postgresql.html +4 -4
- nautobot/project-static/docs/user-guide/administration/security/index.html +4 -4
- nautobot/project-static/docs/user-guide/administration/security/notices.html +4 -4
- nautobot/project-static/docs/user-guide/administration/tools/nautobot-server.html +4 -4
- nautobot/project-static/docs/user-guide/administration/tools/nautobot-shell.html +4 -4
- nautobot/project-static/docs/user-guide/administration/upgrading/database-backup.html +4 -4
- nautobot/project-static/docs/user-guide/administration/upgrading/from-v1/ipam/after-you-upgrade.html +4 -4
- nautobot/project-static/docs/user-guide/administration/upgrading/from-v1/ipam/before-you-upgrade.html +4 -4
- nautobot/project-static/docs/user-guide/administration/upgrading/from-v1/ipam/for-developers.html +4 -4
- nautobot/project-static/docs/user-guide/administration/upgrading/from-v1/ipam/index.html +4 -4
- nautobot/project-static/docs/user-guide/administration/upgrading/from-v1/ipam/whats-changed.html +4 -4
- nautobot/project-static/docs/user-guide/administration/upgrading/from-v1/region-and-site-data-migration-guide.html +4 -4
- nautobot/project-static/docs/user-guide/administration/upgrading/from-v1/upgrading-from-nautobot-v1.html +4 -4
- nautobot/project-static/docs/user-guide/administration/upgrading/upgrading.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/circuits/circuit.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/circuits/circuittermination.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/circuits/circuittype.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/circuits/provider.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/circuits/providernetwork.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/cloud/cloud.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/cloud/cloudaccount.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/cloud/cloudnetwork.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/cloud/cloudnetworkprefixassignment.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/cloud/cloudresourcetype.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/cloud/cloudservice.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/cloud/cloudservicenetworkassignment.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/cable.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/consoleport.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/consoleporttemplate.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/consoleserverport.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/consoleserverporttemplate.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/controller.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/controllermanageddevicegroup.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/device.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/devicebay.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/devicebaytemplate.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/devicefamily.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/deviceredundancygroup.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/devicetype.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/frontport.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/frontporttemplate.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/interface.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/interfaceredundancygroup.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/interfacetemplate.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/inventoryitem.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/location.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/locationtype.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/manufacturer.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/module.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/modulebay.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/modulebaytemplate.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/moduletype.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/platform.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/powerfeed.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/poweroutlet.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/poweroutlettemplate.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/powerpanel.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/powerport.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/powerporttemplate.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/rack.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/rackgroup.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/rackreservation.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/rearport.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/rearporttemplate.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/softwareimagefile.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/softwareversion.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/virtualchassis.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/dcim/virtualdevicecontext.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/extras/configcontext.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/extras/configcontextschema.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/extras/contact.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/extras/team.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/ipam/ipaddress.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/ipam/namespace.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/ipam/prefix.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/ipam/rir.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/ipam/routetarget.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/ipam/service.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/ipam/vlan.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/ipam/vlangroup.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/ipam/vrf.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/overview/introduction.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/tenancy/tenant.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/tenancy/tenantgroup.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/virtualization/cluster.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/virtualization/clustergroup.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/virtualization/clustertype.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/virtualization/virtualmachine.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/virtualization/vminterface.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/wireless/index.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/wireless/radioprofile.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/wireless/supporteddatarate.html +4 -4
- nautobot/project-static/docs/user-guide/core-data-model/wireless/wirelessnetwork.html +4 -4
- nautobot/project-static/docs/user-guide/feature-guides/contacts-and-teams.html +4 -4
- nautobot/project-static/docs/user-guide/feature-guides/custom-fields.html +4 -4
- nautobot/project-static/docs/user-guide/feature-guides/getting-started/creating-devices.html +4 -4
- nautobot/project-static/docs/user-guide/feature-guides/getting-started/creating-location-types-and-locations.html +4 -4
- nautobot/project-static/docs/user-guide/feature-guides/getting-started/index.html +4 -4
- nautobot/project-static/docs/user-guide/feature-guides/getting-started/interfaces.html +4 -4
- nautobot/project-static/docs/user-guide/feature-guides/getting-started/ipam.html +4 -4
- nautobot/project-static/docs/user-guide/feature-guides/getting-started/platforms.html +4 -4
- nautobot/project-static/docs/user-guide/feature-guides/getting-started/search-bar.html +4 -4
- nautobot/project-static/docs/user-guide/feature-guides/getting-started/tenants.html +4 -4
- nautobot/project-static/docs/user-guide/feature-guides/getting-started/vlans-and-vlan-groups.html +4 -4
- nautobot/project-static/docs/user-guide/feature-guides/git-data-source.html +4 -4
- nautobot/project-static/docs/user-guide/feature-guides/graphql.html +4 -4
- nautobot/project-static/docs/user-guide/feature-guides/ip-address-merge-tool.html +4 -4
- nautobot/project-static/docs/user-guide/feature-guides/relationships.html +4 -4
- nautobot/project-static/docs/user-guide/feature-guides/software-image-files-and-versions.html +4 -4
- nautobot/project-static/docs/user-guide/feature-guides/wireless-networks-and-controllers.html +4 -4
- nautobot/project-static/docs/user-guide/index.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/change-logging.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/computedfield.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/customfield.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/customlink.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/dynamicgroup.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/events.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/exporttemplate.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/externalintegration.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/gitrepository.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/graphql.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/graphqlquery.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/imageattachment.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/jobs/index.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/jobs/job-scheduling-and-approvals.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/jobs/jobbutton.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/jobs/jobhook.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/jobs/jobqueue.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/jobs/kubernetes-job-support.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/jobs/managing-jobs.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/jobs/models.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/napalm.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/note.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/objectmetadata.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/relationship.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/rendering-jinja-templates.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/rest-api/authentication.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/rest-api/filtering.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/rest-api/overview.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/rest-api/ui-related-endpoints.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/role.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/savedview.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/secret.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/staticgroupassociation.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/status.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/tag.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/template-filters.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/users/objectpermission.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/users/token.html +4 -4
- nautobot/project-static/docs/user-guide/platform-functionality/webhook.html +4 -4
- nautobot/project-static/js/forms.js +0 -14
- nautobot/wireless/tables.py +1 -0
- nautobot/wireless/templates/wireless/wirelessnetwork_retrieve.html +1 -55
- nautobot/wireless/views.py +33 -28
- {nautobot-2.4.8.dist-info → nautobot-2.4.9.dist-info}/METADATA +3 -3
- {nautobot-2.4.8.dist-info → nautobot-2.4.9.dist-info}/RECORD +364 -361
- {nautobot-2.4.8.dist-info → nautobot-2.4.9.dist-info}/LICENSE.txt +0 -0
- {nautobot-2.4.8.dist-info → nautobot-2.4.9.dist-info}/NOTICE +0 -0
- {nautobot-2.4.8.dist-info → nautobot-2.4.9.dist-info}/WHEEL +0 -0
- {nautobot-2.4.8.dist-info → nautobot-2.4.9.dist-info}/entry_points.txt +0 -0
nautobot/dcim/views.py
CHANGED
|
@@ -686,6 +686,45 @@ class RackReservationUIViewSet(NautobotUIViewSet):
|
|
|
686
686
|
table_class = tables.RackReservationTable
|
|
687
687
|
queryset = RackReservation.objects.all()
|
|
688
688
|
|
|
689
|
+
object_detail_content = object_detail.ObjectDetailContent(
|
|
690
|
+
panels=(
|
|
691
|
+
object_detail.KeyValueTablePanel(
|
|
692
|
+
section=SectionChoices.LEFT_HALF,
|
|
693
|
+
weight=100,
|
|
694
|
+
label="Rack",
|
|
695
|
+
context_data_key="rack_data",
|
|
696
|
+
),
|
|
697
|
+
object_detail.ObjectFieldsPanel(
|
|
698
|
+
section=SectionChoices.LEFT_HALF,
|
|
699
|
+
weight=100,
|
|
700
|
+
label="Reservation Details",
|
|
701
|
+
fields=["unit_list", "tenant", "user", "description"],
|
|
702
|
+
),
|
|
703
|
+
object_detail.Panel(
|
|
704
|
+
section=SectionChoices.RIGHT_HALF,
|
|
705
|
+
weight=100,
|
|
706
|
+
template_path="dcim/rack_elevation.html",
|
|
707
|
+
),
|
|
708
|
+
),
|
|
709
|
+
)
|
|
710
|
+
|
|
711
|
+
def get_extra_context(self, request, instance):
|
|
712
|
+
context = super().get_extra_context(request, instance)
|
|
713
|
+
if self.action == "retrieve":
|
|
714
|
+
context["rack_data"] = self.get_rack_context(instance)
|
|
715
|
+
return context
|
|
716
|
+
|
|
717
|
+
def get_rack_context(self, instance):
|
|
718
|
+
rack = getattr(instance, "rack", None)
|
|
719
|
+
if not rack:
|
|
720
|
+
return {}
|
|
721
|
+
|
|
722
|
+
return {
|
|
723
|
+
"location": rack.location,
|
|
724
|
+
"rack_group": rack.rack_group,
|
|
725
|
+
"rack": rack,
|
|
726
|
+
}
|
|
727
|
+
|
|
689
728
|
def get_object(self):
|
|
690
729
|
obj = super().get_object()
|
|
691
730
|
|
|
@@ -743,20 +782,18 @@ class ManufacturerUIViewSet(NautobotUIViewSet):
|
|
|
743
782
|
#
|
|
744
783
|
# Device types
|
|
745
784
|
#
|
|
746
|
-
|
|
747
|
-
|
|
748
|
-
|
|
749
|
-
|
|
750
|
-
|
|
751
|
-
|
|
752
|
-
|
|
753
|
-
template_name = "dcim/devicetype_list.html"
|
|
754
|
-
|
|
755
|
-
|
|
756
|
-
class DeviceTypeView(generic.ObjectView):
|
|
785
|
+
class DeviceTypeUIViewSet(NautobotUIViewSet):
|
|
786
|
+
bulk_update_form_class = forms.DeviceTypeBulkEditForm
|
|
787
|
+
filterset_class = filters.DeviceTypeFilterSet
|
|
788
|
+
filterset_form_class = forms.DeviceTypeFilterForm
|
|
789
|
+
form_class = forms.DeviceTypeForm
|
|
790
|
+
serializer_class = serializers.DeviceTypeSerializer
|
|
791
|
+
table_class = tables.DeviceTypeTable
|
|
757
792
|
queryset = DeviceType.objects.select_related("manufacturer").prefetch_related("software_image_files")
|
|
758
793
|
|
|
759
794
|
def get_extra_context(self, request, instance):
|
|
795
|
+
if self.action != "retrieve":
|
|
796
|
+
return {}
|
|
760
797
|
instance_count = Device.objects.restrict(request.user).filter(device_type=instance).count()
|
|
761
798
|
|
|
762
799
|
# Component tables
|
|
@@ -831,16 +868,6 @@ class DeviceTypeView(generic.ObjectView):
|
|
|
831
868
|
}
|
|
832
869
|
|
|
833
870
|
|
|
834
|
-
class DeviceTypeEditView(generic.ObjectEditView):
|
|
835
|
-
queryset = DeviceType.objects.all()
|
|
836
|
-
model_form = forms.DeviceTypeForm
|
|
837
|
-
template_name = "dcim/devicetype_edit.html"
|
|
838
|
-
|
|
839
|
-
|
|
840
|
-
class DeviceTypeDeleteView(generic.ObjectDeleteView):
|
|
841
|
-
queryset = DeviceType.objects.all()
|
|
842
|
-
|
|
843
|
-
|
|
844
871
|
class DeviceTypeImportView(generic.ObjectImportView):
|
|
845
872
|
additional_permissions = [
|
|
846
873
|
"dcim.add_devicetype",
|
|
@@ -871,19 +898,6 @@ class DeviceTypeImportView(generic.ObjectImportView):
|
|
|
871
898
|
)
|
|
872
899
|
|
|
873
900
|
|
|
874
|
-
class DeviceTypeBulkEditView(generic.BulkEditView):
|
|
875
|
-
queryset = DeviceType.objects.all()
|
|
876
|
-
filterset = filters.DeviceTypeFilterSet
|
|
877
|
-
table = tables.DeviceTypeTable
|
|
878
|
-
form = forms.DeviceTypeBulkEditForm
|
|
879
|
-
|
|
880
|
-
|
|
881
|
-
class DeviceTypeBulkDeleteView(generic.BulkDeleteView):
|
|
882
|
-
queryset = DeviceType.objects.all()
|
|
883
|
-
filterset = filters.DeviceTypeFilterSet
|
|
884
|
-
table = tables.DeviceTypeTable
|
|
885
|
-
|
|
886
|
-
|
|
887
901
|
#
|
|
888
902
|
# Module types
|
|
889
903
|
#
|
|
@@ -3381,13 +3395,42 @@ class ModuleBayUIViewSet(ModuleBayCommonViewSetMixin, NautobotUIViewSet):
|
|
|
3381
3395
|
table_class = tables.ModuleBayTable
|
|
3382
3396
|
create_template_name = "dcim/device_component_add.html"
|
|
3383
3397
|
|
|
3398
|
+
object_detail_content = object_detail.ObjectDetailContent(
|
|
3399
|
+
panels=(
|
|
3400
|
+
object_detail.ObjectFieldsPanel(
|
|
3401
|
+
weight=100,
|
|
3402
|
+
section=SectionChoices.LEFT_HALF,
|
|
3403
|
+
fields="__all__",
|
|
3404
|
+
hide_if_unset=("parent_device", "parent_module"),
|
|
3405
|
+
),
|
|
3406
|
+
object_detail.ObjectFieldsPanel(
|
|
3407
|
+
weight=100,
|
|
3408
|
+
section=SectionChoices.RIGHT_HALF,
|
|
3409
|
+
context_object_key="installed_module_data",
|
|
3410
|
+
label="Installed Module",
|
|
3411
|
+
),
|
|
3412
|
+
)
|
|
3413
|
+
)
|
|
3414
|
+
|
|
3384
3415
|
def get_extra_context(self, request, instance):
|
|
3416
|
+
context = super().get_extra_context(request, instance)
|
|
3417
|
+
|
|
3385
3418
|
if instance:
|
|
3386
|
-
|
|
3387
|
-
|
|
3388
|
-
|
|
3389
|
-
|
|
3390
|
-
|
|
3419
|
+
# Set breadcrumbs always
|
|
3420
|
+
context.update(
|
|
3421
|
+
{
|
|
3422
|
+
"device_breadcrumb_url": "dcim:device_modulebays",
|
|
3423
|
+
"module_breadcrumb_url": "dcim:module_modulebays",
|
|
3424
|
+
}
|
|
3425
|
+
)
|
|
3426
|
+
|
|
3427
|
+
# Add installed module context
|
|
3428
|
+
context["installed_module_data"] = self._get_installed_module_context(instance)
|
|
3429
|
+
|
|
3430
|
+
return context
|
|
3431
|
+
|
|
3432
|
+
def _get_installed_module_context(self, instance):
|
|
3433
|
+
return getattr(instance, "installed_module", None)
|
|
3391
3434
|
|
|
3392
3435
|
def get_selected_objects_parents_name(self, selected_objects):
|
|
3393
3436
|
selected_object = selected_objects.first()
|
|
@@ -4135,18 +4178,32 @@ class DeviceRedundancyGroupUIViewSet(NautobotUIViewSet):
|
|
|
4135
4178
|
serializer_class = serializers.DeviceRedundancyGroupSerializer
|
|
4136
4179
|
table_class = tables.DeviceRedundancyGroupTable
|
|
4137
4180
|
|
|
4138
|
-
|
|
4139
|
-
|
|
4140
|
-
|
|
4141
|
-
|
|
4142
|
-
|
|
4143
|
-
|
|
4144
|
-
|
|
4145
|
-
|
|
4146
|
-
|
|
4147
|
-
|
|
4148
|
-
|
|
4149
|
-
|
|
4181
|
+
object_detail_content = object_detail.ObjectDetailContent(
|
|
4182
|
+
panels=(
|
|
4183
|
+
object_detail.ObjectFieldsPanel(
|
|
4184
|
+
section=SectionChoices.LEFT_HALF,
|
|
4185
|
+
weight=100,
|
|
4186
|
+
fields="__all__",
|
|
4187
|
+
),
|
|
4188
|
+
object_detail.ObjectsTablePanel(
|
|
4189
|
+
section=SectionChoices.FULL_WIDTH,
|
|
4190
|
+
weight=100,
|
|
4191
|
+
table_class=tables.ControllerTable,
|
|
4192
|
+
table_attribute="controllers_sorted",
|
|
4193
|
+
related_field_name="controller_device_redundancy_group",
|
|
4194
|
+
),
|
|
4195
|
+
object_detail.ObjectsTablePanel(
|
|
4196
|
+
section=SectionChoices.FULL_WIDTH,
|
|
4197
|
+
weight=200,
|
|
4198
|
+
table_class=tables.DeviceTable,
|
|
4199
|
+
table_attribute="devices_sorted",
|
|
4200
|
+
related_field_name="device_redundancy_group",
|
|
4201
|
+
include_columns=[
|
|
4202
|
+
"device_redundancy_group_priority",
|
|
4203
|
+
],
|
|
4204
|
+
),
|
|
4205
|
+
)
|
|
4206
|
+
)
|
|
4150
4207
|
|
|
4151
4208
|
|
|
4152
4209
|
class InterfaceRedundancyGroupUIViewSet(NautobotUIViewSet):
|
|
@@ -4211,36 +4268,31 @@ class DeviceFamilyUIViewSet(NautobotUIViewSet):
|
|
|
4211
4268
|
serializer_class = serializers.DeviceFamilySerializer
|
|
4212
4269
|
table_class = tables.DeviceFamilyTable
|
|
4213
4270
|
lookup_field = "pk"
|
|
4214
|
-
|
|
4215
|
-
|
|
4216
|
-
|
|
4217
|
-
|
|
4218
|
-
|
|
4219
|
-
|
|
4220
|
-
|
|
4221
|
-
|
|
4222
|
-
|
|
4223
|
-
.
|
|
4224
|
-
|
|
4225
|
-
|
|
4226
|
-
|
|
4227
|
-
|
|
4228
|
-
|
|
4229
|
-
|
|
4230
|
-
|
|
4231
|
-
|
|
4232
|
-
|
|
4233
|
-
|
|
4234
|
-
|
|
4235
|
-
|
|
4236
|
-
|
|
4237
|
-
|
|
4238
|
-
|
|
4239
|
-
device_type_count += 1
|
|
4240
|
-
context["total_devices"] = total_devices
|
|
4241
|
-
context["device_type_count"] = device_type_count
|
|
4242
|
-
|
|
4243
|
-
return context
|
|
4271
|
+
object_detail_content = object_detail.ObjectDetailContent(
|
|
4272
|
+
panels=(
|
|
4273
|
+
object_detail.ObjectFieldsPanel(
|
|
4274
|
+
weight=100,
|
|
4275
|
+
section=SectionChoices.LEFT_HALF,
|
|
4276
|
+
fields="__all__",
|
|
4277
|
+
),
|
|
4278
|
+
object_detail.ObjectsTablePanel(
|
|
4279
|
+
weight=100,
|
|
4280
|
+
section=SectionChoices.FULL_WIDTH,
|
|
4281
|
+
table_class=tables.DeviceTypeTable,
|
|
4282
|
+
table_filter="device_family",
|
|
4283
|
+
select_related_fields=["manufacturer"],
|
|
4284
|
+
exclude_columns=["device_family"],
|
|
4285
|
+
),
|
|
4286
|
+
object_detail.ObjectsTablePanel(
|
|
4287
|
+
weight=200,
|
|
4288
|
+
section=SectionChoices.FULL_WIDTH,
|
|
4289
|
+
table_class=tables.DeviceTable,
|
|
4290
|
+
table_filter="device_type__device_family",
|
|
4291
|
+
related_field_name="device_family",
|
|
4292
|
+
exclude_columns=["device_family"],
|
|
4293
|
+
),
|
|
4294
|
+
)
|
|
4295
|
+
)
|
|
4244
4296
|
|
|
4245
4297
|
|
|
4246
4298
|
#
|
nautobot/extras/api/views.py
CHANGED
|
@@ -703,10 +703,8 @@ class JobViewSetBase(
|
|
|
703
703
|
# of errors under messages
|
|
704
704
|
return Response({"errors": e.message_dict if hasattr(e, "error_dict") else e.messages}, status=400)
|
|
705
705
|
|
|
706
|
-
|
|
707
|
-
if
|
|
708
|
-
queue = job_model.default_job_queue
|
|
709
|
-
if queue.queue_type == JobQueueTypeChoices.TYPE_CELERY and not get_worker_count(queue=task_queue):
|
|
706
|
+
job_queue = get_job_queue(task_queue) or job_model.default_job_queue
|
|
707
|
+
if job_queue.queue_type == JobQueueTypeChoices.TYPE_CELERY and not get_worker_count(queue=task_queue):
|
|
710
708
|
raise CeleryWorkerNotRunningException(queue=task_queue)
|
|
711
709
|
|
|
712
710
|
# Default to a null JobResult.
|
|
@@ -737,7 +735,7 @@ class JobViewSetBase(
|
|
|
737
735
|
interval=schedule_data.get("interval"),
|
|
738
736
|
crontab=schedule_data.get("crontab", ""),
|
|
739
737
|
approval_required=approval_required,
|
|
740
|
-
|
|
738
|
+
job_queue=job_queue,
|
|
741
739
|
**job_class.serialize_data(cleaned_data),
|
|
742
740
|
)
|
|
743
741
|
else:
|
|
@@ -748,7 +746,7 @@ class JobViewSetBase(
|
|
|
748
746
|
job_result = JobResult.enqueue_job(
|
|
749
747
|
job_model,
|
|
750
748
|
request.user,
|
|
751
|
-
|
|
749
|
+
job_queue=job_queue,
|
|
752
750
|
**job_class.serialize_data(cleaned_data),
|
|
753
751
|
)
|
|
754
752
|
|
|
@@ -52,7 +52,7 @@ def migrate_job_data(apps, schema_editor):
|
|
|
52
52
|
|
|
53
53
|
# Shouldn't be needed but I've seen cases where it happens - not sure exactly why
|
|
54
54
|
for job_jobresult in JobResult.objects.filter(obj_type__model="jobmodel"):
|
|
55
|
-
print("Fixing up content type on {job_jobresult}")
|
|
55
|
+
print(f"Fixing up content type on {job_jobresult}")
|
|
56
56
|
job_jobresult.obj_type = job_ct
|
|
57
57
|
job_jobresult.save()
|
|
58
58
|
|
nautobot/extras/models/jobs.py
CHANGED
|
@@ -1,10 +1,11 @@
|
|
|
1
1
|
# Data models relating to Jobs
|
|
2
2
|
|
|
3
3
|
import contextlib
|
|
4
|
-
from datetime import timedelta
|
|
4
|
+
from datetime import datetime, timedelta
|
|
5
5
|
import json
|
|
6
6
|
import logging
|
|
7
7
|
import signal
|
|
8
|
+
from typing import Optional, TYPE_CHECKING, Union
|
|
8
9
|
|
|
9
10
|
from billiard.exceptions import SoftTimeLimitExceeded
|
|
10
11
|
from celery.exceptions import NotRegistered
|
|
@@ -58,6 +59,11 @@ from nautobot.extras.utils import (
|
|
|
58
59
|
|
|
59
60
|
from .customfields import CustomFieldModel
|
|
60
61
|
|
|
62
|
+
if TYPE_CHECKING:
|
|
63
|
+
from django.contrib.auth import get_user_model
|
|
64
|
+
|
|
65
|
+
User = get_user_model()
|
|
66
|
+
|
|
61
67
|
logger = logging.getLogger(__name__)
|
|
62
68
|
|
|
63
69
|
|
|
@@ -329,12 +335,12 @@ class Job(PrimaryModel):
|
|
|
329
335
|
raise NotRegistered from err
|
|
330
336
|
|
|
331
337
|
@property
|
|
332
|
-
def task_queues(self):
|
|
338
|
+
def task_queues(self) -> list[str]:
|
|
333
339
|
"""Deprecated backward-compatibility property for the list of queue names for this Job."""
|
|
334
340
|
return self.job_queues.values_list("name", flat=True)
|
|
335
341
|
|
|
336
342
|
@task_queues.setter
|
|
337
|
-
def task_queues(self, value):
|
|
343
|
+
def task_queues(self, value: Union[str, list[str]]):
|
|
338
344
|
job_queues = []
|
|
339
345
|
# value is going to be a comma separated list of queue names
|
|
340
346
|
if isinstance(value, str):
|
|
@@ -748,49 +754,34 @@ class JobResult(BaseModel, CustomFieldModel):
|
|
|
748
754
|
)
|
|
749
755
|
|
|
750
756
|
@classmethod
|
|
751
|
-
def execute_job(cls,
|
|
757
|
+
def execute_job(cls, *args, **kwargs):
|
|
752
758
|
"""
|
|
753
759
|
Create a JobResult instance and run a job in the current process, blocking until the job finishes.
|
|
754
760
|
|
|
755
761
|
Running tasks synchronously in celery is *NOT* supported and if possible `enqueue_job` with synchronous=False
|
|
756
762
|
should be used instead.
|
|
757
763
|
|
|
758
|
-
Args:
|
|
759
|
-
job_model (Job): The Job to be enqueued for execution
|
|
760
|
-
user (User): User object to link to the JobResult instance
|
|
761
|
-
celery_kwargs (dict, optional): Dictionary of kwargs to pass as **kwargs to Celery when job is run
|
|
762
|
-
profile (bool, optional): Whether to run cProfile on the job execution
|
|
763
|
-
job_result (JobResult, optional): Existing JobResult with status PENDING, used in kubernetes job execution
|
|
764
|
-
*job_args: positional args passed to the job task
|
|
765
|
-
**job_kwargs: keyword args passed to the job task
|
|
764
|
+
Args: see `enqueue_job()`
|
|
766
765
|
|
|
767
766
|
Returns:
|
|
768
767
|
JobResult instance
|
|
769
768
|
"""
|
|
770
|
-
return cls.enqueue_job(
|
|
771
|
-
job_model,
|
|
772
|
-
user,
|
|
773
|
-
*job_args,
|
|
774
|
-
celery_kwargs=celery_kwargs,
|
|
775
|
-
profile=profile,
|
|
776
|
-
job_result=job_result,
|
|
777
|
-
synchronous=True,
|
|
778
|
-
**job_kwargs,
|
|
779
|
-
)
|
|
769
|
+
return cls.enqueue_job(*args, **kwargs, synchronous=True)
|
|
780
770
|
|
|
781
771
|
@classmethod
|
|
782
772
|
def enqueue_job(
|
|
783
773
|
cls,
|
|
784
|
-
job_model,
|
|
785
|
-
user,
|
|
774
|
+
job_model: Job,
|
|
775
|
+
user: "User",
|
|
786
776
|
*job_args,
|
|
787
|
-
celery_kwargs=None,
|
|
788
|
-
profile=False,
|
|
789
|
-
schedule=None,
|
|
790
|
-
|
|
791
|
-
|
|
792
|
-
|
|
793
|
-
|
|
777
|
+
celery_kwargs: Optional[dict] = None,
|
|
778
|
+
profile: bool = False,
|
|
779
|
+
schedule: Optional["ScheduledJob"] = None,
|
|
780
|
+
job_queue: Optional["JobQueue"] = None,
|
|
781
|
+
task_queue: Optional[str] = None, # deprecated!
|
|
782
|
+
job_result: Optional["JobResult"] = None,
|
|
783
|
+
synchronous: bool = False,
|
|
784
|
+
ignore_singleton_lock: bool = False,
|
|
794
785
|
**job_kwargs,
|
|
795
786
|
):
|
|
796
787
|
"""Create/Modify a JobResult instance and enqueue a job to be executed asynchronously by a Celery worker.
|
|
@@ -798,13 +789,16 @@ class JobResult(BaseModel, CustomFieldModel):
|
|
|
798
789
|
Args:
|
|
799
790
|
job_model (Job): The Job to be enqueued for execution.
|
|
800
791
|
user (User): User object to link to the JobResult instance.
|
|
801
|
-
celery_kwargs (dict
|
|
802
|
-
profile (bool
|
|
803
|
-
schedule (ScheduledJob
|
|
804
|
-
|
|
805
|
-
|
|
806
|
-
|
|
807
|
-
|
|
792
|
+
celery_kwargs (dict): Dictionary of kwargs to pass as **kwargs to `apply_async()`/`apply()` when job is run.
|
|
793
|
+
profile (bool): If True, dump cProfile stats on the job execution.
|
|
794
|
+
schedule (ScheduledJob): ScheduledJob instance to link to the JobResult.
|
|
795
|
+
Cannot be used with synchronous=True.
|
|
796
|
+
job_queue (JobQueue): Job queue to send the job to. If not set, use the default queue for the given Job.
|
|
797
|
+
task_queue (str): The celery queue name to send the job to. **Deprecated, prefer `job_queue` instead.**
|
|
798
|
+
job_result (JobResult): Existing JobResult with status PENDING, to be modified and to be used
|
|
799
|
+
in kubernetes job execution.
|
|
800
|
+
synchronous (bool): If True, run the job in the current process, blocking until the job completes.
|
|
801
|
+
ignore_singleton_lock (bool): If True, invalidate the singleton lock before running the job.
|
|
808
802
|
This allows singleton jobs to run twice, or makes it possible to remove the lock when the first instance
|
|
809
803
|
of the job failed to remove it for any reason.
|
|
810
804
|
*job_args: positional args passed to the job task (UNUSED)
|
|
@@ -818,6 +812,20 @@ class JobResult(BaseModel, CustomFieldModel):
|
|
|
818
812
|
if schedule is not None and synchronous:
|
|
819
813
|
raise ValueError("Scheduled jobs cannot be run synchronously")
|
|
820
814
|
|
|
815
|
+
if job_queue is not None and task_queue is not None and job_queue.name != task_queue:
|
|
816
|
+
raise ValueError("task_queue and job_queue are mutually exclusive")
|
|
817
|
+
if job_queue is not None and task_queue is None:
|
|
818
|
+
task_queue = job_queue.name
|
|
819
|
+
elif task_queue is not None and job_queue is None:
|
|
820
|
+
job_queue = JobQueue.objects.get(name=task_queue)
|
|
821
|
+
else: # both none
|
|
822
|
+
if celery_kwargs is not None and "queue" in celery_kwargs:
|
|
823
|
+
task_queue = celery_kwargs["queue"]
|
|
824
|
+
job_queue = JobQueue.objects.get(name=task_queue)
|
|
825
|
+
else:
|
|
826
|
+
job_queue = job_model.default_job_queue
|
|
827
|
+
task_queue = job_queue.name
|
|
828
|
+
|
|
821
829
|
if job_result is None:
|
|
822
830
|
job_result = cls.objects.create(
|
|
823
831
|
name=job_model.name,
|
|
@@ -835,10 +843,6 @@ class JobResult(BaseModel, CustomFieldModel):
|
|
|
835
843
|
f"There is a mismatch between the job specified {job_model} and the job associated with the job result {job_result.job_model}"
|
|
836
844
|
)
|
|
837
845
|
|
|
838
|
-
if task_queue is None:
|
|
839
|
-
task_queue = job_model.default_job_queue.name
|
|
840
|
-
|
|
841
|
-
job_queue = JobQueue.objects.get(name=task_queue)
|
|
842
846
|
# Kubernetes Job Queue logic
|
|
843
847
|
# As we execute Kubernetes jobs, we want to execute `run_kubernetes_job_and_return_job_result`
|
|
844
848
|
# the first time the kubernetes job is enqueued to spin up the kubernetes pod.
|
|
@@ -863,6 +867,7 @@ class JobResult(BaseModel, CustomFieldModel):
|
|
|
863
867
|
job_celery_kwargs["time_limit"] = job_model.time_limit
|
|
864
868
|
|
|
865
869
|
if celery_kwargs is not None:
|
|
870
|
+
# TODO: this lets celery_kwargs override keys like `queue` and `nautobot_job_user_id`; is that desirable?
|
|
866
871
|
job_celery_kwargs.update(celery_kwargs)
|
|
867
872
|
|
|
868
873
|
if synchronous:
|
|
@@ -1208,7 +1213,6 @@ class ScheduledJob(BaseModel):
|
|
|
1208
1213
|
ordering = ["name"]
|
|
1209
1214
|
|
|
1210
1215
|
def save(self, *args, **kwargs):
|
|
1211
|
-
self.queue = self.queue or ""
|
|
1212
1216
|
# make sure non-valid crontab doesn't get saved
|
|
1213
1217
|
if self.interval == JobExecutionType.TYPE_CUSTOM:
|
|
1214
1218
|
try:
|
|
@@ -1253,12 +1257,12 @@ class ScheduledJob(BaseModel):
|
|
|
1253
1257
|
return self.to_cron()
|
|
1254
1258
|
|
|
1255
1259
|
@property
|
|
1256
|
-
def queue(self):
|
|
1260
|
+
def queue(self) -> str:
|
|
1257
1261
|
"""Deprecated backward-compatibility property for the queue name this job is scheduled for."""
|
|
1258
1262
|
return self.job_queue.name if self.job_queue else ""
|
|
1259
1263
|
|
|
1260
1264
|
@queue.setter
|
|
1261
|
-
def queue(self, value):
|
|
1265
|
+
def queue(self, value: str):
|
|
1262
1266
|
if value:
|
|
1263
1267
|
try:
|
|
1264
1268
|
self.job_queue = JobQueue.objects.get(name=value)
|
|
@@ -1301,14 +1305,15 @@ class ScheduledJob(BaseModel):
|
|
|
1301
1305
|
cls,
|
|
1302
1306
|
job_model,
|
|
1303
1307
|
user,
|
|
1304
|
-
name=None,
|
|
1305
|
-
start_time=None,
|
|
1306
|
-
interval=JobExecutionType.TYPE_IMMEDIATELY,
|
|
1307
|
-
crontab="",
|
|
1308
|
-
profile=False,
|
|
1309
|
-
approval_required=False,
|
|
1310
|
-
|
|
1311
|
-
|
|
1308
|
+
name: Optional[str] = None,
|
|
1309
|
+
start_time: Optional[datetime] = None,
|
|
1310
|
+
interval: str = JobExecutionType.TYPE_IMMEDIATELY,
|
|
1311
|
+
crontab: str = "",
|
|
1312
|
+
profile: bool = False,
|
|
1313
|
+
approval_required: bool = False,
|
|
1314
|
+
job_queue: Optional[JobQueue] = None,
|
|
1315
|
+
task_queue: Optional[str] = None, # deprecated!
|
|
1316
|
+
ignore_singleton_lock: bool = False,
|
|
1312
1317
|
**job_kwargs,
|
|
1313
1318
|
):
|
|
1314
1319
|
"""
|
|
@@ -1321,21 +1326,32 @@ class ScheduledJob(BaseModel):
|
|
|
1321
1326
|
Parameters:
|
|
1322
1327
|
job_model (JobModel): The job model instance.
|
|
1323
1328
|
user (User): The user who is scheduling the job.
|
|
1324
|
-
name (str
|
|
1325
|
-
start_time (datetime
|
|
1326
|
-
interval (JobExecutionType
|
|
1329
|
+
name (str): The name of the scheduled job. Automatically derived from the job_model and start_time if unset.
|
|
1330
|
+
start_time (datetime): The start time for the job. Defaults to the current time if unset.
|
|
1331
|
+
interval (JobExecutionType): The interval type for the job execution.
|
|
1327
1332
|
Defaults to JobExecutionType.TYPE_IMMEDIATELY.
|
|
1328
|
-
crontab (str
|
|
1329
|
-
profile (bool
|
|
1330
|
-
approval_required (bool
|
|
1331
|
-
|
|
1332
|
-
|
|
1333
|
+
crontab (str): The crontab string for the schedule. Defaults to "".
|
|
1334
|
+
profile (bool): Flag indicating whether to profile the job. Defaults to False.
|
|
1335
|
+
approval_required (bool): Flag indicating if approval is required. Defaults to False.
|
|
1336
|
+
job_queue (JobQueue): The Job queue to use. If unset, use the configured default celery queue.
|
|
1337
|
+
task_queue (str): The queue name to use. **Deprecated, prefer `job_queue`.**
|
|
1338
|
+
ignore_singleton_lock (bool): Whether to ignore singleton locks. Defaults to False.
|
|
1333
1339
|
**job_kwargs: Additional keyword arguments to pass to the job.
|
|
1334
1340
|
|
|
1335
1341
|
Returns:
|
|
1336
1342
|
ScheduledJob instance
|
|
1337
1343
|
"""
|
|
1338
1344
|
|
|
1345
|
+
if job_queue is not None and task_queue is not None and job_queue.name != task_queue:
|
|
1346
|
+
raise ValueError("task_queue and job_queue are mutually exclusive")
|
|
1347
|
+
if job_queue is not None and task_queue is None:
|
|
1348
|
+
task_queue = job_queue.name
|
|
1349
|
+
elif task_queue is not None and job_queue is None:
|
|
1350
|
+
job_queue = JobQueue.objects.get(name=task_queue)
|
|
1351
|
+
else: # both None
|
|
1352
|
+
job_queue = job_model.default_job_queue
|
|
1353
|
+
task_queue = job_queue.name
|
|
1354
|
+
|
|
1339
1355
|
if interval == JobExecutionType.TYPE_IMMEDIATELY:
|
|
1340
1356
|
start_time = timezone.localtime()
|
|
1341
1357
|
name = name or f"{job_model.name} - {start_time}"
|
|
@@ -1376,7 +1392,7 @@ class ScheduledJob(BaseModel):
|
|
|
1376
1392
|
user=user,
|
|
1377
1393
|
approval_required=approval_required,
|
|
1378
1394
|
crontab=crontab,
|
|
1379
|
-
|
|
1395
|
+
job_queue=job_queue,
|
|
1380
1396
|
)
|
|
1381
1397
|
scheduled_job.validated_save()
|
|
1382
1398
|
return scheduled_job
|
nautobot/extras/tables.py
CHANGED
|
@@ -40,6 +40,7 @@ from .models import (
|
|
|
40
40
|
JobLogEntry,
|
|
41
41
|
JobQueue,
|
|
42
42
|
JobResult,
|
|
43
|
+
MetadataChoice,
|
|
43
44
|
MetadataType,
|
|
44
45
|
Note,
|
|
45
46
|
ObjectChange,
|
|
@@ -730,7 +731,7 @@ class JobTable(BaseTable):
|
|
|
730
731
|
accessor="latest_result",
|
|
731
732
|
template_code="""
|
|
732
733
|
{% if value %}
|
|
733
|
-
{{ value.
|
|
734
|
+
{{ value.date_created|date:settings.SHORT_DATETIME_FORMAT }} by {{ value.user }}
|
|
734
735
|
{% else %}
|
|
735
736
|
<span class="text-muted">Never</span>
|
|
736
737
|
{% endif %}
|
|
@@ -1008,6 +1009,15 @@ class MetadataTypeTable(BaseTable):
|
|
|
1008
1009
|
)
|
|
1009
1010
|
|
|
1010
1011
|
|
|
1012
|
+
class MetadataChoiceTable(BaseTable):
|
|
1013
|
+
value = tables.Column()
|
|
1014
|
+
weight = tables.Column()
|
|
1015
|
+
|
|
1016
|
+
class Meta(BaseTable.Meta):
|
|
1017
|
+
model = MetadataChoice
|
|
1018
|
+
fields = ("value", "weight")
|
|
1019
|
+
|
|
1020
|
+
|
|
1011
1021
|
class ObjectMetadataTable(BaseTable):
|
|
1012
1022
|
pk = ToggleColumn()
|
|
1013
1023
|
# NOTE: there is no identity column in this table; this is intentional as we have no detail view for ObjectMetadata
|
|
@@ -1,56 +1,2 @@
|
|
|
1
1
|
{% extends 'generic/object_retrieve.html' %}
|
|
2
|
-
{%
|
|
3
|
-
|
|
4
|
-
{% block content_left_page %}
|
|
5
|
-
<div class="panel panel-default">
|
|
6
|
-
<div class="panel-heading">
|
|
7
|
-
<strong>Computed Field</strong>
|
|
8
|
-
</div>
|
|
9
|
-
|
|
10
|
-
<table class="table table-hover panel-body attr-table">
|
|
11
|
-
<tr>
|
|
12
|
-
<td>Content Type</td>
|
|
13
|
-
<td><span>{{ object.content_type }}</span></td>
|
|
14
|
-
</tr>
|
|
15
|
-
<tr>
|
|
16
|
-
<td>Label</td>
|
|
17
|
-
<td><span>{{ object.label }}</span></td>
|
|
18
|
-
</tr>
|
|
19
|
-
<tr>
|
|
20
|
-
<td>Key</td>
|
|
21
|
-
<td><span>{{ object.key }}</span></td>
|
|
22
|
-
</tr>
|
|
23
|
-
<tr>
|
|
24
|
-
<td>Grouping</td>
|
|
25
|
-
<td>{{ object.grouping | placeholder }}</td>
|
|
26
|
-
</tr>
|
|
27
|
-
<tr>
|
|
28
|
-
<td>Description</td>
|
|
29
|
-
<td><span>{{ object.description|placeholder }}</span></td>
|
|
30
|
-
</tr>
|
|
31
|
-
<tr>
|
|
32
|
-
<td>Fallback Value</td>
|
|
33
|
-
<td><span>{{ object.fallback_value }}</span></td>
|
|
34
|
-
</tr>
|
|
35
|
-
<tr>
|
|
36
|
-
<td>Weight</td>
|
|
37
|
-
<td><span>{{ object.weight }}</span></td>
|
|
38
|
-
</tr>
|
|
39
|
-
<tr>
|
|
40
|
-
<td>Move to Advanced Tab</td>
|
|
41
|
-
<td><span>{{ object.advanced_ui | render_boolean }}</span></td>
|
|
42
|
-
</tr>
|
|
43
|
-
</table>
|
|
44
|
-
</div>
|
|
45
|
-
{% endblock content_left_page %}
|
|
46
|
-
|
|
47
|
-
{% block content_full_width_page %}
|
|
48
|
-
<div class="panel panel-default">
|
|
49
|
-
<div class="panel-heading">
|
|
50
|
-
<strong>Template</strong>
|
|
51
|
-
</div>
|
|
52
|
-
<div class="panel-body">
|
|
53
|
-
<pre>{{ object.template }}</pre>
|
|
54
|
-
</div>
|
|
55
|
-
</div>
|
|
56
|
-
{% endblock content_full_width_page %}
|
|
2
|
+
{% comment %}3.0 TODO: remove this template, which only exists for backward compatibility with 2.4 and earlier{% endcomment %}
|