class SearchFilter(filters.FilterSet):
    """An unusually complicated search filter, which does extra filtering on nicknames, default and non-default
    contact details, unaccented filtering
    """

    def filter_firstname(self, queryset, field_name, value) -> models.QuerySet:
        """Filters on firstname or nickname, accent-insensitive"""
        return queryset.filter(
            models.Q(firstname__unaccent__startswith=value) | models.Q(nickname__unaccent__startswith=value)
        )

    firstname = filters.CharFilter(label='First name', method='filter_firstname')

    surname = filters.CharFilter(
        label='Surname',
        field_name='surname',
        lookup_expr='unaccent__startswith',
    )

    birthdate = filters.DateFilter(label='Birthdate', field_name='birthdate', widget=DatePickerInput())

    def filter_postcode(self, queryset, field_name, value) -> models.QuerySet:
        """Finds postcodes starting the same way, while removing spaces from the search and target"""
        value = re.sub(r'\s+', '', value)
        return queryset.annotate(
            trimmed_postcode=Replace('default_address__postcode', models.Value(' '), models.Value(''))
        ).filter(
            trimmed_postcode__startswith=value,
        )

    postcode = filters.CharFilter(
        label='Postcode',
        method='filter_postcode',
    )

    def filter_email(self, queryset, field_name, value) -> models.QuerySet:
        """Filters on (any) email address, and adds an extra column for the result table to use"""
        return (
            queryset.filter(email__email__contains=value)
            .annotate(
                email_address=models.F('email__email'),
            )
            .distinct()
        )

    email = filters.CharFilter(
        label='Email',
        method='filter_email',
    )

    def filter_phone(self, queryset, field_name, value) -> models.QuerySet:
        """Filters on (any) phone number, and adds an extra column for the result table to use"""
        value = re.sub(r'\s+', '', value)
        return (
            queryset.annotate(phone_number=models.F('phones__number'))  # for table display
            .alias(stripped_phone_number=Replace('phones__number', models.Value(' '), models.Value('')))
            .filter(stripped_phone_number__contains=value)
            .distinct()
        )

    phone = filters.CharFilter(
        label='Phone',
        method='filter_phone',
    )

    def filter_tutors_only(self, queryset, field_name, value) -> models.QuerySet:
        if value:
            return queryset.filter(tutor__id__isnull=False)
        return queryset

    tutors_only = filters.BooleanFilter(
        label='Tutors only?',
        method='filter_tutors_only',
        widget=forms.CheckboxInput,
    )

    class Meta:
        model = Student
        fields = ('firstname', 'surname', 'birthdate', 'postcode', 'phone', 'email', 'tutors_only')
Exemple #2
0
 class PostAdminWithFilterInstances(djadmin2.ModelAdmin2):
     list_filter = [
         django_filters.BooleanFilter(name='published'),
     ]
Exemple #3
0
class ProjectFilter(django_filters.FilterSet):
    project_institutions = django_filters.ModelChoiceFilter(
        label=FieldProject.INSTITUTION,
        queryset=Institution.objects.all(),
        widget=autocomplete.ModelSelect2(url='institution-autocomplete'))
    project_participants = django_filters.ModelChoiceFilter(
        label=FieldProject.PARTICIPANTS,
        queryset=Person.objects.all(),
        widget=autocomplete.ModelSelect2(url='person-autocomplete'))
    project_title_text = django_filters.CharFilter(
        label=FieldProject.TITLE,
        lookup_expr='icontains',
        widget=forms.TextInput(attrs={'class': 'list__form--input'}))
    project_targets = django_filters.ModelMultipleChoiceFilter(
        label=FieldProject.TARGETS,
        queryset=TargetGroup.objects.all(),
        widget=autocomplete.ModelSelect2Multiple(
            url='targetgroup-autocomplete'))
    project_disciplines = django_filters.ModelChoiceFilter(
        label=FieldProject.DISCIPLINES,
        queryset=ResearchDiscipline.objects.all(),
        widget=autocomplete.ModelSelect2(
            url='researchdiscipline-autocomplete'))
    project_cities__region = django_filters.ModelChoiceFilter(
        label=FieldProject.REGIONS,
        queryset=Region.objects.all(),
        widget=autocomplete.ModelSelect2(url='region-autocomplete'))
    project_cities = django_filters.ModelChoiceFilter(
        label=FieldProject.CITIES,
        queryset=City.objects.all(),
        widget=autocomplete.ModelSelect2(url='city-autocomplete'))
    project_date_start = django_filters.DateFilter(
        label=FieldProject.DATE_START,
        lookup_expr='gte',
        widget=forms.DateTimeInput(
            attrs={'class': 'datepicker list__form--input'}))
    project_date_end = django_filters.DateFilter(
        label=FieldProject.DATE_END,
        lookup_expr='lte',
        widget=forms.DateTimeInput(
            attrs={'class': 'datepicker list__form--input'}))
    project_financing = django_filters.CharFilter(
        label=FieldProject.FINANCING,
        lookup_expr='icontains',
        widget=forms.TextInput(attrs={'class': 'list__form--input'}))
    project_keywords = django_filters.ModelMultipleChoiceFilter(
        label=FieldProject.KEYWORDS,
        queryset=Tag.objects.all(),
        widget=autocomplete.ModelSelect2Multiple(url='tag-autocomplete'))
    project_is_accepted = django_filters.BooleanFilter(
        label=FieldProject.IS_ACCEPTED,
        widget=NullBooleanSelect(attrs={'class': 'select2'}))

    o = django_filters.OrderingFilter(fields=(
        ('project_is_promoted', 'project_is_promoted'),
        ('project_date_add', 'project_date_add'),
        ('project_title_text', 'project_title_text'),
        ('project_date_end', 'project_date_end'),
    ), )

    strict = True

    class Meta:
        model = Project
        form = ProjectFilterForm
        fields = [
            'project_institutions', 'project_participants',
            'project_title_text', 'project_targets', 'project_disciplines',
            'project_cities__region', 'project_cities', 'project_date_start',
            'project_date_end', 'project_financing', 'project_keywords',
            'project_is_accepted'
        ]
Exemple #4
0
class LeadGQFilterSet(UserResourceGqlFilterSet):
    ids = IDListFilter(method='filter_leads_id', help_text='Empty ids are ignored.')
    exclude_provided_leads_id = django_filters.BooleanFilter(
        method='filter_exclude_provided_leads_id', help_text='Only used when ids are provided.')
    created_by = IDListFilter()
    modified_by = IDListFilter()
    source_types = MultipleInputFilter(LeadSourceTypeEnum, field_name='source_type')
    priorities = MultipleInputFilter(LeadPriorityEnum, field_name='priority')
    confidentiality = SimpleInputFilter(LeadConfidentialityEnum)
    statuses = MultipleInputFilter(LeadStatusEnum, field_name='status')
    extraction_status = SimpleInputFilter(LeadExtractionStatusEnum, field_name='extraction_status')
    assignees = IDListFilter(field_name='assignee')
    authoring_organization_types = IDListFilter(method='authoring_organization_types_filter')
    author_organizations = IDListFilter(method='authoring_organizations_filter')
    source_organizations = IDListFilter(method='source_organizations_filter')
    # Filter-only enum filter
    has_entries = django_filters.BooleanFilter(method='filter_has_entries', help_text='Lead has entries.')
    has_assessment = django_filters.BooleanFilter(method='filter_has_assessment', help_text='Lead has assessment.')
    entries_filter_data = SimpleInputFilter(
        type(
            'LeadEntriesFilterData',
            (graphene.InputObjectType,),
            get_filtering_args_from_filterset(EntryGQFilterSet, 'entry.schema.EntryListType')
        ),
        method='filtered_entries_filter_data',
    )

    search = django_filters.CharFilter(method='search_filter')

    published_on = django_filters.DateFilter()
    published_on_gte = DateGteFilter(field_name='published_on')
    published_on_lte = DateLteFilter(field_name='published_on')

    emm_entities = django_filters.CharFilter(method='emm_entities_filter')
    emm_keywords = django_filters.CharFilter(method='emm_keywords_filter')
    emm_risk_factors = django_filters.CharFilter(method='emm_risk_factors_filter')

    ordering = MultipleInputFilter(LeadOrderingEnum, method='ordering_filter')

    class Meta:
        model = Lead
        fields = {
            **{
                x: ['exact']
                for x in ['text', 'url']
            },
        }

        filter_overrides = {
            models.CharField: {
                'filter_class': django_filters.CharFilter,
                'extra': lambda _: {
                    'lookup_expr': 'icontains',
                },
            },
        }

    def __init__(self, *args, **kwargs):
        super().__init__(*args, **kwargs)
        self.custom_context = {}

    @property
    def active_project(self) -> Project:
        if self.request is None:
            raise Exception(f'{self.request=} should be defined')
        if self.request.active_project is None:
            raise Exception(f'{self.request.active_project=} should be defined')
        return self.request.active_project

    @staticmethod
    def get_dummy_request(project):
        """
        Use this if request is not available
        """
        return type('DummyRequest', (object,), dict(active_project=project))()

    # Filters methods
    def search_filter(self, qs, name, value):
        # NOTE: This exists to make it compatible with post filter
        if not value:
            return qs
        return qs.filter(
            # By title
            models.Q(title__icontains=value) |
            # By source
            models.Q(source_raw__icontains=value) |
            models.Q(source__title__icontains=value) |
            models.Q(source__parent__title__icontains=value) |
            # By author
            models.Q(author__title__icontains=value) |
            models.Q(author__parent__title__icontains=value) |
            models.Q(author_raw__icontains=value) |
            models.Q(authors__title__icontains=value) |
            models.Q(authors__parent__title__icontains=value) |
            # By URL
            models.Q(url__icontains=value)
        ).distinct()

    def ordering_filter(self, qs, name, value):
        active_entry_count_field = self.custom_context.get('active_entry_count_field')
        for ordering in value:
            # Custom for entries count (use filter or normal entry count)
            if active_entry_count_field and ordering in [
                LeadOrderingEnum.ASC_ENTRIES_COUNT,
                LeadOrderingEnum.DESC_ENTRIES_COUNT,
            ]:
                if ordering == LeadOrderingEnum.ASC_ENTRIES_COUNT:
                    qs = qs.order_by(active_entry_count_field)
                else:
                    qs = qs.order_by(f'-{active_entry_count_field}')
            # Custom for page count with nulls_last
            elif ordering == LeadOrderingEnum.DESC_PAGE_COUNT:
                qs = qs.order_by(models.F('leadpreview__page_count').desc(nulls_last=True))
            elif ordering == LeadOrderingEnum.ASC_PAGE_COUNT:
                qs = qs.order_by(models.F('leadpreview__page_count').asc(nulls_first=True))
            # For remaining
            else:
                qs = qs.order_by(ordering)
        return qs

    def emm_entities_filter(self, qs, name, value):
        splitted = [x for x in value.split(',') if x]
        return qs.filter(emm_entities__in=splitted)

    def emm_keywords_filter(self, qs, name, value):
        splitted = [x for x in value.split(',') if x]
        return qs.filter(emm_triggers__emm_keyword__in=splitted)

    def emm_risk_factors_filter(self, qs, name, value):
        splitted = [x for x in value.split(',') if x]
        return qs.filter(emm_triggers__emm_risk_factor__in=splitted)

    def authoring_organization_types_filter(self, qs, name, value):
        if value:
            qs = qs.annotate(
                organization_types=Coalesce(
                    'authors__parent__organization_type',
                    'authors__organization_type'
                )
            )
            if type(value[0]) == OrganizationType:
                return qs.filter(organization_types__in=[ot.id for ot in value]).distinct()
            return qs.filter(organization_types__in=value).distinct()
        return qs

    def authoring_organizations_filter(self, qs, _, value):
        if value:
            qs = qs.annotate(authoring_organizations=Coalesce('authors__parent_id', 'authors__id'))
            return qs.filter(authoring_organizations__in=value).distinct()
        return qs

    def source_organizations_filter(self, qs, _, value):
        if value:
            qs = qs.annotate(source_organizations=Coalesce('source__parent_id', 'source__id'))
            return qs.filter(source_organizations__in=value).distinct()
        return qs

    def filter_exclude_provided_leads_id(self, qs, *_):
        # NOTE: Used in filter_leads_id
        return qs

    def filter_leads_id(self, qs, _, value):
        if value is None:
            return qs
        if self.data.get('exclude_provided_leads_id'):
            return qs.exclude(id__in=value)
        return qs.filter(id__in=value)

    def filter_has_entries(self, qs, _, value):
        if value is None:
            return qs
        if value:
            return qs.filter(entry_count__gt=0)
        return qs.filter(entry_count=0)

    def filter_has_assessment(self, qs, _, value):
        if value is None:
            return qs
        return qs.filter(assessment__isnull=not value)

    def filtered_entries_filter_data(self, qs, _, value):
        if value is None:
            return qs
        return qs.filter(filtered_entry_count__gt=0)

    def filter_queryset(self, qs):
        def _entry_subquery(entry_qs: models.QuerySet):
            subquery_qs = entry_qs.\
                filter(
                    project=self.active_project,
                    analysis_framework=self.active_project.analysis_framework_id,
                    lead=models.OuterRef('pk'),
                )\
                .values('lead').order_by()\
                .annotate(count=models.Count('id'))\
                .values('count')
            return Coalesce(
                models.Subquery(
                    subquery_qs[:1],
                    output_field=models.IntegerField()
                ), 0,
            )

        # Pre-annotate required fields for entries count (w/wo filters)
        entries_filter_data = self.data.get('entries_filter_data')
        has_entries = self.data.get('has_entries')
        has_entries_count_ordering = any(
            ordering in [
                LeadOrderingEnum.ASC_ENTRIES_COUNT,
                LeadOrderingEnum.DESC_ENTRIES_COUNT,
            ] for ordering in self.data.get('ordering') or []
        )

        # With filter
        if entries_filter_data is not None:
            qs = qs.annotate(
                filtered_entry_count=_entry_subquery(
                    EntryGQFilterSet(
                        data=entries_filter_data,
                        request=self.request,
                    ).qs
                )
            )
            self.custom_context['active_entry_count_field'] = 'filtered_entry_count'
        # Without filter
        if has_entries is not None or (
            entries_filter_data is None and has_entries_count_ordering
        ):
            self.custom_context['active_entry_count_field'] = self.custom_context.\
                get('active_entry_count_field', 'entry_count')
            qs = qs.annotate(
                entry_count=_entry_subquery(Entry.objects.all())
            )
        # Call super function
        return super().filter_queryset(qs)

    @property
    def qs(self):
        return super().qs.distinct()
Exemple #5
0
class OfferingFilter(structure_filters.NameFilterSet,
                     django_filters.FilterSet):
    class Meta:
        model = models.Offering
        fields = []

    customer = core_filters.URLFilter(view_name='customer-detail',
                                      field_name='customer__uuid')
    customer_uuid = django_filters.UUIDFilter(field_name='customer__uuid')
    allowed_customer_uuid = django_filters.UUIDFilter(
        method='filter_allowed_customer')
    service_manager_uuid = django_filters.UUIDFilter(
        method='filter_service_manager')
    project_uuid = django_filters.UUIDFilter(method='filter_project')
    attributes = django_filters.CharFilter(method='filter_attributes')
    state = core_filters.MappedMultipleChoiceFilter(
        choices=[(representation, representation)
                 for db_value, representation in models.Offering.States.CHOICES
                 ],
        choice_mappings={
            representation: db_value
            for db_value, representation in models.Offering.States.CHOICES
        },
    )
    category_uuid = django_filters.UUIDFilter(field_name='category__uuid')
    billable = django_filters.BooleanFilter(widget=BooleanWidget)
    shared = django_filters.BooleanFilter(widget=BooleanWidget)
    description = django_filters.CharFilter(lookup_expr='icontains')
    keyword = django_filters.CharFilter(method='filter_keyword',
                                        label='Keyword')
    o = django_filters.OrderingFilter(fields=('name', 'created', 'type'))
    type = LooseMultipleChoiceFilter()

    def filter_allowed_customer(self, queryset, name, value):
        return queryset.filter_for_customer(value)

    def filter_service_manager(self, queryset, name, value):
        return queryset.filter_for_service_manager(value)

    def filter_project(self, queryset, name, value):
        return queryset.filter_for_project(value)

    def filter_attributes(self, queryset, name, value):
        try:
            value = json.loads(value)
        except ValueError:
            raise rf_exceptions.ValidationError(
                _('Filter attribute is not valid json.'))

        if not isinstance(value, dict):
            raise rf_exceptions.ValidationError(
                _('Filter attribute should be an dict.'))

        for k, v in value.items():
            if isinstance(v, list):
                # If a filter value is a list, use multiple choice.
                queryset = queryset.filter(
                    **{'attributes__{key}__has_any_keys'.format(key=k): v})
            else:
                queryset = queryset.filter(attributes__contains={k: v})
        return queryset

    def filter_keyword(self, queryset, name, value):
        return queryset.filter(
            Q(name__icontains=value)
            | Q(description__icontains=value)
            | Q(customer__name__icontains=value)
            | Q(customer__abbreviation__icontains=value)
            | Q(customer__native_name__icontains=value))
Exemple #6
0
class DeviceFilterSet(
    BaseFilterSet,
    TenancyFilterSet,
    LocalConfigContextFilterSet,
    CustomFieldModelFilterSet,
    CreatedUpdatedFilterSet
):
    q = django_filters.CharFilter(
        method='search',
        label='Search',
    )
    manufacturer_id = django_filters.ModelMultipleChoiceFilter(
        field_name='device_type__manufacturer',
        queryset=Manufacturer.objects.all(),
        label='Manufacturer (ID)',
    )
    manufacturer = django_filters.ModelMultipleChoiceFilter(
        field_name='device_type__manufacturer__slug',
        queryset=Manufacturer.objects.all(),
        to_field_name='slug',
        label='Manufacturer (slug)',
    )
    device_type_id = django_filters.ModelMultipleChoiceFilter(
        queryset=DeviceType.objects.all(),
        label='Device type (ID)',
    )
    role_id = django_filters.ModelMultipleChoiceFilter(
        field_name='device_role_id',
        queryset=DeviceRole.objects.all(),
        label='Role (ID)',
    )
    role = django_filters.ModelMultipleChoiceFilter(
        field_name='device_role__slug',
        queryset=DeviceRole.objects.all(),
        to_field_name='slug',
        label='Role (slug)',
    )
    platform_id = django_filters.ModelMultipleChoiceFilter(
        queryset=Platform.objects.all(),
        label='Platform (ID)',
    )
    platform = django_filters.ModelMultipleChoiceFilter(
        field_name='platform__slug',
        queryset=Platform.objects.all(),
        to_field_name='slug',
        label='Platform (slug)',
    )
    region_id = TreeNodeMultipleChoiceFilter(
        queryset=Region.objects.all(),
        field_name='site__region',
        lookup_expr='in',
        label='Region (ID)',
    )
    region = TreeNodeMultipleChoiceFilter(
        queryset=Region.objects.all(),
        field_name='site__region',
        lookup_expr='in',
        to_field_name='slug',
        label='Region (slug)',
    )
    site_id = django_filters.ModelMultipleChoiceFilter(
        queryset=Site.objects.all(),
        label='Site (ID)',
    )
    site = django_filters.ModelMultipleChoiceFilter(
        field_name='site__slug',
        queryset=Site.objects.all(),
        to_field_name='slug',
        label='Site name (slug)',
    )
    rack_group_id = TreeNodeMultipleChoiceFilter(
        queryset=RackGroup.objects.all(),
        field_name='rack__group',
        lookup_expr='in',
        label='Rack group (ID)',
    )
    rack_id = django_filters.ModelMultipleChoiceFilter(
        field_name='rack',
        queryset=Rack.objects.all(),
        label='Rack (ID)',
    )
    cluster_id = django_filters.ModelMultipleChoiceFilter(
        queryset=Cluster.objects.all(),
        label='VM cluster (ID)',
    )
    model = django_filters.ModelMultipleChoiceFilter(
        field_name='device_type__slug',
        queryset=DeviceType.objects.all(),
        to_field_name='slug',
        label='Device model (slug)',
    )
    status = django_filters.MultipleChoiceFilter(
        choices=DeviceStatusChoices,
        null_value=None
    )
    is_full_depth = django_filters.BooleanFilter(
        field_name='device_type__is_full_depth',
        label='Is full depth',
    )
    mac_address = MultiValueMACAddressFilter(
        field_name='interfaces__mac_address',
        label='MAC address',
    )
    serial = django_filters.CharFilter(
        lookup_expr='iexact'
    )
    has_primary_ip = django_filters.BooleanFilter(
        method='_has_primary_ip',
        label='Has a primary IP',
    )
    virtual_chassis_id = django_filters.ModelMultipleChoiceFilter(
        field_name='virtual_chassis',
        queryset=VirtualChassis.objects.all(),
        label='Virtual chassis (ID)',
    )
    virtual_chassis_member = django_filters.BooleanFilter(
        method='_virtual_chassis_member',
        label='Is a virtual chassis member'
    )
    console_ports = django_filters.BooleanFilter(
        method='_console_ports',
        label='Has console ports',
    )
    console_server_ports = django_filters.BooleanFilter(
        method='_console_server_ports',
        label='Has console server ports',
    )
    power_ports = django_filters.BooleanFilter(
        method='_power_ports',
        label='Has power ports',
    )
    power_outlets = django_filters.BooleanFilter(
        method='_power_outlets',
        label='Has power outlets',
    )
    interfaces = django_filters.BooleanFilter(
        method='_interfaces',
        label='Has interfaces',
    )
    pass_through_ports = django_filters.BooleanFilter(
        method='_pass_through_ports',
        label='Has pass-through ports',
    )
    device_bays = django_filters.BooleanFilter(
        method='_device_bays',
        label='Has device bays',
    )
    tag = TagFilter()

    class Meta:
        model = Device
        fields = ['id', 'name', 'asset_tag', 'face', 'position', 'vc_position', 'vc_priority']

    def search(self, queryset, name, value):
        if not value.strip():
            return queryset
        return queryset.filter(
            Q(name__icontains=value) |
            Q(serial__icontains=value.strip()) |
            Q(inventoryitems__serial__icontains=value.strip()) |
            Q(asset_tag__icontains=value.strip()) |
            Q(comments__icontains=value)
        ).distinct()

    def _has_primary_ip(self, queryset, name, value):
        params = Q(primary_ip4__isnull=False) | Q(primary_ip6__isnull=False)
        if value:
            return queryset.filter(params)
        return queryset.exclude(params)

    def _virtual_chassis_member(self, queryset, name, value):
        return queryset.exclude(virtual_chassis__isnull=value)

    def _console_ports(self, queryset, name, value):
        return queryset.exclude(consoleports__isnull=value)

    def _console_server_ports(self, queryset, name, value):
        return queryset.exclude(consoleserverports__isnull=value)

    def _power_ports(self, queryset, name, value):
        return queryset.exclude(powerports__isnull=value)

    def _power_outlets(self, queryset, name, value):
        return queryset.exclude(poweroutlets__isnull=value)

    def _interfaces(self, queryset, name, value):
        return queryset.exclude(interfaces__isnull=value)

    def _pass_through_ports(self, queryset, name, value):
        return queryset.exclude(
            frontports__isnull=value,
            rearports__isnull=value
        )

    def _device_bays(self, queryset, name, value):
        return queryset.exclude(devicebays__isnull=value)
Exemple #7
0
class MonsterFilter(django_filters.FilterSet):
    name = django_filters.CharFilter(method='filter_name')
    element = django_filters.MultipleChoiceFilter(
        choices=Monster.ELEMENT_CHOICES)
    archetype = django_filters.MultipleChoiceFilter(
        choices=Monster.TYPE_CHOICES)
    awaken_level = django_filters.MultipleChoiceFilter(
        choices=Monster.AWAKEN_CHOICES)
    leader_skill__attribute = django_filters.MultipleChoiceFilter(
        choices=LeaderSkill.ATTRIBUTE_CHOICES)
    leader_skill__area = django_filters.MultipleChoiceFilter(
        choices=LeaderSkill.AREA_CHOICES)
    skills__scaling_stats__pk = django_filters.ModelMultipleChoiceFilter(
        queryset=ScalingStat.objects.all(), to_field_name='pk', conjoined=True)
    skills__cooltime = django_filters.CharFilter(
        method='filter_skills_cooltime')
    effects_logic = django_filters.BooleanFilter(method='filter_effects_logic')
    skills__skill_effect__pk = django_filters.ModelMultipleChoiceFilter(
        queryset=SkillEffect.objects.all(), method='filter_skill_effects')

    class Meta:
        model = Monster
        fields = {
            'name': ['exact'],
            'com2us_id': ['exact'],
            'family_id': ['exact'],
            'element': ['exact'],
            'archetype': ['exact'],
            'base_stars': ['lte', 'gte'],
            'natural_stars': ['lte', 'gte'],
            'obtainable': ['exact'],
            'awaken_level': ['exact'],
            'leader_skill__attribute': ['exact'],
            'leader_skill__area': ['exact'],
            'skills__skill_effect__pk': ['exact'],
            'skills__scaling_stats__pk': ['exact'],
            'skills__cooltime': ['lte', 'gte'],
            'skills__hits': ['lte', 'gte'],
            'effects_logic': ['exact'],
            'fusion_food': ['exact'],
        }

    def filter_name(self, queryset, name, value):
        if value:
            return queryset.filter(
                Q(name__icontains=value)
                | Q(awakens_from__name__icontains=value)
                | Q(awakens_to__name__icontains=value))
        else:
            return queryset

    def filter_skill_effects(self, queryset, name, value):
        old_filtering = self.form.cleaned_data.get('effects_logic', False)
        stat_scaling = self.form.cleaned_data.get('skills__scaling_stats__pk',
                                                  [])
        cooltimes = self.form.cleaned_data.get('skills__cooltime', '')
        max_num_hits = self.form.cleaned_data.get('skills__hits__lte', 99)
        min_num_hits = self.form.cleaned_data.get('skills__hits__gte', 0)

        try:
            cooltimes = cooltimes.split(',')
            min_cooltime = int(cooltimes[0])
            max_cooltime = int(cooltimes[1])
        except:
            min_cooltime = 0
            max_cooltime = 999

        if old_filtering:
            # Filter if any skill on the monster has the designated fields
            for effect in value:
                queryset = queryset.filter(skills__skill_effect=effect)

            for pk in stat_scaling:
                queryset = queryset.filter(skills__scaling_stats=pk)

            cooltime_filter = Q(skills__cooltime__gte=min_cooltime) & Q(
                skills__cooltime__lte=max_cooltime)
            if min_cooltime == 0 or max_cooltime == 0:
                cooltime_filter = Q(
                    skills__cooltime__isnull=True) | cooltime_filter

            queryset = queryset.filter(cooltime_filter,
                                       skills__hits__lte=max_num_hits,
                                       skills__hits__gte=min_num_hits)

            return queryset.distinct()

        else:
            # Filter effects based on effects of each individual skill. This ensures a monster will not show up unless it has
            # the desired effects on the same skill rather than across any skills.
            skills = Skill.objects.all()

            for effect in value:
                skills = skills.filter(skill_effect=effect)

            for pk in stat_scaling:
                skills = skills.filter(scaling_stats=pk)

            cooltime_filter = Q(cooltime__gte=min_cooltime) & Q(
                cooltime__lte=max_cooltime)
            if min_cooltime == 0 or max_cooltime == 0:
                cooltime_filter = Q(cooltime__isnull=True) | cooltime_filter

            skills = skills.filter(cooltime_filter,
                                   hits__lte=max_num_hits,
                                   hits__gte=min_num_hits)

            return queryset.filter(skills__in=skills).distinct()

    def filter_effects_logic(self, queryset, name, value):
        # This field is just used to alter the logic of skill effect filter
        return queryset

    def filter_skills_cooltime(self, queryset, name, value):
        # This field is handled in filter_skill_effects()
        return queryset

    def filter_skills_slot(self, queryset, name, value):
        # This field is handled in filter_skill_effects()
        return queryset

    def filter_skills_hits(self, queryset, name, value):
        # This field is handled in filter_skill_effects()
        return queryset
Exemple #8
0
class VirtualMachineFilterSet(
    BaseFilterSet,
    LocalConfigContextFilterSet,
    TenancyFilterSet,
    CustomFieldModelFilterSet,
    CreatedUpdatedFilterSet
):
    q = django_filters.CharFilter(
        method='search',
        label='Search',
    )
    status = django_filters.MultipleChoiceFilter(
        choices=VirtualMachineStatusChoices,
        null_value=None
    )
    cluster_group_id = django_filters.ModelMultipleChoiceFilter(
        field_name='cluster__group',
        queryset=ClusterGroup.objects.all(),
        label='Cluster group (ID)',
    )
    cluster_group = django_filters.ModelMultipleChoiceFilter(
        field_name='cluster__group__slug',
        queryset=ClusterGroup.objects.all(),
        to_field_name='slug',
        label='Cluster group (slug)',
    )
    cluster_type_id = django_filters.ModelMultipleChoiceFilter(
        field_name='cluster__type',
        queryset=ClusterType.objects.all(),
        label='Cluster type (ID)',
    )
    cluster_type = django_filters.ModelMultipleChoiceFilter(
        field_name='cluster__type__slug',
        queryset=ClusterType.objects.all(),
        to_field_name='slug',
        label='Cluster type (slug)',
    )
    cluster_id = django_filters.ModelMultipleChoiceFilter(
        queryset=Cluster.objects.all(),
        label='Cluster (ID)',
    )
    region_id = TreeNodeMultipleChoiceFilter(
        queryset=Region.objects.all(),
        field_name='cluster__site__region',
        lookup_expr='in',
        label='Region (ID)',
    )
    region = TreeNodeMultipleChoiceFilter(
        queryset=Region.objects.all(),
        field_name='cluster__site__region',
        lookup_expr='in',
        to_field_name='slug',
        label='Region (slug)',
    )
    site_group_id = TreeNodeMultipleChoiceFilter(
        queryset=SiteGroup.objects.all(),
        field_name='cluster__site__group',
        lookup_expr='in',
        label='Site group (ID)',
    )
    site_group = TreeNodeMultipleChoiceFilter(
        queryset=SiteGroup.objects.all(),
        field_name='cluster__site__group',
        lookup_expr='in',
        to_field_name='slug',
        label='Site group (slug)',
    )
    site_id = django_filters.ModelMultipleChoiceFilter(
        field_name='cluster__site',
        queryset=Site.objects.all(),
        label='Site (ID)',
    )
    site = django_filters.ModelMultipleChoiceFilter(
        field_name='cluster__site__slug',
        queryset=Site.objects.all(),
        to_field_name='slug',
        label='Site (slug)',
    )
    role_id = django_filters.ModelMultipleChoiceFilter(
        queryset=DeviceRole.objects.all(),
        label='Role (ID)',
    )
    role = django_filters.ModelMultipleChoiceFilter(
        field_name='role__slug',
        queryset=DeviceRole.objects.all(),
        to_field_name='slug',
        label='Role (slug)',
    )
    platform_id = django_filters.ModelMultipleChoiceFilter(
        queryset=Platform.objects.all(),
        label='Platform (ID)',
    )
    platform = django_filters.ModelMultipleChoiceFilter(
        field_name='platform__slug',
        queryset=Platform.objects.all(),
        to_field_name='slug',
        label='Platform (slug)',
    )
    mac_address = MultiValueMACAddressFilter(
        field_name='interfaces__mac_address',
        label='MAC address',
    )
    has_primary_ip = django_filters.BooleanFilter(
        method='_has_primary_ip',
        label='Has a primary IP',
    )
    tag = TagFilter()

    class Meta:
        model = VirtualMachine
        fields = ['id', 'name', 'cluster', 'vcpus', 'memory', 'disk']

    def search(self, queryset, name, value):
        if not value.strip():
            return queryset
        return queryset.filter(
            Q(name__icontains=value) |
            Q(comments__icontains=value)
        )

    def _has_primary_ip(self, queryset, name, value):
        params = Q(primary_ip4__isnull=False) | Q(primary_ip6__isnull=False)
        if value:
            return queryset.filter(params)
        return queryset.exclude(params)
Exemple #9
0
class RangeFilter(django_filters.FilterSet):
    start_date = django_filters.DateFilter(
        field_name='date',
        lookup_expr='gt',
        input_formats=['%Y-%m-%d', '%d-%m-%Y', '%m-%Y', '%Y'])
    end_date = django_filters.DateFilter(
        field_name='date',
        lookup_expr='lt',
        input_formats=['%Y-%m-%d', '%d-%m-%Y', '%m-%Y', '%Y'])
    date = django_filters.DateFilter(
        field_name='date',
        lookup_expr='contains',
        input_formats=['%Y-%m-%d', '%d-%m-%Y', '%m-%Y', '%Y'])
    os = django_filters.CharFilter(field_name='os',
                                   lookup_expr='icontains',
                                   label="Os")
    country = django_filters.CharFilter(field_name='country',
                                        lookup_expr='icontains',
                                        label="Country")

    annotate = django_filters.CharFilter(method='fields_annotate',
                                         label='annotate')
    fields = django_filters.CharFilter(method='fields_selected',
                                       label='fields')
    cpi = django_filters.BooleanFilter(method='cpi_display', label='cpi')

    class Meta:
        model = Metric
        fields = ('start_date', 'end_date', 'date', 'os', 'country',
                  'annotate', 'fields', 'cpi')

    ## filter to annotate fields by it's function such as Max or Count
    def fields_annotate(self, queryset, value, *args, **kwargs):
        try:
            if args:

                fields = set(args[0].split(','))
                valid_fields = list(
                    queryset.values()[0].keys() if queryset.count() else [])
                valid_prefixes = ['sum', 'max', 'min', 'avg', 'count']

                fields_split = [tuple(f.split("_")) for f in fields]
                fields_to_annotate = dict()

                for m, field in fields_split:
                    if m in valid_prefixes and field in valid_fields:
                        if field not in list(fields_to_annotate.values()):
                            fields_to_annotate[m] = field
                            if m == "max":
                                queryset = queryset.annotate(
                                    **{field + "_": Max(field)})
                            elif m == "min":
                                queryset = queryset.annotate(
                                    **{field + "_": Min(field)})
                            elif m == "avg":
                                queryset = queryset.annotate(
                                    **{field + "_": Avg(field)})
                            elif m == "sum":
                                queryset = queryset.annotate(
                                    **{field + "_": Sum(field)})
                            elif m == "count":
                                queryset = queryset.annotate(
                                    **{field + "_": Count(field)})
        except ValueError:
            pass
        return queryset

    # filter to select specific fields. It is also useful to make a group_by annotation
    def fields_selected(self, queryset, value, *args, **kwargs):
        try:
            if args:
                fields = set(args[0].split(','))
                valid_fields = list(
                    queryset.values()[0].keys() if queryset.count() else [])
                fields_to_lookup = [f for f in fields if f in valid_fields]
                queryset = queryset.values(*fields_to_lookup)
        except ValueError:
            pass
        return queryset

    # filter to display to calculate and render the cpi value - cpi = spend / installs
    def cpi_display(self, queryset, value, *args, **kwargs):
        from django.db import models
        from django.db.models import Sum, F

        try:
            if args:
                value = args[0]
                if value:
                    queryset = queryset.annotate(
                        cpi=Sum(F('spend') / F('installs'),
                                output_field=models.FloatField()))
        except ValueError:
            pass
        return queryset

    # as dicts are not in order, make sure that annotation filter will get executed last to perform the group_by after values
    def filter_queryset(self, queryset):
        cleaned_data = OrderedDict(
            sorted(self.form.cleaned_data.items(), reverse=True))
        fields = cleaned_data.get('fields', None)
        annotate = cleaned_data.get('annotate', None)
        if fields is not None and annotate is not None:
            cleaned_data.move_to_end("annotate")
        for name, value in cleaned_data.items():
            queryset = self.filters[name].filter(queryset, value)
            assert isinstance(queryset, QuerySet), \
                "Expected '%s.%s' to return a QuerySet, but got a %s instead." \
                % (type(self).__name__, name, type(queryset).__name__)
        return queryset
Exemple #10
0
class BaseHookFilter(django_filters.FilterSet):
    author_uuid = django_filters.UUIDFilter(field_name='user__uuid')
    is_active = django_filters.BooleanFilter(widget=BooleanWidget)
    last_published = django_filters.DateTimeFilter()
Exemple #11
0
class MonsterInstanceFilter(django_filters.FilterSet):
    monster__name = django_filters.CharFilter(method='filter_monster__name')
    tags__pk = django_filters.ModelMultipleChoiceFilter(
        queryset=MonsterTag.objects.all(), to_field_name='pk', conjoined=True)
    monster__element = django_filters.MultipleChoiceFilter(
        choices=Monster.ELEMENT_CHOICES)
    monster__archetype = django_filters.MultipleChoiceFilter(
        choices=Monster.TYPE_CHOICES)
    monster__awaken_level = django_filters.MultipleChoiceFilter(
        choices=Monster.AWAKEN_CHOICES)
    priority = django_filters.MultipleChoiceFilter(
        choices=MonsterInstance.PRIORITY_CHOICES)
    monster__leader_skill__attribute = django_filters.MultipleChoiceFilter(
        choices=LeaderSkill.ATTRIBUTE_CHOICES)
    monster__leader_skill__area = django_filters.MultipleChoiceFilter(
        choices=LeaderSkill.AREA_CHOICES)
    monster__skills__scaling_stats__pk = django_filters.ModelMultipleChoiceFilter(
        queryset=ScalingStat.objects.all(), to_field_name='pk', conjoined=True)
    monster__skills__skill_effect__pk = django_filters.ModelMultipleChoiceFilter(
        queryset=SkillEffect.objects.all(),
        method='filter_monster__skills__skill_effect__pk')
    monster__skills__cooltime = django_filters.CharFilter(
        method='filter_monster_skills_cooltime')

    effects_logic = django_filters.BooleanFilter(method='filter_effects_logic')
    monster__fusion_food = django_filters.BooleanFilter(
        method='filter_monster__fusion_food')

    class Meta:
        model = MonsterInstance
        fields = {
            'monster__name': ['exact'],
            'tags__pk': ['exact'],
            'stars': ['gte', 'lte'],
            'level': ['gte', 'lte'],
            'monster__element': ['exact'],
            'monster__archetype': ['exact'],
            'monster__awaken_level': ['exact'],
            'priority': ['exact'],
            'monster__natural_stars': ['gte', 'lte'],
            'monster__leader_skill__attribute': ['exact'],
            'monster__leader_skill__area': ['exact'],
            'monster__skills__skill_effect__pk': ['exact'],
            'monster__skills__scaling_stats__pk': ['exact'],
            'monster__skills__hits': ['gte', 'lte'],
            'effects_logic': ['exact'],
            'fodder': ['exact'],
            'in_storage': ['exact'],
            'monster__fusion_food': ['exact'],
        }

    def filter_monster__name(self, queryset, name, value):
        if value:
            return queryset.filter(
                Q(monster__name__icontains=value)
                | Q(monster__awakens_from__name__icontains=value))
        else:
            return queryset

    def filter_monster__fusion_food(self, queryset, name, value):
        if value:
            return queryset.filter(monster__fusion_food=True).exclude(
                ignore_for_fusion=True)
        else:
            return queryset.filter(
                Q(monster__fusion_food=False) | Q(ignore_for_fusion=True))

    def filter_monster__skills__skill_effect__pk(self, queryset, name, value):
        old_filtering = self.form.cleaned_data.get('effects_logic', False)
        stat_scaling = self.form.cleaned_data.get(
            'monster__skills__scaling_stats__pk', [])
        cooltimes = self.form.cleaned_data.get('monster__skills__cooltime', [])

        try:
            cooltimes = cooltimes.split(',')
            min_cooltime = int(cooltimes[0])
            max_cooltime = int(cooltimes[1])
        except:
            min_cooltime = 0
            max_cooltime = 999

        if old_filtering:
            # Filter if any skill on the monster has the designated fields
            for effect in value:
                queryset = queryset.filter(
                    monster__skills__skill_effect=effect)

            for pk in stat_scaling:
                queryset = queryset.filter(monster__skills__scaling_stats=pk)

            cooltime_filter = Q(
                monster__skills__cooltime__gte=min_cooltime) & Q(
                    monster__skills__cooltime__lte=max_cooltime)
            if min_cooltime == 0 or max_cooltime == 0:
                cooltime_filter = Q(
                    monster__skills__cooltime__isnull=True) | cooltime_filter

            queryset = queryset.filter(cooltime_filter)

            return queryset.distinct()

        else:
            # Filter effects based on effects of each individual skill. This ensures a monster will not show up unless it has
            # the desired effects on the same skill rather than across any skills.

            skills = Skill.objects.all()

            for effect in value:
                skills = skills.filter(skill_effect=effect)

            for pk in stat_scaling:
                skills = skills.filter(scaling_stats=pk)

            cooltime_filter = Q(cooltime__gte=min_cooltime) & Q(
                cooltime__lte=max_cooltime)
            if min_cooltime == 0 or max_cooltime == 0:
                cooltime_filter = Q(cooltime__isnull=True) | cooltime_filter

            skills = skills.filter(cooltime_filter)

            return queryset.filter(monster__skills__in=skills).distinct()

    def filter_effects_logic(self, queryset, name, value):
        # This field is just used to alter the logic of skill effect filter and is used in filter_monster__skills__skill_effect__pk()
        return queryset

    def filter_monster_skills_cooltime(self, queryset, name, value):
        # This field is handled in filter_monster__skills__skill_effect__pk()
        return queryset
Exemple #12
0
class RuleFilter(django_filters.rest_framework.FilterSet):
    name = django_filters.CharFilter(field_name="name", lookup_expr="contains")
    parent = django_filters.CharFilter(field_name="parent__name",
                                       lookup_expr="contains")
    enabled = django_filters.BooleanFilter(field_name="enabled")
Exemple #13
0
class PartnershipAdminFilter(filters.FilterSet):
    ordering = MultipleOrderingFilter(
        fields=(('entity__organization__name', 'partner'), ('city', 'city'),
                ('acronym_path', 'ucl')),
        multiples={
            'country': ['country_name', 'city', 'entity__organization__name'],
        },
    )
    continent = filters.CharFilter(field_name='country_continent_id',
                                   method=filter_pk_from_annotation)
    partnership_type = filters.ChoiceFilter(
        field_name='partnership__partnership_type', )
    supervisor = filters.ModelChoiceFilter(
        field_name='partnership__supervisor', )
    partner_entity = filters.ModelChoiceFilter(field_name='entity')
    tags = filters.ModelMultipleChoiceFilter(field_name='partnership__tags', )
    country = filters.ModelChoiceFilter(
        field_name='country_id',
        method=filter_pk_from_annotation,
    )
    city = filters.CharFilter()
    ucl_entity = filters.ModelChoiceFilter(method='filter_ucl_entity')
    # This is a noop filter, as its logic is in filter_ucl_entity()
    ucl_entity_with_child = filters.BooleanFilter(method=lambda qs, *_: qs)
    partner_type = filters.CharFilter(field_name='entity__organization__type')
    education_level = filters.CharFilter(
        field_name='partnership__years__education_levels', )
    education_field = filters.CharFilter(
        field_name='partnership__years__education_fields', )
    years_entity = filters.CharFilter(method='filter_years_entity')
    university_offer = filters.CharFilter(method='filter_university_offer')
    partner_tags = filters.CharFilter(method='filter_partner_tags')
    erasmus_code = filters.CharFilter(
        field_name='entity__organization__partner__erasmus_code',
        lookup_expr='icontains',
    )
    use_egracons = filters.BooleanFilter(
        field_name='entity__organization__partner__use_egracons',
        widget=CustomNullBooleanSelect())
    is_sms = filters.BooleanFilter(
        field_name='partnership__years__is_sms',
        widget=CustomNullBooleanSelect(),
    )
    is_smp = filters.BooleanFilter(
        field_name='partnership__years__is_smp',
        widget=CustomNullBooleanSelect(),
    )
    is_sta = filters.BooleanFilter(
        field_name='partnership__years__is_sta',
        widget=CustomNullBooleanSelect(),
    )
    is_stt = filters.BooleanFilter(
        field_name='partnership__years__is_stt',
        widget=CustomNullBooleanSelect(),
    )
    is_smst = filters.BooleanFilter(
        field_name='partnership__years__is_smst',
        widget=CustomNullBooleanSelect(),
    )
    funding_type = filters.ModelChoiceFilter(
        field_name='partnership__years__funding_type', )
    funding_program = filters.ModelChoiceFilter(
        field_name='partnership__years__funding_type__program', )
    funding_source = filters.ModelChoiceFilter(
        field_name='partnership__years__funding_type__program__source', )
    partnership_in = filters.CharFilter(method='filter_partnership_in')
    subtype = filters.CharFilter(field_name='partnership__years__subtype', )
    partnership_ending_in = filters.CharFilter(
        method='filter_partnership_ending_in')
    partnership_valid_in = filters.CharFilter(
        method='filter_partnership_valid_in')
    partnership_not_valid_in = filters.CharFilter(
        method='filter_partnership_not_valid_in')
    partnership_with_no_agreements_in = filters.CharFilter(
        method='filter_partnership_with_no_agreements_in')
    partnership_date_type = filters.CharFilter(
        method='filter_partnership_date')
    # Noop filter, their logic is in filter_partnership_special_dates()
    partnership_date_from = filters.DateFilter(method=lambda qs, *_: qs)
    partnership_date_to = filters.DateFilter(method=lambda qs, *_: qs)
    comment = filters.CharFilter(
        field_name='partnership__comment',
        lookup_expr='icontains',
    )
    is_public = filters.BooleanFilter(
        field_name='partnership__is_public',
        widget=CustomNullBooleanSelect(),
    )

    class Meta:
        model = PartnershipPartnerRelation
        fields = [
            'ordering',
            'partnership_type',
            'partner_type',
            'ucl_entity',
            'education_level',
            'years_entity',
            'university_offer',
            'partner_entity',
            'erasmus_code',
            'use_egracons',
            'continent',
            'country',
            'city',
            'partner_tags',
            'education_field',
            'is_sms',
            'is_smp',
            'is_sta',
            'is_stt',
            'is_smst',
            'funding_type',
            'funding_program',
            'funding_source',
            'supervisor',
            'tags',
            'partnership_in',
            'partnership_ending_in',
            'partnership_valid_in',
            'partnership_not_valid_in',
            'partnership_with_no_agreements_in',
            'partnership_date_type',
            'partnership_date_from',
            'partnership_date_to',
            'comment',
            'is_public',
        ]

    @property
    def form(self):
        if not hasattr(self, '_form'):
            if self.is_bound:
                self._form = PartnershipFilterForm(
                    self.data,
                    user=self.request.user,
                    prefix=self.form_prefix,
                )
            else:
                self._form = PartnershipFilterForm(
                    user=self.request.user,
                    prefix=self.form_prefix,
                )
        return self._form

    @staticmethod
    def filter_years_entity(queryset, name, value):
        if value:
            queryset = queryset.filter(
                Q(partnership__years__entities=value)
                | Q(partnership__years__entities__isnull=True))
        return queryset

    def filter_ucl_entity(self, queryset, name, value):
        if value:
            if self.form.cleaned_data.get('ucl_entity_with_child', False):
                # Allow all children of entity too
                cte = EntityVersion.objects.with_parents(entity_id=value.pk)
                qs = cte.queryset().with_cte(cte).values('entity_id')
                queryset = queryset.filter(partnership__ucl_entity__in=qs)
            else:
                queryset = queryset.filter(partnership__ucl_entity=value)

        return queryset

    @staticmethod
    def filter_partner_tags(queryset, name, value):
        if value:
            queryset = queryset.filter(
                entity__organization__partner__tags__in=value)
        return queryset

    @staticmethod
    def filter_university_offer(queryset, name, value):
        if value:
            queryset = queryset.filter(
                Q(partnership__years__offers=value)
                | Q(partnership__years__offers__isnull=True))
        return queryset

    @staticmethod
    def filter_partnership_in(queryset, name, value):
        if value:
            queryset = queryset.annotate(has_in=Exists(
                PartnershipAgreement.objects.filter(
                    partnership=OuterRef('partnership_id'),
                    start_academic_year__start_date__lte=value.start_date,
                    end_academic_year__end_date__gte=value.end_date,
                ))).filter(has_in=True)
        return queryset

    @staticmethod
    def filter_partnership_ending_in(queryset, name, value):
        if value:
            queryset = (queryset.annotate(ending_date=Max(
                'partnership__agreements__end_academic_year__end_date')).
                        filter(ending_date=value.end_date))
        return queryset

    @staticmethod
    def filter_partnership_valid_in(queryset, name, value):
        if value:
            queryset = queryset.annotate(has_valid=Exists(
                PartnershipAgreement.objects.filter(
                    partnership=OuterRef('partnership_id'),
                    status=AgreementStatus.VALIDATED.name,
                    start_academic_year__start_date__lte=value.start_date,
                    end_academic_year__end_date__gte=value.end_date,
                ))).filter(has_valid=True)
        return queryset

    @staticmethod
    def filter_partnership_not_valid_in(queryset, name, value):
        if value:
            queryset = queryset.annotate(
                not_valid_in_has_agreements=Exists(
                    PartnershipAgreement.objects.filter(
                        partnership=OuterRef('partnership_id'),
                    ).filter(
                        start_academic_year__start_date__lte=value.start_date,
                        end_academic_year__end_date__gte=value.end_date,
                    ), ),
                not_valid_in_has_valid_agreements=Exists(
                    PartnershipAgreement.objects.filter(
                        partnership=OuterRef('partnership_id'),
                    ).filter(
                        status=AgreementStatus.VALIDATED.name,
                        start_academic_year__start_date__lte=value.start_date,
                        end_academic_year__end_date__gte=value.end_date,
                    ), )).filter(
                        not_valid_in_has_agreements=True,
                        not_valid_in_has_valid_agreements=False,
                    )
        return queryset

    @staticmethod
    def filter_partnership_with_no_agreements_in(queryset, name, value):
        if value:
            queryset = queryset.annotate(
                no_agreements_in_has_years=Exists(
                    PartnershipYear.objects.filter(
                        partnership=OuterRef('partnership_id'),
                        academic_year=value,
                    )),
                no_agreements_in_has_agreements=Exists(
                    PartnershipAgreement.objects.filter(
                        partnership=OuterRef('partnership_id'),
                        start_academic_year__start_date__lte=value.start_date,
                        end_academic_year__end_date__gte=value.end_date,
                    )),
            ).filter(
                no_agreements_in_has_years=True,
                no_agreements_in_has_agreements=False,
            )
        return queryset

    def filter_partnership_date(self, queryset, name, value):
        # Prevent filtering on partnership when agreement filter
        if isinstance(self, PartnershipAgreementAdminFilter
                      ) and queryset.model == PartnershipPartnerRelation:
            return queryset

        date_from = self.form.cleaned_data['partnership_date_from']
        date_to = self.form.cleaned_data.get('partnership_date_to')
        if value == DateFilterType.ONGOING.name:
            if not date_to:
                # start_date < filter_date < end_date
                return queryset.filter(
                    partnership__start_date__lte=date_from,
                    partnership__end_date__gte=date_from,
                )
            # periods must intersect
            return queryset.filter(
                Q(partnership__start_date__lte=date_from,
                  partnership__end_date__gte=date_from)
                | Q(partnership__start_date__lte=date_to,
                    partnership__end_date__gte=date_to), )
        elif value == DateFilterType.STOPPING.name:
            # filter_date_0 < end_date < filter_date_1
            return queryset.filter(
                partnership__end_date__gte=date_from,
                partnership__end_date__lte=date_to,
            )
Exemple #14
0
class IssueExtFieldFilter(filters.FilterSet):
    isOptional = django_filters.BooleanFilter(name='is_optional')

    class Meta:
        model = IssueExtField
        fields = ('name', 'default', 'isOptional', 'type')
Exemple #15
0
class TraineeFilter(AMYFilterSet):
    search = django_filters.CharFilter(
        method=filter_trainees_by_trainee_name_or_email, label="Name or Email"
    )

    all_persons = django_filters.BooleanFilter(
        label="Include all people, not only trainees",
        method=filter_all_persons,
        widget=widgets.CheckboxInput,
    )

    homework = django_filters.BooleanFilter(
        label="Only trainees with unevaluated homework",
        widget=widgets.CheckboxInput,
        method=filter_trainees_by_unevaluated_homework_presence,
    )

    training_request = django_filters.BooleanFilter(
        label="Is training request present?",
        method=filter_trainees_by_training_request_presence,
    )

    is_instructor = django_filters.ChoiceFilter(
        label="Is Instructor?",
        method=filter_trainees_by_instructor_status,
        choices=[
            ("", "Unknown"),
            ("all", "All instructor badges"),
            ("any", "Any instructor badge "),
            ("swc", "SWC instructor"),
            ("dc", "DC instructor"),
            ("lc", "LC instructor"),
            ("eligible", "No, but eligible to be certified"),
            ("no", "No instructor badge"),
        ],
    )

    training = django_filters.ModelChoiceFilter(
        queryset=Event.objects.ttt(),
        method=filter_trainees_by_training,
        label="Training",
        widget=ModelSelect2Widget(
            data_view="ttt-event-lookup",
            attrs=SELECT2_SIDEBAR,
        ),
    )

    order_by = NamesOrderingFilter(
        fields=(
            "last_login",
            "email",
        ),
    )

    class Meta:
        model = Person
        fields = [
            "search",
            "all_persons",
            "homework",
            "is_instructor",
            "training",
        ]
Exemple #16
0
class DRYFilter(django_filters.FilterSet):
    name = django_filters.CharFilter(lookup_expr='icontains')
    score = django_filters.RangeFilter()
    rank = django_filters.NumberFilter()
    in_stock = django_filters.BooleanFilter()
    price = django_filters.RangeFilter()
Exemple #17
0
class DeviceTypeFilterSet(BaseFilterSet, CustomFieldModelFilterSet, CreatedUpdatedFilterSet):
    q = django_filters.CharFilter(
        method='search',
        label='Search',
    )
    manufacturer_id = django_filters.ModelMultipleChoiceFilter(
        queryset=Manufacturer.objects.all(),
        label='Manufacturer (ID)',
    )
    manufacturer = django_filters.ModelMultipleChoiceFilter(
        field_name='manufacturer__slug',
        queryset=Manufacturer.objects.all(),
        to_field_name='slug',
        label='Manufacturer (slug)',
    )
    console_ports = django_filters.BooleanFilter(
        method='_console_ports',
        label='Has console ports',
    )
    console_server_ports = django_filters.BooleanFilter(
        method='_console_server_ports',
        label='Has console server ports',
    )
    power_ports = django_filters.BooleanFilter(
        method='_power_ports',
        label='Has power ports',
    )
    power_outlets = django_filters.BooleanFilter(
        method='_power_outlets',
        label='Has power outlets',
    )
    interfaces = django_filters.BooleanFilter(
        method='_interfaces',
        label='Has interfaces',
    )
    pass_through_ports = django_filters.BooleanFilter(
        method='_pass_through_ports',
        label='Has pass-through ports',
    )
    device_bays = django_filters.BooleanFilter(
        method='_device_bays',
        label='Has device bays',
    )
    tag = TagFilter()

    class Meta:
        model = DeviceType
        fields = [
            'id', 'model', 'slug', 'part_number', 'u_height', 'is_full_depth', 'subdevice_role',
        ]

    def search(self, queryset, name, value):
        if not value.strip():
            return queryset
        return queryset.filter(
            Q(manufacturer__name__icontains=value) |
            Q(model__icontains=value) |
            Q(part_number__icontains=value) |
            Q(comments__icontains=value)
        )

    def _console_ports(self, queryset, name, value):
        return queryset.exclude(consoleporttemplates__isnull=value)

    def _console_server_ports(self, queryset, name, value):
        return queryset.exclude(consoleserverporttemplates__isnull=value)

    def _power_ports(self, queryset, name, value):
        return queryset.exclude(powerporttemplates__isnull=value)

    def _power_outlets(self, queryset, name, value):
        return queryset.exclude(poweroutlettemplates__isnull=value)

    def _interfaces(self, queryset, name, value):
        return queryset.exclude(interfacetemplates__isnull=value)

    def _pass_through_ports(self, queryset, name, value):
        return queryset.exclude(
            frontporttemplates__isnull=value,
            rearporttemplates__isnull=value
        )

    def _device_bays(self, queryset, name, value):
        return queryset.exclude(devicebaytemplates__isnull=value)
class EducationalOfferFilter(django_filters.FilterSet):
    eduoffer_institution = django_filters.ModelChoiceFilter(
        label=FieldEducationalOffer.INSTITUTION,
        queryset=Institution.objects.all(),
        widget=autocomplete.ModelSelect2(url='institution-autocomplete'))
    eduoffer_position_text = django_filters.CharFilter(
        label=FieldEducationalOffer.POSITION,
        lookup_expr='icontains',
        widget=forms.TextInput(attrs={'class': 'list__form--input'}))
    eduoffer_type = django_filters.ModelMultipleChoiceFilter(
        label=FieldEducationalOffer.TYPE,
        queryset=EducationalOfferType.objects.all(),
        widget=autocomplete.ModelSelect2Multiple(
            url='educationaloffertype-autocomplete'))
    eduoffer_mode = django_filters.ModelMultipleChoiceFilter(
        label=FieldEducationalOffer.MODE,
        queryset=EducationalOfferMode.objects.all(),
        widget=autocomplete.ModelSelect2Multiple(
            url='educationaloffermode-autocomplete'))
    eduoffer_city__region = django_filters.ModelChoiceFilter(
        label=FieldEducationalOffer.REGION,
        queryset=Region.objects.all(),
        widget=autocomplete.ModelSelect2(url='region-autocomplete'))
    eduoffer_city = django_filters.ModelChoiceFilter(
        label=FieldEducationalOffer.CITY,
        queryset=City.objects.all(),
        widget=autocomplete.ModelSelect2(url='city-autocomplete'))
    eduoffer_date_start = django_filters.DateFilter(
        label=FieldEducationalOffer.DATE_START,
        lookup_expr='gte',
        widget=forms.DateInput(
            attrs={'class': 'datepicker list__form--input'}))
    eduoffer_date_end = django_filters.DateFilter(
        label=FieldEducationalOffer.DATE_END,
        lookup_expr='lte',
        widget=forms.DateInput(
            attrs={'class': 'datepicker list__form--input'}))
    eduoffer_keywords = django_filters.ModelMultipleChoiceFilter(
        label=FieldEducationalOffer.KEYWORDS,
        queryset=Tag.objects.all(),
        widget=autocomplete.ModelSelect2Multiple(url='tag-autocomplete'))
    eduoffer_is_accepted = django_filters.BooleanFilter(
        label=FieldEducationalOffer.IS_ACCEPTED,
        widget=NullBooleanSelect(attrs={'class': 'select2'}))

    o = django_filters.OrderingFilter(fields=(
        ('eduoffer_is_promoted', 'eduoffer_is_promoted'),
        ('eduoffer_date_add', 'eduoffer_date_add'),
        ('eduoffer_position_text', 'eduoffer_position_text'),
        ('eduoffer_date_end', 'eduoffer_date_end'),
    ), )

    strict = True

    class Meta:
        model = EducationalOffer
        form = EducationalOfferFilterForm
        fields = [
            'eduoffer_institution', 'eduoffer_position_text', 'eduoffer_type',
            'eduoffer_mode', 'eduoffer_city__region', 'eduoffer_city',
            'eduoffer_date_start', 'eduoffer_date_end', 'eduoffer_keywords',
            'eduoffer_is_accepted'
        ]
Exemple #19
0
class CableTerminationFilterSet(django_filters.FilterSet):
    cabled = django_filters.BooleanFilter(
        field_name='cable',
        lookup_expr='isnull',
        exclude=True
    )
Exemple #20
0
class ResourceFilterSet(django_filters.FilterSet):
    def __init__(self, *args, **kwargs):
        self.user = kwargs.pop('user')
        super().__init__(*args, **kwargs)

    purpose = ParentCharFilter(field_name='purposes__id', lookup_expr='iexact')
    type = django_filters.Filter(field_name='type__id',
                                 lookup_expr='in',
                                 widget=django_filters.widgets.CSVWidget)
    people = django_filters.NumberFilter(field_name='people_capacity',
                                         lookup_expr='gte')
    need_manual_confirmation = django_filters.BooleanFilter(
        field_name='need_manual_confirmation', widget=DRFFilterBooleanWidget)
    is_favorite = django_filters.BooleanFilter(method='filter_is_favorite',
                                               widget=DRFFilterBooleanWidget)
    unit = django_filters.CharFilter(field_name='unit__id',
                                     lookup_expr='iexact')
    resource_group = django_filters.Filter(
        field_name='groups__identifier',
        lookup_expr='in',
        widget=django_filters.widgets.CSVWidget,
        distinct=True)
    equipment = django_filters.Filter(
        field_name='resource_equipment__equipment__id',
        lookup_expr='in',
        widget=django_filters.widgets.CSVWidget,
        distinct=True)
    available_between = django_filters.Filter(
        method='filter_available_between',
        widget=django_filters.widgets.CSVWidget)
    free_of_charge = django_filters.BooleanFilter(
        method='filter_free_of_charge', widget=DRFFilterBooleanWidget)
    municipality = django_filters.Filter(
        field_name='unit__municipality_id',
        lookup_expr='in',
        widget=django_filters.widgets.CSVWidget,
        distinct=True)
    order_by = ResourceOrderingFilter(fields=(
        ('name_fi', 'resource_name_fi'),
        ('name_en', 'resource_name_en'),
        ('name_sv', 'resource_name_sv'),
        ('unit__name_fi', 'unit_name_fi'),
        ('unit__name_en', 'unit_name_en'),
        ('unit__name_sv', 'unit_name_sv'),
        ('type__name_fi', 'type_name_fi'),
        ('type__name_en', 'type_name_en'),
        ('type__name_sv', 'type_name_sv'),
        ('people_capacity', 'people_capacity'),
        ('accessibility_priority', 'accessibility'),
    ), )

    def filter_is_favorite(self, queryset, name, value):
        if not self.user.is_authenticated:
            if value:
                return queryset.none()
            else:
                return queryset

        if value:
            return queryset.filter(favorited_by=self.user)
        else:
            return queryset.exclude(favorited_by=self.user)

    def filter_free_of_charge(self, queryset, name, value):
        qs = Q(min_price__lte=0) | Q(min_price__isnull=True)
        if value:
            return queryset.filter(qs)
        else:
            return queryset.exclude(qs)

    def _deserialize_datetime(self, value):
        try:
            return arrow.get(value).datetime
        except ParserError:
            raise exceptions.ParseError(
                "'%s' must be a timestamp in ISO 8601 format" % value)

    def filter_available_between(self, queryset, name, value):
        if len(value) < 2 or len(value) > 3:
            raise exceptions.ParseError(
                'available_between takes two or three comma-separated values.')

        available_start = self._deserialize_datetime(value[0])
        available_end = self._deserialize_datetime(value[1])

        if available_start.date() != available_end.date():
            raise exceptions.ParseError(
                'available_between timestamps must be on the same day.')
        overlapping_reservations = Reservation.objects.filter(
            resource__in=queryset,
            end__gt=available_start,
            begin__lt=available_end).current()

        if len(value) == 2:
            return self._filter_available_between_whole_range(
                queryset, overlapping_reservations, available_start,
                available_end)
        else:
            try:
                period = datetime.timedelta(minutes=int(value[2]))
            except ValueError:
                raise exceptions.ParseError(
                    'available_between period must be an integer.')
            return self._filter_available_between_with_period(
                queryset, overlapping_reservations, available_start,
                available_end, period)

    def _filter_available_between_whole_range(self, queryset, reservations,
                                              available_start, available_end):
        # exclude resources that have reservation(s) overlapping with the available_between range
        queryset = queryset.exclude(reservations__in=reservations)
        closed_resource_ids = {
            resource.id
            for resource in queryset if not self._is_resource_open(
                resource, available_start, available_end)
        }

        return queryset.exclude(id__in=closed_resource_ids)

    @staticmethod
    def _is_resource_open(resource, start, end):
        opening_hours = resource.get_opening_hours(start, end)
        if len(opening_hours) > 1:
            # range spans over multiple days, assume resources aren't open all night and skip the resource
            return False

        hours = next(iter(opening_hours.values()))[
            0]  # assume there is only one hours obj per day
        if not hours['opens'] and not hours['closes']:
            return False

        start_too_early = hours['opens'] and start < hours['opens']
        end_too_late = hours['closes'] and end > hours['closes']
        if start_too_early or end_too_late:
            return False

        return True

    def _filter_available_between_with_period(self, queryset, reservations,
                                              available_start, available_end,
                                              period):
        reservations = reservations.order_by('begin').select_related(
            'resource')

        reservations_by_resource = collections.defaultdict(list)
        for reservation in reservations:
            reservations_by_resource[reservation.resource_id].append(
                reservation)

        available_resources = set()

        hours_qs = ResourceDailyOpeningHours.objects.filter(
            open_between__overlap=(available_start, available_end, '[)'))

        # check the resources one by one to determine which ones have open slots
        for resource in queryset.prefetch_related(None).prefetch_related(
                Prefetch('opening_hours',
                         queryset=hours_qs,
                         to_attr='prefetched_opening_hours')):
            reservations = reservations_by_resource[resource.id]

            if self._is_resource_available(resource, available_start,
                                           available_end, reservations,
                                           period):
                available_resources.add(resource.id)

        return queryset.filter(id__in=available_resources)

    @staticmethod
    def _is_resource_available(resource, available_start, available_end,
                               reservations, period):
        opening_hours = resource.get_opening_hours(
            available_start, available_end, resource.prefetched_opening_hours)
        hours = next(iter(opening_hours.values()))[
            0]  # assume there is only one hours obj per day

        if not (hours['opens'] or hours['closes']):
            return False

        current = max(
            available_start,
            hours['opens']) if hours['opens'] is not None else available_start
        end = min(
            available_end,
            hours['closes']) if hours['closes'] is not None else available_end

        if current >= end:
            # the resource is already closed
            return False

        if not reservations:
            # the resource has no reservations, just check if the period fits in the resource's opening times
            if end - current >= period:
                return True
            return False

        # try to find an open slot between reservations and opening / closing times.
        # start from period start time or opening time depending on which one is earlier.
        for reservation in reservations:
            if reservation.end <= current:
                # this reservation is in the past
                continue
            if reservation.begin - current >= period:
                # found an open slot before the reservation currently being examined
                return True
            if reservation.end > end:
                # the reservation currently being examined ends after the period or closing time,
                # so no free slots
                return False
            # did not find an open slot before the reservation currently being examined,
            # proceed to next reservation
            current = reservation.end
        else:
            # all reservations checked and no free slot found, check if there is a free slot after the last
            # reservation
            if end - reservation.end >= period:
                return True

        return False

    class Meta:
        model = Resource
        fields = [
            'purpose', 'type', 'people', 'need_manual_confirmation',
            'is_favorite', 'unit', 'available_between', 'min_price'
        ]
Exemple #21
0
class EventDateFilter(django_filters.FilterSet):
    event_start__gte = django_filters.DateTimeFilter(field_name='event_start',
                                                     lookup_expr='gte')
    event_start__lte = django_filters.DateTimeFilter(field_name='event_start',
                                                     lookup_expr='lte')
    event_end__gte = django_filters.DateTimeFilter(field_name='event_end',
                                                   lookup_expr='gte')
    event_end__lte = django_filters.DateTimeFilter(field_name='event_end',
                                                   lookup_expr='lte')
    attendance_event__isnull = django_filters.BooleanFilter(
        field_name='attendance_event', lookup_expr='isnull')
    is_attendee = django_filters.BooleanFilter(field_name='attendance_event',
                                               method='filter_is_attendee')
    can_change = django_filters.BooleanFilter(method='filter_can_change')
    can_attend = django_filters.BooleanFilter(method='filter_can_attend')
    event_type = BaseNumberInFilter(field_name='event_type', lookup_expr='in')
    companies = BaseNumberInFilter(field_name='companies',
                                   lookup_expr='company__in')

    def filter_can_attend(self, queryset, name, value):
        """
        Filter events based on if the user can attend said event.
        """
        """ User cannot attend events if they are not logged in """
        if not self.request.user.is_authenticated:
            return queryset.none()

        if value:
            events_with_attendance = queryset.filter(
                attendance_event__isnull=False)
            events_without_attendance = queryset.filter(
                attendance_event__isnull=True)
            user_attendable_event_pks = []
            for event in events_with_attendance:
                response = event.attendance_event.rules_satisfied(
                    self.request.user)
                can_attend = response.get('status', None)
                if can_attend:
                    user_attendable_event_pks.append(event.id)

            user_attendable_events = events_with_attendance.filter(
                attendance_event__pk__in=user_attendable_event_pks)
            all_available_events = user_attendable_events | events_without_attendance
            return all_available_events

        return queryset.all()

    def filter_is_attendee(self, queryset, name, value):
        """
        Filter events based on if a user is attending them or not.
        """
        """ User cannot attend events if they are not logged in """
        if not self.request.user.is_authenticated:
            return queryset.none()

        user_attendees = Attendee.objects.filter(user=self.request.user)
        attending_events = [attendee.event.pk for attendee in user_attendees]
        if value:
            return queryset.filter(pk__in=attending_events)
        return queryset.all()

    def filter_can_change(self, queryset, name, value):
        """
        Filter events based on if the user has permission to change them
        """
        """ If filter is set to False, don't filter """
        if not value:
            return queryset

        user = self.request.user
        """ User cannot attend events if they are not logged in """
        if not user.is_authenticated:
            return queryset.none()
        """ Don't filter on this field if user is a superuser """
        if user.is_superuser:
            return queryset

        allowed_events = get_objects_for_user(user,
                                              'events.change_event',
                                              accept_global_perms=False,
                                              klass=queryset)
        return allowed_events

    class Meta:
        model = Event
        fields = ('event_start', 'event_end', 'event_type', 'is_attendee')
Exemple #22
0
class SnailMailTaskFilterSet(TaskFilterSet):
    """Allows snail mail tasks to be filtered by category, as well as the
    presence of a tracking number or an agency note."""
    category = django_filters.ChoiceFilter(choices=[('', 'All')] +
                                           SNAIL_MAIL_CATEGORIES)
    has_address = django_filters.ChoiceFilter(
        method='filter_has_address',
        label='Has address',
        choices=BOOLEAN_CHOICES,
    )
    has_attachments = django_filters.ChoiceFilter(
        method='filter_has_attachments',
        label='Has attachments',
        choices=BOOLEAN_CHOICES,
    )
    has_tracking_number = django_filters.ChoiceFilter(
        method='filter_has_tracking_number',
        label='Has tracking number',
        choices=BOOLEAN_CHOICES,
    )
    has_agency_notes = django_filters.ChoiceFilter(
        method='filter_has_agency_notes',
        label='Has agency notes',
        choices=BOOLEAN_CHOICES,
    )
    resolved = django_filters.BooleanFilter(label='Show Resolved',
                                            widget=forms.CheckboxInput())
    resolved_by = django_filters.ModelMultipleChoiceFilter(
        queryset=User.objects.all(),
        widget=autocomplete_light.MultipleChoiceWidget('UserTaskAutocomplete'))

    def blank_choice(self, queryset, name, value):
        """Check if the value is blank"""
        if value == 'True':
            return queryset.exclude(**{name: ''})
        elif value == 'False':
            return queryset.filter(**{name: ''})
        return queryset

    def filter_has_address(self, queryset, name, value):
        """Check if the foia has an address."""
        #pylint: disable=unused-argument
        if value == 'True':
            return queryset.exclude(communication__foia__address=None)
        else:
            return queryset.filter(communication__foia__address=None)

    def filter_has_attachments(self, queryset, name, value):
        """Check if the communication has attachments."""
        #pylint: disable=unused-argument
        if value == 'True':
            return queryset.exclude(communication__files=None)
        else:
            return queryset.filter(communication__files=None)

    def filter_has_tracking_number(self, queryset, name, value):
        """Check if the foia has a tracking number."""
        #pylint: disable=unused-argument
        if value == 'True':
            return queryset.exclude(communication__foia__tracking_ids=None)
        else:
            return queryset.filter(communication__foia__tracking_ids=None)

    def filter_has_agency_notes(self, queryset, name, value):
        """Check if the agency has notes."""
        #pylint: disable=unused-argument
        return self.blank_choice(queryset,
                                 'communication__foia__agency__notes', value)

    class Meta:
        model = SnailMailTask
        fields = [
            'category',
            'has_address',
            'has_attachments',
            'has_tracking_number',
            'has_agency_notes',
            'resolved',
            'resolved_by',
        ]
class PerformanceAlertSummaryFilter(django_filters.FilterSet):
    id = django_filters.NumberFilter(field_name='id')
    status = django_filters.NumberFilter(field_name='status')
    framework = django_filters.NumberFilter(field_name='framework')
    repository = django_filters.NumberFilter(field_name='repository')
    alerts__series_signature = django_filters.NumberFilter(
        field_name='alerts__series_signature')
    filter_text = django_filters.CharFilter(method='_filter_text')
    hide_improvements = django_filters.BooleanFilter(
        method='_hide_improvements')
    hide_related_and_invalid = django_filters.BooleanFilter(
        method='_hide_related_and_invalid')
    with_assignee = django_filters.CharFilter(method='_with_assignee')

    def _filter_text(self, queryset, name, value):
        sep = Value(' ')
        words = value.split(' ')

        contains_all_words = [Q(full_name__contains=word) for word in words]

        # Django's distinct(*fields) isn't supported for MySQL
        # https://code.djangoproject.com/ticket/17974
        filtered_summaries = (queryset.annotate(full_name=Concat(
            'alerts__series_signature__suite',
            sep,
            'alerts__series_signature__test',
            sep,
            'alerts__series_signature__platform__platform',
            sep,
            'alerts__series_signature__extra_options',
            sep,
            'bug_number',
            sep,
            'push__revision',
            output_field=CharField(),
        )).filter(*contains_all_words).values('id').distinct())

        return queryset.filter(id__in=Subquery(filtered_summaries))

    def _hide_improvements(self, queryset, name, value):
        return queryset.annotate(
            total_regressions=Count('alerts__is_regression')).filter(
                alerts__is_regression=True, total_regressions__gte=1)

    def _hide_related_and_invalid(self, queryset, name, value):
        return queryset.exclude(status__in=[
            PerformanceAlertSummary.DOWNSTREAM,
            PerformanceAlertSummary.REASSIGNED,
            PerformanceAlertSummary.INVALID,
        ])

    def _with_assignee(self, queryset, name, value):
        return queryset.filter(assignee__username=value)

    class Meta:
        model = PerformanceAlertSummary
        fields = [
            'id',
            'status',
            'framework',
            'repository',
            'alerts__series_signature',
            'filter_text',
            'hide_improvements',
            'hide_related_and_invalid',
            'with_assignee',
        ]
Exemple #24
0
class DeviceFilter(CustomFieldFilterSet, django_filters.FilterSet):
    q = django_filters.MethodFilter(
        action='search',
        label='Search',
    )
    site_id = django_filters.ModelMultipleChoiceFilter(
        name='rack__site',
        queryset=Site.objects.all(),
        label='Site (ID)',
    )
    site = django_filters.ModelMultipleChoiceFilter(
        name='rack__site',
        queryset=Site.objects.all(),
        to_field_name='slug',
        label='Site name (slug)',
    )
    rack_group_id = django_filters.ModelMultipleChoiceFilter(
        name='rack__group',
        queryset=RackGroup.objects.all(),
        label='Rack group (ID)',
    )
    rack_id = django_filters.ModelMultipleChoiceFilter(
        name='rack',
        queryset=Rack.objects.all(),
        label='Rack (ID)',
    )
    role_id = django_filters.ModelMultipleChoiceFilter(
        name='device_role',
        queryset=DeviceRole.objects.all(),
        label='Role (ID)',
    )
    role = django_filters.ModelMultipleChoiceFilter(
        name='device_role',
        queryset=DeviceRole.objects.all(),
        to_field_name='slug',
        label='Role (slug)',
    )
    tenant_id = NullableModelMultipleChoiceFilter(
        name='tenant',
        queryset=Tenant.objects.all(),
        label='Tenant (ID)',
    )
    tenant = NullableModelMultipleChoiceFilter(
        name='tenant',
        queryset=Tenant.objects.all(),
        to_field_name='slug',
        label='Tenant (slug)',
    )
    device_type_id = django_filters.ModelMultipleChoiceFilter(
        name='device_type',
        queryset=DeviceType.objects.all(),
        label='Device type (ID)',
    )
    manufacturer_id = django_filters.ModelMultipleChoiceFilter(
        name='device_type__manufacturer',
        queryset=Manufacturer.objects.all(),
        label='Manufacturer (ID)',
    )
    manufacturer = django_filters.ModelMultipleChoiceFilter(
        name='device_type__manufacturer',
        queryset=Manufacturer.objects.all(),
        to_field_name='slug',
        label='Manufacturer (slug)',
    )
    model = django_filters.ModelMultipleChoiceFilter(
        name='device_type',
        queryset=DeviceType.objects.all(),
        to_field_name='slug',
        label='Device model (slug)',
    )
    platform_id = NullableModelMultipleChoiceFilter(
        name='platform',
        queryset=Platform.objects.all(),
        label='Platform (ID)',
    )
    platform = NullableModelMultipleChoiceFilter(
        name='platform',
        queryset=Platform.objects.all(),
        to_field_name='slug',
        label='Platform (slug)',
    )
    status = django_filters.BooleanFilter(
        name='status',
        label='Status',
    )
    is_console_server = django_filters.BooleanFilter(
        name='device_type__is_console_server',
        label='Is a console server',
    )
    is_pdu = django_filters.BooleanFilter(
        name='device_type__is_pdu',
        label='Is a PDU',
    )
    is_network_device = django_filters.BooleanFilter(
        name='device_type__is_network_device',
        label='Is a network device',
    )

    class Meta:
        model = Device
        fields = ['q', 'name', 'serial', 'asset_tag', 'site_id', 'site', 'rack_id', 'role_id', 'role', 'device_type_id',
                  'manufacturer_id', 'manufacturer', 'model', 'platform_id', 'platform', 'status', 'is_console_server',
                  'is_pdu', 'is_network_device']

    def search(self, queryset, value):
        return queryset.filter(
            Q(name__icontains=value) |
            Q(serial__icontains=value.strip()) |
            Q(modules__serial__icontains=value.strip()) |
            Q(asset_tag=value.strip()) |
            Q(comments__icontains=value)
        ).distinct()
class ExperimentFilterset(filters.FilterSet):

    search = filters.CharFilter(
        method="filter_search",
        widget=SearchWidget(
            attrs={"class": "form-control", "placeholder": "Search Experiments"}
        ),
    )
    type = filters.MultipleChoiceFilter(
        choices=Experiment.TYPE_CHOICES,
        conjoined=False,
        widget=forms.SelectMultiple(attrs={"class": "form-control"}),
    )
    status = filters.ChoiceFilter(
        empty_label="All Statuses",
        choices=Experiment.STATUS_CHOICES,
        widget=forms.Select(attrs={"class": "form-control"}),
    )
    firefox_channel = filters.ChoiceFilter(
        empty_label="All Channels",
        choices=Experiment.CHANNEL_CHOICES[1:],
        widget=forms.Select(attrs={"class": "form-control"}),
    )
    firefox_version = filters.ChoiceFilter(
        empty_label="All Versions",
        choices=Experiment.VERSION_CHOICES[1:],
        widget=forms.Select(attrs={"class": "form-control"}),
        method="version_filter",
    )
    owner = filters.ModelChoiceFilter(
        empty_label="All Owners",
        queryset=get_user_model().objects.all().order_by("email"),
        widget=forms.Select(attrs={"class": "form-control"}),
    )
    analysis_owner = filters.ModelChoiceFilter(
        empty_label="All Data Scientists",
        queryset=get_user_model().objects.all().order_by("email"),
        widget=forms.Select(attrs={"class": "form-control"}),
    )

    archived = filters.BooleanFilter(
        label="Show archived experiments",
        widget=forms.CheckboxInput(),
        method="archived_filter",
    )
    experiment_date_field = filters.ChoiceFilter(
        empty_label="No Date Restriction",
        choices=[
            (Experiment.EXPERIMENT_STARTS, "Experiment Starts"),
            (Experiment.EXPERIMENT_PAUSES, "Experiment Pauses"),
            (Experiment.EXPERIMENT_ENDS, "Experiment Ends"),
        ],
        widget=forms.Select(attrs={"class": "form-control"}),
        method="experiment_date_field_filter",
    )
    date_range = filters.DateFromToRangeFilter(
        method="date_range_filter",
        widget=DateRangeWidget(attrs={"type": "date", "class": "form-control"}),
    )

    in_qa = filters.BooleanFilter(
        label="Show only experiments in QA",
        widget=forms.CheckboxInput(),
        method="in_qa_filter",
    )

    surveys = filters.BooleanFilter(
        label="Show experiments with surveys",
        widget=forms.CheckboxInput(),
        method="surveys_filter",
    )

    subscribed = filters.BooleanFilter(
        label="Show subscribed experiments",
        widget=forms.CheckboxInput(),
        method="subscribed_filter",
    )

    longrunning = filters.BooleanFilter(
        label="Show long-running experiments",
        widget=forms.CheckboxInput(),
        method="longrunning_filter",
    )

    is_paused = filters.BooleanFilter(
        label="Show enrollment complete experiments",
        widget=forms.CheckboxInput(),
        method="is_paused_filter",
    )

    class Meta:
        model = Experiment
        fields = (
            "search",
            "type",
            "status",
            "firefox_channel",
            "firefox_version",
            "owner",
            "analysis_owner",
            "in_qa",
            "surveys",
            "archived",
            "subscribed",
            "longrunning",
            "is_paused",
        )

    def filter_search(self, queryset, name, value):
        vector = SearchVector(
            "name",
            "short_description",
            "owner__email",
            "analysis_owner__email",
            "slug",
            "related_work",
            "addon_experiment_id",
            "pref_key",
            "public_name",
            "public_description",
            "objectives",
            "analysis",
            "engineering_owner",
            "bugzilla_id",
            "normandy_slug",
            "data_science_bugzilla_url",
            "feature_bugzilla_url",
        )

        query = SearchQuery(value)

        return (
            queryset.annotate(rank=SearchRank(vector, query), search=vector)
            .filter(search=value)
            .order_by("-rank")
        )

    def archived_filter(self, queryset, name, value):
        if not value:
            return queryset.exclude(archived=True)
        return queryset

    def experiment_date_field_filter(self, queryset, name, value):
        # this custom method isn't doing anything. There has to
        # be a custom method to be able to display the select
        # filter that controls which date range we show
        return queryset

    def version_filter(self, queryset, name, value):
        return queryset.filter(
            Q(firefox_min_version__lte=value, firefox_max_version__gte=value)
            | Q(firefox_min_version=value)
        )

    def date_range_filter(self, queryset, name, value):
        date_type = self.form.cleaned_data["experiment_date_field"]

        experiment_date_field = {
            Experiment.EXPERIMENT_STARTS: "start_date",
            Experiment.EXPERIMENT_PAUSES: "enrollment_end_date",
            Experiment.EXPERIMENT_ENDS: "end_date",
        }[date_type]

        results = []

        for experiment in queryset.all():
            date = getattr(experiment, experiment_date_field)

            # enrollment end dates are optional, so there won't always
            # be a pause date for an experiment
            if date:
                if value.start and date < value.start.date():
                    continue
                if value.stop and date > value.stop.date():
                    continue
                results.append(experiment.id)

        return queryset.filter(pk__in=results)

    def in_qa_filter(self, queryset, name, value):
        if value:
            return queryset.filter(review_qa_requested=True, review_qa=False)

        return queryset

    def surveys_filter(self, queryset, name, value):
        if value:
            return queryset.filter(survey_required=True)

        return queryset

    def subscribed_filter(self, queryset, name, value):
        if value:
            return queryset.filter(subscribers__in=[self.request.user.id])

        return queryset

    def longrunning_filter(self, queryset, name, value):
        if value:
            return (
                queryset.exclude(firefox_max_version__exact="")
                .annotate(
                    firefox_min_int=Cast(
                        Func(
                            F("firefox_min_version"),
                            Value(ExperimentConstants.VERSION_REGEX.pattern),
                            function="substring",
                        ),
                        IntegerField(),
                    ),
                    firefox_max_int=Cast(
                        Func(
                            F("firefox_max_version"),
                            Value(ExperimentConstants.VERSION_REGEX.pattern),
                            function="substring",
                        ),
                        IntegerField(),
                    ),
                    version_count=F("firefox_max_int") - F("firefox_min_int"),
                )
                .filter(version_count__gte=3)
            )

        return queryset

    def is_paused_filter(self, queryset, name, value):
        if value:
            return queryset.filter(is_paused=True, status=Experiment.STATUS_LIVE)

        return queryset

    def get_type_display_value(self):
        return ", ".join(
            [
                dict(Experiment.TYPE_CHOICES)[type].replace(" Experiment", "")
                for type in self.data.getlist("type")
            ]
        )

    def get_owner_display_value(self):
        user_id = self.data.get("owner")

        if user_id is not None:
            return str(get_user_model().objects.get(id=user_id))

    def get_display_start_date_info(self):
        experiment_date_field = self.data.get("experiment_date_field")
        date_after = self.data.get("date_range_after")
        date_before = self.data.get("date_range_before")

        if date_after and date_before:
            return f"{experiment_date_field} between {date_after} and {date_before}"
        elif date_after and date_before == "":
            return f"{experiment_date_field} after {date_after}"
        elif date_after == "" and date_before:
            return f"{experiment_date_field} before {date_before}"
        else:
            return ""
Exemple #26
0
class NormaFilterSet(django_filters.FilterSet):

    ano = django_filters.ChoiceFilter(required=False,
                                      label='Ano',
                                      choices=choice_anos_com_normas)

    ementa = django_filters.CharFilter(
        label=_('Pesquisar expressões na ementa'),
        help_text=_(
            '"Para busca no conteúdo das normas, use a Pesquisa Textual"'),
        method='filter_ementa')

    numero = django_filters.CharFilter(label=_('Número'),
                                       method='filter_numero')

    apelido = django_filters.CharFilter(lookup_expr='icontains',
                                        label=_('Apelido'))

    indexacao = django_filters.CharFilter(lookup_expr='icontains',
                                          label=_('Indexação'))

    assuntos = django_filters.ModelChoiceFilter(
        queryset=AssuntoNorma.objects.all())

    vigencia = django_filters.BooleanFilter(label='Vigência',
                                            method='filter_vigencia')

    signeds = django_filters.ChoiceFilter(required=False,
                                          choices=CHOICE_SIGNEDS,
                                          label=_('Com Assinatura Digital?'),
                                          method='filter_signeds')

    o = NormaPesquisaOrderingFilter(help_text='')

    class Meta(FilterOverridesMetaMixin):
        model = NormaJuridica
        fields = [
            'tipo', 'numero', 'ano', 'data', 'data_vigencia',
            'data_publicacao', 'ementa', 'assuntos', 'apelido'
        ]

    def __init__(self, *args, **kwargs):
        super(NormaFilterSet, self).__init__(*args, **kwargs)

        row1 = to_row([('tipo', 4), ('numero', 4), ('ano', 4)])
        row2 = to_row([('ementa', 6), ('assuntos', 6)])
        row3 = to_row([('data', 6), ('data_publicacao', 6)])
        #row4 = to_row([('data_vigencia', 10), ('vigencia', 2)])
        row5 = to_row([('o', 4), ('signeds', 4), ('apelido', 4)])

        self.form.helper = SaplFormHelper()
        self.form.helper.form_method = 'GET'
        self.form.helper.layout = Layout(
            Fieldset(
                _('''
                Pesquisa de Norma<br>
                <small>
                <strong class="text-red">TODOS OS CAMPOS SÃO OPCIONAIS!</strong>
                </small>
                '''),
                row1,
                row2,
                row3,
                row5,  # row4,
                form_actions(label='Pesquisar')))

    def filter_ementa(self, queryset, name, value):
        texto = value.split()
        q = Q()
        for t in texto:
            q &= Q(ementa__icontains=t)
        return queryset.filter(q)

    def filter_signeds(self, queryset, name, value):
        q = Q()

        if not value:
            return queryset

        if value == '1':
            q &= Q(metadata__signs__texto_integral__0__isnull=False)

        else:
            q &= (Q(metadata__signs__texto_integral__isnull=True)
                  | Q(metadata__signs__texto_integral__len=0))

        return queryset.filter(q)

    def filter_vigencia(self, queryset, name, value):
        data_atual = timezone.now()
        if value:
            queryset = queryset.filter(
                Q(data_vigencia__lt=data_atual)
                | Q(data_vigencia__isnull=True))
        else:
            queryset = queryset.filter(data_vigencia__gt=data_atual)

        return queryset

    def filter_numero(self, qs, name, value):

        value = value.replace('.', '')
        value = value.replace(',', '')
        if len(value) > 2:
            qs = qs.filter(numero__icontains=value)
        else:
            qs = qs.filter(numero=value)

        return qs
Exemple #27
0
class DeviceFilter(CustomFieldFilterSet, django_filters.FilterSet):
    id__in = NumericInFilter(name='id', lookup_expr='in')
    q = django_filters.CharFilter(
        method='search',
        label='Search',
    )
    manufacturer_id = django_filters.ModelMultipleChoiceFilter(
        name='device_type__manufacturer',
        queryset=Manufacturer.objects.all(),
        label='Manufacturer (ID)',
    )
    manufacturer = django_filters.ModelMultipleChoiceFilter(
        name='device_type__manufacturer__slug',
        queryset=Manufacturer.objects.all(),
        to_field_name='slug',
        label='Manufacturer (slug)',
    )
    device_type_id = django_filters.ModelMultipleChoiceFilter(
        queryset=DeviceType.objects.all(),
        label='Device type (ID)',
    )
    role_id = django_filters.ModelMultipleChoiceFilter(
        name='device_role_id',
        queryset=DeviceRole.objects.all(),
        label='Role (ID)',
    )
    role = django_filters.ModelMultipleChoiceFilter(
        name='device_role__slug',
        queryset=DeviceRole.objects.all(),
        to_field_name='slug',
        label='Role (slug)',
    )
    tenant_id = NullableModelMultipleChoiceFilter(
        queryset=Tenant.objects.all(),
        label='Tenant (ID)',
    )
    tenant = NullableModelMultipleChoiceFilter(
        name='tenant',
        queryset=Tenant.objects.all(),
        to_field_name='slug',
        label='Tenant (slug)',
    )
    platform_id = NullableModelMultipleChoiceFilter(
        queryset=Platform.objects.all(),
        label='Platform (ID)',
    )
    platform = NullableModelMultipleChoiceFilter(
        name='platform',
        queryset=Platform.objects.all(),
        to_field_name='slug',
        label='Platform (slug)',
    )
    name = NullableCharFieldFilter()
    asset_tag = NullableCharFieldFilter()
    site_id = django_filters.ModelMultipleChoiceFilter(
        queryset=Site.objects.all(),
        label='Site (ID)',
    )
    site = django_filters.ModelMultipleChoiceFilter(
        name='site__slug',
        queryset=Site.objects.all(),
        to_field_name='slug',
        label='Site name (slug)',
    )
    rack_group_id = django_filters.ModelMultipleChoiceFilter(
        name='rack__group',
        queryset=RackGroup.objects.all(),
        label='Rack group (ID)',
    )
    rack_id = NullableModelMultipleChoiceFilter(
        name='rack',
        queryset=Rack.objects.all(),
        label='Rack (ID)',
    )
    model = django_filters.ModelMultipleChoiceFilter(
        name='device_type__slug',
        queryset=DeviceType.objects.all(),
        to_field_name='slug',
        label='Device model (slug)',
    )
    status = django_filters.MultipleChoiceFilter(choices=STATUS_CHOICES)
    is_full_depth = django_filters.BooleanFilter(
        name='device_type__is_full_depth',
        label='Is full depth',
    )
    is_console_server = django_filters.BooleanFilter(
        name='device_type__is_console_server',
        label='Is a console server',
    )
    is_pdu = django_filters.BooleanFilter(
        name='device_type__is_pdu',
        label='Is a PDU',
    )
    is_network_device = django_filters.BooleanFilter(
        name='device_type__is_network_device',
        label='Is a network device',
    )
    mac_address = django_filters.CharFilter(
        method='_mac_address',
        label='MAC address',
    )
    has_primary_ip = django_filters.BooleanFilter(
        method='_has_primary_ip',
        label='Has a primary IP',
    )

    class Meta:
        model = Device
        fields = ['serial']

    def search(self, queryset, name, value):
        if not value.strip():
            return queryset
        qs_filter = (Q(name__icontains=value)
                     | Q(serial__icontains=value.strip())
                     | Q(inventory_items__serial__icontains=value.strip())
                     | Q(asset_tag=value.strip())
                     | Q(comments__icontains=value))
        # If the query value looks like a MAC address, search interfaces as well.
        try:
            mac = EUI(value.strip())
            qs_filter |= Q(interfaces__mac_address=mac)
        except AddrFormatError:
            pass
        return queryset.filter(qs_filter).distinct()

    def _mac_address(self, queryset, name, value):
        value = value.strip()
        if not value:
            return queryset
        try:
            mac = EUI(value.strip())
            return queryset.filter(interfaces__mac_address=mac).distinct()
        except AddrFormatError:
            return queryset.none()

    def _has_primary_ip(self, queryset, name, value):
        if value:
            return queryset.filter(
                Q(primary_ip4__isnull=False) | Q(primary_ip6__isnull=False))
        else:
            return queryset.exclude(
                Q(primary_ip4__isnull=False) | Q(primary_ip6__isnull=False))
Exemple #28
0
class InterfaceFilter(django_filters.FilterSet):
    """
    Not using DeviceComponentFilterSet for Interfaces because we need to check for VirtualChassis membership.
    """
    q = django_filters.CharFilter(
        method='search',
        label='Search',
    )
    device = django_filters.CharFilter(
        method='filter_device',
        field_name='name',
        label='Device',
    )
    device_id = MultiValueNumberFilter(
        method='filter_device_id',
        field_name='pk',
        label='Device (ID)',
    )
    cabled = django_filters.BooleanFilter(field_name='cable',
                                          lookup_expr='isnull',
                                          exclude=True)
    kind = django_filters.CharFilter(
        method='filter_kind',
        label='Kind of interface',
    )
    lag_id = django_filters.ModelMultipleChoiceFilter(
        field_name='lag',
        queryset=Interface.objects.all(),
        label='LAG interface (ID)',
    )
    mac_address = MultiValueMACAddressFilter()
    tag = TagFilter()
    vlan_id = django_filters.CharFilter(method='filter_vlan_id',
                                        label='Assigned VLAN')
    vlan = django_filters.CharFilter(method='filter_vlan',
                                     label='Assigned VID')
    type = django_filters.MultipleChoiceFilter(choices=IFACE_TYPE_CHOICES,
                                               null_value=None)

    class Meta:
        model = Interface
        fields = [
            'id', 'name', 'connection_status', 'type', 'enabled', 'mtu',
            'mgmt_only', 'mode', 'description'
        ]

    def search(self, queryset, name, value):
        if not value.strip():
            return queryset
        return queryset.filter(
            Q(name__icontains=value)
            | Q(description__icontains=value)).distinct()

    def filter_device(self, queryset, name, value):
        try:
            device = Device.objects.get(**{name: value})
            vc_interface_ids = device.vc_interfaces.values_list('id',
                                                                flat=True)
            return queryset.filter(pk__in=vc_interface_ids)
        except Device.DoesNotExist:
            return queryset.none()

    def filter_device_id(self, queryset, name, id_list):
        # Include interfaces belonging to peer virtual chassis members
        vc_interface_ids = []
        try:
            devices = Device.objects.filter(pk__in=id_list)
            for device in devices:
                vc_interface_ids += device.vc_interfaces.values_list('id',
                                                                     flat=True)
            return queryset.filter(pk__in=vc_interface_ids)
        except Device.DoesNotExist:
            return queryset.none()

    def filter_vlan_id(self, queryset, name, value):
        value = value.strip()
        if not value:
            return queryset
        return queryset.filter(
            Q(untagged_vlan_id=value) | Q(tagged_vlans=value))

    def filter_vlan(self, queryset, name, value):
        value = value.strip()
        if not value:
            return queryset
        return queryset.filter(
            Q(untagged_vlan_id__vid=value) | Q(tagged_vlans__vid=value))

    def filter_kind(self, queryset, name, value):
        value = value.strip().lower()
        return {
            'physical': queryset.exclude(type__in=NONCONNECTABLE_IFACE_TYPES),
            'virtual': queryset.filter(type__in=VIRTUAL_IFACE_TYPES),
            'wireless': queryset.filter(type__in=WIRELESS_IFACE_TYPES),
        }.get(value, queryset.none())
Exemple #29
0
class IPAddressFilterSet(BaseFilterSet, TenancyFilterSet, CustomFieldFilterSet,
                         CreatedUpdatedFilterSet):
    q = django_filters.CharFilter(
        method='search',
        label='Search',
    )
    family = django_filters.NumberFilter(field_name='address',
                                         lookup_expr='family')
    parent = django_filters.CharFilter(
        method='search_by_parent',
        label='Parent prefix',
    )
    address = MultiValueCharFilter(
        method='filter_address',
        label='Address',
    )
    mask_length = django_filters.NumberFilter(
        method='filter_mask_length',
        label='Mask length',
    )
    vrf_id = django_filters.ModelMultipleChoiceFilter(
        queryset=VRF.objects.all(),
        label='VRF',
    )
    vrf = django_filters.ModelMultipleChoiceFilter(
        field_name='vrf__rd',
        queryset=VRF.objects.all(),
        to_field_name='rd',
        label='VRF (RD)',
    )
    device = MultiValueCharFilter(
        method='filter_device',
        field_name='name',
        label='Device (name)',
    )
    device_id = MultiValueNumberFilter(
        method='filter_device',
        field_name='pk',
        label='Device (ID)',
    )
    virtual_machine_id = django_filters.ModelMultipleChoiceFilter(
        field_name='interface__virtual_machine',
        queryset=VirtualMachine.objects.all(),
        label='Virtual machine (ID)',
    )
    virtual_machine = django_filters.ModelMultipleChoiceFilter(
        field_name='interface__virtual_machine__name',
        queryset=VirtualMachine.objects.all(),
        to_field_name='name',
        label='Virtual machine (name)',
    )
    interface = django_filters.ModelMultipleChoiceFilter(
        field_name='interface__name',
        queryset=Interface.objects.all(),
        to_field_name='name',
        label='Interface (ID)',
    )
    interface_id = django_filters.ModelMultipleChoiceFilter(
        queryset=Interface.objects.all(),
        label='Interface (ID)',
    )
    assigned_to_interface = django_filters.BooleanFilter(
        method='_assigned_to_interface',
        label='Is assigned to an interface',
    )
    status = django_filters.MultipleChoiceFilter(
        choices=IPAddressStatusChoices, null_value=None)
    role = django_filters.MultipleChoiceFilter(choices=IPAddressRoleChoices)
    tag = TagFilter()

    class Meta:
        model = IPAddress
        fields = ['id', 'dns_name']

    def search(self, queryset, name, value):
        if not value.strip():
            return queryset
        qs_filter = (Q(dns_name__icontains=value)
                     | Q(description__icontains=value)
                     | Q(address__istartswith=value))
        return queryset.filter(qs_filter)

    def search_by_parent(self, queryset, name, value):
        value = value.strip()
        if not value:
            return queryset
        try:
            query = str(netaddr.IPNetwork(value.strip()).cidr)
            return queryset.filter(address__net_host_contained=query)
        except (AddrFormatError, ValueError):
            return queryset.none()

    def filter_address(self, queryset, name, value):
        try:
            return queryset.filter(address__net_in=value)
        except ValidationError:
            return queryset.none()

    def filter_mask_length(self, queryset, name, value):
        if not value:
            return queryset
        return queryset.filter(address__net_mask_length=value)

    def filter_device(self, queryset, name, value):
        try:
            devices = Device.objects.prefetch_related('device_type').filter(
                **{'{}__in'.format(name): value})
            vc_interface_ids = []
            for device in devices:
                vc_interface_ids.extend(
                    [i['id'] for i in device.vc_interfaces.values('id')])
            return queryset.filter(interface_id__in=vc_interface_ids)
        except Device.DoesNotExist:
            return queryset.none()

    def _assigned_to_interface(self, queryset, name, value):
        return queryset.exclude(interface__isnull=value)
Exemple #30
0
class DomainFilter(django_filters.FilterSet):
    """
    Filter :model:`shepherd.Domain` model for searching.

    **Fields**

    ``name``
        Case insensitive search of the name field contents
    ``categorization``
        Case insensitive search of the categorization field
    ``health_status``
        Checkbox choice filter using :model:`shepherd.HealthStatus`
    ``domain_status``
        Checkbox choice filter using :model:`shepherd.DomainStatus`
    ``exclude_expired``
        Checkbox to exclude expired domains from search results
    """

    name = django_filters.CharFilter(
        lookup_expr="icontains",
        label="Domain Name Contains",
        widget=TextInput(attrs={
            "placeholder": "Domain Name",
            "autocomplete": "off"
        }),
    )
    categorization = django_filters.CharFilter(
        lookup_expr="icontains",
        label="Categories Contain",
        widget=TextInput(attrs={
            "placeholder": "Category",
            "autocomplete": "off"
        }),
    )
    health_status = django_filters.ModelMultipleChoiceFilter(
        queryset=HealthStatus.objects.all(),
        widget=forms.CheckboxSelectMultiple,
        label="",
    )
    domain_status = django_filters.ModelMultipleChoiceFilter(
        queryset=DomainStatus.objects.all(),
        widget=forms.CheckboxSelectMultiple,
        label="",
    )

    exclude_expired = django_filters.BooleanFilter(
        label="Filter Expired",
        method="filter_expired",
        widget=forms.CheckboxInput,
    )

    class Meta:
        model = Domain
        fields = ["name", "categorization", "health_status", "domain_status"]

    def filter_expired(self, queryset, name, value):
        """
        Choose to include or exclude expired domains in search results.
        """
        if value:
            # return queryset.filter(Q(expiration__lt=date.today()) & Q(auto_renew=False))
            return queryset.filter(
                Q(expiration__gte=date.today()) | Q(auto_renew=True))
        return queryset

    def __init__(self, *args, **kwargs):
        super().__init__(*args, **kwargs)
        self.helper = FormHelper()
        self.helper.form_method = "get"
        self.helper.form_class = "newitem"
        self.helper.form_show_labels = True
        # Layout the form for Bootstrap
        self.helper.layout = Layout(
            Row(
                Column(
                    PrependedText("name", '<i class="fas fa-filter"></i>'),
                    css_class="col-md-6",
                ),
                Column(
                    PrependedText("categorization",
                                  '<i class="fas fa-filter"></i>'),
                    css_class="col-md-6",
                ),
                css_class="form-row",
            ),
            Accordion(
                AccordionGroup("Domain Status",
                               InlineCheckboxes("domain_status"),
                               SwitchToggle("exclude_expired")),
                AccordionGroup("Health Status",
                               InlineCheckboxes("health_status")),
            ),
            ButtonHolder(
                HTML("""
                    <a class="btn btn-info col-md-2" role="button" href="{%  url 'shepherd:domain_create' %}">Create</a>
                    """),
                Submit("submit_btn",
                       "Filter",
                       css_class="btn btn-primary col-md-2"),
                HTML("""
                    <a class="btn btn-outline-secondary col-md-2" role="button" href="{%  url 'shepherd:domains' %}">Reset</a>
                    """),
            ),
        )