我的应用具有以下几种通过模型的多对多关系:
class Person(models.Model):
name = models.CharField()
class Group(models.Model):
name = models.CharField()
members = models.ManyToManyField(Person, through='Membership')
class Membership(models.Model):
person = models.ForeignKey(Person)
group = models.ForeignKey(Group)
date_joined = models.DateField() # Extra info on the relationship
在没有成员资格中间类型(选项A)的graphql中表示此数据似乎很直观:
{
"data": {
"persons": [
{
"id": "1",
"name": "Jack",
"groups": [
{
"id": 3, # From Group-model
"name": "Students", # From Group-model
"date_joined": "2019-01-01" # From Membership-model
},
...
]
}
]
}
}
vs。选项B:
{
"data": {
"persons": [
{
"id": "1",
"name": "Jack",
"memberships": [
{
"id": 9,
"date_joined": "2019-01-01"
"group": {
"id": 3,
"name": "Students"
}
},
...
]
}
]
}
}
我找不到有关如何使用(django-)石墨烯实现选项A的任何示例。如何做到这一点,是否可以立即使用?
两种方法的优缺点是什么?数据也需要经常更改,这会改变判决吗?
答案 0 :(得分:0)
您可以通过创建一个表示两个模型中字段的类型来实现此目的。例如:
import graphene
from graphene_django.types import DjangoObjectType
# hybrid type, expresses some characteristics of Member and Group
class UserGroupType(DjangoObjectType):
class Meta:
model = Membership
# date_joined is automatically derived from the membership
# instance, name and id are declared below.
fields = ('id', 'name', 'date_joined', )
id = graphene.ID()
name = graphene.String()
def resolve_id(value_obj, info):
return value_obj.group.pk
def resolve_name(value_obj, info):
return value_obj.group.name
class PersonType(DjangoObjectType):
class Meta:
model = Person
# id and name are automatically derived from the person
# instance, groups is declared below, overriding the
# normal model relationship.
fields = ('id', 'name', 'groups', )
groups = graphene.List(UserGroupType)
def resolve_groups(value_obj, info):
return value_obj.memberships
对于从石墨烯的ObjectType(DjangoObjectType descends from)构建的任何类型,要在输出中表示字段,您需要做两件事:
DjangoObjectType
评估您提供的模型以自动生成这些模型,并使用fields attribute来定制要显示的属性。
通过自定义fields
,然后为要添加的内容添加手动道具/解析器,可以使类型返回您想要的任何内容。
请注意,解析器不会收到self
作为第一个参数,而是会收到value object。值对象是查询解析器的返回值,通常是模型的实例或与过滤器匹配的模型数组等。