我目前为我的项目定义了以下突变:
我的班级CAST AS
用于定义用作我的突变输入的石墨烯字段
PlanetAttribute
我的班级class PlanetAttribute:
name = graphene.String(required=True, description="Name of the planet.")
rotation_period = graphene.String(default_value="unknown", description="Rotation period of the planet.")
orbital_period = graphene.String(default_value="unknown", description="Orbital period of the planet.")
diameter = graphene.String(default_value="unknown", description="Diameter of the planet.")
climate = graphene.String(default_value="unknown", description="Climate period of the planet.")
gravity = graphene.String(default_value="unknown", description="Gravity of the planet.")
terrain = graphene.String(default_value="unknown", description="Terrain of the planet.")
surface_water = graphene.String(default_value="unknown", description="Surface water of the planet.")
population = graphene.String(default_value="unknown", description="Population of the planet.")
url = graphene.String(default_value="unknown", description="URL of the planet in the Star Wars API.")
用于定义Graphene输入对象类型。请注意,它从上面定义的CreatePlanetInput
类继承其属性。
PlanetAttribute
我的班级class CreatePlanetInput(graphene.InputObjectType, PlanetAttribute):
"""Arguments to create a planet."""
pass
是我的Graphene突变类,它以CreatePlanet
类作为参数。
CreatePlanetInput
我不想在class CreatePlanet(graphene.Mutation):
"""Create a planet."""
planet = graphene.Field(lambda: Planet, description="Planet created by this mutation.")
class Arguments:
input = CreatePlanetInput(required=True)
def mutate(self, info, input):
data = utils.input_to_dictionary(input)
data['created'] = datetime.utcnow()
data['edited'] = datetime.utcnow()
planet = ModelPlanet(**data)
db_session.add(planet)
db_session.commit()
return CreatePlanet(planet=planet)
类中手动声明变异输入,而是从我的SQLALchemy类PlanetAttribute
动态生成它们,其定义如下:
ModelPlanet
你会怎么做?
请注意,我还在此处发布了问题:https://github.com/graphql-python/graphene-sqlalchemy/issues/112
答案 0 :(得分:2)
我解决了创建这个类的问题:
from graphene.types.utils import yank_fields_from_attrs
from graphene.utils.subclass_with_meta import SubclassWithMeta_Meta
from graphene_sqlalchemy.registry import get_global_registry
from graphene_sqlalchemy.types import construct_fields
class SQLAlchemyInputObjectType(graphene.InputObjectType):
@classmethod
def __init_subclass_with_meta__( # pylint: disable=arguments-differ
cls, model=None, registry=None, only_fields=(), exclude_fields=(),
optional_fields=(), **options
):
if not registry:
registry = get_global_registry()
sqla_fields = yank_fields_from_attrs(
construct_fields(model, registry, only_fields, exclude_fields),
_as=graphene.Field,
)
for key, value in sqla_fields.items():
if key in optional_fields:
type_ = value.type if isinstance(
value.type, SubclassWithMeta_Meta) else value.type.of_type
value = type_(
description=value.description
)
setattr(cls, key, value)
super(SQLAlchemyInputObjectType, cls).__init_subclass_with_meta__(
**options
)
您可以将其用于:
class CreatePlanetInput(SQLAlchemyInputObjectType):
class Meta:
model = ModelPlanet
exclude_fields = ('id', )
我尝试使其与SQLAlchemyObjectType
的行为相似,因此only_fields
和exclude_fields
应该按预期工作。
我还添加了optional_fields
,这使得它不是必需的,适用于更新变异。
它确实处理简单的情况,比如标量字段。关系,如peopleList
,您需要手动声明。