nautobot 2.4.17__py3-none-any.whl → 2.4.19__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.

Files changed (627) hide show
  1. nautobot/apps/ui.py +6 -0
  2. nautobot/apps/views.py +2 -0
  3. nautobot/circuits/tables.py +1 -1
  4. nautobot/circuits/templates/circuits/circuit_create.html +7 -7
  5. nautobot/circuits/templates/circuits/circuit_retrieve.html +1 -5
  6. nautobot/circuits/templates/circuits/circuittermination_create.html +26 -26
  7. nautobot/circuits/templates/circuits/circuittermination_retrieve.html +1 -8
  8. nautobot/circuits/templates/circuits/inc/circuit_termination.html +20 -20
  9. nautobot/circuits/templates/circuits/inc/circuit_termination_header_extra_content.html +3 -3
  10. nautobot/circuits/templates/circuits/inc/circuit_termination_speed_fragment.html +9 -0
  11. nautobot/circuits/templates/circuits/providernetwork_retrieve.html +1 -3
  12. nautobot/circuits/tests/integration/test_circuit.py +2 -2
  13. nautobot/circuits/views.py +49 -15
  14. nautobot/cloud/templates/cloud/cloudaccount_retrieve.html +1 -4
  15. nautobot/cloud/templates/cloud/cloudnetwork_retrieve.html +1 -7
  16. nautobot/cloud/templates/cloud/cloudresourcetype_retrieve.html +1 -3
  17. nautobot/cloud/templates/cloud/cloudservice_retrieve.html +1 -5
  18. nautobot/cloud/views.py +45 -0
  19. nautobot/core/filters.py +2 -2
  20. nautobot/core/graphql/generators.py +5 -2
  21. nautobot/core/jobs/bulk_actions.py +48 -85
  22. nautobot/core/models/querysets.py +2 -1
  23. nautobot/core/settings.py +1 -0
  24. nautobot/core/settings.yaml +9 -0
  25. nautobot/core/tables.py +21 -23
  26. nautobot/core/templates/40x.html +15 -15
  27. nautobot/core/templates/500.html +21 -21
  28. nautobot/core/templates/admin/app_index.html +8 -8
  29. nautobot/core/templates/admin/base.html +104 -104
  30. nautobot/core/templates/admin/change_form.html +65 -65
  31. nautobot/core/templates/admin/change_list.html +60 -60
  32. nautobot/core/templates/admin/change_list_results.html +39 -39
  33. nautobot/core/templates/admin/config/config.html +47 -47
  34. nautobot/core/templates/admin/delete_confirmation.html +47 -47
  35. nautobot/core/templates/admin/edit_inline/stacked.html +124 -124
  36. nautobot/core/templates/admin/edit_inline/tabular.html +60 -60
  37. nautobot/core/templates/admin/includes/fieldset.html +4 -4
  38. nautobot/core/templates/admin/index.html +60 -60
  39. nautobot/core/templates/admin/prepopulated_fields_js.html +18 -18
  40. nautobot/core/templates/admin/submit_line.html +4 -4
  41. nautobot/core/templates/base_django.html +46 -46
  42. nautobot/core/templates/buttons/consolidated_bulk_action_buttons.html +8 -8
  43. nautobot/core/templates/buttons/consolidated_detail_view_action_buttons.html +8 -8
  44. nautobot/core/templates/buttons/export.html +3 -3
  45. nautobot/core/templates/components/breadcrumbs.html +19 -0
  46. nautobot/core/templates/components/button/default.html +3 -3
  47. nautobot/core/templates/components/button/dropdown.html +7 -7
  48. nautobot/core/templates/components/button/formbutton.html +4 -4
  49. nautobot/core/templates/components/panel/body_content_data_table.html +1 -1
  50. nautobot/core/templates/components/panel/body_wrapper_generic_table.html +3 -0
  51. nautobot/core/templates/components/panel/footer_content_table.html +3 -1
  52. nautobot/core/templates/components/panel/header_extra_content_table.html +10 -1
  53. nautobot/core/templates/components/tab/content_wrapper.html +1 -1
  54. nautobot/core/templates/components/tab/label_wrapper.html +1 -1
  55. nautobot/core/templates/components/tab/label_wrapper_distinct_view.html +10 -3
  56. nautobot/core/templates/generic/object_bulk_add_component.html +40 -40
  57. nautobot/core/templates/generic/object_bulk_create.html +3 -3
  58. nautobot/core/templates/generic/object_bulk_destroy.html +6 -6
  59. nautobot/core/templates/generic/object_bulk_update.html +52 -52
  60. nautobot/core/templates/generic/object_changelog.html +0 -2
  61. nautobot/core/templates/generic/object_import.html +33 -33
  62. nautobot/core/templates/generic/object_list.html +271 -268
  63. nautobot/core/templates/generic/object_notes.html +0 -2
  64. nautobot/core/templates/generic/object_retrieve.html +264 -257
  65. nautobot/core/templates/graphene/graphiql.html +127 -127
  66. nautobot/core/templates/home.html +62 -62
  67. nautobot/core/templates/inc/computed_fields/panel_data.html +13 -13
  68. nautobot/core/templates/inc/created_updated.html +8 -8
  69. nautobot/core/templates/inc/custom_fields/panel_data.html +13 -13
  70. nautobot/core/templates/inc/dynamic_groups_panel.html +11 -11
  71. nautobot/core/templates/inc/footer.html +19 -19
  72. nautobot/core/templates/inc/javascript.html +1 -1
  73. nautobot/core/templates/inc/media.html +46 -46
  74. nautobot/core/templates/inc/nav_menu.html +1 -1
  75. nautobot/core/templates/inc/relationships_table_rows.html +22 -22
  76. nautobot/core/templates/inc/tenant_table_row.html +1 -1
  77. nautobot/core/templates/login.html +77 -77
  78. nautobot/core/templates/media_failure.html +38 -38
  79. nautobot/core/templates/panel_table.html +1 -1
  80. nautobot/core/templates/rest_framework/api.html +3 -3
  81. nautobot/core/templates/search.html +1 -1
  82. nautobot/core/templates/swagger_ui.html +9 -9
  83. nautobot/core/templates/utilities/confirmation_form.html +18 -18
  84. nautobot/core/templates/utilities/render_field.html +1 -1
  85. nautobot/core/templates/utilities/render_jinja2.html +43 -43
  86. nautobot/core/templates/utilities/templatetags/filter_form_modal.html +56 -56
  87. nautobot/core/templates/utilities/templatetags/utilization_graph.html +1 -1
  88. nautobot/core/templates/utilities/theme_preview.html +799 -799
  89. nautobot/core/templates/utilities/worker_status.html +122 -122
  90. nautobot/core/templates/widgets/clearable_file.html +3 -3
  91. nautobot/core/templates/widgets/sluginput.html +1 -1
  92. nautobot/core/templatetags/buttons.py +8 -2
  93. nautobot/core/templatetags/helpers.py +24 -0
  94. nautobot/core/templatetags/ui_framework.py +40 -5
  95. nautobot/core/testing/filters.py +37 -21
  96. nautobot/core/testing/integration.py +7 -4
  97. nautobot/core/testing/views.py +49 -5
  98. nautobot/core/tests/test_breadcrumbs.py +78 -4
  99. nautobot/core/tests/test_commands.py +7 -4
  100. nautobot/core/tests/test_graphql.py +20 -5
  101. nautobot/core/tests/test_jobs.py +34 -21
  102. nautobot/core/tests/test_tables.py +43 -6
  103. nautobot/core/tests/test_templatetags_ui_framework.py +146 -0
  104. nautobot/core/tests/test_titles.py +2 -2
  105. nautobot/core/tests/test_ui.py +188 -1
  106. nautobot/core/tests/test_utils.py +35 -0
  107. nautobot/core/tests/test_views.py +45 -0
  108. nautobot/core/tests/test_views_generic.py +43 -0
  109. nautobot/core/tests/test_views_utils.py +239 -5
  110. nautobot/core/ui/breadcrumbs.py +220 -28
  111. nautobot/core/ui/bulk_buttons.py +8 -0
  112. nautobot/core/ui/object_detail.py +181 -60
  113. nautobot/core/ui/titles.py +10 -5
  114. nautobot/core/utils/requests.py +27 -2
  115. nautobot/core/views/__init__.py +24 -3
  116. nautobot/core/views/generic.py +70 -35
  117. nautobot/core/views/mixins.py +226 -122
  118. nautobot/core/views/utils.py +270 -1
  119. nautobot/dcim/api/serializers.py +8 -2
  120. nautobot/dcim/constants.py +1 -0
  121. nautobot/dcim/factory.py +4 -3
  122. nautobot/dcim/filters/mixins.py +1 -2
  123. nautobot/dcim/forms.py +5 -1
  124. nautobot/dcim/migrations/0074_alter_rack_u_height.py +21 -0
  125. nautobot/dcim/models/devices.py +30 -1
  126. nautobot/dcim/models/racks.py +2 -2
  127. nautobot/dcim/tables/__init__.py +2 -0
  128. nautobot/dcim/tables/devices.py +24 -0
  129. nautobot/dcim/tables/power.py +2 -2
  130. nautobot/dcim/templates/dcim/cable.html +53 -53
  131. nautobot/dcim/templates/dcim/cable_connect.html +182 -182
  132. nautobot/dcim/templates/dcim/cable_trace.html +1 -1
  133. nautobot/dcim/templates/dcim/console_port_connection_list.html +5 -5
  134. nautobot/dcim/templates/dcim/consoleport.html +86 -86
  135. nautobot/dcim/templates/dcim/consoleserverport.html +86 -86
  136. nautobot/dcim/templates/dcim/controller_create.html +34 -34
  137. nautobot/dcim/templates/dcim/controllermanageddevicegroup_create.html +68 -68
  138. nautobot/dcim/templates/dcim/device/base.html +1 -114
  139. nautobot/dcim/templates/dcim/device/config.html +17 -17
  140. nautobot/dcim/templates/dcim/device/consoleports.html +1 -52
  141. nautobot/dcim/templates/dcim/device/consoleserverports.html +1 -52
  142. nautobot/dcim/templates/dcim/device/devicebays.html +1 -48
  143. nautobot/dcim/templates/dcim/device/frontports.html +1 -52
  144. nautobot/dcim/templates/dcim/device/interfaces.html +1 -56
  145. nautobot/dcim/templates/dcim/device/inventory.html +1 -48
  146. nautobot/dcim/templates/dcim/device/lldp_neighbors.html +64 -64
  147. nautobot/dcim/templates/dcim/device/modulebays.html +1 -48
  148. nautobot/dcim/templates/dcim/device/poweroutlets.html +1 -52
  149. nautobot/dcim/templates/dcim/device/powerports.html +1 -52
  150. nautobot/dcim/templates/dcim/device/rearports.html +1 -52
  151. nautobot/dcim/templates/dcim/device/status.html +66 -66
  152. nautobot/dcim/templates/dcim/device/wireless.html +1 -72
  153. nautobot/dcim/templates/dcim/device.html +4 -422
  154. nautobot/dcim/templates/dcim/device_component.html +0 -19
  155. nautobot/dcim/templates/dcim/device_component_add.html +25 -25
  156. nautobot/dcim/templates/dcim/device_create.html +229 -0
  157. nautobot/dcim/templates/dcim/device_edit.html +2 -227
  158. nautobot/dcim/templates/dcim/devicebay.html +41 -41
  159. nautobot/dcim/templates/dcim/devicebay_populate.html +32 -32
  160. nautobot/dcim/templates/dcim/devicetype_component_add.html +28 -28
  161. nautobot/dcim/templates/dcim/devicetype_retrieve.html +1 -3
  162. nautobot/dcim/templates/dcim/frontport.html +84 -84
  163. nautobot/dcim/templates/dcim/inc/cable_toggle_buttons.html +1 -1
  164. nautobot/dcim/templates/dcim/inc/device_interface_filter.html +8 -0
  165. nautobot/dcim/templates/dcim/inc/device_napalm_tabs.html +1 -15
  166. nautobot/dcim/templates/dcim/inc/location_hierarchy.html +22 -22
  167. nautobot/dcim/templates/dcim/interface.html +206 -206
  168. nautobot/dcim/templates/dcim/interface_connection_list.html +5 -5
  169. nautobot/dcim/templates/dcim/interfaceredundancygroupassociation_create.html +6 -6
  170. nautobot/dcim/templates/dcim/inventoryitem.html +44 -44
  171. nautobot/dcim/templates/dcim/inventoryitem_add.html +32 -32
  172. nautobot/dcim/templates/dcim/inventoryitem_edit.html +22 -22
  173. nautobot/dcim/templates/dcim/location_migrate_data_to_contact.html +46 -46
  174. nautobot/dcim/templates/dcim/location_retrieve.html +1 -7
  175. nautobot/dcim/templates/dcim/locationtype.html +1 -6
  176. nautobot/dcim/templates/dcim/locationtype_retrieve.html +1 -7
  177. nautobot/dcim/templates/dcim/module/base.html +85 -85
  178. nautobot/dcim/templates/dcim/module_interfaces.html +1 -1
  179. nautobot/dcim/templates/dcim/module_modulebays.html +1 -1
  180. nautobot/dcim/templates/dcim/module_retrieve.html +52 -52
  181. nautobot/dcim/templates/dcim/module_update.html +61 -61
  182. nautobot/dcim/templates/dcim/modulebay_destroy.html +1 -1
  183. nautobot/dcim/templates/dcim/modulebay_retrieve.html +83 -99
  184. nautobot/dcim/templates/dcim/modulebay_update.html +33 -33
  185. nautobot/dcim/templates/dcim/modulefamily_retrieve.html +1 -1
  186. nautobot/dcim/templates/dcim/moduletype_retrieve.html +140 -144
  187. nautobot/dcim/templates/dcim/platform_create.html +38 -38
  188. nautobot/dcim/templates/dcim/power_port_connection_list.html +5 -5
  189. nautobot/dcim/templates/dcim/powerfeed_retrieve.html +1 -8
  190. nautobot/dcim/templates/dcim/poweroutlet.html +85 -85
  191. nautobot/dcim/templates/dcim/powerpanel_retrieve.html +1 -8
  192. nautobot/dcim/templates/dcim/powerport.html +91 -91
  193. nautobot/dcim/templates/dcim/rack_elevation_list.html +18 -18
  194. nautobot/dcim/templates/dcim/rack_retrieve.html +264 -274
  195. nautobot/dcim/templates/dcim/rackreservation_retrieve.html +0 -3
  196. nautobot/dcim/templates/dcim/rearport.html +78 -78
  197. nautobot/dcim/templates/dcim/virtualchassis_retrieve.html +1 -50
  198. nautobot/dcim/templates/dcim/virtualdevicecontext_retrieve.html +1 -5
  199. nautobot/dcim/tests/integration/test_device_bulk_operations.py +3 -2
  200. nautobot/dcim/tests/integration/test_location_bulk_operations.py +6 -2
  201. nautobot/dcim/tests/test_api.py +33 -1
  202. nautobot/dcim/tests/test_views.py +189 -4
  203. nautobot/dcim/ui.py +29 -0
  204. nautobot/dcim/urls.py +1 -109
  205. nautobot/dcim/utils.py +30 -0
  206. nautobot/dcim/views.py +1149 -550
  207. nautobot/extras/filters/mixins.py +1 -1
  208. nautobot/extras/forms/forms.py +15 -0
  209. nautobot/extras/models/groups.py +10 -1
  210. nautobot/extras/models/jobs.py +2 -2
  211. nautobot/extras/plugins/views.py +18 -5
  212. nautobot/extras/tables.py +24 -2
  213. nautobot/extras/templates/extras/computedfield_edit.html +4 -4
  214. nautobot/extras/templates/extras/configcontext_update.html +1 -1
  215. nautobot/extras/templates/extras/configcontextschema_retrieve.html +32 -32
  216. nautobot/extras/templates/extras/customfield_retrieve.html +1 -128
  217. nautobot/extras/templates/extras/customfield_update.html +23 -23
  218. nautobot/extras/templates/extras/dynamicgroup.html +2 -99
  219. nautobot/extras/templates/extras/dynamicgroup_edit.html +2 -199
  220. nautobot/extras/templates/extras/dynamicgroup_retrieve.html +99 -0
  221. nautobot/extras/templates/extras/dynamicgroup_update.html +199 -0
  222. nautobot/extras/templates/extras/gitrepository.html +2 -82
  223. nautobot/extras/templates/extras/gitrepository_list.html +10 -10
  224. nautobot/extras/templates/extras/gitrepository_object_edit.html +2 -13
  225. nautobot/extras/templates/extras/gitrepository_retrieve.html +82 -0
  226. nautobot/extras/templates/extras/gitrepository_update.html +13 -0
  227. nautobot/extras/templates/extras/graphqlquery_retrieve.html +73 -73
  228. nautobot/extras/templates/extras/inc/configcontext_format.html +2 -2
  229. nautobot/extras/templates/extras/inc/job_table.html +10 -10
  230. nautobot/extras/templates/extras/inc/jobresult.html +21 -21
  231. nautobot/extras/templates/extras/inc/jobresult_js.html +6 -6
  232. nautobot/extras/templates/extras/inc/tags_panel.html +10 -10
  233. nautobot/extras/templates/extras/job.html +64 -64
  234. nautobot/extras/templates/extras/job_approval_request.html +9 -9
  235. nautobot/extras/templates/extras/job_bulk_edit.html +13 -13
  236. nautobot/extras/templates/extras/job_edit.html +45 -45
  237. nautobot/extras/templates/extras/job_list.html +4 -4
  238. nautobot/extras/templates/extras/jobresult_retrieve.html +0 -25
  239. nautobot/extras/templates/extras/marketplace.html +101 -101
  240. nautobot/extras/templates/extras/metadatatype_create.html +20 -20
  241. nautobot/extras/templates/extras/note_retrieve.html +0 -52
  242. nautobot/extras/templates/extras/object_assign_contact_or_team.html +18 -18
  243. nautobot/extras/templates/extras/object_configcontext.html +1 -3
  244. nautobot/extras/templates/extras/objectchange.html +2 -165
  245. nautobot/extras/templates/extras/objectchange_retrieve.html +165 -0
  246. nautobot/extras/templates/extras/plugin_detail.html +44 -48
  247. nautobot/extras/templates/extras/plugins_list.html +9 -11
  248. nautobot/extras/templates/extras/plugins_tiles.html +26 -26
  249. nautobot/extras/templates/extras/relationship_edit.html +4 -4
  250. nautobot/extras/templates/extras/role_retrieve.html +13 -13
  251. nautobot/extras/templates/extras/scheduled_jobs_approval_queue_list.html +21 -21
  252. nautobot/extras/templates/extras/scheduledjob.html +128 -128
  253. nautobot/extras/templates/extras/secret_create.html +53 -53
  254. nautobot/extras/templates/extras/secretsgroup_update.html +13 -13
  255. nautobot/extras/templates/extras/templatetags/plugin_object_detail_tabs.html +3 -3
  256. nautobot/extras/templates/extras/webhook.html +79 -79
  257. nautobot/extras/tests/integration/test_relationships.py +6 -6
  258. nautobot/extras/tests/test_dynamicgroups.py +73 -18
  259. nautobot/extras/tests/test_filters.py +1 -1
  260. nautobot/extras/tests/test_jobs.py +2 -0
  261. nautobot/extras/tests/test_views.py +8 -3
  262. nautobot/extras/urls.py +3 -97
  263. nautobot/extras/views.py +524 -456
  264. nautobot/ipam/filters.py +2 -2
  265. nautobot/ipam/migrations/0053_alter_vrfdeviceassignment_options_and_more.py +20 -0
  266. nautobot/ipam/models.py +34 -0
  267. nautobot/ipam/querysets.py +3 -3
  268. nautobot/ipam/signals.py +6 -1
  269. nautobot/ipam/tables.py +3 -1
  270. nautobot/ipam/templates/ipam/inc/prefix_header_extra_content_table.html +4 -0
  271. nautobot/ipam/templates/ipam/inc/toggle_available.html +8 -8
  272. nautobot/ipam/templates/ipam/inc/vlangroup_header.html +4 -4
  273. nautobot/ipam/templates/ipam/ipaddress.html +119 -123
  274. nautobot/ipam/templates/ipam/ipaddress_assign.html +10 -10
  275. nautobot/ipam/templates/ipam/ipaddress_edit.html +1 -1
  276. nautobot/ipam/templates/ipam/ipaddress_merge.html +180 -180
  277. nautobot/ipam/templates/ipam/ipaddresstointerface_retrieve.html +48 -48
  278. nautobot/ipam/templates/ipam/prefix.html +2 -115
  279. nautobot/ipam/templates/ipam/prefix_create.html +34 -0
  280. nautobot/ipam/templates/ipam/prefix_edit.html +1 -34
  281. nautobot/ipam/templates/ipam/prefix_retrieve.html +3 -0
  282. nautobot/ipam/templates/ipam/service_retrieve.html +1 -6
  283. nautobot/ipam/templates/ipam/vlan_retrieve.html +1 -7
  284. nautobot/ipam/templates/ipam/vrf_edit.html +1 -1
  285. nautobot/ipam/tests/test_api.py +5 -0
  286. nautobot/ipam/tests/test_models.py +387 -0
  287. nautobot/ipam/tests/test_querysets.py +46 -0
  288. nautobot/ipam/tests/test_views.py +34 -0
  289. nautobot/ipam/ui.py +145 -0
  290. nautobot/ipam/urls.py +1 -46
  291. nautobot/ipam/utils/__init__.py +26 -0
  292. nautobot/ipam/utils/migrations.py +1 -1
  293. nautobot/ipam/views.py +234 -112
  294. nautobot/project-static/docs/404.html +11 -11
  295. nautobot/project-static/docs/apps/index.html +11 -11
  296. nautobot/project-static/docs/apps/nautobot-apps.html +11 -11
  297. nautobot/project-static/docs/assets/javascripts/{bundle.92b07e13.min.js → bundle.f55a23d4.min.js} +2 -2
  298. nautobot/project-static/docs/assets/javascripts/{bundle.92b07e13.min.js.map → bundle.f55a23d4.min.js.map} +2 -2
  299. nautobot/project-static/docs/assets/stylesheets/{main.7e37652d.min.css → main.e53b48f4.min.css} +1 -1
  300. nautobot/project-static/docs/assets/stylesheets/{main.7e37652d.min.css.map → main.e53b48f4.min.css.map} +1 -1
  301. nautobot/project-static/docs/code-reference/nautobot/apps/__init__.html +11 -11
  302. nautobot/project-static/docs/code-reference/nautobot/apps/admin.html +11 -11
  303. nautobot/project-static/docs/code-reference/nautobot/apps/api.html +11 -11
  304. nautobot/project-static/docs/code-reference/nautobot/apps/change_logging.html +11 -11
  305. nautobot/project-static/docs/code-reference/nautobot/apps/choices.html +11 -11
  306. nautobot/project-static/docs/code-reference/nautobot/apps/config.html +11 -11
  307. nautobot/project-static/docs/code-reference/nautobot/apps/constants.html +11 -11
  308. nautobot/project-static/docs/code-reference/nautobot/apps/datasources.html +11 -11
  309. nautobot/project-static/docs/code-reference/nautobot/apps/events.html +11 -11
  310. nautobot/project-static/docs/code-reference/nautobot/apps/exceptions.html +11 -11
  311. nautobot/project-static/docs/code-reference/nautobot/apps/factory.html +11 -11
  312. nautobot/project-static/docs/code-reference/nautobot/apps/filters.html +11 -11
  313. nautobot/project-static/docs/code-reference/nautobot/apps/forms.html +11 -11
  314. nautobot/project-static/docs/code-reference/nautobot/apps/graphql.html +11 -11
  315. nautobot/project-static/docs/code-reference/nautobot/apps/jobs.html +11 -11
  316. nautobot/project-static/docs/code-reference/nautobot/apps/models.html +11 -11
  317. nautobot/project-static/docs/code-reference/nautobot/apps/querysets.html +11 -11
  318. nautobot/project-static/docs/code-reference/nautobot/apps/secrets.html +11 -11
  319. nautobot/project-static/docs/code-reference/nautobot/apps/tables.html +11 -11
  320. nautobot/project-static/docs/code-reference/nautobot/apps/testing.html +83 -11
  321. nautobot/project-static/docs/code-reference/nautobot/apps/ui.html +1265 -281
  322. nautobot/project-static/docs/code-reference/nautobot/apps/urls.html +11 -11
  323. nautobot/project-static/docs/code-reference/nautobot/apps/utils.html +12 -12
  324. nautobot/project-static/docs/code-reference/nautobot/apps/views.html +452 -29
  325. nautobot/project-static/docs/development/apps/api/configuration-view.html +11 -11
  326. nautobot/project-static/docs/development/apps/api/database-backend-config.html +11 -11
  327. nautobot/project-static/docs/development/apps/api/models/django-admin.html +11 -11
  328. nautobot/project-static/docs/development/apps/api/models/global-search.html +11 -11
  329. nautobot/project-static/docs/development/apps/api/models/graphql.html +11 -11
  330. nautobot/project-static/docs/development/apps/api/models/index.html +11 -11
  331. nautobot/project-static/docs/development/apps/api/nautobot-app-config.html +12 -12
  332. nautobot/project-static/docs/development/apps/api/platform-features/custom-validators.html +11 -11
  333. nautobot/project-static/docs/development/apps/api/platform-features/filter-extensions.html +11 -11
  334. nautobot/project-static/docs/development/apps/api/platform-features/git-repository-content.html +11 -11
  335. nautobot/project-static/docs/development/apps/api/platform-features/index.html +11 -11
  336. nautobot/project-static/docs/development/apps/api/platform-features/jinja2-filters.html +11 -11
  337. nautobot/project-static/docs/development/apps/api/platform-features/jobs.html +11 -11
  338. nautobot/project-static/docs/development/apps/api/platform-features/prepopulating-data.html +11 -11
  339. nautobot/project-static/docs/development/apps/api/platform-features/secrets-providers.html +11 -11
  340. nautobot/project-static/docs/development/apps/api/platform-features/table-extensions.html +11 -11
  341. nautobot/project-static/docs/development/apps/api/platform-features/uniquely-identify-objects.html +11 -11
  342. nautobot/project-static/docs/development/apps/api/prometheus.html +11 -11
  343. nautobot/project-static/docs/development/apps/api/setup.html +11 -11
  344. nautobot/project-static/docs/development/apps/api/testing.html +11 -11
  345. nautobot/project-static/docs/development/apps/api/ui-extensions/banners.html +11 -11
  346. nautobot/project-static/docs/development/apps/api/ui-extensions/home-page.html +11 -11
  347. nautobot/project-static/docs/development/apps/api/ui-extensions/index.html +11 -11
  348. nautobot/project-static/docs/development/apps/api/ui-extensions/navigation.html +11 -11
  349. nautobot/project-static/docs/development/apps/api/ui-extensions/object-views.html +11 -11
  350. nautobot/project-static/docs/development/apps/api/views/base-template.html +11 -11
  351. nautobot/project-static/docs/development/apps/api/views/core-view-overrides.html +11 -11
  352. nautobot/project-static/docs/development/apps/api/views/django-generic-views.html +11 -11
  353. nautobot/project-static/docs/development/apps/api/views/help-documentation.html +11 -11
  354. nautobot/project-static/docs/development/apps/api/views/index.html +11 -11
  355. nautobot/project-static/docs/development/apps/api/views/nautobot-generic-views.html +11 -11
  356. nautobot/project-static/docs/development/apps/api/views/nautobotuiviewset.html +11 -11
  357. nautobot/project-static/docs/development/apps/api/views/nautobotuiviewsetrouter.html +11 -11
  358. nautobot/project-static/docs/development/apps/api/views/notes.html +11 -11
  359. nautobot/project-static/docs/development/apps/api/views/rest-api.html +11 -11
  360. nautobot/project-static/docs/development/apps/api/views/urls.html +11 -11
  361. nautobot/project-static/docs/development/apps/index.html +11 -11
  362. nautobot/project-static/docs/development/apps/migration/code-updates.html +11 -11
  363. nautobot/project-static/docs/development/apps/migration/dependency-updates.html +11 -11
  364. nautobot/project-static/docs/development/apps/migration/from-v1.html +11 -11
  365. nautobot/project-static/docs/development/apps/migration/model-updates/dcim.html +11 -11
  366. nautobot/project-static/docs/development/apps/migration/model-updates/extras.html +11 -11
  367. nautobot/project-static/docs/development/apps/migration/model-updates/global.html +11 -11
  368. nautobot/project-static/docs/development/apps/migration/model-updates/ipam.html +11 -11
  369. nautobot/project-static/docs/development/apps/migration/ui-component-framework/best-practices.html +11 -11
  370. nautobot/project-static/docs/development/apps/migration/ui-component-framework/breadcrumbs-titles.html +11 -11
  371. nautobot/project-static/docs/development/apps/migration/ui-component-framework/custom-content.html +11 -11
  372. nautobot/project-static/docs/development/apps/migration/ui-component-framework/index.html +11 -11
  373. nautobot/project-static/docs/development/apps/migration/ui-component-framework/migration-steps.html +11 -11
  374. nautobot/project-static/docs/development/apps/porting-from-netbox.html +11 -11
  375. nautobot/project-static/docs/development/core/application-registry.html +11 -11
  376. nautobot/project-static/docs/development/core/best-practices.html +11 -11
  377. nautobot/project-static/docs/development/core/bootstrap-ui.html +11 -11
  378. nautobot/project-static/docs/development/core/caching.html +11 -11
  379. nautobot/project-static/docs/development/core/controllers.html +11 -11
  380. nautobot/project-static/docs/development/core/docker-compose-advanced-use-cases.html +11 -11
  381. nautobot/project-static/docs/development/core/generic-views.html +11 -11
  382. nautobot/project-static/docs/development/core/getting-started.html +50 -63
  383. nautobot/project-static/docs/development/core/homepage.html +11 -11
  384. nautobot/project-static/docs/development/core/index.html +11 -11
  385. nautobot/project-static/docs/development/core/minikube-dev-environment-for-k8s-jobs.html +11 -11
  386. nautobot/project-static/docs/development/core/model-checklist.html +11 -11
  387. nautobot/project-static/docs/development/core/model-features.html +11 -11
  388. nautobot/project-static/docs/development/core/natural-keys.html +11 -11
  389. nautobot/project-static/docs/development/core/navigation-menu.html +11 -11
  390. nautobot/project-static/docs/development/core/release-checklist.html +11 -11
  391. nautobot/project-static/docs/development/core/role-internals.html +11 -11
  392. nautobot/project-static/docs/development/core/settings.html +11 -11
  393. nautobot/project-static/docs/development/core/style-guide.html +15 -11
  394. nautobot/project-static/docs/development/core/templates.html +11 -11
  395. nautobot/project-static/docs/development/core/testing.html +11 -11
  396. nautobot/project-static/docs/development/core/ui-component-framework.html +17 -22
  397. nautobot/project-static/docs/development/core/user-preferences.html +11 -11
  398. nautobot/project-static/docs/development/index.html +11 -11
  399. nautobot/project-static/docs/development/jobs/getting-started.html +11 -11
  400. nautobot/project-static/docs/development/jobs/index.html +11 -11
  401. nautobot/project-static/docs/development/jobs/installation.html +11 -11
  402. nautobot/project-static/docs/development/jobs/job-extensions.html +11 -11
  403. nautobot/project-static/docs/development/jobs/job-logging.html +11 -11
  404. nautobot/project-static/docs/development/jobs/job-patterns.html +11 -11
  405. nautobot/project-static/docs/development/jobs/job-structure.html +11 -11
  406. nautobot/project-static/docs/development/jobs/migration/from-v1.html +11 -11
  407. nautobot/project-static/docs/development/jobs/testing.html +11 -11
  408. nautobot/project-static/docs/index.html +11 -11
  409. nautobot/project-static/docs/objects.inv +0 -0
  410. nautobot/project-static/docs/overview/application_stack.html +11 -11
  411. nautobot/project-static/docs/overview/design_philosophy.html +11 -11
  412. nautobot/project-static/docs/release-notes/index.html +11 -11
  413. nautobot/project-static/docs/release-notes/version-1.0.html +11 -11
  414. nautobot/project-static/docs/release-notes/version-1.1.html +11 -11
  415. nautobot/project-static/docs/release-notes/version-1.2.html +11 -11
  416. nautobot/project-static/docs/release-notes/version-1.3.html +11 -11
  417. nautobot/project-static/docs/release-notes/version-1.4.html +11 -11
  418. nautobot/project-static/docs/release-notes/version-1.5.html +11 -11
  419. nautobot/project-static/docs/release-notes/version-1.6.html +11 -11
  420. nautobot/project-static/docs/release-notes/version-2.0.html +11 -11
  421. nautobot/project-static/docs/release-notes/version-2.1.html +11 -11
  422. nautobot/project-static/docs/release-notes/version-2.2.html +11 -11
  423. nautobot/project-static/docs/release-notes/version-2.3.html +11 -11
  424. nautobot/project-static/docs/release-notes/version-2.4.html +418 -11
  425. nautobot/project-static/docs/search/search_index.json +1 -1
  426. nautobot/project-static/docs/sitemap.xml +300 -300
  427. nautobot/project-static/docs/sitemap.xml.gz +0 -0
  428. nautobot/project-static/docs/user-guide/administration/configuration/authentication/ldap.html +11 -11
  429. nautobot/project-static/docs/user-guide/administration/configuration/authentication/remote.html +11 -11
  430. nautobot/project-static/docs/user-guide/administration/configuration/authentication/sso.html +11 -11
  431. nautobot/project-static/docs/user-guide/administration/configuration/index.html +11 -11
  432. nautobot/project-static/docs/user-guide/administration/configuration/redis.html +11 -11
  433. nautobot/project-static/docs/user-guide/administration/configuration/settings.html +38 -11
  434. nautobot/project-static/docs/user-guide/administration/configuration/time-zones.html +11 -11
  435. nautobot/project-static/docs/user-guide/administration/guides/celery-queues.html +89 -14
  436. nautobot/project-static/docs/user-guide/administration/guides/docker.html +11 -11
  437. nautobot/project-static/docs/user-guide/administration/guides/health-checks.html +11 -11
  438. nautobot/project-static/docs/user-guide/administration/guides/permissions.html +11 -11
  439. nautobot/project-static/docs/user-guide/administration/guides/prometheus-metrics.html +11 -11
  440. nautobot/project-static/docs/user-guide/administration/guides/replicating-nautobot.html +11 -11
  441. nautobot/project-static/docs/user-guide/administration/guides/request-profiling.html +11 -11
  442. nautobot/project-static/docs/user-guide/administration/guides/s3-django-storage.html +11 -11
  443. nautobot/project-static/docs/user-guide/administration/guides/selinux-troubleshooting.html +11 -11
  444. nautobot/project-static/docs/user-guide/administration/installation/app-install.html +11 -11
  445. nautobot/project-static/docs/user-guide/administration/installation/external-authentication.html +11 -11
  446. nautobot/project-static/docs/user-guide/administration/installation/http-server.html +11 -11
  447. nautobot/project-static/docs/user-guide/administration/installation/index.html +11 -11
  448. nautobot/project-static/docs/user-guide/administration/installation/install_system.html +11 -11
  449. nautobot/project-static/docs/user-guide/administration/installation/nautobot.html +11 -11
  450. nautobot/project-static/docs/user-guide/administration/installation/services.html +11 -11
  451. nautobot/project-static/docs/user-guide/administration/migration/migrating-from-netbox.html +11 -11
  452. nautobot/project-static/docs/user-guide/administration/migration/migrating-from-postgresql.html +11 -11
  453. nautobot/project-static/docs/user-guide/administration/security/index.html +11 -11
  454. nautobot/project-static/docs/user-guide/administration/security/notices.html +11 -11
  455. nautobot/project-static/docs/user-guide/administration/tools/nautobot-server.html +11 -11
  456. nautobot/project-static/docs/user-guide/administration/tools/nautobot-shell.html +11 -11
  457. nautobot/project-static/docs/user-guide/administration/upgrading/database-backup.html +11 -11
  458. nautobot/project-static/docs/user-guide/administration/upgrading/from-v1/ipam/after-you-upgrade.html +11 -11
  459. nautobot/project-static/docs/user-guide/administration/upgrading/from-v1/ipam/before-you-upgrade.html +11 -11
  460. nautobot/project-static/docs/user-guide/administration/upgrading/from-v1/ipam/for-developers.html +11 -11
  461. nautobot/project-static/docs/user-guide/administration/upgrading/from-v1/ipam/index.html +11 -11
  462. nautobot/project-static/docs/user-guide/administration/upgrading/from-v1/ipam/whats-changed.html +11 -11
  463. nautobot/project-static/docs/user-guide/administration/upgrading/from-v1/region-and-site-data-migration-guide.html +11 -11
  464. nautobot/project-static/docs/user-guide/administration/upgrading/from-v1/upgrading-from-nautobot-v1.html +11 -11
  465. nautobot/project-static/docs/user-guide/administration/upgrading/upgrading.html +11 -11
  466. nautobot/project-static/docs/user-guide/core-data-model/circuits/circuit.html +11 -11
  467. nautobot/project-static/docs/user-guide/core-data-model/circuits/circuittermination.html +11 -11
  468. nautobot/project-static/docs/user-guide/core-data-model/circuits/circuittype.html +11 -11
  469. nautobot/project-static/docs/user-guide/core-data-model/circuits/provider.html +11 -11
  470. nautobot/project-static/docs/user-guide/core-data-model/circuits/providernetwork.html +11 -11
  471. nautobot/project-static/docs/user-guide/core-data-model/cloud/cloud.html +11 -11
  472. nautobot/project-static/docs/user-guide/core-data-model/cloud/cloudaccount.html +11 -11
  473. nautobot/project-static/docs/user-guide/core-data-model/cloud/cloudnetwork.html +11 -11
  474. nautobot/project-static/docs/user-guide/core-data-model/cloud/cloudnetworkprefixassignment.html +11 -11
  475. nautobot/project-static/docs/user-guide/core-data-model/cloud/cloudresourcetype.html +11 -11
  476. nautobot/project-static/docs/user-guide/core-data-model/cloud/cloudservice.html +11 -11
  477. nautobot/project-static/docs/user-guide/core-data-model/cloud/cloudservicenetworkassignment.html +11 -11
  478. nautobot/project-static/docs/user-guide/core-data-model/dcim/cable.html +11 -11
  479. nautobot/project-static/docs/user-guide/core-data-model/dcim/consoleport.html +11 -11
  480. nautobot/project-static/docs/user-guide/core-data-model/dcim/consoleporttemplate.html +11 -11
  481. nautobot/project-static/docs/user-guide/core-data-model/dcim/consoleserverport.html +11 -11
  482. nautobot/project-static/docs/user-guide/core-data-model/dcim/consoleserverporttemplate.html +11 -11
  483. nautobot/project-static/docs/user-guide/core-data-model/dcim/controller.html +11 -11
  484. nautobot/project-static/docs/user-guide/core-data-model/dcim/controllermanageddevicegroup.html +11 -11
  485. nautobot/project-static/docs/user-guide/core-data-model/dcim/device.html +11 -11
  486. nautobot/project-static/docs/user-guide/core-data-model/dcim/devicebay.html +11 -11
  487. nautobot/project-static/docs/user-guide/core-data-model/dcim/devicebaytemplate.html +11 -11
  488. nautobot/project-static/docs/user-guide/core-data-model/dcim/devicefamily.html +11 -11
  489. nautobot/project-static/docs/user-guide/core-data-model/dcim/deviceredundancygroup.html +11 -11
  490. nautobot/project-static/docs/user-guide/core-data-model/dcim/devicetype.html +11 -11
  491. nautobot/project-static/docs/user-guide/core-data-model/dcim/frontport.html +11 -11
  492. nautobot/project-static/docs/user-guide/core-data-model/dcim/frontporttemplate.html +11 -11
  493. nautobot/project-static/docs/user-guide/core-data-model/dcim/interface.html +11 -11
  494. nautobot/project-static/docs/user-guide/core-data-model/dcim/interfaceredundancygroup.html +11 -11
  495. nautobot/project-static/docs/user-guide/core-data-model/dcim/interfacetemplate.html +11 -11
  496. nautobot/project-static/docs/user-guide/core-data-model/dcim/inventoryitem.html +11 -11
  497. nautobot/project-static/docs/user-guide/core-data-model/dcim/location.html +11 -11
  498. nautobot/project-static/docs/user-guide/core-data-model/dcim/locationtype.html +11 -11
  499. nautobot/project-static/docs/user-guide/core-data-model/dcim/manufacturer.html +11 -11
  500. nautobot/project-static/docs/user-guide/core-data-model/dcim/module.html +11 -11
  501. nautobot/project-static/docs/user-guide/core-data-model/dcim/modulebay.html +11 -11
  502. nautobot/project-static/docs/user-guide/core-data-model/dcim/modulebaytemplate.html +11 -11
  503. nautobot/project-static/docs/user-guide/core-data-model/dcim/modulefamily.html +11 -11
  504. nautobot/project-static/docs/user-guide/core-data-model/dcim/moduletype.html +11 -11
  505. nautobot/project-static/docs/user-guide/core-data-model/dcim/platform.html +11 -11
  506. nautobot/project-static/docs/user-guide/core-data-model/dcim/powerfeed.html +11 -11
  507. nautobot/project-static/docs/user-guide/core-data-model/dcim/poweroutlet.html +11 -11
  508. nautobot/project-static/docs/user-guide/core-data-model/dcim/poweroutlettemplate.html +11 -11
  509. nautobot/project-static/docs/user-guide/core-data-model/dcim/powerpanel.html +11 -11
  510. nautobot/project-static/docs/user-guide/core-data-model/dcim/powerport.html +11 -11
  511. nautobot/project-static/docs/user-guide/core-data-model/dcim/powerporttemplate.html +11 -11
  512. nautobot/project-static/docs/user-guide/core-data-model/dcim/rack.html +11 -11
  513. nautobot/project-static/docs/user-guide/core-data-model/dcim/rackgroup.html +11 -11
  514. nautobot/project-static/docs/user-guide/core-data-model/dcim/rackreservation.html +11 -11
  515. nautobot/project-static/docs/user-guide/core-data-model/dcim/rearport.html +11 -11
  516. nautobot/project-static/docs/user-guide/core-data-model/dcim/rearporttemplate.html +11 -11
  517. nautobot/project-static/docs/user-guide/core-data-model/dcim/softwareimagefile.html +11 -11
  518. nautobot/project-static/docs/user-guide/core-data-model/dcim/softwareversion.html +11 -11
  519. nautobot/project-static/docs/user-guide/core-data-model/dcim/virtualchassis.html +11 -11
  520. nautobot/project-static/docs/user-guide/core-data-model/dcim/virtualdevicecontext.html +11 -11
  521. nautobot/project-static/docs/user-guide/core-data-model/extras/configcontext.html +11 -11
  522. nautobot/project-static/docs/user-guide/core-data-model/extras/configcontextschema.html +11 -11
  523. nautobot/project-static/docs/user-guide/core-data-model/extras/contact.html +11 -11
  524. nautobot/project-static/docs/user-guide/core-data-model/extras/team.html +11 -11
  525. nautobot/project-static/docs/user-guide/core-data-model/ipam/ipaddress.html +11 -11
  526. nautobot/project-static/docs/user-guide/core-data-model/ipam/namespace.html +11 -11
  527. nautobot/project-static/docs/user-guide/core-data-model/ipam/prefix.html +11 -11
  528. nautobot/project-static/docs/user-guide/core-data-model/ipam/rir.html +11 -11
  529. nautobot/project-static/docs/user-guide/core-data-model/ipam/routetarget.html +11 -11
  530. nautobot/project-static/docs/user-guide/core-data-model/ipam/service.html +11 -11
  531. nautobot/project-static/docs/user-guide/core-data-model/ipam/vlan.html +11 -11
  532. nautobot/project-static/docs/user-guide/core-data-model/ipam/vlangroup.html +11 -11
  533. nautobot/project-static/docs/user-guide/core-data-model/ipam/vrf.html +11 -11
  534. nautobot/project-static/docs/user-guide/core-data-model/overview/introduction.html +11 -11
  535. nautobot/project-static/docs/user-guide/core-data-model/tenancy/tenant.html +11 -11
  536. nautobot/project-static/docs/user-guide/core-data-model/tenancy/tenantgroup.html +11 -11
  537. nautobot/project-static/docs/user-guide/core-data-model/virtualization/cluster.html +11 -11
  538. nautobot/project-static/docs/user-guide/core-data-model/virtualization/clustergroup.html +11 -11
  539. nautobot/project-static/docs/user-guide/core-data-model/virtualization/clustertype.html +11 -11
  540. nautobot/project-static/docs/user-guide/core-data-model/virtualization/virtualmachine.html +11 -11
  541. nautobot/project-static/docs/user-guide/core-data-model/virtualization/vminterface.html +11 -11
  542. nautobot/project-static/docs/user-guide/core-data-model/wireless/index.html +11 -11
  543. nautobot/project-static/docs/user-guide/core-data-model/wireless/radioprofile.html +11 -11
  544. nautobot/project-static/docs/user-guide/core-data-model/wireless/supporteddatarate.html +11 -11
  545. nautobot/project-static/docs/user-guide/core-data-model/wireless/wirelessnetwork.html +11 -11
  546. nautobot/project-static/docs/user-guide/feature-guides/contacts-and-teams.html +11 -11
  547. nautobot/project-static/docs/user-guide/feature-guides/custom-fields.html +11 -11
  548. nautobot/project-static/docs/user-guide/feature-guides/getting-started/creating-devices.html +11 -11
  549. nautobot/project-static/docs/user-guide/feature-guides/getting-started/creating-location-types-and-locations.html +11 -11
  550. nautobot/project-static/docs/user-guide/feature-guides/getting-started/index.html +11 -11
  551. nautobot/project-static/docs/user-guide/feature-guides/getting-started/interfaces.html +11 -11
  552. nautobot/project-static/docs/user-guide/feature-guides/getting-started/ipam.html +11 -11
  553. nautobot/project-static/docs/user-guide/feature-guides/getting-started/platforms.html +11 -11
  554. nautobot/project-static/docs/user-guide/feature-guides/getting-started/search-bar.html +11 -11
  555. nautobot/project-static/docs/user-guide/feature-guides/getting-started/tenants.html +11 -11
  556. nautobot/project-static/docs/user-guide/feature-guides/getting-started/vlans-and-vlan-groups.html +11 -11
  557. nautobot/project-static/docs/user-guide/feature-guides/git-data-source.html +11 -11
  558. nautobot/project-static/docs/user-guide/feature-guides/graphql.html +11 -11
  559. nautobot/project-static/docs/user-guide/feature-guides/ip-address-merge-tool.html +11 -11
  560. nautobot/project-static/docs/user-guide/feature-guides/relationships.html +11 -11
  561. nautobot/project-static/docs/user-guide/feature-guides/software-image-files-and-versions.html +11 -11
  562. nautobot/project-static/docs/user-guide/feature-guides/wireless-networks-and-controllers.html +11 -11
  563. nautobot/project-static/docs/user-guide/index.html +11 -11
  564. nautobot/project-static/docs/user-guide/platform-functionality/change-logging.html +11 -11
  565. nautobot/project-static/docs/user-guide/platform-functionality/computedfield.html +11 -11
  566. nautobot/project-static/docs/user-guide/platform-functionality/customfield.html +11 -11
  567. nautobot/project-static/docs/user-guide/platform-functionality/customlink.html +11 -11
  568. nautobot/project-static/docs/user-guide/platform-functionality/dynamicgroup.html +11 -11
  569. nautobot/project-static/docs/user-guide/platform-functionality/events.html +11 -11
  570. nautobot/project-static/docs/user-guide/platform-functionality/exporttemplate.html +11 -11
  571. nautobot/project-static/docs/user-guide/platform-functionality/externalintegration.html +11 -11
  572. nautobot/project-static/docs/user-guide/platform-functionality/gitrepository.html +11 -11
  573. nautobot/project-static/docs/user-guide/platform-functionality/graphql.html +11 -11
  574. nautobot/project-static/docs/user-guide/platform-functionality/graphqlquery.html +11 -11
  575. nautobot/project-static/docs/user-guide/platform-functionality/imageattachment.html +11 -11
  576. nautobot/project-static/docs/user-guide/platform-functionality/jobs/index.html +11 -11
  577. nautobot/project-static/docs/user-guide/platform-functionality/jobs/job-scheduling-and-approvals.html +11 -11
  578. nautobot/project-static/docs/user-guide/platform-functionality/jobs/jobbutton.html +11 -11
  579. nautobot/project-static/docs/user-guide/platform-functionality/jobs/jobhook.html +11 -11
  580. nautobot/project-static/docs/user-guide/platform-functionality/jobs/jobqueue.html +11 -11
  581. nautobot/project-static/docs/user-guide/platform-functionality/jobs/kubernetes-job-support.html +11 -11
  582. nautobot/project-static/docs/user-guide/platform-functionality/jobs/managing-jobs.html +11 -11
  583. nautobot/project-static/docs/user-guide/platform-functionality/jobs/models.html +11 -11
  584. nautobot/project-static/docs/user-guide/platform-functionality/napalm.html +11 -11
  585. nautobot/project-static/docs/user-guide/platform-functionality/note.html +11 -11
  586. nautobot/project-static/docs/user-guide/platform-functionality/objectmetadata.html +11 -11
  587. nautobot/project-static/docs/user-guide/platform-functionality/relationship.html +11 -11
  588. nautobot/project-static/docs/user-guide/platform-functionality/rendering-jinja-templates.html +11 -11
  589. nautobot/project-static/docs/user-guide/platform-functionality/rest-api/authentication.html +11 -11
  590. nautobot/project-static/docs/user-guide/platform-functionality/rest-api/filtering.html +11 -11
  591. nautobot/project-static/docs/user-guide/platform-functionality/rest-api/overview.html +11 -11
  592. nautobot/project-static/docs/user-guide/platform-functionality/rest-api/ui-related-endpoints.html +11 -11
  593. nautobot/project-static/docs/user-guide/platform-functionality/role.html +11 -11
  594. nautobot/project-static/docs/user-guide/platform-functionality/savedview.html +11 -11
  595. nautobot/project-static/docs/user-guide/platform-functionality/secret.html +11 -11
  596. nautobot/project-static/docs/user-guide/platform-functionality/staticgroupassociation.html +11 -11
  597. nautobot/project-static/docs/user-guide/platform-functionality/status.html +11 -11
  598. nautobot/project-static/docs/user-guide/platform-functionality/tag.html +11 -11
  599. nautobot/project-static/docs/user-guide/platform-functionality/template-filters.html +11 -11
  600. nautobot/project-static/docs/user-guide/platform-functionality/users/objectpermission.html +11 -11
  601. nautobot/project-static/docs/user-guide/platform-functionality/users/token.html +11 -11
  602. nautobot/project-static/docs/user-guide/platform-functionality/webhook.html +11 -11
  603. nautobot/project-static/img/nautobot_icon.svg +32 -34
  604. nautobot/project-static/js/table_sorting_indicator.js +0 -2
  605. nautobot/tenancy/templates/tenancy/tenant.html +1 -7
  606. nautobot/tenancy/views.py +13 -0
  607. nautobot/users/templates/users/api_tokens.html +4 -4
  608. nautobot/users/templates/users/base.html +28 -28
  609. nautobot/virtualization/templates/virtualization/cluster.html +64 -64
  610. nautobot/virtualization/templates/virtualization/inc/virtualmachine_vminterface_filter.html +8 -0
  611. nautobot/virtualization/templates/virtualization/virtualmachine_component_add.html +25 -25
  612. nautobot/virtualization/templates/virtualization/virtualmachine_retrieve.html +1 -251
  613. nautobot/virtualization/templates/virtualization/vminterface.html +70 -70
  614. nautobot/virtualization/urls.py +0 -12
  615. nautobot/virtualization/views.py +158 -54
  616. nautobot/wireless/templates/wireless/wirelessnetwork_create.html +13 -13
  617. nautobot/wireless/tests/integration/test_radio_profile.py +1 -1
  618. {nautobot-2.4.17.dist-info → nautobot-2.4.19.dist-info}/METADATA +4 -4
  619. {nautobot-2.4.17.dist-info → nautobot-2.4.19.dist-info}/RECORD +623 -607
  620. nautobot/core/templates/inc/breadcrumbs.html +0 -14
  621. nautobot/ipam/templates/ipam/prefix_ipaddresses.html +0 -11
  622. nautobot/ipam/templates/ipam/prefix_prefixes.html +0 -11
  623. nautobot/project-static/docs/requirements.txt +0 -14
  624. {nautobot-2.4.17.dist-info → nautobot-2.4.19.dist-info}/LICENSE.txt +0 -0
  625. {nautobot-2.4.17.dist-info → nautobot-2.4.19.dist-info}/NOTICE +0 -0
  626. {nautobot-2.4.17.dist-info → nautobot-2.4.19.dist-info}/WHEEL +0 -0
  627. {nautobot-2.4.17.dist-info → nautobot-2.4.19.dist-info}/entry_points.txt +0 -0
@@ -1,25 +1,44 @@
1
1
  import datetime
2
2
  from io import BytesIO
3
+ import logging
3
4
  import urllib.parse
4
5
 
6
+ from django.conf import settings
5
7
  from django.contrib import messages
8
+ from django.core.cache import cache
6
9
  from django.core.exceptions import FieldError, ValidationError
7
10
  from django.db.models import ForeignKey
8
11
  from django.utils.html import format_html, format_html_join
9
12
  from django.utils.safestring import mark_safe
10
13
  from django_tables2 import RequestConfig
14
+ from prometheus_client import REGISTRY
15
+ from prometheus_client.utils import floatToGoString
11
16
  from rest_framework import exceptions, serializers
12
17
 
13
18
  from nautobot.core.api.fields import ChoiceField, ContentTypeField, TimeZoneSerializerField
14
19
  from nautobot.core.api.parsers import NautobotCSVParser
15
20
  from nautobot.core.models.utils import is_taggable
21
+ from nautobot.core.utils import lookup
16
22
  from nautobot.core.utils.data import is_uuid
17
23
  from nautobot.core.utils.filtering import get_filter_field_label
18
- from nautobot.core.utils.lookup import get_created_and_last_updated_usernames_for_model, get_form_for_model
24
+ from nautobot.core.utils.lookup import (
25
+ get_created_and_last_updated_usernames_for_model,
26
+ get_filterset_for_model,
27
+ get_form_for_model,
28
+ get_view_for_model,
29
+ )
30
+ from nautobot.core.utils.requests import normalize_querydict
19
31
  from nautobot.core.views.paginator import EnhancedPaginator, get_paginate_count
20
32
  from nautobot.extras.models import SavedView
21
33
  from nautobot.extras.tables import AssociatedContactsTable, DynamicGroupTable, ObjectMetadataTable
22
34
 
35
+ logger = logging.getLogger(__name__)
36
+
37
+ METRICS_CACHE_KEY = "nautobot_app_metrics_cache"
38
+ always_generated_metrics = [
39
+ "nautobot_app_metrics_processing_ms" # Always generate this metric to track the processing time of Nautobot App metrics, improved with caching.
40
+ ]
41
+
23
42
 
24
43
  def check_filter_for_display(filters, field_name, values):
25
44
  """
@@ -399,3 +418,253 @@ def get_saved_views_for_user(user, list_url):
399
418
  return shared_saved_views | user_owned_saved_views
400
419
 
401
420
  return shared_saved_views
421
+
422
+
423
+ def is_metrics_experimental_caching_enabled():
424
+ """Return True if METRICS_EXPERIMENTAL_CACHING_DURATION is set to a positive integer."""
425
+ return settings.METRICS_EXPERIMENTAL_CACHING_DURATION > 0
426
+
427
+
428
+ def generate_latest_with_cache(registry=REGISTRY):
429
+ """A vendored version of prometheus_client.generate_latest that caches Nautobot App metrics."""
430
+
431
+ def sample_line(line):
432
+ if line.labels:
433
+ labelstr = "{{{0}}}".format(
434
+ ",".join(
435
+ [
436
+ '{}="{}"'.format(k, v.replace("\\", r"\\").replace("\n", r"\n").replace('"', r"\""))
437
+ for k, v in sorted(line.labels.items())
438
+ ]
439
+ )
440
+ )
441
+ else:
442
+ labelstr = ""
443
+ timestamp = ""
444
+ if line.timestamp is not None:
445
+ # Convert to milliseconds.
446
+ timestamp = f" {int(float(line.timestamp) * 1000):d}"
447
+ return f"{line.name}{labelstr} {floatToGoString(line.value)}{timestamp}\n"
448
+
449
+ cached_lines = []
450
+ output = []
451
+ # NOTE: In the original prometheus_client code the lines are written to output directly,
452
+ # here we are going to cache some lines so we need to build each metric's output separately.
453
+ # So instead of `output.append(line)` we do
454
+ # `this_metric_output.append(line)` and then `output.extend(this_metric_output)`
455
+ for metric in registry.collect():
456
+ this_metric_output = []
457
+ try:
458
+ mname = metric.name
459
+ mtype = metric.type
460
+ # Munging from OpenMetrics into Prometheus format.
461
+ if mtype == "counter":
462
+ mname = mname + "_total"
463
+ elif mtype == "info":
464
+ mname = mname + "_info"
465
+ mtype = "gauge"
466
+ elif mtype == "stateset":
467
+ mtype = "gauge"
468
+ elif mtype == "gaugehistogram":
469
+ # A gauge histogram is really a gauge,
470
+ # but this captures the structure better.
471
+ mtype = "histogram"
472
+ elif mtype == "unknown":
473
+ mtype = "untyped"
474
+
475
+ this_metric_output.append(
476
+ "# HELP {} {}\n".format(mname, metric.documentation.replace("\\", r"\\").replace("\n", r"\n"))
477
+ )
478
+ this_metric_output.append(f"# TYPE {mname} {mtype}\n")
479
+
480
+ om_samples = {}
481
+ for s in metric.samples:
482
+ for suffix in ["_created", "_gsum", "_gcount"]:
483
+ if s.name == metric.name + suffix:
484
+ # OpenMetrics specific sample, put in a gauge at the end.
485
+ om_samples.setdefault(suffix, []).append(sample_line(s))
486
+ break
487
+ else:
488
+ this_metric_output.append(sample_line(s))
489
+ except Exception as exception:
490
+ exception.args = (exception.args or ("",)) + (metric,)
491
+ raise
492
+
493
+ for suffix, lines in sorted(om_samples.items()):
494
+ this_metric_output.append(
495
+ "# HELP {}{} {}\n".format(
496
+ metric.name, suffix, metric.documentation.replace("\\", r"\\").replace("\n", r"\n")
497
+ )
498
+ )
499
+ this_metric_output.append(f"# TYPE {metric.name}{suffix} gauge\n")
500
+ this_metric_output.extend(lines)
501
+
502
+ # BEGIN Nautobot-specific logic
503
+ # If the metric name starts with nautobot_, we cache the lines
504
+ if metric.name.startswith("nautobot_") and metric.name not in always_generated_metrics:
505
+ cached_lines.extend(this_metric_output)
506
+ # END Nautobot-specific logic
507
+
508
+ # Always add the metric output to the final output
509
+ output.extend(this_metric_output)
510
+
511
+ # BEGIN Nautobot-specific logic
512
+ # Add in any previously cached metrics.
513
+ # Note that this is mutually-exclusive with the above block, that is to say,
514
+ # either cached_lines will be populated OR collector.local_cache will be populated,
515
+ # never both at the same time.
516
+ for collector in registry._collector_to_names:
517
+ # This is to avoid a race condition where between the time to collect the metrics and
518
+ # the time to generate the output, the cache is expired and we miss some metrics.
519
+ if hasattr(collector, "local_cache") and collector.local_cache:
520
+ output.extend(collector.local_cache)
521
+ del collector.local_cache # avoid re-using stale data on next call
522
+
523
+ # If we have any cached lines, and the cache is empty or expired, update the cache.
524
+ if cached_lines and not cache.get(METRICS_CACHE_KEY):
525
+ cache.set(METRICS_CACHE_KEY, cached_lines, timeout=settings.METRICS_EXPERIMENTAL_CACHING_DURATION)
526
+ # END Nautobot-specific logic
527
+
528
+ return "".join(output).encode("utf-8")
529
+
530
+
531
+ def get_bulk_queryset_from_view(
532
+ user, content_type, filter_query_params, pk_list, saved_view_id, action, delete_all=None, edit_all=None, log=None
533
+ ):
534
+ """
535
+ Return a queryset for bulk operations based on the provided parameters.
536
+
537
+ Args:
538
+ user: The user performing the bulk operation.
539
+ model: The model class on which the bulk operation is being performed.
540
+ delete_all: Boolean indicating whether the operation applies to pk_list or not.
541
+ edit_all: Boolean indicating whether the operation applies to pk_list or not.
542
+ filter_query_params: A dictionary of filter parameters to apply to the queryset as produced by convert_querydict_to_dict(request.GET).
543
+ pk_list: A list of primary keys to include, when not using a filter.
544
+ saved_view_id: (Optional) UUID of a saved view to apply additional filters from.
545
+
546
+ Returns:
547
+ A Django queryset representing the objects to be affected by the bulk operation.
548
+
549
+ Notes:
550
+ Start
551
+ ├── !is_all and pk_list: Return queryset filtered by pk_list
552
+ ├── !is_all and !pk_list: Return empty queryset
553
+ ├── is_all and !saved_view_id and !filter_query_params: Return all objects
554
+ ├── is_all and filter_query_params: Return queryset filtered by filter_query_params
555
+ ├── is_all and saved_view_id: Return queryset filtered by saved_view_filter_params
556
+ ├── is_all and not saved_view_id: Return queryset filtered by saved_view_filter_params
557
+ └── else: raise RuntimeError
558
+ """
559
+ model = content_type.model_class()
560
+ if not log:
561
+ log = logger
562
+
563
+ action_valid = (action == "delete" and delete_all is not None) or (action == "change" and edit_all is not None)
564
+ if not action_valid:
565
+ raise RuntimeError(
566
+ f"Invalid parameters *_all param for action {action}, got: delete_all={delete_all}, edit_all={edit_all}"
567
+ )
568
+
569
+ view_name = None
570
+ is_all = None
571
+ # Based on action_valid one of these must be True
572
+ if action == "delete":
573
+ view_name = "BulkDelete"
574
+ is_all = delete_all
575
+ elif action == "change":
576
+ view_name = "BulkEdit"
577
+ is_all = edit_all
578
+
579
+ # The view_class is determined from model on purpose, as view_class the view as a param, will not work
580
+ # with a job. It is better to be consistent with each with sending the same params that will
581
+ # always be available from to the confirmation page and to the job.
582
+ view_class = get_view_for_model(model, view_type=view_name)
583
+
584
+ if not view_class:
585
+ raise RuntimeError(f"No view found for model {model} to determine base queryset.")
586
+
587
+ queryset = view_class.queryset.restrict(user, action)
588
+
589
+ # The filterset_class is determined from model on purpose, as filterset_class the view as a param, will not work
590
+ # with a job. It is better to be consistent with each with sending the same params that will
591
+ # always be available from to the confirmation page and to the job.
592
+ filterset_class = get_filterset_for_model(model)
593
+
594
+ if not filterset_class:
595
+ log.debug(f"No filterset_class found for model {model}, returning all objects")
596
+ return queryset
597
+
598
+ filterset_class = lookup.get_filterset_for_model(model)
599
+ if filterset_class:
600
+ filter_query_params = normalize_querydict(filter_query_params, filterset=filterset_class())
601
+ log.debug(f"Normalized filter_query_params: {filter_query_params}")
602
+ else:
603
+ filter_query_params = {}
604
+
605
+ # The form actually sends the pks and the "all" parameter, so seeing pk_list by itself is not
606
+ # sufficient to determine if we are filtering by pk_list or by all. We need to see is_all=False.
607
+ if not is_all and pk_list:
608
+ log.debug("Filtering by PK list")
609
+ return queryset.filter(pk__in=pk_list)
610
+
611
+ # Should this ever happen?
612
+ if not is_all and not pk_list:
613
+ log.debug("Filtering by None, as no PKs provided for bulk operation, returning empty queryset")
614
+ return queryset.none()
615
+
616
+ # The query params when you manually delete filters from the UI include on the saved view filter
617
+ # set the flag all_filters_removed to true. If that is the case, we ignore the saved view below, by setting it
618
+ # to None here
619
+ if filter_query_params.get("all_filters_removed"):
620
+ log.debug("The `all_filters_removed` flag is set, ignoring saved view")
621
+ saved_view_id = None
622
+ filter_query_params.pop("all_filters_removed")
623
+
624
+ new_filter_query_params = {}
625
+
626
+ filterset = filterset_class()
627
+ for key, value in filter_query_params.items():
628
+ if filterset.filters.get(key) is not None:
629
+ new_filter_query_params[key] = value
630
+ else:
631
+ log.debug(f"Query parameter `{key}` not found in `{filterset_class}`, discarding it")
632
+ filter_query_params = new_filter_query_params
633
+
634
+ # short circuit if no filtering is needed
635
+ if is_all and not saved_view_id and not filter_query_params:
636
+ log.debug("No filters or saved view specified, returning all objects")
637
+ return queryset
638
+
639
+ # This covers if there is a filter and a saved view, as when you have both,
640
+ # the saved view filters show up in the query params or the url.
641
+ if is_all and filter_query_params:
642
+ log.debug(f"Filtering by parameters: {filter_query_params}")
643
+ inner_queryset = filterset_class(filter_query_params, queryset).qs.values("pk")
644
+ # We take this approach because filterset.qs has already applied .distinct(),
645
+ # and performing a .delete directly on a queryset with .distinct applied is not allowed.
646
+ return queryset.filter(pk__in=inner_queryset)
647
+
648
+ saved_view_filter_params = {}
649
+ if saved_view_id:
650
+ try:
651
+ saved_view_obj = SavedView.objects.get(id=saved_view_id)
652
+ except SavedView.DoesNotExist:
653
+ return queryset.none()
654
+ saved_view_filter_params = saved_view_obj.config.get("filter_params", {})
655
+
656
+ # This covers the case where there is a saved view but no additional filter parameters.
657
+ if is_all and saved_view_filter_params:
658
+ log.debug(f"Filtering by saved view parameters: {saved_view_filter_params}")
659
+ inner_queryset = filterset_class(saved_view_filter_params, queryset).qs.values("pk")
660
+ # We take this approach because filterset.qs has already applied .distinct(),
661
+ # and performing a .delete directly on a queryset with .distinct applied is not allowed.
662
+ return queryset.filter(pk__in=inner_queryset)
663
+
664
+ # short circuit if no filtering is applied with a saved view
665
+ if is_all and not saved_view_filter_params:
666
+ log.debug("Saved view with no filters specified, returning all objects")
667
+ return queryset
668
+
669
+ log.debug("No valid operation found to generate bulk queryset.")
670
+ raise RuntimeError("No valid operation found to generate bulk queryset.")
@@ -1027,7 +1027,10 @@ class DeviceTypeToSoftwareImageFileSerializer(ValidatedModelSerializer):
1027
1027
 
1028
1028
  class ControllerSerializer(TaggedModelSerializerMixin, NautobotModelSerializer):
1029
1029
  capabilities = serializers.ListField(
1030
- child=ChoiceField(choices=ControllerCapabilitiesChoices, required=False), allow_empty=True, required=False
1030
+ child=ChoiceField(choices=ControllerCapabilitiesChoices, required=False),
1031
+ allow_empty=True,
1032
+ allow_null=True,
1033
+ required=False,
1031
1034
  )
1032
1035
 
1033
1036
  class Meta:
@@ -1037,7 +1040,10 @@ class ControllerSerializer(TaggedModelSerializerMixin, NautobotModelSerializer):
1037
1040
 
1038
1041
  class ControllerManagedDeviceGroupSerializer(TaggedModelSerializerMixin, NautobotModelSerializer):
1039
1042
  capabilities = serializers.ListField(
1040
- child=ChoiceField(choices=ControllerCapabilitiesChoices, required=False), allow_empty=True, required=False
1043
+ child=ChoiceField(choices=ControllerCapabilitiesChoices, required=False),
1044
+ allow_empty=True,
1045
+ allow_null=True,
1046
+ required=False,
1041
1047
  )
1042
1048
 
1043
1049
  class Meta:
@@ -7,6 +7,7 @@ from .choices import InterfaceTypeChoices
7
7
  #
8
8
 
9
9
  RACK_U_HEIGHT_DEFAULT = 42
10
+ RACK_U_HEIGHT_MAXIMUM = 500
10
11
 
11
12
  RACK_ELEVATION_BORDER_WIDTH = 2
12
13
  RACK_ELEVATION_LEGEND_WIDTH_DEFAULT = 30
nautobot/dcim/factory.py CHANGED
@@ -31,6 +31,7 @@ from nautobot.dcim.choices import (
31
31
  SoftwareImageFileHashingAlgorithmChoices,
32
32
  SubdeviceRoleChoices,
33
33
  )
34
+ from nautobot.dcim.constants import RACK_U_HEIGHT_MAXIMUM
34
35
  from nautobot.dcim.models import (
35
36
  ConsolePortTemplate,
36
37
  ConsoleServerPortTemplate,
@@ -634,7 +635,7 @@ class RackFactory(PrimaryModelFactory):
634
635
  type = factory.Maybe("has_type", factory.Faker("random_element", elements=RackTypeChoices.values()), "")
635
636
 
636
637
  width = factory.Faker("random_element", elements=RackWidthChoices.values())
637
- u_height = factory.Faker("pyint", min_value=10, max_value=100)
638
+ u_height = factory.Faker("pyint", min_value=10, max_value=RACK_U_HEIGHT_MAXIMUM)
638
639
  desc_units = NautobotBoolIterator()
639
640
 
640
641
  has_outer_width = NautobotBoolIterator()
@@ -743,7 +744,7 @@ class ControllerFactory(PrimaryModelFactory):
743
744
  capabilities = factory.Maybe(
744
745
  "has_capabilities",
745
746
  factory.Faker("random_elements", elements=ControllerCapabilitiesChoices.values(), unique=True),
746
- [],
747
+ None,
747
748
  )
748
749
  platform = random_instance(Platform)
749
750
  location = random_instance(lambda: Location.objects.get_for_model(Controller), allow_null=False)
@@ -770,7 +771,7 @@ class ControllerManagedDeviceGroupFactory(PrimaryModelFactory):
770
771
  capabilities = factory.Maybe(
771
772
  "has_capabilities",
772
773
  factory.Faker("random_elements", elements=ControllerCapabilitiesChoices.values(), unique=True),
773
- [],
774
+ None,
774
775
  )
775
776
  weight = factory.Faker("pyint", min_value=1, max_value=1000)
776
777
 
@@ -38,8 +38,7 @@ from nautobot.dcim.models import (
38
38
  RearPort,
39
39
  RearPortTemplate,
40
40
  )
41
- from nautobot.extras.filters import CustomFieldModelFilterSetMixin
42
- from nautobot.extras.filters.mixins import RelationshipModelFilterSetMixin
41
+ from nautobot.extras.filters.mixins import CustomFieldModelFilterSetMixin, RelationshipModelFilterSetMixin
43
42
 
44
43
 
45
44
  class CableTerminationModelFilterSetMixin(django_filters.FilterSet):
nautobot/dcim/forms.py CHANGED
@@ -37,6 +37,7 @@ from nautobot.core.forms import (
37
37
  )
38
38
  from nautobot.core.forms.constants import BOOLEAN_WITH_BLANK_CHOICES
39
39
  from nautobot.core.forms.fields import LaxURLField
40
+ from nautobot.dcim.constants import RACK_U_HEIGHT_MAXIMUM
40
41
  from nautobot.dcim.form_mixins import (
41
42
  LocatableModelBulkEditFormMixin,
42
43
  LocatableModelFilterFormMixin,
@@ -612,7 +613,7 @@ class RackBulkEditForm(
612
613
  required=False,
613
614
  widget=StaticSelect2(),
614
615
  )
615
- u_height = forms.IntegerField(required=False, label="Height (U)", min_value=1, max_value=100)
616
+ u_height = forms.IntegerField(required=False, label="Height (U)", min_value=1, max_value=RACK_U_HEIGHT_MAXIMUM)
616
617
  desc_units = forms.NullBooleanField(required=False, widget=BulkEditNullBooleanSelect, label="Descending units")
617
618
  outer_width = forms.IntegerField(required=False, min_value=1)
618
619
  outer_depth = forms.IntegerField(required=False, min_value=1)
@@ -5193,6 +5194,8 @@ class SoftwareImageFileFilterForm(NautobotFilterForm, StatusModelFilterFormMixin
5193
5194
  class SoftwareImageFileForm(NautobotModelForm):
5194
5195
  """SoftwareImageFile credit/edit form."""
5195
5196
 
5197
+ software_version = DynamicModelChoiceField(queryset=SoftwareVersion.objects.all())
5198
+
5196
5199
  device_types = DynamicModelMultipleChoiceField(
5197
5200
  queryset=DeviceType.objects.all(),
5198
5201
  required=False,
@@ -5339,6 +5342,7 @@ class SoftwareVersionFilterForm(NautobotFilterForm, StatusModelFilterFormMixin):
5339
5342
  class SoftwareVersionForm(NautobotModelForm):
5340
5343
  """SoftwareVersion credit/edit form."""
5341
5344
 
5345
+ platform = DynamicModelChoiceField(queryset=Platform.objects.all())
5342
5346
  release_date = NullableDateField(required=False, widget=DatePicker())
5343
5347
  end_of_support_date = NullableDateField(required=False, widget=DatePicker())
5344
5348
  field_order = [
@@ -0,0 +1,21 @@
1
+ # Generated by Django 4.2.24 on 2025-09-17 08:28
2
+
3
+ import django.core.validators
4
+ from django.db import migrations, models
5
+
6
+
7
+ class Migration(migrations.Migration):
8
+ dependencies = [
9
+ ("dcim", "0073_alter_powerport_power_factor_and_more"),
10
+ ]
11
+
12
+ operations = [
13
+ migrations.AlterField(
14
+ model_name="rack",
15
+ name="u_height",
16
+ field=models.PositiveSmallIntegerField(
17
+ default=42,
18
+ validators=[django.core.validators.MinValueValidator(1), django.core.validators.MaxValueValidator(500)],
19
+ ),
20
+ ),
21
+ ]
@@ -31,7 +31,10 @@ from nautobot.dcim.utils import get_all_network_driver_mappings, get_network_dri
31
31
  from nautobot.extras.models import ChangeLoggedModel, ConfigContextModel, RoleField, StatusField
32
32
  from nautobot.extras.querysets import ConfigContextModelQuerySet
33
33
  from nautobot.extras.utils import extras_features
34
- from nautobot.wireless.models import ControllerManagedDeviceGroupWirelessNetworkAssignment
34
+ from nautobot.wireless.models import (
35
+ ControllerManagedDeviceGroupRadioProfileAssignment,
36
+ ControllerManagedDeviceGroupWirelessNetworkAssignment,
37
+ )
35
38
 
36
39
  from .device_components import (
37
40
  ConsolePort,
@@ -940,6 +943,10 @@ class Device(PrimaryModel, ConfigContextModel):
940
943
  """
941
944
  return self.virtual_chassis.master if self.virtual_chassis else None
942
945
 
946
+ @property
947
+ def is_vc_master(self):
948
+ return self == self.get_vc_master()
949
+
943
950
  @property
944
951
  def vc_interfaces(self):
945
952
  """
@@ -1079,6 +1086,28 @@ class Device(PrimaryModel, ConfigContextModel):
1079
1086
  """
1080
1087
  return RearPort.objects.filter(Q(device=self) | Q(module__in=self.all_modules))
1081
1088
 
1089
+ @property
1090
+ def radio_profile_assignments(self):
1091
+ """
1092
+ Returns all Controller Managed Device Group Radio Profile Assignments linked to this device group.
1093
+ """
1094
+ if self.controller_managed_device_group is None:
1095
+ return ControllerManagedDeviceGroupRadioProfileAssignment.objects.none()
1096
+ return ControllerManagedDeviceGroupRadioProfileAssignment.objects.filter(
1097
+ controller_managed_device_group=self.controller_managed_device_group
1098
+ )
1099
+
1100
+ @property
1101
+ def wireless_network_assignments(self):
1102
+ """
1103
+ Returns all Controller Managed Device Group Wireless Network Assignments linked to this device group.
1104
+ """
1105
+ if self.controller_managed_device_group is None:
1106
+ return ControllerManagedDeviceGroupWirelessNetworkAssignment.objects.none()
1107
+ return ControllerManagedDeviceGroupWirelessNetworkAssignment.objects.filter(
1108
+ controller_managed_device_group=self.controller_managed_device_group
1109
+ )
1110
+
1082
1111
 
1083
1112
  #
1084
1113
  # Virtual chassis
@@ -14,7 +14,7 @@ from nautobot.core.models.utils import array_to_string
14
14
  from nautobot.core.utils.config import get_settings_or_config
15
15
  from nautobot.core.utils.data import UtilizationData
16
16
  from nautobot.dcim.choices import DeviceFaceChoices, RackDimensionUnitChoices, RackTypeChoices, RackWidthChoices
17
- from nautobot.dcim.constants import RACK_ELEVATION_LEGEND_WIDTH_DEFAULT, RACK_U_HEIGHT_DEFAULT
17
+ from nautobot.dcim.constants import RACK_ELEVATION_LEGEND_WIDTH_DEFAULT, RACK_U_HEIGHT_DEFAULT, RACK_U_HEIGHT_MAXIMUM
18
18
  from nautobot.dcim.elevations import RackElevationSVG
19
19
  from nautobot.extras.models import RoleField, StatusField
20
20
  from nautobot.extras.utils import extras_features
@@ -153,7 +153,7 @@ class Rack(PrimaryModel):
153
153
  u_height = models.PositiveSmallIntegerField(
154
154
  default=RACK_U_HEIGHT_DEFAULT,
155
155
  verbose_name="Height (U)",
156
- validators=[MinValueValidator(1), MaxValueValidator(100)],
156
+ validators=[MinValueValidator(1), MaxValueValidator(RACK_U_HEIGHT_MAXIMUM)],
157
157
  help_text="Height in rack units",
158
158
  )
159
159
  desc_units = models.BooleanField(
@@ -39,6 +39,7 @@ from .devices import (
39
39
  RearPortTable,
40
40
  SoftwareImageFileTable,
41
41
  SoftwareVersionTable,
42
+ VirtualChassisMembersTable,
42
43
  VirtualChassisTable,
43
44
  VirtualDeviceContextTable,
44
45
  )
@@ -125,6 +126,7 @@ __all__ = (
125
126
  "RearPortTemplateTable",
126
127
  "SoftwareImageFileTable",
127
128
  "SoftwareVersionTable",
129
+ "VirtualChassisMembersTable",
128
130
  "VirtualChassisTable",
129
131
  "VirtualDeviceContextTable",
130
132
  )
@@ -154,6 +154,30 @@ class PlatformTable(BaseTable):
154
154
  #
155
155
 
156
156
 
157
+ class VirtualChassisMembersTable(BaseTable):
158
+ name = tables.TemplateColumn(order_by=("_name",), template_code=DEVICE_LINK, verbose_name="Device")
159
+ vc_position = tables.TemplateColumn(
160
+ verbose_name="Position", template_code='<span class="badge badge-default">{{ record.vc_position }}</span>'
161
+ )
162
+ master = BooleanColumn(accessor="is_vc_master", verbose_name="Master")
163
+ vc_priority = tables.Column(verbose_name="Priority")
164
+
165
+ class Meta(BaseTable.Meta):
166
+ model = Device
167
+ fields = (
168
+ "name",
169
+ "vc_position",
170
+ "master",
171
+ "vc_priority",
172
+ )
173
+ default_columns = (
174
+ "name",
175
+ "vc_position",
176
+ "master",
177
+ "vc_priority",
178
+ )
179
+
180
+
157
181
  class DeviceTable(StatusTableMixin, RoleTableMixin, BaseTable):
158
182
  pk = ToggleColumn()
159
183
  name = tables.TemplateColumn(order_by=("_name",), template_code=DEVICE_LINK)
@@ -76,8 +76,8 @@ class PowerFeedTable(StatusTableMixin, CableTerminationTable):
76
76
  rack = tables.Column(linkify=True)
77
77
  type = ChoiceFieldColumn()
78
78
  power_path = tables.Column()
79
- occupied_positions = tables.Column(accessor="occupied_positions", verbose_name="Position")
80
- phase_designation = tables.Column(accessor="phase_designation", verbose_name="Phase Designation")
79
+ occupied_positions = tables.Column(accessor="occupied_positions", verbose_name="Position", orderable=False)
80
+ phase_designation = tables.Column(accessor="phase_designation", verbose_name="Phase Designation", orderable=False)
81
81
  max_utilization = tables.TemplateColumn(template_code="{{ value }}%")
82
82
  available_power = tables.Column(verbose_name="Available power (VA)")
83
83
  tags = TagColumn(url_name="dcim:powerfeed_list")