6

我有以下查询:

const getPage = gql`
    query Page($path: String!) {
        page(path: $path) @rest(type: "Page", path: "{args.path}") {
            blocks @type(name: Block) {
                name
                posts @type(name: Post) {
                    body
                    author
                }
            }
            authors @type(name: Author) {
                name
            }
        }
    }

里面blocks.posts.author只有一个。AuthorId作者对象包含所有可用的作者。

我想AuthorId用它的相应对象替换/匹配。是否可以在一个查询中执行此操作?

我也不介意仅对 Author 进行单独的查询(提取将被缓存,不会发出新请求),但我仍然不知道如何通过 2 个查询匹配它。

示例 API 响应

{
   blocks: [
      {
         posts: [
             {
                id: 1,
                title: 'My post',
                author: 12,
             }
         ]
      }
   ],
   authors: [
      {
         id: 12,
         name: 'John Doe'
      }
   ]
}

我想要的 1 个查询author在 a 内post成为完整的作者对象。

4

2 回答 2

0

好问题。使用 GraphQL,您可以扩展任何字段并从中选择所需的确切子字段,因此,如果您也在后端使用 GraphQL,这将不是问题。您可以在此处执行一些解决方法:

如果所有 Author 对象都在 A​​pollo 缓存中,并且您可以访问每个 Author 的 id,则可以使用ApolloClient.readFragment访问其他属性,如下所示:

const authorId = ...; // the id of the author

const authorInfo = client.readFragment({
  id: authorId,
  fragment: gql`
    fragment AuthorInfo on Author {
      id
      name
      # anything else you want here
    }
  `,
});

尽管值得注意的是,对于问题中的原始查询,如果您将所有 Author 对象作为查询的属性,则可以只使用 Javascript 操作从 Author id 转到 object。

const authorId = ...; // the id of the author
data.page.authors.find(author => author.id === authorId);
于 2019-07-25T18:10:42.323 回答
0

以下应该工作。

首先,使用@export指令将作者 ID 作为变量捕获。然后使用路径内的导出变量添加一个具有其他名称的新字段,并用@restauthor装饰它。

所以查询看起来像这样:

query Page($path: String!) {
    page(path: $path) @rest(type: "Page", path: "{args.path}") {
        blocks @type(name: Block) {
            name
            posts @type(name: Post) {
                body
                author @export(as: "authorId")
                authorFull @rest(
                    path: '/authors/{exportVariables.authorId}'
                    type: 'Author'
                ) {
                    name
                }
            }
        }
        authors @type(name: Author) {
            name
        }
    }
}

您可以使用该fieldNameNormalizer 选项将响应中的属性重命名为author具有不同名称的字段(例如,authorId)。理想情况下,这仍然适用于上述内容,因此您可以避免使用奇怪的字段名称,authorFull但 apollo-link-rest 有点不稳定,所以没有承诺。

于 2019-07-31T12:33:37.947 回答