You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何避免在React组件中对GraphQL嵌套片段调用useFragment?

问题:如何避免对GraphQL嵌套子片段调用useFragment?

现有通过GraphQL Codegen生成的嵌套片段及关联子片段代码如下:

import { graphql } from '../../generated/graphql';

export const regularErrorFragmentDocument = graphql(`
  fragment regularError on FieldError {
    field
    message
  }
`);

export const regularUserFragmentDocument = graphql(`
  fragment regularUser on User {
    id
    username
  }
`);

export const regularUserResponseFragmentDocument = graphql(`
  fragment regularUserResponse on UserResponse {
    errors {
      ...regularError
    }
    user {
      ...regularUser
    }
  }
`);

在React组件中的使用方式如下:

if (response.data?.login) {
  const data = useFragment(regularUserResponseFragmentDocument, response.data.login);
  const errorsData = useFragment(regularErrorFragmentDocument, data.errors);
  if (errorsData) {
    setErrors(toErrorMap([...errorsData]));
  }
  const userData = useFragment(regularUserFragmentDocument, data.user);
  if (userData) {
    await router.push('/');
  }
}

请问是否存在方法可以避免对其中的嵌套子片段调用useFragment?


回答

完全可以避免重复调用useFragment,核心是让主片段返回的数据自动包含子片段的类型与字段信息,无需单独对子片段执行useFragment,以下是两种可行方案:

方案1:配置GraphQL Codegen自动处理嵌套片段类型

确保你的GraphQL Codegen配置(如codegen.ts)启用了片段类型合并(使用@graphql-codegen/client-preset预设即可默认支持),这样生成的主片段类型会自动包含嵌套子片段的所有字段。

修改后组件中的使用代码可简化为:

if (response.data?.login) {
  const data = useFragment(regularUserResponseFragmentDocument, response.data.login);
  if (data.errors) {
    setErrors(toErrorMap([...data.errors]));
  }
  if (data.user) {
    await router.push('/');
  }
}

此时data.errors和data.user会直接携带regularError、regularUser片段定义的字段,无需额外调用子片段的useFragment。

方案2:内联子片段字段(不推荐)

如果不想调整Codegen配置,也可以直接在主片段中写出子片段的字段,替代子片段引用:

export const regularUserResponseFragmentDocument = graphql(`
  fragment regularUserResponse on UserResponse {
    errors {
      field
      message
    }
    user {
      id
      username
    }
  }
`);

这种方式能直接通过主片段的useFragment获取完整字段,但缺点是字段代码重复,后续维护子片段时需要同步修改主片段,不利于代码复用。

关键说明

当主片段引用子片段时,GraphQL Codegen会自动合并类型信息,只要配置正确,useFragment返回的data对象就会包含嵌套字段的完整类型,之前的重复调用是因为类型推断未生效或Codegen配置未正确处理嵌套片段。


内容的提问来源于stack exchange,提问作者El Anonimo

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.14 08:40:37