views.py 25 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749
  1. from django.contrib import messages
  2. from django.db import transaction
  3. from django.shortcuts import get_object_or_404, redirect, render
  4. from django.utils.translation import gettext_lazy as _
  5. from dcim.views import PathTraceView
  6. from ipam.models import ASN
  7. from netbox.views import generic
  8. from tenancy.views import ObjectContactsView
  9. from utilities.forms import ConfirmationForm
  10. from utilities.query import count_related
  11. from utilities.views import GetRelatedModelsMixin, register_model_view
  12. from . import filtersets, forms, tables
  13. from .models import *
  14. #
  15. # Providers
  16. #
  17. @register_model_view(Provider, 'list', path='', detail=False)
  18. class ProviderListView(generic.ObjectListView):
  19. queryset = Provider.objects.annotate(
  20. count_circuits=count_related(Circuit, 'provider'),
  21. asn_count=count_related(ASN, 'providers'),
  22. account_count=count_related(ProviderAccount, 'provider'),
  23. )
  24. filterset = filtersets.ProviderFilterSet
  25. filterset_form = forms.ProviderFilterForm
  26. table = tables.ProviderTable
  27. @register_model_view(Provider)
  28. class ProviderView(GetRelatedModelsMixin, generic.ObjectView):
  29. queryset = Provider.objects.all()
  30. def get_extra_context(self, request, instance):
  31. return {
  32. 'related_models': self.get_related_models(request, instance),
  33. }
  34. @register_model_view(Provider, 'add', detail=False)
  35. @register_model_view(Provider, 'edit')
  36. class ProviderEditView(generic.ObjectEditView):
  37. queryset = Provider.objects.all()
  38. form = forms.ProviderForm
  39. @register_model_view(Provider, 'delete')
  40. class ProviderDeleteView(generic.ObjectDeleteView):
  41. queryset = Provider.objects.all()
  42. @register_model_view(Provider, 'bulk_import', detail=False)
  43. class ProviderBulkImportView(generic.BulkImportView):
  44. queryset = Provider.objects.all()
  45. model_form = forms.ProviderImportForm
  46. @register_model_view(Provider, 'bulk_edit', path='edit', detail=False)
  47. class ProviderBulkEditView(generic.BulkEditView):
  48. queryset = Provider.objects.annotate(
  49. count_circuits=count_related(Circuit, 'provider')
  50. )
  51. filterset = filtersets.ProviderFilterSet
  52. table = tables.ProviderTable
  53. form = forms.ProviderBulkEditForm
  54. @register_model_view(Provider, 'bulk_delete', path='delete', detail=False)
  55. class ProviderBulkDeleteView(generic.BulkDeleteView):
  56. queryset = Provider.objects.annotate(
  57. count_circuits=count_related(Circuit, 'provider')
  58. )
  59. filterset = filtersets.ProviderFilterSet
  60. table = tables.ProviderTable
  61. @register_model_view(Provider, 'contacts')
  62. class ProviderContactsView(ObjectContactsView):
  63. queryset = Provider.objects.all()
  64. #
  65. # ProviderAccounts
  66. #
  67. @register_model_view(ProviderAccount, 'list', path='', detail=False)
  68. class ProviderAccountListView(generic.ObjectListView):
  69. queryset = ProviderAccount.objects.annotate(
  70. count_circuits=count_related(Circuit, 'provider_account')
  71. )
  72. filterset = filtersets.ProviderAccountFilterSet
  73. filterset_form = forms.ProviderAccountFilterForm
  74. table = tables.ProviderAccountTable
  75. @register_model_view(ProviderAccount)
  76. class ProviderAccountView(GetRelatedModelsMixin, generic.ObjectView):
  77. queryset = ProviderAccount.objects.all()
  78. def get_extra_context(self, request, instance):
  79. return {
  80. 'related_models': self.get_related_models(request, instance),
  81. }
  82. @register_model_view(ProviderAccount, 'add', detail=False)
  83. @register_model_view(ProviderAccount, 'edit')
  84. class ProviderAccountEditView(generic.ObjectEditView):
  85. queryset = ProviderAccount.objects.all()
  86. form = forms.ProviderAccountForm
  87. @register_model_view(ProviderAccount, 'delete')
  88. class ProviderAccountDeleteView(generic.ObjectDeleteView):
  89. queryset = ProviderAccount.objects.all()
  90. @register_model_view(ProviderAccount, 'bulk_import', detail=False)
  91. class ProviderAccountBulkImportView(generic.BulkImportView):
  92. queryset = ProviderAccount.objects.all()
  93. model_form = forms.ProviderAccountImportForm
  94. table = tables.ProviderAccountTable
  95. @register_model_view(ProviderAccount, 'bulk_edit', path='edit', detail=False)
  96. class ProviderAccountBulkEditView(generic.BulkEditView):
  97. queryset = ProviderAccount.objects.annotate(
  98. count_circuits=count_related(Circuit, 'provider_account')
  99. )
  100. filterset = filtersets.ProviderAccountFilterSet
  101. table = tables.ProviderAccountTable
  102. form = forms.ProviderAccountBulkEditForm
  103. @register_model_view(ProviderAccount, 'bulk_delete', path='delete', detail=False)
  104. class ProviderAccountBulkDeleteView(generic.BulkDeleteView):
  105. queryset = ProviderAccount.objects.annotate(
  106. count_circuits=count_related(Circuit, 'provider_account')
  107. )
  108. filterset = filtersets.ProviderAccountFilterSet
  109. table = tables.ProviderAccountTable
  110. @register_model_view(ProviderAccount, 'contacts')
  111. class ProviderAccountContactsView(ObjectContactsView):
  112. queryset = ProviderAccount.objects.all()
  113. #
  114. # Provider networks
  115. #
  116. @register_model_view(ProviderNetwork, 'list', path='', detail=False)
  117. class ProviderNetworkListView(generic.ObjectListView):
  118. queryset = ProviderNetwork.objects.all()
  119. filterset = filtersets.ProviderNetworkFilterSet
  120. filterset_form = forms.ProviderNetworkFilterForm
  121. table = tables.ProviderNetworkTable
  122. @register_model_view(ProviderNetwork)
  123. class ProviderNetworkView(GetRelatedModelsMixin, generic.ObjectView):
  124. queryset = ProviderNetwork.objects.all()
  125. def get_extra_context(self, request, instance):
  126. return {
  127. 'related_models': self.get_related_models(
  128. request,
  129. instance,
  130. extra=(
  131. (
  132. Circuit.objects.restrict(request.user, 'view').filter(terminations___provider_network=instance),
  133. 'provider_network_id',
  134. ),
  135. ),
  136. ),
  137. }
  138. @register_model_view(ProviderNetwork, 'add', detail=False)
  139. @register_model_view(ProviderNetwork, 'edit')
  140. class ProviderNetworkEditView(generic.ObjectEditView):
  141. queryset = ProviderNetwork.objects.all()
  142. form = forms.ProviderNetworkForm
  143. @register_model_view(ProviderNetwork, 'delete')
  144. class ProviderNetworkDeleteView(generic.ObjectDeleteView):
  145. queryset = ProviderNetwork.objects.all()
  146. @register_model_view(ProviderNetwork, 'bulk_import', detail=False)
  147. class ProviderNetworkBulkImportView(generic.BulkImportView):
  148. queryset = ProviderNetwork.objects.all()
  149. model_form = forms.ProviderNetworkImportForm
  150. @register_model_view(ProviderNetwork, 'bulk_edit', path='edit', detail=False)
  151. class ProviderNetworkBulkEditView(generic.BulkEditView):
  152. queryset = ProviderNetwork.objects.all()
  153. filterset = filtersets.ProviderNetworkFilterSet
  154. table = tables.ProviderNetworkTable
  155. form = forms.ProviderNetworkBulkEditForm
  156. @register_model_view(ProviderNetwork, 'bulk_delete', path='delete', detail=False)
  157. class ProviderNetworkBulkDeleteView(generic.BulkDeleteView):
  158. queryset = ProviderNetwork.objects.all()
  159. filterset = filtersets.ProviderNetworkFilterSet
  160. table = tables.ProviderNetworkTable
  161. #
  162. # Circuit Types
  163. #
  164. @register_model_view(CircuitType, 'list', path='', detail=False)
  165. class CircuitTypeListView(generic.ObjectListView):
  166. queryset = CircuitType.objects.annotate(
  167. circuit_count=count_related(Circuit, 'type')
  168. )
  169. filterset = filtersets.CircuitTypeFilterSet
  170. filterset_form = forms.CircuitTypeFilterForm
  171. table = tables.CircuitTypeTable
  172. @register_model_view(CircuitType)
  173. class CircuitTypeView(GetRelatedModelsMixin, generic.ObjectView):
  174. queryset = CircuitType.objects.all()
  175. def get_extra_context(self, request, instance):
  176. return {
  177. 'related_models': self.get_related_models(request, instance),
  178. }
  179. @register_model_view(CircuitType, 'add', detail=False)
  180. @register_model_view(CircuitType, 'edit')
  181. class CircuitTypeEditView(generic.ObjectEditView):
  182. queryset = CircuitType.objects.all()
  183. form = forms.CircuitTypeForm
  184. @register_model_view(CircuitType, 'delete')
  185. class CircuitTypeDeleteView(generic.ObjectDeleteView):
  186. queryset = CircuitType.objects.all()
  187. @register_model_view(CircuitType, 'bulk_import', detail=False)
  188. class CircuitTypeBulkImportView(generic.BulkImportView):
  189. queryset = CircuitType.objects.all()
  190. model_form = forms.CircuitTypeImportForm
  191. @register_model_view(CircuitType, 'bulk_edit', path='edit', detail=False)
  192. class CircuitTypeBulkEditView(generic.BulkEditView):
  193. queryset = CircuitType.objects.annotate(
  194. circuit_count=count_related(Circuit, 'type')
  195. )
  196. filterset = filtersets.CircuitTypeFilterSet
  197. table = tables.CircuitTypeTable
  198. form = forms.CircuitTypeBulkEditForm
  199. @register_model_view(CircuitType, 'bulk_delete', path='delete', detail=False)
  200. class CircuitTypeBulkDeleteView(generic.BulkDeleteView):
  201. queryset = CircuitType.objects.annotate(
  202. circuit_count=count_related(Circuit, 'type')
  203. )
  204. filterset = filtersets.CircuitTypeFilterSet
  205. table = tables.CircuitTypeTable
  206. #
  207. # Circuits
  208. #
  209. @register_model_view(Circuit, 'list', path='', detail=False)
  210. class CircuitListView(generic.ObjectListView):
  211. queryset = Circuit.objects.prefetch_related(
  212. 'tenant__group', 'termination_a__termination', 'termination_z__termination',
  213. )
  214. filterset = filtersets.CircuitFilterSet
  215. filterset_form = forms.CircuitFilterForm
  216. table = tables.CircuitTable
  217. @register_model_view(Circuit)
  218. class CircuitView(generic.ObjectView):
  219. queryset = Circuit.objects.all()
  220. @register_model_view(Circuit, 'add', detail=False)
  221. @register_model_view(Circuit, 'edit')
  222. class CircuitEditView(generic.ObjectEditView):
  223. queryset = Circuit.objects.all()
  224. form = forms.CircuitForm
  225. @register_model_view(Circuit, 'delete')
  226. class CircuitDeleteView(generic.ObjectDeleteView):
  227. queryset = Circuit.objects.all()
  228. @register_model_view(Circuit, 'bulk_import', detail=False)
  229. class CircuitBulkImportView(generic.BulkImportView):
  230. queryset = Circuit.objects.all()
  231. model_form = forms.CircuitImportForm
  232. additional_permissions = [
  233. 'circuits.add_circuittermination',
  234. ]
  235. related_object_forms = {
  236. 'terminations': forms.CircuitTerminationImportRelatedForm,
  237. }
  238. def prep_related_object_data(self, parent, data):
  239. data.update({'circuit': parent})
  240. return data
  241. @register_model_view(Circuit, 'bulk_edit', path='edit', detail=False)
  242. class CircuitBulkEditView(generic.BulkEditView):
  243. queryset = Circuit.objects.prefetch_related(
  244. 'tenant__group', 'termination_a__termination', 'termination_z__termination',
  245. )
  246. filterset = filtersets.CircuitFilterSet
  247. table = tables.CircuitTable
  248. form = forms.CircuitBulkEditForm
  249. @register_model_view(Circuit, 'bulk_delete', path='delete', detail=False)
  250. class CircuitBulkDeleteView(generic.BulkDeleteView):
  251. queryset = Circuit.objects.prefetch_related(
  252. 'tenant__group', 'termination_a__termination', 'termination_z__termination',
  253. )
  254. filterset = filtersets.CircuitFilterSet
  255. table = tables.CircuitTable
  256. class CircuitSwapTerminations(generic.ObjectEditView):
  257. """
  258. Swap the A and Z terminations of a circuit.
  259. """
  260. queryset = Circuit.objects.all()
  261. def get(self, request, pk):
  262. circuit = get_object_or_404(self.queryset, pk=pk)
  263. form = ConfirmationForm()
  264. # Circuit must have at least one termination to swap
  265. if not circuit.termination_a and not circuit.termination_z:
  266. messages.error(request, _(
  267. "No terminations have been defined for circuit {circuit}."
  268. ).format(circuit=circuit))
  269. return redirect('circuits:circuit', pk=circuit.pk)
  270. return render(request, 'circuits/circuit_terminations_swap.html', {
  271. 'circuit': circuit,
  272. 'termination_a': circuit.termination_a,
  273. 'termination_z': circuit.termination_z,
  274. 'form': form,
  275. 'panel_class': 'light',
  276. 'button_class': 'primary',
  277. 'return_url': circuit.get_absolute_url(),
  278. })
  279. def post(self, request, pk):
  280. circuit = get_object_or_404(self.queryset, pk=pk)
  281. form = ConfirmationForm(request.POST)
  282. if form.is_valid():
  283. termination_a = CircuitTermination.objects.filter(pk=circuit.termination_a_id).first()
  284. termination_z = CircuitTermination.objects.filter(pk=circuit.termination_z_id).first()
  285. if termination_a and termination_z:
  286. # Use a placeholder to avoid an IntegrityError on the (circuit, term_side) unique constraint
  287. with transaction.atomic():
  288. termination_a.term_side = '_'
  289. termination_a.save()
  290. termination_z.term_side = 'A'
  291. termination_z.save()
  292. termination_a.term_side = 'Z'
  293. termination_a.save()
  294. circuit.refresh_from_db()
  295. circuit.termination_a = termination_z
  296. circuit.termination_z = termination_a
  297. circuit.save()
  298. elif termination_a:
  299. termination_a.term_side = 'Z'
  300. termination_a.save()
  301. circuit.refresh_from_db()
  302. circuit.termination_a = None
  303. circuit.save()
  304. else:
  305. termination_z.term_side = 'A'
  306. termination_z.save()
  307. circuit.refresh_from_db()
  308. circuit.termination_z = None
  309. circuit.save()
  310. messages.success(request, _("Swapped terminations for circuit {circuit}.").format(circuit=circuit))
  311. return redirect('circuits:circuit', pk=circuit.pk)
  312. return render(request, 'circuits/circuit_terminations_swap.html', {
  313. 'circuit': circuit,
  314. 'termination_a': circuit.termination_a,
  315. 'termination_z': circuit.termination_z,
  316. 'form': form,
  317. 'panel_class': 'default',
  318. 'button_class': 'primary',
  319. 'return_url': circuit.get_absolute_url(),
  320. })
  321. @register_model_view(Circuit, 'contacts')
  322. class CircuitContactsView(ObjectContactsView):
  323. queryset = Circuit.objects.all()
  324. #
  325. # Circuit terminations
  326. #
  327. @register_model_view(CircuitTermination, 'list', path='', detail=False)
  328. class CircuitTerminationListView(generic.ObjectListView):
  329. queryset = CircuitTermination.objects.all()
  330. filterset = filtersets.CircuitTerminationFilterSet
  331. filterset_form = forms.CircuitTerminationFilterForm
  332. table = tables.CircuitTerminationTable
  333. @register_model_view(CircuitTermination)
  334. class CircuitTerminationView(generic.ObjectView):
  335. queryset = CircuitTermination.objects.all()
  336. @register_model_view(CircuitTermination, 'add', detail=False)
  337. @register_model_view(CircuitTermination, 'edit')
  338. class CircuitTerminationEditView(generic.ObjectEditView):
  339. queryset = CircuitTermination.objects.all()
  340. form = forms.CircuitTerminationForm
  341. @register_model_view(CircuitTermination, 'delete')
  342. class CircuitTerminationDeleteView(generic.ObjectDeleteView):
  343. queryset = CircuitTermination.objects.all()
  344. @register_model_view(CircuitTermination, 'bulk_import', detail=False)
  345. class CircuitTerminationBulkImportView(generic.BulkImportView):
  346. queryset = CircuitTermination.objects.all()
  347. model_form = forms.CircuitTerminationImportForm
  348. @register_model_view(CircuitTermination, 'bulk_edit', path='edit', detail=False)
  349. class CircuitTerminationBulkEditView(generic.BulkEditView):
  350. queryset = CircuitTermination.objects.all()
  351. filterset = filtersets.CircuitTerminationFilterSet
  352. table = tables.CircuitTerminationTable
  353. form = forms.CircuitTerminationBulkEditForm
  354. @register_model_view(CircuitTermination, 'bulk_delete', path='delete', detail=False)
  355. class CircuitTerminationBulkDeleteView(generic.BulkDeleteView):
  356. queryset = CircuitTermination.objects.all()
  357. filterset = filtersets.CircuitTerminationFilterSet
  358. table = tables.CircuitTerminationTable
  359. # Trace view
  360. register_model_view(CircuitTermination, 'trace', kwargs={'model': CircuitTermination})(PathTraceView)
  361. #
  362. # Circuit Groups
  363. #
  364. @register_model_view(CircuitGroup, 'list', path='', detail=False)
  365. class CircuitGroupListView(generic.ObjectListView):
  366. queryset = CircuitGroup.objects.annotate(
  367. circuit_group_assignment_count=count_related(CircuitGroupAssignment, 'group')
  368. )
  369. filterset = filtersets.CircuitGroupFilterSet
  370. filterset_form = forms.CircuitGroupFilterForm
  371. table = tables.CircuitGroupTable
  372. @register_model_view(CircuitGroup)
  373. class CircuitGroupView(GetRelatedModelsMixin, generic.ObjectView):
  374. queryset = CircuitGroup.objects.all()
  375. def get_extra_context(self, request, instance):
  376. return {
  377. 'related_models': self.get_related_models(request, instance),
  378. }
  379. @register_model_view(CircuitGroup, 'add', detail=False)
  380. @register_model_view(CircuitGroup, 'edit')
  381. class CircuitGroupEditView(generic.ObjectEditView):
  382. queryset = CircuitGroup.objects.all()
  383. form = forms.CircuitGroupForm
  384. @register_model_view(CircuitGroup, 'delete')
  385. class CircuitGroupDeleteView(generic.ObjectDeleteView):
  386. queryset = CircuitGroup.objects.all()
  387. @register_model_view(CircuitGroup, 'bulk_import', detail=False)
  388. class CircuitGroupBulkImportView(generic.BulkImportView):
  389. queryset = CircuitGroup.objects.all()
  390. model_form = forms.CircuitGroupImportForm
  391. @register_model_view(CircuitGroup, 'bulk_edit', path='edit', detail=False)
  392. class CircuitGroupBulkEditView(generic.BulkEditView):
  393. queryset = CircuitGroup.objects.all()
  394. filterset = filtersets.CircuitGroupFilterSet
  395. table = tables.CircuitGroupTable
  396. form = forms.CircuitGroupBulkEditForm
  397. @register_model_view(CircuitGroup, 'bulk_delete', path='delete', detail=False)
  398. class CircuitGroupBulkDeleteView(generic.BulkDeleteView):
  399. queryset = CircuitGroup.objects.all()
  400. filterset = filtersets.CircuitGroupFilterSet
  401. table = tables.CircuitGroupTable
  402. #
  403. # Circuit Groups
  404. #
  405. @register_model_view(CircuitGroupAssignment, 'list', path='', detail=False)
  406. class CircuitGroupAssignmentListView(generic.ObjectListView):
  407. queryset = CircuitGroupAssignment.objects.all()
  408. filterset = filtersets.CircuitGroupAssignmentFilterSet
  409. filterset_form = forms.CircuitGroupAssignmentFilterForm
  410. table = tables.CircuitGroupAssignmentTable
  411. @register_model_view(CircuitGroupAssignment)
  412. class CircuitGroupAssignmentView(generic.ObjectView):
  413. queryset = CircuitGroupAssignment.objects.all()
  414. @register_model_view(CircuitGroupAssignment, 'add', detail=False)
  415. @register_model_view(CircuitGroupAssignment, 'edit')
  416. class CircuitGroupAssignmentEditView(generic.ObjectEditView):
  417. queryset = CircuitGroupAssignment.objects.all()
  418. form = forms.CircuitGroupAssignmentForm
  419. @register_model_view(CircuitGroupAssignment, 'delete')
  420. class CircuitGroupAssignmentDeleteView(generic.ObjectDeleteView):
  421. queryset = CircuitGroupAssignment.objects.all()
  422. @register_model_view(CircuitGroupAssignment, 'bulk_import', detail=False)
  423. class CircuitGroupAssignmentBulkImportView(generic.BulkImportView):
  424. queryset = CircuitGroupAssignment.objects.all()
  425. model_form = forms.CircuitGroupAssignmentImportForm
  426. @register_model_view(CircuitGroupAssignment, 'bulk_edit', path='edit', detail=False)
  427. class CircuitGroupAssignmentBulkEditView(generic.BulkEditView):
  428. queryset = CircuitGroupAssignment.objects.all()
  429. filterset = filtersets.CircuitGroupAssignmentFilterSet
  430. table = tables.CircuitGroupAssignmentTable
  431. form = forms.CircuitGroupAssignmentBulkEditForm
  432. @register_model_view(CircuitGroupAssignment, 'bulk_delete', path='delete', detail=False)
  433. class CircuitGroupAssignmentBulkDeleteView(generic.BulkDeleteView):
  434. queryset = CircuitGroupAssignment.objects.all()
  435. filterset = filtersets.CircuitGroupAssignmentFilterSet
  436. table = tables.CircuitGroupAssignmentTable
  437. #
  438. # Virtual circuit Types
  439. #
  440. @register_model_view(VirtualCircuitType, 'list', path='', detail=False)
  441. class VirtualCircuitTypeListView(generic.ObjectListView):
  442. queryset = VirtualCircuitType.objects.annotate(
  443. virtual_circuit_count=count_related(VirtualCircuit, 'type')
  444. )
  445. filterset = filtersets.VirtualCircuitTypeFilterSet
  446. filterset_form = forms.VirtualCircuitTypeFilterForm
  447. table = tables.VirtualCircuitTypeTable
  448. @register_model_view(VirtualCircuitType)
  449. class VirtualCircuitTypeView(GetRelatedModelsMixin, generic.ObjectView):
  450. queryset = VirtualCircuitType.objects.all()
  451. def get_extra_context(self, request, instance):
  452. return {
  453. 'related_models': self.get_related_models(request, instance),
  454. }
  455. @register_model_view(VirtualCircuitType, 'add', detail=False)
  456. @register_model_view(VirtualCircuitType, 'edit')
  457. class VirtualCircuitTypeEditView(generic.ObjectEditView):
  458. queryset = VirtualCircuitType.objects.all()
  459. form = forms.VirtualCircuitTypeForm
  460. @register_model_view(VirtualCircuitType, 'delete')
  461. class VirtualCircuitTypeDeleteView(generic.ObjectDeleteView):
  462. queryset = VirtualCircuitType.objects.all()
  463. @register_model_view(VirtualCircuitType, 'bulk_import', detail=False)
  464. class VirtualCircuitTypeBulkImportView(generic.BulkImportView):
  465. queryset = VirtualCircuitType.objects.all()
  466. model_form = forms.VirtualCircuitTypeImportForm
  467. @register_model_view(VirtualCircuitType, 'bulk_edit', path='edit', detail=False)
  468. class VirtualCircuitTypeBulkEditView(generic.BulkEditView):
  469. queryset = VirtualCircuitType.objects.annotate(
  470. circuit_count=count_related(Circuit, 'type')
  471. )
  472. filterset = filtersets.VirtualCircuitTypeFilterSet
  473. table = tables.VirtualCircuitTypeTable
  474. form = forms.VirtualCircuitTypeBulkEditForm
  475. @register_model_view(VirtualCircuitType, 'bulk_delete', path='delete', detail=False)
  476. class VirtualCircuitTypeBulkDeleteView(generic.BulkDeleteView):
  477. queryset = VirtualCircuitType.objects.annotate(
  478. circuit_count=count_related(Circuit, 'type')
  479. )
  480. filterset = filtersets.VirtualCircuitTypeFilterSet
  481. table = tables.VirtualCircuitTypeTable
  482. #
  483. # Virtual circuits
  484. #
  485. class VirtualCircuitListView(generic.ObjectListView):
  486. queryset = VirtualCircuit.objects.annotate(
  487. termination_count=count_related(VirtualCircuitTermination, 'virtual_circuit')
  488. )
  489. filterset = filtersets.VirtualCircuitFilterSet
  490. filterset_form = forms.VirtualCircuitFilterForm
  491. table = tables.VirtualCircuitTable
  492. @register_model_view(VirtualCircuit)
  493. class VirtualCircuitView(generic.ObjectView):
  494. queryset = VirtualCircuit.objects.all()
  495. @register_model_view(VirtualCircuit, 'edit')
  496. class VirtualCircuitEditView(generic.ObjectEditView):
  497. queryset = VirtualCircuit.objects.all()
  498. form = forms.VirtualCircuitForm
  499. @register_model_view(VirtualCircuit, 'delete')
  500. class VirtualCircuitDeleteView(generic.ObjectDeleteView):
  501. queryset = VirtualCircuit.objects.all()
  502. class VirtualCircuitBulkImportView(generic.BulkImportView):
  503. queryset = VirtualCircuit.objects.all()
  504. model_form = forms.VirtualCircuitImportForm
  505. additional_permissions = [
  506. 'circuits.add_virtualcircuittermination',
  507. ]
  508. related_object_forms = {
  509. 'terminations': forms.VirtualCircuitTerminationImportRelatedForm,
  510. }
  511. def prep_related_object_data(self, parent, data):
  512. data.update({'virtual_circuit': parent})
  513. return data
  514. class VirtualCircuitBulkEditView(generic.BulkEditView):
  515. queryset = VirtualCircuit.objects.annotate(
  516. termination_count=count_related(VirtualCircuitTermination, 'virtual_circuit')
  517. )
  518. filterset = filtersets.VirtualCircuitFilterSet
  519. table = tables.VirtualCircuitTable
  520. form = forms.VirtualCircuitBulkEditForm
  521. class VirtualCircuitBulkDeleteView(generic.BulkDeleteView):
  522. queryset = VirtualCircuit.objects.annotate(
  523. termination_count=count_related(VirtualCircuitTermination, 'virtual_circuit')
  524. )
  525. filterset = filtersets.VirtualCircuitFilterSet
  526. table = tables.VirtualCircuitTable
  527. #
  528. # Virtual circuit terminations
  529. #
  530. class VirtualCircuitTerminationListView(generic.ObjectListView):
  531. queryset = VirtualCircuitTermination.objects.all()
  532. filterset = filtersets.VirtualCircuitTerminationFilterSet
  533. filterset_form = forms.VirtualCircuitTerminationFilterForm
  534. table = tables.VirtualCircuitTerminationTable
  535. @register_model_view(VirtualCircuitTermination)
  536. class VirtualCircuitTerminationView(generic.ObjectView):
  537. queryset = VirtualCircuitTermination.objects.all()
  538. @register_model_view(VirtualCircuitTermination, 'edit')
  539. class VirtualCircuitTerminationEditView(generic.ObjectEditView):
  540. queryset = VirtualCircuitTermination.objects.all()
  541. form = forms.VirtualCircuitTerminationForm
  542. @register_model_view(VirtualCircuitTermination, 'delete')
  543. class VirtualCircuitTerminationDeleteView(generic.ObjectDeleteView):
  544. queryset = VirtualCircuitTermination.objects.all()
  545. class VirtualCircuitTerminationBulkImportView(generic.BulkImportView):
  546. queryset = VirtualCircuitTermination.objects.all()
  547. model_form = forms.VirtualCircuitTerminationImportForm
  548. class VirtualCircuitTerminationBulkEditView(generic.BulkEditView):
  549. queryset = VirtualCircuitTermination.objects.all()
  550. filterset = filtersets.VirtualCircuitTerminationFilterSet
  551. table = tables.VirtualCircuitTerminationTable
  552. form = forms.VirtualCircuitTerminationBulkEditForm
  553. class VirtualCircuitTerminationBulkDeleteView(generic.BulkDeleteView):
  554. queryset = VirtualCircuitTermination.objects.all()
  555. filterset = filtersets.VirtualCircuitTerminationFilterSet
  556. table = tables.VirtualCircuitTerminationTable