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

如何修改Gatsby GraphQL返回数据且不改动原始缓存数据?

Gatsby 对 GraphQL 返回数据的处理逻辑

Gatsby 客户端侧的 GraphQL 查询结果会被存储在全局公共缓存中,所有页面共享同一份缓存数据引用。你直接修改查询返回的 data 对象属性时,本质是修改了缓存中的原始数据,下一次访问同页面读取缓存时,拿到的就是被修改后的数据,自然会出现属性不存在的报错。
你之前用 map 没有生效的原因是只拷贝了数组本身,数组中存储的 car 对象依然是原始缓存对象的引用,修改 car 的属性依然会污染缓存。

解决方案

方案1:页面内深拷贝数据后处理

在页面中处理时,先拷贝每个节点对象,再修改属性,避免操作原始引用:

const IndexPage = ({ data: { allWpMasina } }) => {
  // 拷贝每个car对象,重写目标属性,完全不触碰原始缓存数据
  const cars = allWpMasina.nodes.map(car => ({
    ...car,
    // 可选链兼容无属性的极端场景,避免报错
    atrumkarbas: car.atrumkarbas?.nodes?.[0]?.name ?? ''
  }))
  // 后续业务代码直接使用处理后的cars数组即可
}

方案2:构建阶段自定义字段(更推荐)

直接在 Gatsby 构建阶段通过自定义 Schema 和解析器,把预处理逻辑放在服务端,客户端直接查询处理好的字段,从根源避免缓存污染问题:

  1. 在项目根目录的 gatsby-node.js 中添加如下配置:
exports.createSchemaCustomization = ({ actions }) => {
  const { createTypes } = actions
  // 自定义新增字段
  createTypes(`
    type WpMasina implements Node {
      atrumkarbasName: String!
    }
  `)
}

exports.createResolvers = ({ createResolvers }) => {
  createResolvers({
    WpMasina: {
      atrumkarbasName: {
        resolve(source) {
          // 构建阶段就把属性处理好
          return source.atrumkarbas?.nodes?.[0]?.name ?? ''
        }
      }
    }
  })
}
  1. 修改页面的 GraphQL 查询语句,直接查询新字段:
export const query = graphql`
    query {
        allWpMasina(limit: 6) {
            nodes {
                id
                atrumkarbasName
            }
        }
    }
`;

之后页面中可以直接通过 car.atrumkarbasName 拿到目标值,不需要额外处理,也不会出现缓存相关问题。


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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.28 00:57:01