diff --git a/src/documents/filters.py b/src/documents/filters.py index 2c8baa62f..1770f8514 100644 --- a/src/documents/filters.py +++ b/src/documents/filters.py @@ -156,6 +156,16 @@ class CustomFieldFilterSet(FilterSet): class CustomFieldsFilter(Filter): def filter(self, qs, value): if value: + fields_with_matching_selects = CustomField.objects.filter( + extra_data__icontains=value, + ) + option_ids = [] + if fields_with_matching_selects.count() > 0: + for field in fields_with_matching_selects: + options = field.extra_data.get("select_options", []) + for index, option in enumerate(options): + if option.lower().find(value.lower()) != -1: + option_ids.extend([index]) return ( qs.filter(custom_fields__field__name__icontains=value) | qs.filter(custom_fields__value_text__icontains=value) @@ -166,6 +176,7 @@ class CustomFieldsFilter(Filter): | qs.filter(custom_fields__value_url__icontains=value) | qs.filter(custom_fields__value_monetary__icontains=value) | qs.filter(custom_fields__value_document_ids__icontains=value) + | qs.filter(custom_fields__value_select__in=option_ids) ) else: return qs diff --git a/src/documents/tests/test_api_documents.py b/src/documents/tests/test_api_documents.py index 4ad6cb828..5a8169d1d 100644 --- a/src/documents/tests/test_api_documents.py +++ b/src/documents/tests/test_api_documents.py @@ -641,6 +641,38 @@ class TestDocumentApi(DirectoriesMixin, DocumentConsumeDelayMixin, APITestCase): self.assertEqual(len(results), 1) self.assertEqual(results[0]["id"], doc3.id) + def test_custom_field_select_filter(self): + """ + GIVEN: + - Documents with select custom field values + WHEN: + - API request with custom field filtering is made + THEN: + - Only docs with selected custom field values are returned + """ + doc1 = Document.objects.create(checksum="1", content="test 1") + Document.objects.create(checksum="2", content="test 2") + custom_field_select = CustomField.objects.create( + name="Test Custom Field Select", + data_type=CustomField.FieldDataType.SELECT, + extra_data={ + "select_options": ["Option 1", "Choice 2"], + }, + ) + CustomFieldInstance.objects.create( + document=doc1, + field=custom_field_select, + value_select=1, + ) + + r = self.client.get("/api/documents/?custom_fields__icontains=choice") + self.assertEqual(r.status_code, status.HTTP_200_OK) + self.assertEqual(r.data["count"], 1) + + r = self.client.get("/api/documents/?custom_fields__icontains=option") + self.assertEqual(r.status_code, status.HTTP_200_OK) + self.assertEqual(r.data["count"], 0) + def test_document_checksum_filter(self): Document.objects.create( title="none1",