mirror of
https://github.com/graphql-python/graphene.git
synced 2025-02-08 23:50:38 +03:00
Improved Interface/ObjectType is_type_of abstraction
This commit is contained in:
parent
907a093117
commit
b772499b9b
|
@ -16,6 +16,16 @@ class GrapheneInterfaceType(GrapheneGraphQLType, GraphQLInterfaceType):
|
||||||
|
|
||||||
class InterfaceTypeMeta(type):
|
class InterfaceTypeMeta(type):
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def _get_interface_options(meta):
|
||||||
|
return Options(
|
||||||
|
meta,
|
||||||
|
name=None,
|
||||||
|
description=None,
|
||||||
|
graphql_type=None,
|
||||||
|
abstract=False
|
||||||
|
)
|
||||||
|
|
||||||
def __new__(cls, name, bases, attrs):
|
def __new__(cls, name, bases, attrs):
|
||||||
super_new = super(InterfaceTypeMeta, cls).__new__
|
super_new = super(InterfaceTypeMeta, cls).__new__
|
||||||
|
|
||||||
|
@ -24,13 +34,7 @@ class InterfaceTypeMeta(type):
|
||||||
if not is_base_type(bases, InterfaceTypeMeta):
|
if not is_base_type(bases, InterfaceTypeMeta):
|
||||||
return super_new(cls, name, bases, attrs)
|
return super_new(cls, name, bases, attrs)
|
||||||
|
|
||||||
options = Options(
|
options = cls._get_interface_options(attrs.pop('Meta', None))
|
||||||
attrs.pop('Meta', None),
|
|
||||||
name=None,
|
|
||||||
description=None,
|
|
||||||
graphql_type=None,
|
|
||||||
abstract=False
|
|
||||||
)
|
|
||||||
|
|
||||||
fields = get_fields(Interface, attrs, bases)
|
fields = get_fields(Interface, attrs, bases)
|
||||||
attrs = attrs_without_fields(attrs, fields)
|
attrs = attrs_without_fields(attrs, fields)
|
||||||
|
@ -41,6 +45,7 @@ class InterfaceTypeMeta(type):
|
||||||
options.graphql_type = GrapheneInterfaceType(
|
options.graphql_type = GrapheneInterfaceType(
|
||||||
graphene_type=cls,
|
graphene_type=cls,
|
||||||
name=options.name or cls.__name__,
|
name=options.name or cls.__name__,
|
||||||
|
resolve_type=cls.resolve_type,
|
||||||
description=options.description or cls.__doc__,
|
description=options.description or cls.__doc__,
|
||||||
fields=fields,
|
fields=fields,
|
||||||
)
|
)
|
||||||
|
@ -59,6 +64,7 @@ def attrs_without_fields(attrs, fields):
|
||||||
|
|
||||||
|
|
||||||
class Interface(six.with_metaclass(InterfaceTypeMeta)):
|
class Interface(six.with_metaclass(InterfaceTypeMeta)):
|
||||||
|
resolve_type = None
|
||||||
|
|
||||||
def __init__(self, *args, **kwargs):
|
def __init__(self, *args, **kwargs):
|
||||||
from .objecttype import ObjectType
|
from .objecttype import ObjectType
|
||||||
|
|
|
@ -26,22 +26,6 @@ class GrapheneObjectType(GrapheneGraphQLType, GraphQLObjectType):
|
||||||
if isinstance(interface, GrapheneInterfaceType):
|
if isinstance(interface, GrapheneInterfaceType):
|
||||||
interface.graphene_type.implements(self.graphene_type)
|
interface.graphene_type.implements(self.graphene_type)
|
||||||
|
|
||||||
@property
|
|
||||||
def is_type_of(self):
|
|
||||||
return self._is_type_of or self.default_is_type_of
|
|
||||||
|
|
||||||
@is_type_of.setter
|
|
||||||
def is_type_of(self, is_type_of):
|
|
||||||
self._is_type_of = is_type_of
|
|
||||||
|
|
||||||
def default_is_type_of(self, interface, context, info):
|
|
||||||
from ..utils.get_graphql_type import get_graphql_type
|
|
||||||
try:
|
|
||||||
graphql_type = get_graphql_type(type(interface))
|
|
||||||
return graphql_type.name == self.name
|
|
||||||
except:
|
|
||||||
return False
|
|
||||||
|
|
||||||
|
|
||||||
def get_interfaces(interfaces):
|
def get_interfaces(interfaces):
|
||||||
from ..utils.get_graphql_type import get_graphql_type
|
from ..utils.get_graphql_type import get_graphql_type
|
||||||
|
@ -51,6 +35,13 @@ def get_interfaces(interfaces):
|
||||||
yield graphql_type
|
yield graphql_type
|
||||||
|
|
||||||
|
|
||||||
|
def is_objecttype(bases):
|
||||||
|
for base in bases:
|
||||||
|
if issubclass(base, ObjectType):
|
||||||
|
return True
|
||||||
|
return False
|
||||||
|
|
||||||
|
|
||||||
# We inherit from InterfaceTypeMeta instead of type for being able
|
# We inherit from InterfaceTypeMeta instead of type for being able
|
||||||
# to have ObjectTypes extending Interfaces using Python syntax, like:
|
# to have ObjectTypes extending Interfaces using Python syntax, like:
|
||||||
# class MyObjectType(ObjectType, MyInterface)
|
# class MyObjectType(ObjectType, MyInterface)
|
||||||
|
@ -61,9 +52,13 @@ class ObjectTypeMeta(InterfaceTypeMeta):
|
||||||
|
|
||||||
# Also ensure initialization is only performed for subclasses of Model
|
# Also ensure initialization is only performed for subclasses of Model
|
||||||
# (excluding Model class itself).
|
# (excluding Model class itself).
|
||||||
|
|
||||||
if not is_base_type(bases, ObjectTypeMeta):
|
if not is_base_type(bases, ObjectTypeMeta):
|
||||||
return super_new(cls, name, bases, attrs)
|
return super_new(cls, name, bases, attrs)
|
||||||
|
|
||||||
|
if not is_objecttype(bases):
|
||||||
|
return super(ObjectTypeMeta, cls).__new__(cls, name, bases, attrs)
|
||||||
|
|
||||||
options = Options(
|
options = Options(
|
||||||
attrs.pop('Meta', None),
|
attrs.pop('Meta', None),
|
||||||
name=None,
|
name=None,
|
||||||
|
@ -86,6 +81,7 @@ class ObjectTypeMeta(InterfaceTypeMeta):
|
||||||
name=options.name or cls.__name__,
|
name=options.name or cls.__name__,
|
||||||
description=options.description or cls.__doc__,
|
description=options.description or cls.__doc__,
|
||||||
fields=fields,
|
fields=fields,
|
||||||
|
is_type_of=cls.is_type_of,
|
||||||
interfaces=tuple(get_interfaces(interfaces + base_interfaces))
|
interfaces=tuple(get_interfaces(interfaces + base_interfaces))
|
||||||
)
|
)
|
||||||
else:
|
else:
|
||||||
|
@ -147,3 +143,12 @@ class ObjectType(six.with_metaclass(ObjectTypeMeta)):
|
||||||
raise TypeError(
|
raise TypeError(
|
||||||
"'%s' is an invalid keyword argument for this function" %
|
"'%s' is an invalid keyword argument for this function" %
|
||||||
list(kwargs)[0])
|
list(kwargs)[0])
|
||||||
|
|
||||||
|
@classmethod
|
||||||
|
def is_type_of(cls, interface, context, info):
|
||||||
|
from ..utils.get_graphql_type import get_graphql_type
|
||||||
|
try:
|
||||||
|
graphql_type = get_graphql_type(type(interface))
|
||||||
|
return graphql_type.name == cls._meta.graphql_type.name
|
||||||
|
except:
|
||||||
|
return False
|
||||||
|
|
Loading…
Reference in New Issue
Block a user