自定义REST接口返回200,刷新购物车页能看到新商品,但页面右上角Mini Cart数量一直不变。手动执行customerData.reload(['cart'])后马上正确。说明Quote保存没有问题,断点在Private Content的section失效机制:标准add-to-cart动作会让cart section过期,自定义URL默认不会。

先在浏览器确认本地section状态

require(['Magento_Customer/js/customer-data'], function (customerData) {
    console.log(customerData.get('cart')());
    console.log(localStorage.getItem('mage-cache-storage'));
    console.log(localStorage.getItem('mage-cache-storage-section-invalidation'));
});

查看加购请求响应Cookie是否更新private_content_version,并观察随后有没有customer/section/load请求。若Quote已变但没有section/load,就是失效没触发;若发了请求却仍返回旧数据,再查SectionSource和服务端缓存。

为自定义Action声明section失效

在模块etc/frontend/sections.xml里把实际Action路径映射到cart。路径必须与前端请求的路由一致,不是Controller类名。

<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:noNamespaceSchemaLocation="urn:magento:module:Magento_Customer:etc/sections.xsd">
  <action name="vendor/cart/add">
    <section name="cart" />
  </action>
</config>

配置后清config和full_page缓存,重新加载页面让sections配置进入前端。对于GraphQL或完全绕过Magento标准前端Action的PWA,请由应用在mutation成功后更新本地Apollo状态或显式重新拉取cart,不能指望Luma的sections.xml自动工作。

不要用setTimeout假装修好

有些代码加购后延迟一秒调用reload,网络慢时仍竞态,网络快时又多发请求。应该等待加购Promise成功,再invalidate并reload。

return addRequest(payload).then(function () {
    customerData.invalidate(['cart']);
    return customerData.reload(['cart'], true);
});

若接口响应失败,不要reload并显示成功数量。错误分支应保留旧状态并给出明确提示。

section/load返回旧值时继续查

  • Cart SectionSource是否读当前Checkout Session的Quote
  • 自定义接口是否使用了另一个store或mask cart id
  • 会话Cookie Domain、SameSite和Path是否让两个请求不在同一会话
  • 反向代理是否错误缓存customer/section/load
  • 插件是否给cart section source返回了静态缓存数据

customer/section/load属于个性化响应,CDN应pass或正确标记private。用两个浏览器会话交叉测试,确认绝不会互相看到购物车数量。

完整验证

  • 商品页标准加购与自定义接口加购都即时更新
  • 删除、改数量、应用优惠码后Mini Cart同步
  • 多Store切换后读取对应Quote
  • 无痕游客与登录客户都正常
  • 快速连续点击两次不会倒退到较旧的section响应
Mini Cart是Quote状态的一个客户端投影。修复目标是让成功的购物车变更触发可靠失效,而不是每隔几秒全量刷新。