繁体   English   中英

Apollo Server:将参数传递给嵌套解析器

[英]Apollo Server: pass arguments to nested resolvers

我的 GraphQL 查询如下所示:

{
    p1: property(someArgs: "some_value") {
        id
        nestedField {
            id
            moreNestedField {
                id
            }
        }
    }
}

在服务器端,我使用 Apollo Server。 我有一个用于property的解析器和其他用于nestedFieldmoreNestedField解析器。 我需要在嵌套解析器上检索someArgs的值。 我尝试使用解析器上可用的context来执行此操作:

property: (_, {someArgs}, ctx) => {
    ctx.someArgs = someArgs;

    // Do something
}

但这不起作用,因为上下文在所有解析器之间共享,因此如果我的查询有多个property ,则上下文值不会很好。

我还尝试使用我的嵌套解析器上的info可用的path 我可以进入property领域,但我没有这里的论点......

我还尝试添加一些关于info数据,但它没有在嵌套解析器上共享。

在所有解析器上添加参数不是一种选择,因为它会使查询变得非常臃肿且编写起来很麻烦,我不希望那样。

有什么想法吗?

谢谢!

可以使用当前返回的值将参数传递给子解析器。 稍后将从响应中删除其他数据。

我将“借用”丹尼尔的代码,但没有特定的参数 - 将参数作为参考传递(适合/更干净/对于更多参数更易读):

function propertyResolver (parent, args) {
  const property = await getProperty()
  property.propertyArgs = args
  return property
}

// if this level args required in deeper resolvers
function nestedPropertyResolver (parent, args) {
  const nestedProperty = await getNestedProperty()
  nestedProperty.propertyArgs = parent.propertyArgs
  nestedProperty.nestedPropertyArgs = args
  return nestedProperty
}

function moreNestedPropertyResolver (parent) {
  // do something with parent.propertyArgs.someArgs
}

正如丹尼尔斯所说,这种方法的功能有限。 您可以chain结果并在子解析器中有条件地做一些事情。 您将拥有父级和过滤后的子级...使用子条件未过滤的父级(例如在 SQL ... WHERE ... AND ... AND ... 连接表上),这可以在父解析器中完成。

请在此处查看有关如何传递参数的答案: https : //stackoverflow.com/a/63300135/11497165

为了简化它,您可以使用 args 定义您的字段类型:

在您的类型定义中

type Query{
  getCar(color: String): Car
  ... other queries
}

type Car{
  door(color: String): Door // <-- added args
  id: ID
  previousOwner(offset: Int, limit: Int): Owner // <-- added args
  ...
}

然后,在您的客户端查询中(来自 apollo 客户端或您的 gql 查询):

query getCar(carId:'123'){
  door(color:'grey') // <-- add variable
  id
  previousOwner(offset: 3) // <-- added variable
  ... other queries
}

您应该能够在您的子解析器参数中访问颜色:

在您的解析器中:

Car{
  door(root,args,context){
   const color = args.color // <-- access your arguments here
  }
  previousOwner(root,args,context){
   const offset = args.offset // <-- access your arguments here
   const limit = args.limit // <-- access your arguments here
  }
  ...others
}

对于您的示例:

会是这样

{
    p1: property(someArgs: "some_value") { // <-- added variable
        id
        nestedField(someArgs: "some_value") { // <-- added variable
            id
            moreNestedField(offset: 5) {
                id
            }
        }
    }
}

您可以像这样通过父字段传递值:

function propertyResolver (parent, { someArgs }) {
  const property = await getProperty()
  property.someArgs = someArgs
  return property
}

function nestedPropertyResolver ({ someArgs }) {
  const nestedProperty = await getNestedProperty()
  nestedProperty.someArgs = someArgs
  return nestedProperty
}

function moreNestedPropertyResolver ({ someArgs }) {
  // do something with someArgs
}

请注意,这是否有效,它也可能首先指出您的架构设计存在潜在问题。 根据您解析这些字段的方式(从数据库中获取它们、向另一个 API 发出请求等),最好采用完全不同的方法——例如,通过在根解析器中预先加载所有内容。 但是,如果没有更多上下文,就很难提出任何其他建议。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM