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

如何从Apollo InMemoryCache查询全部实体?缓存查询报错求助

解决Apollo InMemoryCache无参数查询全部实体的问题

我明白你遇到的问题了——带分页参数的entities查询能正常命中缓存,但无参数查询全部实体时,Apollo找不到对应的ROOT_QUERY.entities字段。这是因为带参数的查询在缓存中会被存储为带参数标识的键(比如entities({"limit":10,"offset":0})),而无参数查询直接找的是entities这个无参数键,缓存里根本没有这个条目。

要解决这个问题,确实需要通过InMemoryCache的cacheResolvers选项,为无参数的entities查询自定义缓存解析逻辑,从缓存中收集所有已存在的实体。下面是具体的实现方案:

步骤1:配置缓存解析器

在创建InMemoryCache时,为Query类型的entities字段添加解析函数,该函数不需要接收参数,直接从缓存中提取所有目标实体:

import { InMemoryCache, gql } from '@apollo/client';

const cache = new InMemoryCache({
  cacheResolvers: {
    Query: {
      // 处理无参数的entities查询
      entities: () => {
        // 步骤1:获取缓存中所有类型为"Entity"的实体键
        // 缓存中单个实体的键格式为:`__typename:EntityId`,比如`Entity:123`
        const entityCacheKeys = Object.keys(cache.extract()).filter(
          key => key.startsWith('Entity:')
        );

        // 步骤2:遍历键,读取每个实体的片段数据
        return entityCacheKeys.map(key => 
          cache.readFragment({
            id: key,
            fragment: gql`
              fragment FullEntity on Entity {
                __typename
                EntityId
                // 这里可以添加你需要的其他实体字段
              }
            `
          })
        );
      }
    }
  }
});

步骤2:确保无参数查询的结构匹配

你的无参数查询最好和带参数的查询保持字段一致(比如包含__typename),这样Apollo能正确匹配解析器返回的结果:

query LocalEntityList {
  entities {
    __typename
    EntityId
    // 其他需要的字段
  }
}

关键逻辑说明

  • 我们通过cache.extract()获取整个缓存的原始数据,筛选出所有属于Entity类型的实体键。
  • 用cache.readFragment()读取每个实体的指定字段,确保返回的结构和查询要求一致。
  • 这种方式不依赖之前的分页查询缓存,只要实体被加载到过缓存中,就能被收集返回,比合并分页结果更可靠。

如果你的实体类型不是Entity,记得把代码中的Entity替换成你实际的__typename值。

内容的提问来源于stack exchange,提问作者Pierre-Alexandre

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.15 08:12:18