【发布时间】:2019-10-15 11:08:19
【问题描述】:
由于某种原因,我很难弄清楚如何将 GraphQL 接口的解析器和实现该接口的类型结合起来。
假设我有以下架构:
interface IPerson {
id: ID!
firstName: String!
lastName: String!
}
type ClubMember implements IPerson {
...IPerson fields
memberType: String!
memberSince: DateTime!
}
type StaffMember implements IPerson {
...IPerson fields
hireDate: DateTime!
reportsTo: StaffMember
}
extend type Query {
people(ids: [Int!]): [IPerson]
}
包含所有字段的完整 ClubMember 查询,例如:
query {
people(ids: [123456,234567,345678]) {
id
firstName
lastName
... on ClubMember {
memberType
memberSince
}
}
}
会产生如下响应:
[
{
"id": 123456,
"firstName": "Member",
"lastName": "McMemberface",
"memberType": "VIP",
"memberSince": "2019-05-28T16:05:55+00:00"
},
...etc.
]
我已经使用了apollo-server 中的makeExecutableSchema() 和inheritResolversFromInterfaces: true,并且我希望能够通过支持IPerson、ClubMember 的模型类来为每个接口/类型使用默认解析器, etc. 返回的对象只包含与每种类型相关的字段,即IPerson 的模型类只获取IPerson 所需的字段等。也就是说,上面的响应将执行 2 条 SQL 语句:
SELECT id, firstName, lastName FROM Contacts WHERE id IN(?);
和
SELECT contactId, memberType, memberSince FROM Members WHERE contactId IN(?);
当然,我可以通过在数据库级别执行 JOIN 来获取一条 SQL 语句中的所有数据,但我真的希望有一种(也是唯一一种)方法来解析 IPerson 所需的字段,并让其他类型使用自己的解析器来扩充该数据。
我的问题是,我是否需要自己在解析器中为 people 查询类型将结果对象“加入”在一起?例如
const resolvers = {
Query: {
people: function( parent, args, context, info ) {
let persons = context.models.Person.getByIds( args.ids );
let members = context.models.Member.getByIds( args.ids );
/*
return an array of {...person, ...member} where person.id === member.id
*/
}
}
}
或者阿波罗有什么方法可以为我们处理这个问题?我想要apollo-resolvers 之类的东西吗? docs on unions and interfaces 不是很有帮助;我在IPerson 上有__resolveType,但文档没有指定如何解析每种具体类型的字段。有没有更好的方法来使用 Dataloader 或其他方法来实现这一点?
我认为this question 与我的问题有关,因为如果查询不通过片段请求该类型的任何字段,我不想获取具体类型的数据。 Github 上还有this issue。
非常感谢!
编辑:
__resolveType 如下所示:
{
IPerson: {
__resolveType: function ( parent, context, info ) {
if ( parent.memberType ) {
return 'ClubMember';
}
...etc.
}
}
}
【问题讨论】:
-
你的 __resolveType 函数是什么样的?
-
抱歉格式化:{ IPerson: { __resolveType: function( parent, context, info ) { if ( parent.memberType ) { return 'ClubMember'; } ...等等。 }
标签: graphql apollo-server