Inheritance 如何在GraphQL中继承或扩展typeDefs

Inheritance 如何在GraphQL中继承或扩展typeDefs,inheritance,schema,graphql,extend,extends,Inheritance,Schema,Graphql,Extend,Extends,我有一个类型的用户。用户也可以是类型的团队成员。用户和团队成员之间的唯一区别是添加了一个字段teamRole:String。因此,我想做如下操作,以避免冗余定义所有用户字段 type User { id: ID!, name: String, (many other field defs) } type TeamMember extends User { teamRole: String, } 有人知道这个的语法吗?我原以为extend就是答

我有一个
类型的用户
。用户也可以是
类型的团队成员
用户
团队成员
之间的唯一区别是添加了一个字段
teamRole:String
。因此,我想做如下操作,以避免冗余定义所有用户字段

  type User {
    id: ID!,
    name: String,
    (many other field defs)
  }

  type TeamMember extends User  {
    teamRole: String,
  }

有人知道这个的语法吗?我原以为
extend
就是答案,但它更像是javascript的
prototype

如果您有一个基本模式,并且希望在此基础上构建两个或多个可用模式,那么
extend
关键字就非常好了。例如,您可以使用所有模式共享的查询定义根
Query
类型,然后在每个模式中扩展它,以添加特定于该模式的查询。它还可以用于模块化模式。然而,它只是一种向现有类型添加功能的机制——不能用于创建新类型

GraphQL本身并不支持继承。没有语法可以帮助您避免跨多个类型重复字段

您可以利用字符串插值来避免反复键入相同的字段:

const sharedFields = `
  foo: String
  bar: String
`
const typeDefs = `
  type A {
    ${sharedFields}
  }

  type B {
    ${sharedFields}
  }
`
除此之外,您还可以利用类似的库,它允许您利用继承和泛型类型。尽管如此,以这种方式生成的模式仍然必须编译为有效的SDL——像
graphql-s2s
这样的库充其量只能提供一些语法上的糖分和更好的DX

最后,您可以重新构造您的类型,以避免字段重复,而代价是更结构化的响应。例如,不要这样做:

type A {
  a: Int
  foo: String
  bar: String
}

type B {
  b: Int
  foo: String
  bar: String
}
您可以这样做:

type X {
  foo: String
  bar: String
  aOrB: AOrB
}

union AOrB = A | B

type A {
  a: Int
}

type B {
  b: Int
}

使用类似graphql-s2s的模式传输程序来实现继承可能有些过分,而graphql-s2s在2021年已经过时

请查看此阿波罗服务器指令:

const typeDefs=gql`
对象上的指令@inherits(类型:String!)
类型车{
制造商:字符串
颜色:字符串
}
类型特斯拉@继承(类型:“汽车”){
制造商:字符串
爸爸:绳子
型号:字符串
}
`;
类InheritsDirective扩展SchemaDirectiveVisitor{
visitObject(类型){
const fields=type.getFields();
const baseType=this.schema.getTypeMap()[this.args.type];
Object.entries(baseType.getFields()).forEach(([name,field])=>{
如果(字段[名称]==未定义){
字段[名称]=字段;
}
});
}
}

谢谢!这正是我想要的。嗯,不完全是这样,因为在理想情况下,我不需要另一个包裹,但能给我所需要的。我使用的是我的服务器,所以我必须声明,这也比idea少。如果你知道更好的办法,我洗耳恭听。谢谢这是真的吗?截至2019年年中仍不可用?@A.com是。您可以看到最新的规范。@Alexander,这不是一个标准指令——它使用的是什么库?当我使用google搜索确切的短语“@inherit from”时,这个堆栈溢出问题是唯一显示的页面。你发明了一个全新的句子。