
前端GraphQL【免费下载链接】apollo Apollo/GraphQL integration for VueJS项目地址https://gitcode.com/gh_mirrors/apollo2/apollo点击查看免费下载useFragment是 Vue Apollo 组合式 API 中用于从 Apollo 缓存读取 GraphQL 片段数据并保持完全响应式的核心组合函数。本文以 Result 接口文档 为骨架逐字段拆解useFragment返回值中complete、current、missing、result、resultState与onNextState的含义与类型并结合仓库源码 useFragment.ts 说明这些字段是如何被生产、更新与维护的。读完本文你将能准确判断片段数据是完整命中缓存还是部分缺失并根据状态选择正确的渲染分支。一、Result 接口概览useFragment(options)返回一个Result对象官方文档将其定义为 Result returned by useFragment由 useFragment 返回的结果。它由两部分组成Operation data操作数据complete、current、missing、result、resultState全部是响应式RefEvents事件onNextState用于在片段数据变化时进行命令式回调。从 源码实现 可以看到useFragmentImpl的返回值正是按这一结构组织的return { current: currentState as ReadonlyRefuseFragment.CurrentTData, result, resultState, complete, missing, onNextState: nextStateEvent.on as unknown as EventHookOnuseFragment.CurrentTData, }其中result、resultState、complete、missing均是从currentState这个shallowRef派生的computed值而current本身就是这个单一状态源的引用。官方建议在业务中优先使用current因为它是一个可辨识联合类型discriminated union可以根据resultState收窄result的类型详见 fragments 指南 与 queries 文档 中为什么推荐 current的论述。二、操作数据字段详解1. result片段查找的最终产物result:Refobject|object[]result是一个包含 GraphQL 片段查找完成后结果的Ref。单个实体时为object传入实体数组时为object[]。注意其类型是宽松的对象object这正是current联合类型存在的原因只有通过current.resultState的收窄TypeScript 才能推断出更精确的字段结构。官方文档描述为An object containing the result of your GraphQL fragment lookup after it completes.在实现中result并非独立维护而是直接取自currentState.value?.result见 源码const result computed(() currentState.value?.result)也就是说result与current.result始终指向同一个值二者是同一状态的不同出口。2. resultState结果完整度描述resultState:Refcomplete|partialresultState描述result的完整程度只有两个取值partial部分数据可以从缓存满足但result不完整。只有当returnPartialData为true时才会出现completeresult是完全满足的查询结果且要么来自缓存、要么来自网络for 片段场景即完全命中缓存。这个字段直接来源于 Apollo Client 缓存层的watchFragment结果。在 源码 中toCurrent帮助函数将 Apollo 的WatchFragmentResult转换为useFragment.Current格式其中dataState被重命名为resultState、data被重命名为resultfunction toCurrentTData( watchResult: ApolloClient.WatchFragmentResultTData | TData[], ): useFragment.CurrentTData | TData[] { const { data, dataState, ...rest } watchResult return { result: data, resultState: dataState, ...rest } as unknown as useFragment.CurrentTData | TData[] }由于dataState在 Apollo 中同样是complete | partial联合这一重命名保持了语义一致同时让组合层 API 与useQuery的命名风格统一。3. complete片段数据是否完整complete:Refboolean布尔值表示片段数据是否完整。官方定义Whether the fragment data is complete.片段数据是否完整。当complete为false时说明缓存中缺少该片段所请求的部分字段此时应配合missing查看具体缺失项。实现上源码const complete computed(() currentState.value?.complete ?? false)注意在currentState尚未有值时complete会回退为false这保证了初始渲染阶段的安全默认值。4. missing缺失字段错误树missing:RefMissingTree当complete为false时missing是一棵缺失字段错误树Tree of missing field errors类型为 Apollo 的MissingTree来自apollo/client/cache。在 Current 接口 中missing被标记为可选missing?因为当数据完整时它不存在。实现端同样做了保护源码const missing computed(() currentState.value missing in currentState.value ? currentState.value.missing : undefined, )只有当当前状态中确实存在missing字段时才返回它否则返回undefined。借助missing树你可以定位到具体是哪个字段如avatar未命中缓存从而决定是回退渲染、触发 refetch 还是显示占位内容。5. current可辨识联合的当前状态current:RefCurrentcurrent是当前状态的总入口类型为Current接口可辨识联合类型聚合了上述全部状态字段export interface Current { complete: boolean result: object | Arrayobject resultState: complete | partial missing?: MissingTree }它由currentState这个shallowRef直接暴露源码。因为resultState作为判别字段存在模板与 TS 中可以这样收窄div v-ifcurrent.resultState complete {{ current.result.name }} ({{ current.result.email }}) /div当current.resultState complete时current.result被推断为完整的片段数据对象无需额外类型断言。三、EventsonNextState 事件钩子onNextState:EventHookOnCurrentonNextState是在片段数据发生变化时触发的事件钩子类型来自 vueuse 的EventHookOn。它是命令式imperative监听缓存更新的入口适合在响应式模板之外如日志、埋点、联动副作用处理状态流转。官方文档定义Event triggered when fragment data changes.片段数据变化时触发的事件。实现上源码它基于 vueuse 的createEventHook构建并在订阅 ApollowatchFragment返回的 observable 时触发const nextStateEvent createEventHookunknown() // 订阅缓存更新 subscription.value newObservable.subscribe({ next: (watchResult) { nextStateEvent.trigger(toCurrent(watchResult)) }, })每次 Apollo 缓存广播新的片段结果时onNextState都会收到转换后的Current状态。典型用法见 fragments 指南const { onNextState } useFragment({ fragment: USER_FIELDS, from: props.user, }) onNextState((state) { console.log(Fragment data changed:, state) })四、状态生产链路从 watchFragment 到 Result理解Result各字段如何被填充关键在于源码中的一条完整链路useFragment.ts构造 observable根据from解析出的缓存 ID通过cache.identify解析from值见 resolveFromToId调用getClient().watchFragment()得到一个ObservableFragment同步取初始值通过observable.getCurrentResult()同步获得当前缓存快照经toCurrent转换后写入currentState订阅更新watch(observable, ..., { immediate: true })监听 observable 变化每次收到next事件就把新状态trigger给onNextState从而更新currentState派生字段result、resultState、complete、missing全部由currentState计算派生保证单一状态源作用域清理onScopeDispose中unsubscribe()释放订阅避免组件卸载后内存泄漏。空值与初始状态的处理当from为null或尚未解析出缓存 ID 时observable 为undefined此时useFragment使用冻结的空对象作为初始状态源码const nullResult Object.freeze({ result: {}, resultState: partial, complete: false, }) as useFragment.Currentany const nullArrayResult Object.freeze({ result: [], resultState: partial, complete: false, }) as useFragment.Currentany单实体场景初始result为{}数组场景为[]二者均为partial且complete: false。这与 Apollo Client 不支持空结果的约定保持一致也让开发者在数据尚未就绪时可以安全地访问result而不会得到undefined。五、与 Options 的配合影响 Result 的关键配置Result的语义受 Options 接口 中几个配置项的直接影响配置项类型默认值对 Result 的影响fragmentMaybeRefOrGetterDocumentNode—决定读取哪些字段字段是否命中缓存直接决定complete/resultState/missingfragmentNameMaybeRefOrGetterstring—文档含多个片段时指定片段名影响解析结果variablesMaybeRefOrGetterReactiveVariablesParameter—带变量片段的取值来源见 ReactiveVariablesParameterfromMaybeRefOrGetterFromValue \| FromValue[]—数据源决定读取哪些缓存实体FromValue支持{ __typename, id }对象、{ __ref }引用或字符串 ID见 FromValueoptimisticbooleantrue为false时跳过乐观缓存result中不含乐观数据clientIdstring—指定命名 Apollo 客户端影响缓存来源其中from是最关键的它既可以传单个实体也可以传实体数组。当传入数组时result变为object[]且每个下标与from中的实体一一对应resultState只有在每一项都完整时才为complete见 fragments 指南。另外optimistic默认值为true实现中通过options.value.optimistic ?? true传入watchFragmentOptions源码这直接决定了result中是否包含尚未提交到真实缓存的乐观更新数据。六、实践建议与典型模式综合上述字段语义推荐以下实践模式优先消费current而非单独字段利用resultState联合类型的收窄能力模板中在current.resultState complete分支内安全访问current.result用completemissing做降级渲染当complete为false时可通过missing判断缺失字段决定展示骨架屏还是触发补充加载用onNextState做命令式副作用如埋点上报、记录状态流转、联动其他非响应式系统避免在模板中堆叠复杂 watcher注意partial的前置条件resultState partial只在returnPartialData开启时出现业务侧应理解这是尽力而为的数据不应作为完整数据提交初始状态是安全的即使from尚未就绪result也只会是{}单实体或[]数组不会抛空引用错误可放心在首帧渲染。七、相关资源Result 接口文档本文主体字段完整定义Current 接口文档current字段的联合类型定义Options 接口文档影响 Result 语义的配置项FromValue 类型别名from支持的三种缓存标识形式ReactiveVariablesParameter 类型别名变量的响应式传参方式useFragment 源码状态生产链路与字段派生实现Fragments 使用指南useFragment的完整实战用例包括数组读取与事件钩子赞分享前端GraphQL【免费下载链接】apollo Apollo/GraphQL integration for VueJS项目地址https://gitcode.com/gh_mirrors/apollo2/apollo点击查看免费下载相关推荐RealtimeSTT AudioToTextRecorder 配置完全指南构造函数全参数详解与源码级调优RealtimeSTT AudioToTextRecorder 配置完全指南构造函数全参数详解与源码级调优 AudioToTextRecorder 是 Rea前端GraphQLvue/apollo-composable 的 useFragment 完全指南从 Apollo 缓存中响应式读取 Fragment 数据vue/apollo composable 的 useFragment 完全指南从 Apollo 缓存中响应式读取 Fragment 数据 useFragm前端GraphQLPuter CreateAppResult 对象详解读懂 puter.apps.create() 的返回结构Puter CreateAppResult 对象详解读懂 puter.apps.create 的返回结构 CreateAppResult 是 Puter Ja后端前端云原生上一篇MAA助手明日方舟自动日常快速入门指南连上模拟器全流程15分钟下一篇Wechaty终极错误处理与调试指南10个常见问题排查和解决方案创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考