graphene-djangoではrelayを使う前提であるので注意

grahpene-djangoのハマりポイントとして、filterを作る際にフロントではrelayを使う前提であると言うことが一つ挙げられる。

docs.graphene-python.org


順調にquery, mutationを実装していき、relayを使わない決断をしてしまったあと、filterを実装するとき、公式サイトでこれを見つける。

https://docs.graphene-python.org/projects/django/en/latest/tutorial-relay/
https://docs.graphene-python.org/projects/django/en/latest/filtering/

# cookbook/ingredients/schema.py
from graphene import relay, ObjectType
from graphene_django import DjangoObjectType
from graphene_django.filter import DjangoFilterConnectionField

from ingredients.models import Category, Ingredient


# Graphene will automatically map the Category model's fields onto the CategoryNode.
# This is configured in the CategoryNode's Meta class (as you can see below)
class CategoryNode(DjangoObjectType):
    class Meta:
        model = Category
        filter_fields = ['name', 'ingredients']
        interfaces = (relay.Node, )


class IngredientNode(DjangoObjectType):
    class Meta:
        model = Ingredient
        # Allow for some more advanced filtering here
        filter_fields = {
            'name': ['exact', 'icontains', 'istartswith'],
            'notes': ['exact', 'icontains'],
            'category': ['exact'],
            'category__name': ['exact'],
        }
        interfaces = (relay.Node, )


class Query(object):
    category = relay.Node.Field(CategoryNode)
    all_categories = DjangoFilterConnectionField(CategoryNode)

    ingredient = relay.Node.Field(IngredientNode)
    all_ingredients = DjangoFilterConnectionField(IngredientNode)
query {
  allCategories {
    edges {
      node {
        name,
        ingredients {
          edges {
            node {
              name
            }
          }
        }
      }
    }
  }
}

これはあんまりイケてない。relayを使うとそうなのかもしれないけれど、relayを使っていないのにこのqueryの返りはダメだ。
本当はこうしたい

query {
  allCategories {
    name,
    ingredients {
      name
    }
  }
}

なるほど、もしかするとrelayを使わないといけないの?と思いissueを確認すると、
github.com

引用

Did you have any feedback on whether your propose is valid? It would be awesome to have that baked in graphene-django (I really don't want to use relay).

I'd gladly help with the implementation

I still do not understand why graphene-django only focuses on the implementation of graphql with Relay since Django can be used with any frontend framework

とにかくみんな困っているみたいだ。(I really don't want to use relay).

解決法

graphene-django-extrasを使う
github.com

This package add some extra functionalities to graphene-django to facilitate the graphql use without Relay:

  1. Allows pagination and filtering on Queries.
  2. Allows to define DjangoRestFramework serializers based Mutations.
  3. Allows use Directives on Queries and Fragments.

つまり without Relayでfilterやpagenationを実装できると言うことである。
5000円寄付しました。ありがとうeamigo86。