filtersets.py 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386
  1. import django_filters
  2. from django.contrib.auth.models import User
  3. from django.contrib.contenttypes.models import ContentType
  4. from django.db.models import Q
  5. from dcim.models import DeviceRole, DeviceType, Platform, Region, Site, SiteGroup
  6. from netbox.filtersets import BaseFilterSet, ChangeLoggedModelFilterSet
  7. from tenancy.models import Tenant, TenantGroup
  8. from utilities.filters import ContentTypeFilter, MultiValueCharFilter, MultiValueNumberFilter
  9. from virtualization.models import Cluster, ClusterGroup
  10. from .choices import *
  11. from .models import *
  12. __all__ = (
  13. 'ConfigContextFilterSet',
  14. 'ContentTypeFilterSet',
  15. 'CustomFieldFilterSet',
  16. 'CustomLinkFilterSet',
  17. 'ExportTemplateFilterSet',
  18. 'ImageAttachmentFilterSet',
  19. 'JournalEntryFilterSet',
  20. 'LocalConfigContextFilterSet',
  21. 'ObjectChangeFilterSet',
  22. 'TagFilterSet',
  23. 'WebhookFilterSet',
  24. )
  25. EXACT_FILTER_TYPES = (
  26. CustomFieldTypeChoices.TYPE_BOOLEAN,
  27. CustomFieldTypeChoices.TYPE_DATE,
  28. CustomFieldTypeChoices.TYPE_INTEGER,
  29. CustomFieldTypeChoices.TYPE_SELECT,
  30. )
  31. class WebhookFilterSet(BaseFilterSet):
  32. content_types = ContentTypeFilter()
  33. http_method = django_filters.MultipleChoiceFilter(
  34. choices=WebhookHttpMethodChoices
  35. )
  36. class Meta:
  37. model = Webhook
  38. fields = [
  39. 'id', 'content_types', 'name', 'type_create', 'type_update', 'type_delete', 'payload_url', 'enabled',
  40. 'http_method', 'http_content_type', 'secret', 'ssl_verification', 'ca_file_path',
  41. ]
  42. class CustomFieldFilterSet(BaseFilterSet):
  43. content_types = ContentTypeFilter()
  44. class Meta:
  45. model = CustomField
  46. fields = ['id', 'content_types', 'name', 'required', 'filter_logic', 'weight']
  47. class CustomLinkFilterSet(BaseFilterSet):
  48. class Meta:
  49. model = CustomLink
  50. fields = ['id', 'content_type', 'name', 'link_text', 'link_url', 'weight', 'group_name', 'new_window']
  51. class ExportTemplateFilterSet(BaseFilterSet):
  52. class Meta:
  53. model = ExportTemplate
  54. fields = ['id', 'content_type', 'name']
  55. class ImageAttachmentFilterSet(BaseFilterSet):
  56. created = django_filters.DateTimeFilter()
  57. content_type = ContentTypeFilter()
  58. class Meta:
  59. model = ImageAttachment
  60. fields = ['id', 'content_type_id', 'object_id', 'name']
  61. class JournalEntryFilterSet(ChangeLoggedModelFilterSet):
  62. q = django_filters.CharFilter(
  63. method='search',
  64. label='Search',
  65. )
  66. created = django_filters.DateTimeFromToRangeFilter()
  67. assigned_object_type = ContentTypeFilter()
  68. created_by_id = django_filters.ModelMultipleChoiceFilter(
  69. queryset=User.objects.all(),
  70. label='User (ID)',
  71. )
  72. created_by = django_filters.ModelMultipleChoiceFilter(
  73. field_name='created_by__username',
  74. queryset=User.objects.all(),
  75. to_field_name='username',
  76. label='User (name)',
  77. )
  78. kind = django_filters.MultipleChoiceFilter(
  79. choices=JournalEntryKindChoices
  80. )
  81. class Meta:
  82. model = JournalEntry
  83. fields = ['id', 'assigned_object_type_id', 'assigned_object_id', 'created', 'kind']
  84. def search(self, queryset, name, value):
  85. if not value.strip():
  86. return queryset
  87. return queryset.filter(comments__icontains=value)
  88. class TagFilterSet(ChangeLoggedModelFilterSet):
  89. q = django_filters.CharFilter(
  90. method='search',
  91. label='Search',
  92. )
  93. content_type = MultiValueCharFilter(
  94. method='_content_type'
  95. )
  96. content_type_id = MultiValueNumberFilter(
  97. method='_content_type_id'
  98. )
  99. class Meta:
  100. model = Tag
  101. fields = ['id', 'name', 'slug', 'color']
  102. def search(self, queryset, name, value):
  103. if not value.strip():
  104. return queryset
  105. return queryset.filter(
  106. Q(name__icontains=value) |
  107. Q(slug__icontains=value)
  108. )
  109. def _content_type(self, queryset, name, values):
  110. ct_filter = Q()
  111. # Compile list of app_label & model pairings
  112. for value in values:
  113. try:
  114. app_label, model = value.lower().split('.')
  115. ct_filter |= Q(
  116. app_label=app_label,
  117. model=model
  118. )
  119. except ValueError:
  120. pass
  121. # Get ContentType instances
  122. content_types = ContentType.objects.filter(ct_filter)
  123. return queryset.filter(extras_taggeditem_items__content_type__in=content_types).distinct()
  124. def _content_type_id(self, queryset, name, values):
  125. # Get ContentType instances
  126. content_types = ContentType.objects.filter(pk__in=values)
  127. return queryset.filter(extras_taggeditem_items__content_type__in=content_types).distinct()
  128. class ConfigContextFilterSet(ChangeLoggedModelFilterSet):
  129. q = django_filters.CharFilter(
  130. method='search',
  131. label='Search',
  132. )
  133. region_id = django_filters.ModelMultipleChoiceFilter(
  134. field_name='regions',
  135. queryset=Region.objects.all(),
  136. label='Region',
  137. )
  138. region = django_filters.ModelMultipleChoiceFilter(
  139. field_name='regions__slug',
  140. queryset=Region.objects.all(),
  141. to_field_name='slug',
  142. label='Region (slug)',
  143. )
  144. site_group = django_filters.ModelMultipleChoiceFilter(
  145. field_name='site_groups__slug',
  146. queryset=SiteGroup.objects.all(),
  147. to_field_name='slug',
  148. label='Site group (slug)',
  149. )
  150. site_group_id = django_filters.ModelMultipleChoiceFilter(
  151. field_name='site_groups',
  152. queryset=SiteGroup.objects.all(),
  153. label='Site group',
  154. )
  155. site_id = django_filters.ModelMultipleChoiceFilter(
  156. field_name='sites',
  157. queryset=Site.objects.all(),
  158. label='Site',
  159. )
  160. site = django_filters.ModelMultipleChoiceFilter(
  161. field_name='sites__slug',
  162. queryset=Site.objects.all(),
  163. to_field_name='slug',
  164. label='Site (slug)',
  165. )
  166. device_type_id = django_filters.ModelMultipleChoiceFilter(
  167. field_name='device_types',
  168. queryset=DeviceType.objects.all(),
  169. label='Device type',
  170. )
  171. role_id = django_filters.ModelMultipleChoiceFilter(
  172. field_name='roles',
  173. queryset=DeviceRole.objects.all(),
  174. label='Role',
  175. )
  176. role = django_filters.ModelMultipleChoiceFilter(
  177. field_name='roles__slug',
  178. queryset=DeviceRole.objects.all(),
  179. to_field_name='slug',
  180. label='Role (slug)',
  181. )
  182. platform_id = django_filters.ModelMultipleChoiceFilter(
  183. field_name='platforms',
  184. queryset=Platform.objects.all(),
  185. label='Platform',
  186. )
  187. platform = django_filters.ModelMultipleChoiceFilter(
  188. field_name='platforms__slug',
  189. queryset=Platform.objects.all(),
  190. to_field_name='slug',
  191. label='Platform (slug)',
  192. )
  193. cluster_group_id = django_filters.ModelMultipleChoiceFilter(
  194. field_name='cluster_groups',
  195. queryset=ClusterGroup.objects.all(),
  196. label='Cluster group',
  197. )
  198. cluster_group = django_filters.ModelMultipleChoiceFilter(
  199. field_name='cluster_groups__slug',
  200. queryset=ClusterGroup.objects.all(),
  201. to_field_name='slug',
  202. label='Cluster group (slug)',
  203. )
  204. cluster_id = django_filters.ModelMultipleChoiceFilter(
  205. field_name='clusters',
  206. queryset=Cluster.objects.all(),
  207. label='Cluster',
  208. )
  209. tenant_group_id = django_filters.ModelMultipleChoiceFilter(
  210. field_name='tenant_groups',
  211. queryset=TenantGroup.objects.all(),
  212. label='Tenant group',
  213. )
  214. tenant_group = django_filters.ModelMultipleChoiceFilter(
  215. field_name='tenant_groups__slug',
  216. queryset=TenantGroup.objects.all(),
  217. to_field_name='slug',
  218. label='Tenant group (slug)',
  219. )
  220. tenant_id = django_filters.ModelMultipleChoiceFilter(
  221. field_name='tenants',
  222. queryset=Tenant.objects.all(),
  223. label='Tenant',
  224. )
  225. tenant = django_filters.ModelMultipleChoiceFilter(
  226. field_name='tenants__slug',
  227. queryset=Tenant.objects.all(),
  228. to_field_name='slug',
  229. label='Tenant (slug)',
  230. )
  231. tag = django_filters.ModelMultipleChoiceFilter(
  232. field_name='tags__slug',
  233. queryset=Tag.objects.all(),
  234. to_field_name='slug',
  235. label='Tag (slug)',
  236. )
  237. class Meta:
  238. model = ConfigContext
  239. fields = ['id', 'name', 'is_active']
  240. def search(self, queryset, name, value):
  241. if not value.strip():
  242. return queryset
  243. return queryset.filter(
  244. Q(name__icontains=value) |
  245. Q(description__icontains=value) |
  246. Q(data__icontains=value)
  247. )
  248. #
  249. # Filter for Local Config Context Data
  250. #
  251. class LocalConfigContextFilterSet(django_filters.FilterSet):
  252. local_context_data = django_filters.BooleanFilter(
  253. method='_local_context_data',
  254. label='Has local config context data',
  255. )
  256. def _local_context_data(self, queryset, name, value):
  257. return queryset.exclude(local_context_data__isnull=value)
  258. class ObjectChangeFilterSet(BaseFilterSet):
  259. q = django_filters.CharFilter(
  260. method='search',
  261. label='Search',
  262. )
  263. time = django_filters.DateTimeFromToRangeFilter()
  264. changed_object_type = ContentTypeFilter()
  265. user_id = django_filters.ModelMultipleChoiceFilter(
  266. queryset=User.objects.all(),
  267. label='User (ID)',
  268. )
  269. user = django_filters.ModelMultipleChoiceFilter(
  270. field_name='user__username',
  271. queryset=User.objects.all(),
  272. to_field_name='username',
  273. label='User name',
  274. )
  275. class Meta:
  276. model = ObjectChange
  277. fields = [
  278. 'id', 'user', 'user_name', 'request_id', 'action', 'changed_object_type_id', 'changed_object_id',
  279. 'object_repr',
  280. ]
  281. def search(self, queryset, name, value):
  282. if not value.strip():
  283. return queryset
  284. return queryset.filter(
  285. Q(user_name__icontains=value) |
  286. Q(object_repr__icontains=value)
  287. )
  288. #
  289. # Job Results
  290. #
  291. class JobResultFilterSet(BaseFilterSet):
  292. q = django_filters.CharFilter(
  293. method='search',
  294. label='Search',
  295. )
  296. created = django_filters.DateTimeFilter()
  297. completed = django_filters.DateTimeFilter()
  298. status = django_filters.MultipleChoiceFilter(
  299. choices=JobResultStatusChoices,
  300. null_value=None
  301. )
  302. class Meta:
  303. model = JobResult
  304. fields = [
  305. 'id', 'created', 'completed', 'status', 'user', 'obj_type', 'name'
  306. ]
  307. def search(self, queryset, name, value):
  308. if not value.strip():
  309. return queryset
  310. return queryset.filter(
  311. Q(user__username__icontains=value)
  312. )
  313. #
  314. # ContentTypes
  315. #
  316. class ContentTypeFilterSet(django_filters.FilterSet):
  317. q = django_filters.CharFilter(
  318. method='search',
  319. label='Search',
  320. )
  321. class Meta:
  322. model = ContentType
  323. fields = ['id', 'app_label', 'model']
  324. def search(self, queryset, name, value):
  325. if not value.strip():
  326. return queryset
  327. return queryset.filter(
  328. Q(app_label__icontains=value) |
  329. Q(model__icontains=value)
  330. )