From 75946f97f5a7d822a42983b18b12640a642684c0 Mon Sep 17 00:00:00 2001 From: Alejandro Nunez Capote Date: Mon, 3 Jun 2019 01:06:18 -0400 Subject: [PATCH] testing interaction between DjangoFilterConnectionField and DjangoESFilterConnectionField to get a QS --- .../elasticsearch/filter/fields.py | 4 +- .../elasticsearch/filter/filterset.py | 2 +- .../elasticsearch/tests/filters.py | 26 +++++++++ .../elasticsearch/tests/test_fields.py | 56 ++++++++++++++++++- 4 files changed, 83 insertions(+), 5 deletions(-) diff --git a/graphene_django/elasticsearch/filter/fields.py b/graphene_django/elasticsearch/filter/fields.py index bbacadb..5324d0b 100644 --- a/graphene_django/elasticsearch/filter/fields.py +++ b/graphene_django/elasticsearch/filter/fields.py @@ -1,13 +1,13 @@ +from elasticsearch_dsl.query import Query from graphene_django.elasticsearch.filter.bridges import QuerysetBridge from graphene_django.filter import DjangoFilterConnectionField -from elasticsearch_dsl.query import Query class DjangoESFilterConnectionField(DjangoFilterConnectionField): """A Field to replace DjangoFilterConnectionField manager by QuerysetBridge""" def get_manager(self): - """Retuning a QuerysetBridge to replace the direct use over the QS""" + """Returning a QuerysetBridge to replace the direct use over the QS""" return QuerysetBridge(search=self.filterset_class._meta.index.search()) def merge_querysets(cls, default_queryset, queryset): diff --git a/graphene_django/elasticsearch/filter/filterset.py b/graphene_django/elasticsearch/filter/filterset.py index 556e2aa..cb10793 100644 --- a/graphene_django/elasticsearch/filter/filterset.py +++ b/graphene_django/elasticsearch/filter/filterset.py @@ -92,7 +92,7 @@ class FilterSetES(six.with_metaclass(FilterSetESMetaclass, object)): """ query_base = Q("bool") for name, filter_es in six.iteritems(self.declared_filters): - query_filter = filter_es.get_q(self.data) + query_filter = filter_es.get_q(self.data) if len(self.data) else None if query_filter is not None: query_base += query_filter return query_base diff --git a/graphene_django/elasticsearch/tests/filters.py b/graphene_django/elasticsearch/tests/filters.py index 2cabc80..c0aed52 100644 --- a/graphene_django/elasticsearch/tests/filters.py +++ b/graphene_django/elasticsearch/tests/filters.py @@ -1,8 +1,34 @@ +from graphene import ObjectType +from django_elasticsearch_dsl import DocType, Index +from graphene_django.tests.models import Article +from graphene_django.filter.tests.test_fields import ArticleNode from graphene_django.elasticsearch.filter import filters +from graphene_django.elasticsearch.filter.fields import DjangoESFilterConnectionField from graphene_django.elasticsearch.filter.filterset import FilterSetES +ads_index = Index('articles') + + +@ads_index.doc_type +class ArticleDocument(DocType): + """Article document describing Index""" + class Meta(object): + """Metaclass config""" + model = Article + class ArticleFilterES(FilterSetES): + """Article Filter for ES""" + class Meta(object): + """Metaclass data""" + index = ArticleDocument headline = filters.StringFilterES(attr='headline') + + +class ESFilterQuery(ObjectType): + """A query for ES fields""" + articles = DjangoESFilterConnectionField( + ArticleNode, filterset_class=ArticleFilterES + ) diff --git a/graphene_django/elasticsearch/tests/test_fields.py b/graphene_django/elasticsearch/tests/test_fields.py index 62f73d6..5fab90e 100644 --- a/graphene_django/elasticsearch/tests/test_fields.py +++ b/graphene_django/elasticsearch/tests/test_fields.py @@ -1,9 +1,13 @@ +from datetime import datetime + import pytest +from mock import mock +from graphene import Schema +from graphene_django.tests.models import Article, Reporter from graphene_django.filter.tests.test_fields import assert_arguments, ArticleNode - -from graphene_django.elasticsearch.tests.filters import ArticleFilterES from graphene_django.utils import DJANGO_FILTER_INSTALLED, DJANGO_ELASTICSEARCH_DSL_INSTALLED +from graphene_django.elasticsearch.tests.filters import ArticleFilterES, ESFilterQuery pytestmark = [] @@ -25,3 +29,51 @@ pytestmark.append(pytest.mark.django_db) def test_filter_string_fields(): field = DjangoFilterConnectionField(ArticleNode, filterset_class=ArticleFilterES) assert_arguments(field, "headline", "headline_term") + + +def test_filter_query(): + r1 = Reporter.objects.create(first_name="r1", last_name="r1", email="r1@test.com") + + a1 = Article.objects.create( + headline="a1", + pub_date=datetime.now(), + pub_date_time=datetime.now(), + reporter=r1, + editor=r1, + ) + a2 = Article.objects.create( + headline="a2", + pub_date=datetime.now(), + pub_date_time=datetime.now(), + reporter=r1, + editor=r1, + ) + + query = """ + query { + articles { + edges { + node { + headline + } + } + } + } + """ + + mock_count = mock.Mock(return_value=3) + mock_slice = mock.Mock(return_value=mock.Mock(to_queryset=mock.Mock( + return_value=Article.objects.filter(pk__in=[a1.id, a2.id]) + ))) + + with mock.patch('django_elasticsearch_dsl.search.Search.count', mock_count),\ + mock.patch('django_elasticsearch_dsl.search.Search.__getitem__', mock_slice): + + schema = Schema(query=ESFilterQuery) + result = schema.execute(query) + + assert not result.errors + + assert len(result.data["articles"]["edges"]) == 2 + assert result.data["articles"]["edges"][0]["node"]["headline"] == "a1" + assert result.data["articles"]["edges"][1]["node"]["headline"] == "a2"