← 返回文档导航

📶 BeeX 弱网缓存专项

离线包启动 · 接口缓存 · 后台刷新 · 数据新鲜度 · 库存异常治理
一句话: 印尼当地网络不稳定时,BeeX 不能把“打开 App”建立在实时网络成功上。 App 先加载本地 H5 离线包,H5 先展示可信缓存,核心接口在后台刷新;但涉及钱、库存、购买入口的动作必须回到云端做实时校验。 这份文档专门讲清楚每一层缓存的职责、过期策略、失效方式和测试方法。
当前状态
🔵 专项建设中
离线包核心已通;首页商品列表有 72 小时缓存;热门品牌不过期缓存;商品详情和库存校验还需要进一步收口。
核心原则
缓存只解决“快”和“弱网可用”;不能用缓存决定“能不能付款、能不能返现、有没有库存”。这些必须实时验。
本页给谁看
App、H5、服务端、测试和运营。排查“首页慢、白屏、旧商品又出现、无库存商品展示”都从这里开始。

一、为什么要做弱网专项

BeeX 的主要用户在印尼和马来,实际网络环境会出现高延迟、DNS 慢、切后台重连、运营商不稳定、WhatsApp 跳转回来后网络瞬断等情况。如果每次打开首页都等远端 H5 和所有接口返回,用户会看到长时间白屏或空列表。

所以我们采用“本地先可用,云端再校准”的策略:

  1. App 启动优先加载本地 H5 离线包,不等网络。
  2. 首页先读 H5 本地接口缓存,页面先有内容。
  3. 后台刷新接口,刷新成功后覆盖缓存并更新界面。
  4. 商品详情、转链、提现、支付、登录等强一致动作必须实时请求云端。
  5. 只要平台字段明确商品不可买,后端和前端都要过滤;平台字段缺失时,进入详情或购买前再做二次校验。
铁律: 缓存可以让页面先显示,但不能让用户基于旧数据完成资金动作。返现金额、商品价格、优惠券核销、提现金额、支付密码、最终购买链接都必须以云端实时返回为准。

二、弱网下 App 启动主流程

flowchart TD
  A["用户打开 BeeX App"]:::app
  B["Native 查本地 active H5 包"]:::app
  C{"active 包存在且可读?"}:::decision
  D["加载内置 H5 包"]:::app
  E["加载 active/index.html"]:::app
  F["H5 首屏渲染"]:::h5
  G["H5 读接口缓存
首页商品/品牌/活动"]:::cache H["Native 延迟检查 H5 包更新"]:::native I["H5 后台刷新首页接口"]:::h5 J{"刷新成功?"}:::decision K["覆盖缓存并刷新 UI"]:::ok L["保留缓存
显示弱网提示"]:::bad M{"发现新 H5 包?"}:::decision N["下载 ready 包
校验 sha256"]:::native O["提示用户刷新或下次启动激活"]:::native A-->B-->C C--"否"-->D-->F C--"是"-->E-->F F-->G F-->H G-->I-->J J--"是"-->K J--"否"-->L H-->M M--"否"-->F M--"是"-->N-->O classDef app fill:#f0fdf4,stroke:#15803d,color:#166534; classDef native fill:#eff6ff,stroke:#1d4ed8,color:#1e40af; classDef h5 fill:#f5f3ff,stroke:#8b5cf6,color:#5b21b6; classDef cache fill:#fff7ed,stroke:#f97316,color:#9a3412; classDef decision fill:#fef3c7,stroke:#e07c00,color:#7a4f24,stroke-width:2px; classDef ok fill:#f0fdf4,stroke:#15803d,color:#15803d,stroke-width:2px; classDef bad fill:#fff5f5,stroke:#dc2626,color:#991b1b,stroke-width:2px;

三、缓存分层总表

层级缓存什么保存位置过期/刷新能否直接决定业务动作代码位置
App H5 离线包完整 H5 静态资源: HTML/CSS/JS/图片App 沙盒目录 + 安装包内置资源启动后后台查新;下载完成后用户刷新或下次启动激活不能。只决定页面代码版本。beex-app/lib/src/services/h5_package_manager.dart
首页商品列表ALL / 高返佣 / TikTok / Shopee 商品摘要H5 localStorage72 小时内先命中缓存;进入首页后台刷新;缓存 schema 变更会整体失效不能。点击详情/购买仍需实时校验。beex-app-h5/app/composables/useHighCommissionProducts.ts
热门品牌品牌图标、关键词、品牌名、返现文案,以及品牌配置更新时间H5 localStorage品牌入口不过期;后台刷新成功后覆盖。固定商品发生增删改时服务端同步更新品牌时间戳品牌入口不能直接决定购买。进入品牌页后优先读取运营配置的固定商品快照,点击详情/购买仍需实时校验;未配置固定商品才回退关键词或店铺搜索。beex-app-h5/app/utils/popularBrandsCache.ts
beex-app-h5/app/pages/brands/result.vue
商品详情摘要列表点击时带过去的商品卡片数据sessionStorage / 路由参数只用于秒开;详情页随后调 /products/resolve 刷新不能。只做首屏占位。beex-app-h5/app/pages/product-detail.vue
推荐商品店铺推荐、品类推荐H5 localStorage短期缓存 + 后台刷新;空结果要有 fallback不能。推荐列表只负责导流。beex-app-h5/app/pages/product-detail.vue
用户资料/收益我的页、收益页部分数据H5 状态缓存进入页面后台刷新;失败时保留旧数据并提示不能。提现前必须实时查钱包。beex-app-h5/app/composables/useCachedApiState.ts
平台高佣商品池TikTok Partner Campaign 商品BeeX 数据库服务端定时同步 TikTok;商品状态和库存仍可能变化不能。购买前仍需平台生成链接成功。TiktokPartnerCampaignProductSyncService.java

四、首页商品缓存逻辑

首页商品缓存的目标是:弱网下打开首页不要空白,用户切换 ALL / TikTok / Shopee 时不要反复等待同一批数据。

4.1 当前策略

项目当前值说明
缓存时间72 小时72 小时内先显示缓存;后台刷新成功后更新缓存。
缓存 keyhigh-commission-products:{schema}:{country}:{keyword}:{platform}:{source}:{pageSize}schema 用来一次性废掉旧缓存。当前已加入 v2-stock-filter,避免旧的无库存脏数据继续展示。
切 Tab先读对应 Tab 缓存切换 ALL / TikTok / Shopee 不重复拉取同一份 72 小时内的新缓存。
下拉刷新强制当前 Tab 请求云端当前 Tab 刷新;其他 Tab 可后台预取,但不会阻塞当前页面。
加载更多带 cursor 请求云端追加到当前缓存快照,并做去重。
前端兜底过滤隐藏无价格/无返现/无购买链接商品不能替代后端过滤,只防止明显脏缓存展示。
flowchart TD
  A["进入首页或切换商品 Tab"]:::h5
  B["计算缓存 key
国家+关键词+平台+来源+页大小+schema"]:::cache C{"本地缓存存在?"}:::decision D["先展示缓存"]:::cache E["显示骨架屏"]:::h5 F{"缓存 fresh 且非强刷?"}:::decision G["结束:不请求云端"]:::ok H["请求 /api/v1/products/high-commission"]:::be I{"请求成功?"}:::decision J["过滤明显异常商品
写入新缓存+刷新 UI"]:::ok K["保留旧缓存
展示弱网/失败提示"]:::bad A-->B-->C C--"是"-->D-->F C--"否"-->E-->H F--"是"-->G F--"否/强刷"-->H H-->I I--"是"-->J I--"否"-->K classDef h5 fill:#f5f3ff,stroke:#8b5cf6,color:#5b21b6; classDef cache fill:#fff7ed,stroke:#f97316,color:#9a3412; classDef be fill:#ecfeff,stroke:#0891b2,color:#155e75; classDef decision fill:#fef3c7,stroke:#e07c00,color:#7a4f24,stroke-width:2px; classDef ok fill:#f0fdf4,stroke:#15803d,color:#15803d,stroke-width:2px; classDef bad fill:#fff5f5,stroke:#dc2626,color:#991b1b,stroke-width:2px;

4.2 为什么过滤了无库存商品还会回来

原因表现处理方式
旧 H5 本地缓存服务端已过滤,但用户设备上仍展示旧商品缓存 key 增加 schema 版本;当前为 v2-stock-filter
平台字段缺失TikTok Partner Campaign 缓存商品没有 stock/has_inventory/soldCount列表只能过滤“已知不可买”;进入详情/生成链接前必须实时校验。
平台实时变更同步时有库存,用户点击时已经售罄购买前以平台生成链接和详情解析结果为准,失败时提示商品不可购买。
缓存时间过长72 小时内商品状态变化但用户仍看到旧摘要关键字段变化时升 schema;运营可临时下发禁用/黑名单。
库存规则: 只要平台字段明确表示 stock=0has_inventory=falsesoldOut=trueoutOfStock=truecanBuy=false,列表必须过滤。字段不存在时不能假装“有库存”,只能标记为库存未知,购买前实时校验。

五、哪些数据可以缓存,哪些不能缓存

数据/动作是否可缓存展示是否可用缓存提交规则
首页 Banner / 品牌入口可以不涉及提交允许长期缓存,后台刷新覆盖。
商品列表摘要可以不可以列表可先展示缓存,详情/转链前必须刷新。
商品详情可以先展示摘要不可以进入详情后调用 /api/v1/products/resolve 更新价格、返现、来源、库存线索。
最终购买链接不建议缓存不可以每次点击购买都调用 /api/v1/affiliate-links/generate,拿最新 tracking 和平台链接。
商品价格可以缓存展示不可以提交购买时云端重新计算,邀请码当场校验。
优惠券可用状态可以缓存展示不可以使用券时云端按订单/活动/有效期实时核销。
钱包余额/可提现金额可以缓存展示不可以提现提交前实时查余额、KYC、支付密码和风控。
登录态Native 安全存储可以用于请求鉴权Token 过期时刷新;刷新失败引导重新登录。

六、弱网体验规则

场景用户看到什么系统动作不能做什么
首次安装,无网络加载安装包内置 H5,首页可打开;接口区显示弱网/暂无数据等待网络恢复后后台刷新不能白屏;不能卡死在启动页。
已有缓存,网络慢先看到上次商品列表和品牌入口接口在后台刷新,成功后替换不能每次切 Tab 都重新等待。
缓存商品已售罄详情页应提示商品不可购买或隐藏购买按钮详情/转链前实时校验平台状态不能让用户继续承诺返现。
H5 有新包页面先正常用;下载完成后提示刷新ready 包校验通过后等待激活不能启动时先等更新包下载。
H5 新包白屏用户自动回到上一版Native 激活失败回滚 previous 并上报不能把用户永久锁在坏包。
WhatsApp 回跳后网络断保留当前页,显示登录/换链处理中继续轮询或给重试按钮不能丢失用户刚刚复制/回跳的上下文。

七、监控与日志

监控点需要记录用途
启动耗时Native 开始启动、本地 H5 加载完成、首个 H5 API 请求时间判断白屏是离线包、WebView 还是接口慢。
H5 包状态currentH5Version、active/ready/previous、下载结果、sha256 校验、回滚原因排查“为什么还是旧页面/为什么白屏”。
接口缓存命中cacheKey、updatedAt、trigger、platform、cursor、是否 force解释“为什么没有重新请求/为什么旧商品出现”。
商品过滤platform、productId、source、过滤原因: NO_PRICE/NO_CASHBACK/OUT_OF_STOCK/UNAVAILABLE排查无库存商品和 Rp0 商品。
用户反馈日志包设备、App 版本、H5 版本、接口失败、截图前后的本地日志弱网问题必须能由非开发人员提交证据。

八、测试用例清单

编号用例验收标准状态
NW-01断网启动 App不能白屏;能加载内置 H5;接口区有弱网提示。🟡 待补自动化
NW-02弱网 3G 启动本地 H5 先打开;更新检查不阻塞首屏。🔵 手工验证中
NW-03首页有缓存后切换 Tab72 小时内命中缓存;不重复拉同一 Tab;后台刷新成功后 UI 替换。✅ 已接入
NW-04服务端过滤规则调整后升缓存 schema 后旧商品不再展示。✅ 已接入 v2-stock-filter
NW-05商品无价格/无返现/无购买链接前端兜底不展示。✅ 已接入
NW-06Partner Campaign 库存未知商品列表可展示但详情/购买前实时校验;失败时提示不可买。🟡 待完善
NW-07下载到坏 H5 包sha256 不一致直接丢弃;激活失败自动回滚。🔵 需回归
NW-08用户提交日志反馈zip 上传私有 OSS,AI Worker 完成脱敏分析、飞书通知并把最终状态写回数据库。✅ 测试/生产已验收

九、后续专项任务

优先级任务说明负责人
P0商品详情/购买前实时校验Partner Campaign 商品进入详情后,用平台最新接口补价格、返现、库存线索;生成购买链接失败时给用户明确提示。服务端 + H5
P0库存未知字段透出后端返回 availabilityStatus: AVAILABLE / UNAVAILABLE / UNKNOWN,前端展示“预计”并隐藏不可靠购买入口。服务端 + H5
P1商品/店铺黑名单运营或用户反馈不可购买商品后,按平台商品 ID/店铺 ID 临时禁用。后台 + 服务端
P1缓存可观测面板调试浮窗里展示 H5 版本、缓存 key、缓存时间、最近接口结果,支持一键清首页缓存。App + H5
P1弱网自动化用例用 Playwright/移动端脚本模拟离线、慢网、接口 500、缓存命中。QA + 前端
P2缓存策略后台化把首页商品 TTL、品牌 TTL、详情推荐 TTL 放到 runtime-config,用于线上动态调参。服务端 + H5

十、本专项可配参数

参数当前值配置位置说明状态
首页商品缓存 TTL72 小时useHighCommissionProducts.ts后续建议进入 runtime-config。🔵 代码固定
首页商品缓存 schemav2-stock-filteruseHighCommissionProducts.ts用于一次性废掉旧缓存。✅ 已接入
热门品牌缓存 TTL不过期popularBrandsCache.ts接口刷新成功后覆盖。✅ 已接入
H5 包更新检查延迟页面加载后延迟检查h5_package_manager.dart不能阻塞首屏。✅ 已接入
H5 包灰度比例由版本记录决定h5_package_versions.rollout_percent控制新包覆盖范围。✅ 已接入
H5 包强更由版本记录决定h5_package_versions.force_update强更时提示用户刷新。✅ 已接入
商品黑名单〔TODO〕待建后台配置用于处理平台不返回库存字段但实际不可买的商品。🟡 待做