mirror of
https://github.com/graphql-python/graphene-django.git
synced 2025-07-13 17:52:19 +03:00
add a new subclass and a few tests [WIP]
This commit is contained in:
parent
1e34dfb3e5
commit
ff69b07267
60
graphene_django/input_types.py
Normal file
60
graphene_django/input_types.py
Normal file
|
@ -0,0 +1,60 @@
|
||||||
|
import collections
|
||||||
|
from graphene_django import converter, utils
|
||||||
|
|
||||||
|
from graphene.types.utils import merge
|
||||||
|
from graphene.utils.is_base_type import is_base_type
|
||||||
|
|
||||||
|
|
||||||
|
def convert_fields(model, only_fields, exclude_fields):
|
||||||
|
model_fields = utils.get_model_fields(model=model)
|
||||||
|
fields = collections.OrderedDict()
|
||||||
|
|
||||||
|
for name, field in model_fields:
|
||||||
|
is_not_in_only = only_fields and name not in only_fields
|
||||||
|
is_already_created = name in model_fields
|
||||||
|
is_excluded = name in exclude_fields or is_already_created
|
||||||
|
# https://docs.djangoproject.com/en/1.10/ref/models/fields/#django.db.models.ForeignKey.related_query_name
|
||||||
|
is_no_backref = str(name).endswith('+')
|
||||||
|
if is_not_in_only or is_excluded or is_no_backref:
|
||||||
|
# We skip this field if we specify only_fields and is not
|
||||||
|
# in there. Or when we exclude this field in exclude_fields.
|
||||||
|
# Or when there is no back reference.
|
||||||
|
continue
|
||||||
|
converted = converter.convert_django_field(field, None)
|
||||||
|
if not converted:
|
||||||
|
continue
|
||||||
|
|
||||||
|
fields[name] = converted
|
||||||
|
print(fields)
|
||||||
|
return fields
|
||||||
|
|
||||||
|
|
||||||
|
class DjangoModelInputMeta(type):
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def __new__(cls, name, bases, attrs):
|
||||||
|
# We'll get called also for non-user classes like DjangoModelInput. Only
|
||||||
|
# kick in when called for a sub-class.
|
||||||
|
if not is_base_type(bases, DjangoModelInputMeta):
|
||||||
|
return type.__new__(cls, name, bases, attrs)
|
||||||
|
|
||||||
|
# Pop Meta info. Must be removed from class, otherwise graphene will
|
||||||
|
# complain.
|
||||||
|
meta = attrs.pop('Meta')
|
||||||
|
if not hasattr(meta, 'exclude_fields'):
|
||||||
|
setattr(meta, 'exclude_fields', ())
|
||||||
|
if not hasattr(meta, 'only_fields'):
|
||||||
|
setattr(meta, 'only_fields', ())
|
||||||
|
fields = convert_fields(model=meta.model, only_fields=meta.only_fields, exclude_fields=meta.exclude_fields)
|
||||||
|
attrs = merge(attrs, fields)
|
||||||
|
|
||||||
|
return type.__new__(cls, name, bases, attrs)
|
||||||
|
|
||||||
|
|
||||||
|
class DjangoModelInput(metaclass=DjangoModelInputMeta):
|
||||||
|
"""
|
||||||
|
Derive a mutation's Input class from this and define a meta class with
|
||||||
|
`model` and `only_fields` members. This will populate the input class
|
||||||
|
with the converted django members.
|
||||||
|
"""
|
||||||
|
pass
|
96
graphene_django/tests/test_input_type.py
Normal file
96
graphene_django/tests/test_input_type.py
Normal file
|
@ -0,0 +1,96 @@
|
||||||
|
from mock import patch
|
||||||
|
|
||||||
|
from graphene import ObjectType, Schema, Mutation, String
|
||||||
|
|
||||||
|
from .. import registry
|
||||||
|
from ..input_types import DjangoModelInput
|
||||||
|
|
||||||
|
from .models import Reporter as ReporterModel
|
||||||
|
|
||||||
|
|
||||||
|
def test_mutation_execution_with_exclude_fields():
|
||||||
|
registry.reset_global_registry()
|
||||||
|
|
||||||
|
class CreateReporter(Mutation):
|
||||||
|
|
||||||
|
first_name = String()
|
||||||
|
last_name = String()
|
||||||
|
email = String()
|
||||||
|
|
||||||
|
class Input(DjangoModelInput):
|
||||||
|
|
||||||
|
class Meta:
|
||||||
|
model = ReporterModel
|
||||||
|
exclude_fields = ('id', 'pets', 'a_choice', 'films', 'articles')
|
||||||
|
|
||||||
|
def mutate(self, args, context, info):
|
||||||
|
first_name = args.get('first_name')
|
||||||
|
last_name = args.get('last_name')
|
||||||
|
email = args.get('email')
|
||||||
|
return CreateReporter(first_name=first_name, last_name=last_name, email=email)
|
||||||
|
|
||||||
|
class MyMutation(ObjectType):
|
||||||
|
reporter_input = CreateReporter.Field()
|
||||||
|
|
||||||
|
class Query(ObjectType):
|
||||||
|
a = String()
|
||||||
|
|
||||||
|
schema = Schema(query=Query, mutation=MyMutation)
|
||||||
|
result = schema.execute(''' mutation mymutation {
|
||||||
|
reporterInput(firstName:"Peter", lastName: "test", email: "test@test.com") {
|
||||||
|
firstName
|
||||||
|
lastName
|
||||||
|
email
|
||||||
|
}
|
||||||
|
}
|
||||||
|
''')
|
||||||
|
assert not result.errors
|
||||||
|
assert result.data == {
|
||||||
|
'reporterInput': {
|
||||||
|
'firstName': 'Peter',
|
||||||
|
'lastName': 'test',
|
||||||
|
'email': "test@test.com"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
def test_mutation_execution():
|
||||||
|
registry.reset_global_registry()
|
||||||
|
|
||||||
|
class ReporterInput(Mutation):
|
||||||
|
|
||||||
|
first_name = String()
|
||||||
|
last_name = String()
|
||||||
|
|
||||||
|
class Input(DjangoModelInput):
|
||||||
|
|
||||||
|
class Meta:
|
||||||
|
model = ReporterModel
|
||||||
|
only_fields = ('first_name', 'last_name')
|
||||||
|
|
||||||
|
def mutate(self, args, context, info):
|
||||||
|
first_name = args.get('first_name')
|
||||||
|
last_name = args.get('last_name')
|
||||||
|
return ReporterInput(first_name=first_name, last_name=last_name)
|
||||||
|
|
||||||
|
class MyMutation(ObjectType):
|
||||||
|
reporter_input = ReporterInput.Field()
|
||||||
|
|
||||||
|
class Query(ObjectType):
|
||||||
|
a = String()
|
||||||
|
|
||||||
|
schema = Schema(query=Query, mutation=MyMutation)
|
||||||
|
result = schema.execute(''' mutation mymutation {
|
||||||
|
reporterInput(firstName:"Peter", lastName: "test") {
|
||||||
|
firstName
|
||||||
|
lastName
|
||||||
|
}
|
||||||
|
}
|
||||||
|
''')
|
||||||
|
assert not result.errors
|
||||||
|
assert result.data == {
|
||||||
|
'reporterInput': {
|
||||||
|
'firstName': 'Peter',
|
||||||
|
'lastName': 'test',
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user