nautobot 3.0.0a2__py3-none-any.whl → 3.0.0a3__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/apps/choices.py +0 -2
- nautobot/apps/filters.py +7 -9
- nautobot/apps/models.py +2 -2
- nautobot/apps/ui.py +9 -1
- nautobot/circuits/filters.py +3 -2
- nautobot/circuits/navigation.py +3 -2
- nautobot/circuits/templates/circuits/circuit.html +1 -1
- nautobot/circuits/templates/circuits/circuit_create.html +3 -3
- nautobot/circuits/templates/circuits/circuittermination.html +1 -1
- nautobot/circuits/templates/circuits/circuittermination_create.html +9 -24
- nautobot/circuits/templates/circuits/circuittype.html +1 -1
- nautobot/circuits/templates/circuits/inc/circuit_termination_cable_fragment.html +6 -6
- nautobot/circuits/templates/circuits/inc/speed_widget.html +12 -12
- nautobot/circuits/templates/circuits/providernetwork.html +1 -1
- nautobot/circuits/tests/integration/test_circuit.py +10 -13
- nautobot/cloud/filters.py +1 -1
- nautobot/cloud/navigation.py +3 -2
- nautobot/core/api/schema.py +1 -1
- nautobot/core/api/serializers.py +6 -1
- nautobot/core/api/urls.py +1 -0
- nautobot/core/api/views.py +8 -0
- nautobot/core/apps/__init__.py +11 -10
- nautobot/core/celery/__init__.py +3 -5
- nautobot/core/checks.py +46 -0
- nautobot/core/cli/bootstrap_v3_to_v5.py +70 -1
- nautobot/core/cli/migrate_deprecated_templates.py +200 -0
- nautobot/core/constants.py +3 -0
- nautobot/core/context_processors.py +9 -1
- nautobot/core/forms/forms.py +1 -1
- nautobot/core/jobs/__init__.py +6 -3
- nautobot/core/jobs/groups.py +31 -1
- nautobot/core/management/commands/generate_test_data.py +28 -9
- nautobot/core/models/generics.py +9 -1
- nautobot/core/models/tree_queries.py +10 -5
- nautobot/core/settings.py +18 -12
- nautobot/core/settings.yaml +13 -7
- nautobot/core/signals.py +12 -1
- nautobot/core/tables.py +13 -6
- nautobot/core/templates/40x.html +1 -1
- nautobot/core/templates/500.html +2 -2
- nautobot/core/templates/admin/config/config.html +12 -12
- nautobot/core/templates/admin/index.html +3 -3
- nautobot/core/templates/buttons/export.html +1 -1
- nautobot/core/templates/components/button/dropdown.html +5 -3
- nautobot/core/templates/components/panel/body_wrapper_generic_table.html +1 -1
- nautobot/core/templates/components/panel/panel.html +3 -3
- nautobot/core/templates/components/tab/content_wrapper.html +2 -3
- nautobot/core/templates/components/tab/label_wrapper_distinct_view.html +1 -1
- nautobot/core/templates/echarts/echarts.html +1 -1
- nautobot/core/templates/generic/object_bulk_add_component.html +2 -1
- nautobot/core/templates/generic/object_bulk_create.html +4 -3
- nautobot/core/templates/generic/object_bulk_destroy.html +3 -3
- nautobot/core/templates/generic/object_bulk_remove.html +2 -2
- nautobot/core/templates/generic/object_bulk_update.html +5 -4
- nautobot/core/templates/generic/object_create.html +5 -4
- nautobot/core/templates/generic/object_import.html +2 -1
- nautobot/core/templates/generic/object_list.html +12 -4
- nautobot/core/templates/generic/object_notes.html +5 -3
- nautobot/core/templates/generic/object_retrieve.html +2 -3
- nautobot/core/templates/graphene/graphiql.html +7 -7
- nautobot/core/templates/home.html +1 -1
- nautobot/core/templates/import_success.html +2 -1
- nautobot/core/templates/inc/computed_fields/panel_data.html +1 -1
- nautobot/core/templates/inc/created_updated.html +7 -3
- nautobot/core/templates/inc/custom_fields/panel_data.html +1 -1
- nautobot/core/templates/inc/form_static_field.html +6 -0
- nautobot/core/templates/inc/header.html +1 -1
- nautobot/core/templates/inc/image_attachments.html +2 -1
- nautobot/core/templates/inc/nav_menu.html +2 -1
- nautobot/core/templates/inc/search_panel.html +4 -4
- nautobot/core/templates/login.html +4 -2
- nautobot/core/templates/nautobot_config.py.j2 +6 -5
- nautobot/core/templates/redoc_ui.html +7 -0
- nautobot/core/templates/search.html +1 -1
- nautobot/core/templates/swagger_ui.html +17 -3
- nautobot/core/templates/system_jobs/import_objects.html +1 -2
- nautobot/core/templates/utilities/confirmation_form.html +2 -2
- nautobot/core/templates/utilities/obj_table.html +10 -2
- nautobot/core/templates/utilities/render_field.html +7 -7
- nautobot/core/templates/utilities/render_jinja2.html +2 -2
- nautobot/core/templates/utilities/templatetags/filter_form_drawer.html +4 -4
- nautobot/core/templates/utilities/theme_preview.html +16 -3
- nautobot/core/templates/widgets/selectwithdisabled_option.html +3 -1
- nautobot/core/templatetags/helpers.py +52 -6
- nautobot/core/testing/api.py +68 -9
- nautobot/core/testing/filters.py +0 -23
- nautobot/core/testing/integration.py +23 -10
- nautobot/core/testing/mixins.py +2 -0
- nautobot/core/testing/views.py +4 -0
- nautobot/core/tests/integration/test_app_home.py +34 -30
- nautobot/core/tests/integration/test_app_navbar.py +3 -0
- nautobot/core/tests/nautobot_config_without_example_apps.py +4 -0
- nautobot/core/tests/runner.py +9 -1
- nautobot/core/tests/test_api.py +5 -3
- nautobot/core/tests/test_breadcrumbs.py +6 -7
- nautobot/core/tests/test_checks.py +28 -0
- nautobot/core/tests/test_cli.py +40 -0
- nautobot/core/tests/test_config.py +2 -1
- nautobot/core/tests/test_forms.py +55 -13
- nautobot/core/tests/test_jobs.py +75 -1
- nautobot/core/tests/test_nautobot_server.py +2 -0
- nautobot/core/tests/test_navigations.py +76 -1
- nautobot/core/tests/test_patch_social_django.py +42 -0
- nautobot/core/tests/test_tables.py +3 -1
- nautobot/core/tests/test_templatetags_helpers.py +53 -13
- nautobot/core/tests/test_templatetags_ui_framework.py +4 -4
- nautobot/core/tests/test_tree_queries.py +14 -1
- nautobot/core/tests/test_ui.py +1 -1
- nautobot/core/tests/test_utils.py +31 -4
- nautobot/core/tests/test_views.py +159 -31
- nautobot/core/ui/breadcrumbs.py +2 -12
- nautobot/core/ui/choices.py +142 -10
- nautobot/core/ui/constants.py +76 -12
- nautobot/core/ui/object_detail.py +92 -12
- nautobot/core/urls.py +12 -1
- nautobot/core/utils/cache.py +2 -1
- nautobot/core/utils/filtering.py +17 -17
- nautobot/core/utils/lookup.py +3 -8
- nautobot/core/utils/module_loading.py +21 -0
- nautobot/core/utils/patch_social_django.py +128 -0
- nautobot/core/views/__init__.py +38 -1
- nautobot/core/views/generic.py +3 -3
- nautobot/core/views/mixins.py +15 -3
- nautobot/core/views/renderers.py +2 -0
- nautobot/core/views/viewsets.py +2 -1
- nautobot/data_validation/apps.py +1 -5
- nautobot/data_validation/custom_validators.py +4 -4
- nautobot/data_validation/filters.py +1 -1
- nautobot/data_validation/forms.py +40 -0
- nautobot/data_validation/migrations/0001_initial.py +0 -7
- nautobot/data_validation/migrations/0002_data_migration_from_app.py +0 -12
- nautobot/data_validation/models.py +16 -7
- nautobot/data_validation/navigation.py +8 -1
- nautobot/data_validation/tables.py +12 -5
- nautobot/data_validation/templates/data_validation/datacompliance_tab.html +1 -0
- nautobot/data_validation/templates/data_validation/device_constraints.html +61 -0
- nautobot/data_validation/tests/__init__.py +2 -2
- nautobot/data_validation/tests/migrations/test_migrations.py +83 -3
- nautobot/data_validation/tests/test_data_compliance_rules.py +12 -7
- nautobot/data_validation/tests/test_filters.py +8 -6
- nautobot/data_validation/tests/test_models.py +15 -0
- nautobot/data_validation/tests/test_views.py +190 -32
- nautobot/data_validation/urls.py +2 -5
- nautobot/data_validation/views.py +73 -40
- nautobot/dcim/api/serializers.py +0 -13
- nautobot/dcim/apps.py +4 -0
- nautobot/dcim/choices.py +16 -0
- nautobot/dcim/custom_validators.py +84 -0
- nautobot/dcim/filter_mixins.py +353 -4
- nautobot/dcim/{filters/__init__.py → filters.py} +2 -35
- nautobot/dcim/forms.py +1 -1
- nautobot/dcim/migrations/0078_remove_device_location_tenant_name_uniqueness.py +16 -0
- nautobot/dcim/migrations/0079_device_name_data_migration.py +59 -0
- nautobot/dcim/models/device_components.py +81 -68
- nautobot/dcim/models/devices.py +13 -16
- nautobot/dcim/navigation.py +7 -6
- nautobot/dcim/tables/devices.py +3 -0
- nautobot/dcim/tables/template_code.py +14 -14
- nautobot/dcim/templates/dcim/cable.html +2 -61
- nautobot/dcim/templates/dcim/cable_connect.html +28 -112
- nautobot/dcim/templates/dcim/cable_edit.html +2 -5
- nautobot/dcim/templates/dcim/cable_retrieve.html +61 -0
- nautobot/dcim/templates/dcim/cable_trace.html +1 -3
- nautobot/dcim/templates/dcim/cable_update.html +5 -0
- nautobot/dcim/templates/dcim/consoleport.html +6 -5
- nautobot/dcim/templates/dcim/consoleserverport.html +6 -5
- nautobot/dcim/templates/dcim/device/config.html +2 -2
- nautobot/dcim/templates/dcim/device/consoleports.html +1 -1
- nautobot/dcim/templates/dcim/device/consoleserverports.html +1 -1
- nautobot/dcim/templates/dcim/device/devicebays.html +1 -1
- nautobot/dcim/templates/dcim/device/frontports.html +1 -1
- nautobot/dcim/templates/dcim/device/interfaces.html +1 -1
- nautobot/dcim/templates/dcim/device/inventory.html +1 -1
- nautobot/dcim/templates/dcim/device/lldp_neighbors.html +1 -1
- nautobot/dcim/templates/dcim/device/modulebays.html +1 -1
- nautobot/dcim/templates/dcim/device/poweroutlets.html +1 -1
- nautobot/dcim/templates/dcim/device/powerports.html +1 -1
- nautobot/dcim/templates/dcim/device/rearports.html +1 -1
- nautobot/dcim/templates/dcim/device/status.html +8 -8
- nautobot/dcim/templates/dcim/device/wireless.html +1 -1
- nautobot/dcim/templates/dcim/device.html +1 -1
- nautobot/dcim/templates/dcim/device_component_add.html +2 -2
- nautobot/dcim/templates/dcim/device_create.html +5 -3
- nautobot/dcim/templates/dcim/device_interface_delete.html +1 -1
- nautobot/dcim/templates/dcim/device_list.html +73 -10
- nautobot/dcim/templates/dcim/devicebay_populate.html +2 -2
- nautobot/dcim/templates/dcim/devicetype.html +1 -1
- nautobot/dcim/templates/dcim/devicetype_component_add.html +2 -2
- nautobot/dcim/templates/dcim/footer_convert_to_contact_or_team_record.html +14 -0
- nautobot/dcim/templates/dcim/frontport.html +9 -8
- nautobot/dcim/templates/dcim/inc/edit_form_softwareversion_js.html +2 -2
- nautobot/dcim/templates/dcim/interface.html +26 -6
- nautobot/dcim/templates/dcim/interface_bulk_delete.html +1 -1
- nautobot/dcim/templates/dcim/inventoryitem_add.html +3 -1
- nautobot/dcim/templates/dcim/inventoryitem_bulk_delete.html +1 -1
- nautobot/dcim/templates/dcim/inventoryitem_edit.html +3 -1
- nautobot/dcim/templates/dcim/location_retrieve.html +1 -242
- nautobot/dcim/templates/dcim/module/base.html +49 -9
- nautobot/dcim/templates/dcim/module_list.html +57 -8
- nautobot/dcim/templates/dcim/modulefamily_retrieve.html +1 -1
- nautobot/dcim/templates/dcim/moduletype_retrieve.html +49 -9
- nautobot/dcim/templates/dcim/platform_create.html +1 -1
- nautobot/dcim/templates/dcim/powerfeed.html +1 -1
- nautobot/dcim/templates/dcim/powerpanel.html +1 -1
- nautobot/dcim/templates/dcim/powerport.html +5 -4
- nautobot/dcim/templates/dcim/rack_elevation_list.html +16 -4
- nautobot/dcim/templates/dcim/rack_retrieve.html +33 -15
- nautobot/dcim/templates/dcim/rearport.html +7 -6
- nautobot/dcim/templates/dcim/virtualchassis.html +1 -1
- nautobot/dcim/templates/dcim/virtualchassis_add_member.html +16 -14
- nautobot/dcim/templates/dcim/virtualchassis_update.html +14 -6
- nautobot/dcim/tests/integration/test_controller.py +1 -0
- nautobot/dcim/tests/test_api.py +8 -0
- nautobot/dcim/tests/test_custom_validators.py +229 -0
- nautobot/dcim/tests/test_filters.py +12 -6
- nautobot/dcim/tests/test_models.py +63 -4
- nautobot/dcim/tests/test_views.py +63 -22
- nautobot/dcim/urls.py +64 -21
- nautobot/dcim/utils.py +3 -3
- nautobot/dcim/views.py +547 -273
- nautobot/extras/api/views.py +9 -1
- nautobot/extras/choices.py +2 -13
- nautobot/extras/{filters/mixins.py → filter_mixins.py} +1 -1
- nautobot/extras/{filters/customfields.py → filter_mixins_customfields.py} +42 -6
- nautobot/extras/{filters/__init__.py → filters.py} +14 -46
- nautobot/extras/forms/forms.py +5 -13
- nautobot/extras/forms/mixins.py +0 -41
- nautobot/extras/management/__init__.py +9 -0
- nautobot/extras/migrations/0127_approval_workflow_models.py +6 -6
- nautobot/extras/migrations/0129_jobresult_debug_log_count_jobresult_error_log_count_and_more.py +37 -0
- nautobot/extras/migrations/0130_jobresult_generate_log_entry_counts.py +42 -0
- nautobot/extras/models/__init__.py +1 -2
- nautobot/extras/models/approvals.py +22 -13
- nautobot/extras/models/contacts.py +2 -0
- nautobot/extras/models/groups.py +44 -5
- nautobot/extras/models/jobs.py +59 -1
- nautobot/extras/models/mixins.py +28 -0
- nautobot/extras/models/models.py +13 -0
- nautobot/extras/models/secrets.py +1 -0
- nautobot/extras/models/statuses.py +0 -15
- nautobot/extras/navigation.py +13 -9
- nautobot/extras/plugins/__init__.py +33 -55
- nautobot/extras/plugins/tables.py +3 -3
- nautobot/extras/plugins/urls.py +2 -21
- nautobot/extras/plugins/utils.py +1 -33
- nautobot/extras/plugins/views.py +0 -4
- nautobot/extras/signals.py +20 -19
- nautobot/extras/tables.py +52 -68
- nautobot/extras/templates/extras/approval_dashboard.html +7 -5
- nautobot/extras/templates/extras/approvalworkflowdefinition_update.html +4 -2
- nautobot/extras/templates/extras/approvalworkflowstage_retrieve.html +20 -12
- nautobot/extras/templates/extras/computedfield.html +1 -1
- nautobot/extras/templates/extras/configcontext.html +1 -1
- nautobot/extras/templates/extras/configcontextschema_validation.html +2 -2
- nautobot/extras/templates/extras/customfield.html +1 -1
- nautobot/extras/templates/extras/dynamicgroup_retrieve.html +11 -5
- nautobot/extras/templates/extras/dynamicgroup_update.html +1 -1
- nautobot/extras/templates/extras/gitrepository_result.html +0 -2
- nautobot/extras/templates/extras/graphqlquery_retrieve.html +1 -96
- nautobot/extras/templates/extras/inc/approval_buttons_column.html +20 -6
- nautobot/extras/templates/extras/inc/bulk_edit_overridable_field.html +8 -7
- nautobot/extras/templates/extras/inc/configcontext_format.html +10 -3
- nautobot/extras/templates/extras/inc/graphqlquery_execute.html +71 -0
- nautobot/extras/templates/extras/inc/job_tiles.html +15 -3
- nautobot/extras/templates/extras/inc/json_format.html +10 -3
- nautobot/extras/templates/extras/inc/overridable_field.html +13 -12
- nautobot/extras/templates/extras/job.html +29 -12
- nautobot/extras/templates/extras/job_bulk_edit.html +18 -0
- nautobot/extras/templates/extras/job_edit.html +52 -46
- nautobot/extras/templates/extras/job_list.html +29 -25
- nautobot/extras/templates/extras/marketplace.html +5 -9
- nautobot/extras/templates/extras/object_configcontext.html +1 -1
- nautobot/extras/templates/extras/object_dynamicgroups.html +2 -2
- nautobot/extras/templates/extras/objectchange_retrieve.html +19 -37
- nautobot/extras/templates/extras/plugin_detail.html +26 -21
- nautobot/extras/templates/extras/plugins_list.html +16 -26
- nautobot/extras/templates/extras/role_retrieve.html +64 -0
- nautobot/extras/templates/extras/scheduledjob.html +4 -2
- nautobot/extras/templates/extras/secretsgroup.html +1 -1
- nautobot/extras/templates/extras/tag.html +1 -1
- nautobot/extras/templatetags/custom_links.py +12 -12
- nautobot/extras/templatetags/job_buttons.py +14 -12
- nautobot/extras/test_jobs/invalid_import.py +9 -0
- nautobot/extras/test_jobs/log_counts_by_level.py +23 -0
- nautobot/extras/test_jobs/missing_import.py +11 -0
- nautobot/extras/tests/integration/test_configcontextschema.py +27 -26
- nautobot/extras/tests/integration/test_customfields.py +8 -7
- nautobot/extras/tests/integration/test_dynamicgroups.py +5 -1
- nautobot/extras/tests/integration/test_plugin_banner.py +3 -0
- nautobot/extras/tests/integration/test_plugins.py +18 -6
- nautobot/extras/tests/test_api.py +27 -18
- nautobot/extras/tests/test_approvals.py +38 -38
- nautobot/extras/tests/test_changelog.py +35 -3
- nautobot/extras/tests/test_customfields.py +22 -13
- nautobot/extras/tests/test_customfields_filters.py +479 -0
- nautobot/extras/tests/test_dynamicgroups.py +39 -1
- nautobot/extras/tests/test_filters.py +21 -19
- nautobot/extras/tests/test_forms.py +18 -21
- nautobot/extras/tests/test_jobs.py +25 -4
- nautobot/extras/tests/test_migrations.py +1 -0
- nautobot/extras/tests/test_models.py +13 -31
- nautobot/extras/tests/test_plugins.py +36 -10
- nautobot/extras/tests/test_views.py +31 -30
- nautobot/extras/views.py +81 -19
- nautobot/ipam/factory.py +7 -0
- nautobot/ipam/filter_mixins.py +38 -0
- nautobot/ipam/filters.py +27 -38
- nautobot/ipam/formfields.py +1 -1
- nautobot/ipam/forms.py +6 -3
- nautobot/ipam/migrations/0030_ipam__namespaces.py +13 -0
- nautobot/ipam/migrations/0031_ipam___data_migrations.py +4 -1
- nautobot/ipam/migrations/0054_namespace_tenant.py +25 -0
- nautobot/ipam/models.py +29 -2
- nautobot/ipam/navigation.py +3 -2
- nautobot/ipam/signals.py +71 -0
- nautobot/ipam/tables.py +13 -6
- nautobot/ipam/templates/ipam/inc/toggle_available.html +10 -10
- nautobot/ipam/templates/ipam/inc/vlangroup_header.html +1 -0
- nautobot/ipam/templates/ipam/ipaddress.html +14 -0
- nautobot/ipam/templates/ipam/ipaddress_merge.html +3 -3
- nautobot/ipam/templates/ipam/ipaddresstointerface_retrieve.html +1 -0
- nautobot/ipam/templates/ipam/namespace_update.html +15 -0
- nautobot/ipam/templates/ipam/prefix_delete.html +1 -1
- nautobot/ipam/templates/ipam/prefix_list.html +14 -13
- nautobot/ipam/templates/ipam/service.html +1 -1
- nautobot/ipam/templates/ipam/vlan.html +1 -1
- nautobot/ipam/templates/ipam/vlan_interfaces.html +1 -1
- nautobot/ipam/templates/ipam/vlan_vminterfaces.html +1 -1
- nautobot/ipam/tests/migration/test_migrations.py +89 -0
- nautobot/ipam/tests/test_api.py +13 -6
- nautobot/ipam/tests/test_filters.py +10 -0
- nautobot/ipam/tests/test_forms.py +1 -1
- nautobot/ipam/tests/test_models.py +43 -1
- nautobot/ipam/tests/test_tables.py +1 -2
- nautobot/ipam/tests/test_utils.py +1 -1
- nautobot/ipam/tests/test_views.py +13 -14
- nautobot/ipam/ui.py +0 -17
- nautobot/ipam/utils/migrations.py +16 -2
- nautobot/ipam/utils/testing.py +9 -3
- nautobot/ipam/views.py +46 -6
- nautobot/project-static/dist/css/nautobot.css +1 -1
- nautobot/project-static/dist/css/nautobot.css.map +1 -1
- nautobot/project-static/dist/js/nautobot.js +1 -1
- nautobot/project-static/dist/js/nautobot.js.map +1 -1
- nautobot/project-static/js/cabletrace.js +1 -1
- nautobot/project-static/js/interface_filtering.js +20 -16
- nautobot/project-static/nautobot-icons/battery-3.svg +3 -0
- nautobot/project-static/nautobot-icons/cloud.svg +1 -1
- nautobot/project-static/nautobot-icons/control-panel.svg +1 -1
- nautobot/project-static/nautobot-icons/device-lifecycle.svg +1 -1
- nautobot/project-static/nautobot-icons/elements.svg +1 -1
- nautobot/project-static/nautobot-icons/extensibility.svg +3 -0
- nautobot/project-static/nautobot-icons/hammer.svg +1 -1
- nautobot/project-static/nautobot-icons/organization.svg +3 -0
- nautobot/project-static/nautobot-icons/secrets.svg +1 -1
- nautobot/project-static/nautobot-icons/security.svg +3 -0
- nautobot/project-static/nautobot-icons/server.svg +1 -1
- nautobot/project-static/nautobot-icons/star-filled.svg +1 -1
- nautobot/project-static/nautobot-icons/star.svg +1 -1
- nautobot/tenancy/api/serializers.py +1 -0
- nautobot/tenancy/api/views.py +2 -1
- nautobot/tenancy/{filters/__init__.py → filters.py} +2 -10
- nautobot/tenancy/navigation.py +3 -1
- nautobot/tenancy/tests/test_filters.py +0 -2
- nautobot/tenancy/views.py +2 -1
- nautobot/ui/src/js/collapse.js +3 -3
- nautobot/ui/src/js/nautobot.js +16 -0
- nautobot/ui/src/scss/colors.scss +1 -1
- nautobot/ui/src/scss/nautobot.scss +61 -28
- nautobot/users/templates/users/profile.html +45 -12
- nautobot/users/templates/users/sessionkey_delete.html +1 -1
- nautobot/users/tests/test_api.py +4 -0
- nautobot/users/views.py +4 -2
- nautobot/virtualization/models.py +1 -68
- nautobot/virtualization/navigation.py +3 -2
- nautobot/virtualization/templates/virtualization/virtual_machine_vminterface_delete.html +1 -1
- nautobot/virtualization/templates/virtualization/virtualmachine.html +1 -1
- nautobot/virtualization/templates/virtualization/virtualmachine_list.html +2 -2
- nautobot/virtualization/templates/virtualization/virtualmachine_update.html +3 -1
- nautobot/virtualization/tests/test_api.py +3 -0
- nautobot/virtualization/tests/test_models.py +44 -4
- nautobot/vpn/__init__.py +0 -0
- nautobot/vpn/api/serializers.py +113 -0
- nautobot/vpn/api/urls.py +19 -0
- nautobot/vpn/api/views.py +70 -0
- nautobot/vpn/apps.py +8 -0
- nautobot/vpn/choices.py +171 -0
- nautobot/vpn/factory.py +209 -0
- nautobot/vpn/filters.py +233 -0
- nautobot/vpn/forms.py +486 -0
- nautobot/vpn/homepage.py +19 -0
- nautobot/vpn/migrations/0001_initial.py +541 -0
- nautobot/vpn/migrations/0002_populate_defaults.py +199 -0
- nautobot/vpn/migrations/__init__.py +0 -0
- nautobot/vpn/models.py +527 -0
- nautobot/vpn/navigation.py +98 -0
- nautobot/vpn/tables.py +380 -0
- nautobot/vpn/templates/vpn/vpnprofile.html +2 -0
- nautobot/vpn/templates/vpn/vpnprofile_create.html +150 -0
- nautobot/vpn/tests/__init__.py +0 -0
- nautobot/vpn/tests/test_api.py +341 -0
- nautobot/vpn/tests/test_filters.py +139 -0
- nautobot/vpn/tests/test_forms.py +294 -0
- nautobot/vpn/tests/test_models.py +97 -0
- nautobot/vpn/tests/test_views.py +281 -0
- nautobot/vpn/urls.py +16 -0
- nautobot/vpn/views.py +437 -0
- nautobot/wireless/navigation.py +3 -2
- nautobot/wireless/tests/integration/test_radio_profile.py +1 -5
- nautobot/wireless/tests/test_api.py +1 -1
- {nautobot-3.0.0a2.dist-info → nautobot-3.0.0a3.dist-info}/METADATA +14 -14
- {nautobot-3.0.0a2.dist-info → nautobot-3.0.0a3.dist-info}/RECORD +417 -366
- {nautobot-3.0.0a2.dist-info → nautobot-3.0.0a3.dist-info}/entry_points.txt +1 -0
- nautobot/data_validation/template_content.py +0 -42
- nautobot/dcim/filters/mixins.py +0 -354
- nautobot/ipam/templates/ipam/inc/prefix_header_extra_content_table.html +0 -4
- /nautobot/tenancy/{filters/mixins.py → filter_mixins.py} +0 -0
- {nautobot-3.0.0a2.dist-info → nautobot-3.0.0a3.dist-info}/LICENSE.txt +0 -0
- {nautobot-3.0.0a2.dist-info → nautobot-3.0.0a3.dist-info}/NOTICE +0 -0
- {nautobot-3.0.0a2.dist-info → nautobot-3.0.0a3.dist-info}/WHEEL +0 -0
|
@@ -6,69 +6,69 @@
|
|
|
6
6
|
<div class="card">
|
|
7
7
|
<div class="card-header"><strong>Job Source</strong></div>
|
|
8
8
|
<div class="card-body">
|
|
9
|
-
<div class="mb-10 d-flex justify-content-center">
|
|
9
|
+
<div class="mb-10 d-lg-flex justify-content-center">
|
|
10
10
|
<label class="col-lg-3 col-form-label">Module</label>
|
|
11
|
-
<div class="col-lg-9
|
|
11
|
+
<div class="col-lg-9 pt-6">
|
|
12
12
|
<code>{{ obj.module_name }}</code>
|
|
13
13
|
<span class="form-text">Dotted name of the Python module providing this job</span>
|
|
14
14
|
</div>
|
|
15
15
|
</div>
|
|
16
|
-
<div class="mb-10 d-flex justify-content-center">
|
|
16
|
+
<div class="mb-10 d-lg-flex justify-content-center">
|
|
17
17
|
<label class="col-lg-3 col-form-label">Job Class</label>
|
|
18
|
-
<div class="col-lg-9
|
|
18
|
+
<div class="col-lg-9 pt-6">
|
|
19
19
|
<code>{{ obj.job_class_name }}</code>
|
|
20
20
|
<span class="form-text">Name of the Python class providing this job</span>
|
|
21
21
|
</div>
|
|
22
22
|
</div>
|
|
23
|
-
<div class="mb-10 d-flex justify-content-center">
|
|
23
|
+
<div class="mb-10 d-lg-flex justify-content-center">
|
|
24
24
|
<div class="col-lg-9 offset-lg-3">
|
|
25
|
-
<div class="form-check">
|
|
26
|
-
<
|
|
27
|
-
|
|
25
|
+
<div class="form-check mt-6">
|
|
26
|
+
<input class="form-check-input" id="id_installed" name="installed" type="checkbox" disabled {% if obj.installed %}checked{% endif %}>
|
|
27
|
+
<label class="form-check-label" for="id_installed">
|
|
28
28
|
Installed
|
|
29
|
+
<span class="form-text">
|
|
30
|
+
Whether the Python class providing this job is presently installed and loadable
|
|
31
|
+
</span>
|
|
29
32
|
</label>
|
|
30
|
-
<span class="form-text">
|
|
31
|
-
Whether the Python class providing this job is presently installed and loadable
|
|
32
|
-
</span>
|
|
33
33
|
</div>
|
|
34
34
|
</div>
|
|
35
35
|
</div>
|
|
36
|
-
<div class="mb-10 d-flex justify-content-center">
|
|
36
|
+
<div class="mb-10 d-lg-flex justify-content-center">
|
|
37
37
|
<div class="col-lg-9 offset-lg-3">
|
|
38
|
-
<div class="form-check">
|
|
39
|
-
<
|
|
40
|
-
|
|
38
|
+
<div class="form-check mt-6">
|
|
39
|
+
<input class="form-check-input" id="id_supports_dryrun" name="supports_dryrun" type="checkbox" disabled {% if obj.supports_dryrun %}checked{% endif %}>
|
|
40
|
+
<label class="form-check-label" for="id_supports_dryrun">
|
|
41
41
|
Supports dryrun
|
|
42
|
+
<span class="form-text">
|
|
43
|
+
Whether this job supports bypassing approval when running with dryrun argument set to true
|
|
44
|
+
</span>
|
|
42
45
|
</label>
|
|
43
|
-
<span class="form-text">
|
|
44
|
-
Whether this job supports bypassing approval when running with dryrun argument set to true
|
|
45
|
-
</span>
|
|
46
46
|
</div>
|
|
47
47
|
</div>
|
|
48
48
|
</div>
|
|
49
|
-
<div class="mb-10 d-flex justify-content-center">
|
|
49
|
+
<div class="mb-10 d-lg-flex justify-content-center">
|
|
50
50
|
<div class="col-lg-9 offset-lg-3">
|
|
51
|
-
<div class="form-check">
|
|
52
|
-
<
|
|
53
|
-
|
|
51
|
+
<div class="form-check mt-6">
|
|
52
|
+
<input class="form-check-input" id="id_is_job_hook_receiver" name="is_job_hook_receiver" type="checkbox" disabled {% if obj.is_job_hook_receiver %}checked{% endif %}>
|
|
53
|
+
<label class="form-check-label" for="id_is_job_hook_receiver">
|
|
54
54
|
Is job hook receiver
|
|
55
|
+
<span class="form-text">
|
|
56
|
+
Whether this job is a job hook receiver
|
|
57
|
+
</span>
|
|
55
58
|
</label>
|
|
56
|
-
<span class="form-text">
|
|
57
|
-
Whether this job is a job hook receiver
|
|
58
|
-
</span>
|
|
59
59
|
</div>
|
|
60
60
|
</div>
|
|
61
61
|
</div>
|
|
62
|
-
<div class="mb-10 d-flex justify-content-center">
|
|
62
|
+
<div class="mb-10 d-lg-flex justify-content-center">
|
|
63
63
|
<div class="col-lg-9 offset-lg-3">
|
|
64
|
-
<div class="form-check">
|
|
65
|
-
<
|
|
66
|
-
|
|
64
|
+
<div class="form-check mt-6">
|
|
65
|
+
<input class="form-check-input" id="id_is_job_button_receiver" name="is_job_button_receiver" type="checkbox" disabled {% if obj.is_job_button_receiver %}checked{% endif %}>
|
|
66
|
+
<label class="form-check-label" for="id_is_job_button_receiver">
|
|
67
67
|
Is job button receiver
|
|
68
|
+
<span class="form-text">
|
|
69
|
+
Whether this job is a job button receiver
|
|
70
|
+
</span>
|
|
68
71
|
</label>
|
|
69
|
-
<span class="form-text">
|
|
70
|
-
Whether this job is a job button receiver
|
|
71
|
-
</span>
|
|
72
72
|
</div>
|
|
73
73
|
</div>
|
|
74
74
|
</div>
|
|
@@ -103,12 +103,15 @@
|
|
|
103
103
|
{{ block.super }}
|
|
104
104
|
{{ obj.job_class.properties_dict | json_script:"job_class_properties" }}
|
|
105
105
|
<script>
|
|
106
|
+
/*
|
|
107
|
+
* Because some of the form fields are Select2 widgets, we need to stick with jQuery here for now
|
|
108
|
+
*/
|
|
106
109
|
const job_class_properties = JSON.parse(document.getElementById("job_class_properties").textContent);
|
|
107
110
|
const description_default = $("#id_description").val();
|
|
108
|
-
|
|
111
|
+
/* All id_*_override fields */
|
|
109
112
|
$("[id^=id_][id$=_override]").change(function() {
|
|
110
113
|
const override_id = $(this).attr("id");
|
|
111
|
-
|
|
114
|
+
/* What's the form field this is an override for? */
|
|
112
115
|
const field_id = override_id.slice(0, -9);
|
|
113
116
|
const field = $("#" + field_id);
|
|
114
117
|
const field_name = field_id.slice(3);
|
|
@@ -116,32 +119,32 @@
|
|
|
116
119
|
field.attr("readonly", null);
|
|
117
120
|
field.prop("disabled", false);
|
|
118
121
|
} else {
|
|
119
|
-
|
|
122
|
+
/* Revert the field to its default value */
|
|
120
123
|
if (field.attr("type") == "checkbox") {
|
|
121
|
-
|
|
124
|
+
/* Do we have a job class object to derive properties from? */
|
|
122
125
|
if (job_class_properties != "") {
|
|
123
126
|
field.prop("checked", job_class_properties[field_name]);
|
|
124
127
|
} else {
|
|
125
|
-
|
|
128
|
+
/* No, we don't - it's probably not installed */
|
|
126
129
|
field.prop("checked", field.attr("checked"));
|
|
127
130
|
}
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
131
|
+
/*
|
|
132
|
+
* Checkboxes can't be "readonly" in HTML :-(
|
|
133
|
+
* Note that "disabled" fields aren't included in form submission, so we have to be sure to
|
|
134
|
+
* re-enable them at form submission time.
|
|
135
|
+
*/
|
|
133
136
|
field.prop("disabled", true);
|
|
134
137
|
} else {
|
|
135
|
-
|
|
138
|
+
/* Do we have a job class object to derive properties from? */
|
|
136
139
|
if (job_class_properties != "") {
|
|
137
140
|
if (field_name != "job_queues" && field_name != "default_job_queue") {
|
|
138
141
|
field.val(job_class_properties[field_name]);
|
|
139
142
|
}
|
|
140
143
|
} else if (field_name != "description") {
|
|
141
|
-
|
|
144
|
+
/* No, we don't - it's probably not installed */
|
|
142
145
|
field.val(field.attr("value"));
|
|
143
146
|
} else {
|
|
144
|
-
|
|
147
|
+
/* Textarea fields don't have a "value" attribute */
|
|
145
148
|
field.val(description_default);
|
|
146
149
|
}
|
|
147
150
|
if (field_name == "job_queues" || field_name == "default_job_queue") {
|
|
@@ -154,7 +157,10 @@
|
|
|
154
157
|
});
|
|
155
158
|
$("[id^=id_][id$=_override]").change();
|
|
156
159
|
|
|
157
|
-
|
|
160
|
+
/*
|
|
161
|
+
* As mentioned above, we need to re-enable all checkboxes, job_queues and default_job_queue fields
|
|
162
|
+
* on form submission so they get included
|
|
163
|
+
*/
|
|
158
164
|
$("form").submit(function() {
|
|
159
165
|
$('input[type="checkbox"]:disabled').each(function() {
|
|
160
166
|
$(this).prop("disabled", false);
|
|
@@ -3,12 +3,22 @@
|
|
|
3
3
|
|
|
4
4
|
{% block extra_styles %}
|
|
5
5
|
<style>
|
|
6
|
+
tr a.job_run {
|
|
7
|
+
display: inline-flex;
|
|
8
|
+
gap: 0.625rem; /* 10px */
|
|
9
|
+
}
|
|
10
|
+
|
|
6
11
|
tr a.job_run .btn {
|
|
7
|
-
|
|
12
|
+
align-self: flex-start;
|
|
13
|
+
margin-block: -0.09375rem; /* -1.5px */
|
|
8
14
|
}
|
|
9
15
|
|
|
10
|
-
tr
|
|
11
|
-
|
|
16
|
+
tr :last-child {
|
|
17
|
+
margin-bottom: 0;
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
tr.disabled td {
|
|
21
|
+
color: var(--bs-secondary-color);
|
|
12
22
|
}
|
|
13
23
|
|
|
14
24
|
tr.disabled a.job_run {
|
|
@@ -17,19 +27,27 @@
|
|
|
17
27
|
}
|
|
18
28
|
|
|
19
29
|
tr.disabled a.job_run .btn {
|
|
20
|
-
cursor:
|
|
30
|
+
cursor: inherit;
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
tr.disabled p {
|
|
34
|
+
color: inherit;
|
|
21
35
|
}
|
|
22
36
|
</style>
|
|
23
37
|
{% endblock %}
|
|
24
38
|
|
|
25
39
|
{% block buttons %}
|
|
26
|
-
<div class="btn-group">
|
|
27
|
-
<a
|
|
28
|
-
|
|
40
|
+
<div class="btn-group" role="group">
|
|
41
|
+
<a href="{% django_querystring display='list' %}"
|
|
42
|
+
class="btn btn-primary{% if display == 'list' %} bg-primary nb-text-body-bg{% endif %}">
|
|
43
|
+
<span class="mdi mdi-view-sequential" aria-hidden="true"></span> List
|
|
29
44
|
</a>
|
|
30
|
-
|
|
31
|
-
|
|
45
|
+
{# djlint:off B123 #}
|
|
46
|
+
<a href="{% django_querystring display='tiles' %}"
|
|
47
|
+
class="btn btn-primary{% if display == 'tiles' %} bg-primary nb-text-body-bg{% endif %}">
|
|
48
|
+
<span class="mdi mdi-view-grid" aria-hidden="true"></span> Tiles
|
|
32
49
|
</a>
|
|
50
|
+
{# djlint:on B123 #}
|
|
33
51
|
</div>
|
|
34
52
|
|
|
35
53
|
<button
|
|
@@ -38,22 +56,8 @@
|
|
|
38
56
|
data-nb-toggle="collapse-all"
|
|
39
57
|
data-nb-target="#job_accordion .collapse"
|
|
40
58
|
type="button"
|
|
41
|
-
{% if display == "tiles" %}disabled
|
|
59
|
+
{% if display == "tiles" %}disabled{% endif %}
|
|
42
60
|
>
|
|
43
|
-
Collapse All
|
|
61
|
+
Collapse All Groups
|
|
44
62
|
</button>
|
|
45
63
|
{% endblock %}
|
|
46
|
-
|
|
47
|
-
{% block javascript %}
|
|
48
|
-
{{ block.super }}
|
|
49
|
-
<script>
|
|
50
|
-
document.addEventListener('DOMContentLoaded', () => {
|
|
51
|
-
// Set display anchor links without losing other potentially active query params such as applied filters.
|
|
52
|
-
[...document.querySelectorAll('.set-job_list-display')].forEach((button) => {
|
|
53
|
-
const queryParams = new URLSearchParams(window.location.search);
|
|
54
|
-
queryParams.set('display', button.dataset.display);
|
|
55
|
-
button.setAttribute('href', `?${queryParams.toString()}`);
|
|
56
|
-
});
|
|
57
|
-
});
|
|
58
|
-
</script>
|
|
59
|
-
{% endblock %}
|
|
@@ -60,18 +60,14 @@
|
|
|
60
60
|
{% block document_title %}{% render_title "plain" %}{% endblock %}
|
|
61
61
|
|
|
62
62
|
{% block content %}
|
|
63
|
-
<div class="row d-print-none">
|
|
63
|
+
<div class="row d-print-none mb-16">
|
|
64
64
|
<div class="col-lg-12">
|
|
65
|
-
|
|
65
|
+
<div class="float-end">
|
|
66
|
+
<a class="btn btn-primary" href="{% url 'apps:apps_list' %}">See Installed Apps</a>
|
|
67
|
+
</div>
|
|
66
68
|
</div>
|
|
67
69
|
</div>
|
|
68
70
|
|
|
69
|
-
<div class="float-end d-print-none">
|
|
70
|
-
<a class="btn btn-primary" href="{% url 'apps:apps_list' %}">See Installed Apps</a>
|
|
71
|
-
</div>
|
|
72
|
-
|
|
73
|
-
<h1>{% block page_heading %}{% render_title %}{% endblock page_heading %}</h1>
|
|
74
|
-
|
|
75
71
|
<div class="row">
|
|
76
72
|
<div class="col-lg-12">
|
|
77
73
|
<section class="nb-tiles">
|
|
@@ -119,7 +115,7 @@
|
|
|
119
115
|
{% if app.docs|default:None != None %}
|
|
120
116
|
<a href="{{ app.docs }}" class="btn btn-info btn-sm" target="_blank" data-bs-title="Docs">
|
|
121
117
|
{% else %}
|
|
122
|
-
<a
|
|
118
|
+
<a aria-disabled="true" class="btn btn-info btn-sm disabled" data-bs-title="No docs provided">
|
|
123
119
|
{% endif %}
|
|
124
120
|
<span class="mdi mdi-book-open-page-variant"></span>
|
|
125
121
|
</a>
|
|
@@ -8,7 +8,7 @@
|
|
|
8
8
|
<div class="card">
|
|
9
9
|
<div class="card-header">
|
|
10
10
|
<strong>Rendered Context</strong>
|
|
11
|
-
{% include 'extras/inc/configcontext_format.html' %}
|
|
11
|
+
{% include 'extras/inc/configcontext_format.html' with data_format=format %}
|
|
12
12
|
</div>
|
|
13
13
|
<div class="card-body">
|
|
14
14
|
{% include 'extras/inc/json_data.html' with data=rendered_context format=format %}
|
|
@@ -7,8 +7,8 @@
|
|
|
7
7
|
{% block content %}
|
|
8
8
|
<div class="alert alert-warning">
|
|
9
9
|
Dynamic group membership is cached for performance reasons, therefore this page may not always be up-to-date.
|
|
10
|
-
<br>You can refresh the membership of any specific group by
|
|
11
|
-
<a href="{% url 'extras:dynamicgroup_list' %}">Dynamic Groups list view</a
|
|
10
|
+
<br>You can refresh the membership of any specific group by accessing it from the list below or from the
|
|
11
|
+
<a href="{% url 'extras:dynamicgroup_list' %}">Dynamic Groups list view</a> and clicking the "Refresh Members" button.
|
|
12
12
|
<br>You can also refresh the membership of all groups by running the
|
|
13
13
|
<a href="{% url 'extras:job_run_by_class_path' class_path='nautobot.core.jobs.groups.RefreshDynamicGroupCaches' %}">Refresh Dynamic Group Caches job</a>.
|
|
14
14
|
</div>
|
|
@@ -4,36 +4,6 @@
|
|
|
4
4
|
|
|
5
5
|
{% block title %}{{ object }} - Change Log{% endblock %}
|
|
6
6
|
|
|
7
|
-
{% block header %}
|
|
8
|
-
<div class="row d-print-none">
|
|
9
|
-
<div class="col-md-8 col-lg-9">
|
|
10
|
-
<ol class="breadcrumb">
|
|
11
|
-
<li class="breadcrumb-item"><a href="{% url 'extras:objectchange_list' %}">Change Log</a></li>
|
|
12
|
-
{% if object.related_object.get_absolute_url %}
|
|
13
|
-
<li class="breadcrumb-item"><a href="{{ object.related_object.get_absolute_url }}changelog/">{{ object.related_object }}</a></li>
|
|
14
|
-
{% elif object.changed_object and object.changed_object.get_absolute_url %}
|
|
15
|
-
<li class="breadcrumb-item"><a href="{{ object.changed_object.get_absolute_url }}changelog/">{{ object.changed_object }}</a></li>
|
|
16
|
-
{% elif object.changed_object is not None %}
|
|
17
|
-
<li class="breadcrumb-item">{{ object.changed_object }}</li>
|
|
18
|
-
{% endif %}
|
|
19
|
-
<li class="breadcrumb-item">{{ object }}</li>
|
|
20
|
-
</ol>
|
|
21
|
-
</div>
|
|
22
|
-
<div class="col-md-4 col-lg-3">
|
|
23
|
-
<form action="{% url 'extras:objectchange_list' %}" method="get">
|
|
24
|
-
<div class="input-group">
|
|
25
|
-
<input type="text" name="q" class="form-control" placeholder="Search change logs" />
|
|
26
|
-
<span class="input-group-btn">
|
|
27
|
-
<button type="submit" class="btn btn-primary">
|
|
28
|
-
<span class="mdi mdi-magnify" aria-hidden="true"></span>
|
|
29
|
-
</button>
|
|
30
|
-
</span>
|
|
31
|
-
</div>
|
|
32
|
-
</form>
|
|
33
|
-
</div>
|
|
34
|
-
</div>
|
|
35
|
-
{% endblock %}
|
|
36
|
-
|
|
37
7
|
{% block content %}
|
|
38
8
|
<div class="row">
|
|
39
9
|
<div class="col-lg-5">
|
|
@@ -113,13 +83,25 @@
|
|
|
113
83
|
<div class="card">
|
|
114
84
|
<div class="card-header">
|
|
115
85
|
<strong>Difference</strong>
|
|
116
|
-
<div class="btn-group btn-group-
|
|
117
|
-
|
|
118
|
-
<
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
86
|
+
<div class="btn-group btn-group-sm float-end d-print-none" role="group">
|
|
87
|
+
{% if prev_change %}
|
|
88
|
+
<a href="{% url 'extras:objectchange' pk=prev_change.pk %}" class="btn btn-secondary">
|
|
89
|
+
<span class="mdi mdi-chevron-left" aria-hidden="true"></span> Previous
|
|
90
|
+
</a>
|
|
91
|
+
{% else %}
|
|
92
|
+
<a aria-disabled="true" class="btn btn-secondary disabled">
|
|
93
|
+
<span class="mdi mdi-chevron-left" aria-hidden="true"></span> Previous
|
|
94
|
+
</a>
|
|
95
|
+
{% endif %}
|
|
96
|
+
{% if next_change %}
|
|
97
|
+
<a href="{% url 'extras:objectchange' pk=next_change.pk %}" class="btn btn-secondary">
|
|
98
|
+
Next <span class="mdi mdi-chevron-right" aria-hidden="true"></span>
|
|
99
|
+
</a>
|
|
100
|
+
{% else %}
|
|
101
|
+
<a aria-disabled="true" class="btn btn-secondary disabled">
|
|
102
|
+
Next <span class="mdi mdi-chevron-right" aria-hidden="true"></span>
|
|
103
|
+
</a>
|
|
104
|
+
{% endif %}
|
|
123
105
|
</div>
|
|
124
106
|
</div>
|
|
125
107
|
<div class="card-body">
|
|
@@ -4,29 +4,34 @@
|
|
|
4
4
|
|
|
5
5
|
{% block breadcrumbs_wrapper %}{% render_breadcrumbs %}{% endblock breadcrumbs_wrapper %}
|
|
6
6
|
|
|
7
|
-
{% block header %}
|
|
8
|
-
<div class="float-end d-print-none">
|
|
9
|
-
{% block buttons %}
|
|
10
|
-
{% if app_data.home_url %}
|
|
11
|
-
<a href="{% url app_data.home_url %}" class="btn btn-primary">
|
|
12
|
-
<span class="mdi mdi-home"></span> App Home
|
|
13
|
-
</a>
|
|
14
|
-
{% endif %}
|
|
15
|
-
{% if app_data.config_url %}
|
|
16
|
-
<a href="{% url app_data.config_url %}" class="btn btn-warning">
|
|
17
|
-
<span class="mdi mdi-cog"></span> App Configuration
|
|
18
|
-
</a>
|
|
19
|
-
{% endif %}
|
|
20
|
-
{% if app_data.docs_url %}
|
|
21
|
-
<a href="{% url app_data.docs_url %}" class="btn btn-info">
|
|
22
|
-
<span class="mdi mdi-cog"></span> App Documentation
|
|
23
|
-
</a>
|
|
24
|
-
{% endif %}
|
|
25
|
-
{% endblock buttons %}
|
|
26
|
-
</div>
|
|
27
|
-
{% endblock header %}
|
|
7
|
+
{% block header %}{% endblock header %}
|
|
28
8
|
|
|
29
9
|
{% block content %}
|
|
10
|
+
|
|
11
|
+
<div class="row d-print-none mb-16">
|
|
12
|
+
<div class="col-lg-12">
|
|
13
|
+
<div class="float-end d-print-none">
|
|
14
|
+
{% block buttons %}
|
|
15
|
+
{% if app_data.home_url %}
|
|
16
|
+
<a href="{% url app_data.home_url %}" class="btn btn-primary">
|
|
17
|
+
<span class="mdi mdi-home"></span> App Home
|
|
18
|
+
</a>
|
|
19
|
+
{% endif %}
|
|
20
|
+
{% if app_data.config_url %}
|
|
21
|
+
<a href="{% url app_data.config_url %}" class="btn btn-warning">
|
|
22
|
+
<span class="mdi mdi-cog"></span> App Configuration
|
|
23
|
+
</a>
|
|
24
|
+
{% endif %}
|
|
25
|
+
{% if app_data.docs_url %}
|
|
26
|
+
<a href="{% url app_data.docs_url %}" class="btn btn-info">
|
|
27
|
+
<span class="mdi mdi-cog"></span> App Documentation
|
|
28
|
+
</a>
|
|
29
|
+
{% endif %}
|
|
30
|
+
{% endblock buttons %}
|
|
31
|
+
</div>
|
|
32
|
+
</div>
|
|
33
|
+
</div>
|
|
34
|
+
|
|
30
35
|
<div class="row">
|
|
31
36
|
<div class="col-lg-6">
|
|
32
37
|
{% block content_left_page %}
|
|
@@ -8,27 +8,26 @@
|
|
|
8
8
|
{% endblock %}
|
|
9
9
|
|
|
10
10
|
{% block content %}
|
|
11
|
-
<div class="row d-print-none">
|
|
11
|
+
<div class="row d-print-none mb-16">
|
|
12
12
|
<div class="col-lg-12">
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
13
|
+
<div class="float-end d-print-none">
|
|
14
|
+
<div class="btn-group" role="group">
|
|
15
|
+
<a href="{% django_querystring display='list' %}"
|
|
16
|
+
class="btn btn-primary{% if display == 'list' %} bg-primary nb-text-body-bg{% endif %}">
|
|
17
|
+
<span class="mdi mdi-view-sequential" aria-hidden="true"></span> List
|
|
18
|
+
</a>
|
|
19
|
+
{# djlint:off B123 #}
|
|
20
|
+
<a href="{% django_querystring display='tiles' %}"
|
|
21
|
+
class="btn btn-primary{% if display == 'tiles' %} bg-primary nb-text-body-bg{% endif %}">
|
|
22
|
+
<span class="mdi mdi-view-grid" aria-hidden="true"></span> Tiles
|
|
23
|
+
</a>
|
|
24
|
+
{# djlint:on B123 #}
|
|
25
|
+
</div>
|
|
16
26
|
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
<a class="btn btn-secondary set-apps-display" data-display="tiles" href="" title="Tiles">
|
|
20
|
-
<span class="mdi mdi-view-grid{% if display == "list" %}-outline{% endif %}"></span>
|
|
21
|
-
</a>
|
|
22
|
-
<a class="btn btn-secondary set-apps-display" data-display="list" href="" title="List">
|
|
23
|
-
<span class="mdi mdi-view-sequential{% if display == "tiles" %}-outline{% endif %}"></span>
|
|
24
|
-
</a>
|
|
27
|
+
<a class="btn btn-primary" href="{% url 'apps:apps_marketplace' %}">Visit Apps Marketplace</a>
|
|
28
|
+
</div>
|
|
25
29
|
</div>
|
|
26
|
-
|
|
27
|
-
<a class="btn btn-primary" href="{% url 'apps:apps_marketplace' %}">Visit Apps Marketplace</a>
|
|
28
30
|
</div>
|
|
29
|
-
|
|
30
|
-
<h1>{% block page_heading %}{% render_title %}{% endblock %}</h1>
|
|
31
|
-
|
|
32
31
|
<div class="row">
|
|
33
32
|
<div class="col-lg-12">
|
|
34
33
|
{% if filter_form %}
|
|
@@ -47,13 +46,4 @@
|
|
|
47
46
|
{% block javascript %}
|
|
48
47
|
{{ block.super }}
|
|
49
48
|
<script src="{% static 'js/tableconfig.js' %}"></script>
|
|
50
|
-
|
|
51
|
-
<script>
|
|
52
|
-
// Set display anchor links without losing other potentially active query params such as applied filters.
|
|
53
|
-
[...document.querySelectorAll('.set-apps-display')].forEach(button => {
|
|
54
|
-
const queryParams = new URLSearchParams(window.location.search);
|
|
55
|
-
queryParams.set('display', button.dataset.display);
|
|
56
|
-
button.setAttribute('href', `?${queryParams.toString()}`);
|
|
57
|
-
});
|
|
58
|
-
</script>
|
|
59
49
|
{% endblock %}
|
|
@@ -223,4 +223,68 @@
|
|
|
223
223
|
</div>
|
|
224
224
|
{% include 'inc/paginator.html' with paginator=vdc_table.paginator page=vdc_table.page %}
|
|
225
225
|
{% endif %}
|
|
226
|
+
{% if vpn_table %}
|
|
227
|
+
<div class="card">
|
|
228
|
+
<div class="card-header">
|
|
229
|
+
<strong>VPNs</strong>
|
|
230
|
+
</div>
|
|
231
|
+
{% include 'inc/table.html' with table=vpn_table %}
|
|
232
|
+
{% if perms.vpn.add_vpn %}
|
|
233
|
+
<div class="card-footer text-end d-print-none">
|
|
234
|
+
<a href="{% url 'vpn:vpn_add' %}?role={{ object.pk }}" class="btn btn-sm btn-primary">
|
|
235
|
+
<span class="mdi mdi-plus-thick" aria-hidden="true"></span> Add VPN
|
|
236
|
+
</a>
|
|
237
|
+
</div>
|
|
238
|
+
{% endif %}
|
|
239
|
+
</div>
|
|
240
|
+
{% include 'inc/paginator.html' with paginator=vpn_table.paginator page=vpn_table.page %}
|
|
241
|
+
{% endif %}
|
|
242
|
+
{% if vpn_profile_table %}
|
|
243
|
+
<div class="card">
|
|
244
|
+
<div class="card-header">
|
|
245
|
+
<strong>VPN Profiles</strong>
|
|
246
|
+
</div>
|
|
247
|
+
{% include 'inc/table.html' with table=vpn_profile_table %}
|
|
248
|
+
{% if perms.vpn.add_vpnprofile %}
|
|
249
|
+
<div class="card-footer text-end d-print-none">
|
|
250
|
+
<a href="{% url 'vpn:vpnprofile_add' %}?role={{ object.pk }}" class="btn btn-sm btn-primary">
|
|
251
|
+
<span class="mdi mdi-plus-thick" aria-hidden="true"></span> Add VPN Profile
|
|
252
|
+
</a>
|
|
253
|
+
</div>
|
|
254
|
+
{% endif %}
|
|
255
|
+
</div>
|
|
256
|
+
{% include 'inc/paginator.html' with paginator=vpn_profile_table.paginator page=vpn_profile_table.page %}
|
|
257
|
+
{% endif %}
|
|
258
|
+
{% if vpn_tunnel_table %}
|
|
259
|
+
<div class="card">
|
|
260
|
+
<div class="card-header">
|
|
261
|
+
<strong>VPN Tunnels</strong>
|
|
262
|
+
</div>
|
|
263
|
+
{% include 'inc/table.html' with table=vpn_tunnel_table %}
|
|
264
|
+
{% if perms.vpn.add_vpntunnel %}
|
|
265
|
+
<div class="card-footer text-end d-print-none">
|
|
266
|
+
<a href="{% url 'vpn:vpntunnel_add' %}?role={{ object.pk }}" class="btn btn-sm btn-primary">
|
|
267
|
+
<span class="mdi mdi-plus-thick" aria-hidden="true"></span> Add VPN Tunnel
|
|
268
|
+
</a>
|
|
269
|
+
</div>
|
|
270
|
+
{% endif %}
|
|
271
|
+
</div>
|
|
272
|
+
{% include 'inc/paginator.html' with paginator=vpn_tunnel_table.paginator page=vpn_tunnel_table.page %}
|
|
273
|
+
{% endif %}
|
|
274
|
+
{% if vpn_tunnel_endpoint_table %}
|
|
275
|
+
<div class="card">
|
|
276
|
+
<div class="card-header">
|
|
277
|
+
<strong>VPN Tunnel Endpoints</strong>
|
|
278
|
+
</div>
|
|
279
|
+
{% include 'inc/table.html' with table=vpn_tunnel_endpoint_table %}
|
|
280
|
+
{% if perms.vpn.add_vpntunnelendpoint %}
|
|
281
|
+
<div class="card-footer text-end d-print-none">
|
|
282
|
+
<a href="{% url 'vpn:vpntunnelendpoint_add' %}?role={{ object.pk }}" class="btn btn-sm btn-primary">
|
|
283
|
+
<span class="mdi mdi-plus-thick" aria-hidden="true"></span> Add VPN Tunnel Endpoint
|
|
284
|
+
</a>
|
|
285
|
+
</div>
|
|
286
|
+
{% endif %}
|
|
287
|
+
</div>
|
|
288
|
+
{% include 'inc/paginator.html' with paginator=vpn_tunnel_endpoint_table.paginator page=vpn_tunnel_endpoint_table.page %}
|
|
289
|
+
{% endif %}
|
|
226
290
|
{% endblock content_full_width_page %}
|
|
@@ -102,7 +102,8 @@
|
|
|
102
102
|
<td>
|
|
103
103
|
{{ object.start_time|timezone:object.time_zone|date:settings.SHORT_DATETIME_FORMAT }}
|
|
104
104
|
{% if default_time_zone != object.time_zone %}
|
|
105
|
-
|
|
105
|
+
{{ object.time_zone }}
|
|
106
|
+
<br>{{ object.start_time|timezone:default_time_zone|date:settings.SHORT_DATETIME_FORMAT }} {{ default_time_zone }}
|
|
106
107
|
{% endif %}
|
|
107
108
|
</td>
|
|
108
109
|
</tr>
|
|
@@ -112,7 +113,8 @@
|
|
|
112
113
|
{% if object.last_run_at %}
|
|
113
114
|
{{ object.last_run_at|timezone:object.time_zone|date:settings.SHORT_DATETIME_FORMAT }}
|
|
114
115
|
{% if default_time_zone != object.time_zone %}
|
|
115
|
-
|
|
116
|
+
{{ object.time_zone }}
|
|
117
|
+
<br>{{ object.last_run_at|timezone:default_time_zone|date:settings.SHORT_DATETIME_FORMAT }} {{ default_time_zone }}
|
|
116
118
|
{% endif %}
|
|
117
119
|
{% else %}
|
|
118
120
|
{{ object.last_run_at|placeholder }}
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
{% extends "
|
|
1
|
+
{% extends "generic/object_retrieve.html" %}
|
|
2
2
|
{% comment %}3.0 TODO: remove this template, which only exists for backward compatibility with 2.4 and earlier{% endcomment %}
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
{% extends '
|
|
1
|
+
{% extends 'generic/object_retrieve.html' %}
|
|
2
2
|
{% comment %}3.0 TODO: remove this template, which only exists for backward compatibility with 2.4 and earlier{% endcomment %}
|