Files
goauto/docs/03-business-rules-and-glossary.md
T
QiuSWandClaude Opus 5 482ba3408a docs: sync business rules and code map mirrors for #241
线上 Wiki 已更新并回读:
Business-Rules-and-Glossary  afb3eb896e41d9aea0f15ad2682ec70b7a3924ea
Architecture-and-Code-Map    d547c17924ac53422232ad9d6c55a34c8cd8d63c
镜像由 harness.py sync 从线上重建,sync --check 通过,未反向覆盖 Wiki。

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01NTDbDcwbDw1TSAcE6wfh2F
2026-09-08 15:24:11 +08:00

81 KiB
Raw Blame History

generated: true (请先修改 Gitea Wiki,禁止直接编辑本文件) wiki_page: Business-Rules-and-Glossary wiki_url: https://git.ilapage.cn/OPC/goauto/wiki/Business-Rules-and-Glossary.- wiki_revision: afb3eb896e41d9aea0f15ad2682ec70b7a3924ea synchronized_at: 2026-09-08T07:16:32Z

业务规则与术语

当前范围

当前已实施范围包含 PDD 商品最新档案与采集闭环、虾皮商品档案、SYB 商品与后台导入、采购任务服务、Admin 采购任务与人工处理页面、Android 采购演练,以及 #36 的正式地址后缀与创建待付款订单能力。#36 尚未获得真机创建订单授权和验收;物流采集与自动回填仍由独立工单推进。

PDD 商品

  • PDD URL 由管理员人工录入。
  • 服务端必须规范化 URL 并提取 goods_id;提取失败时拒绝保存。
  • goods_id 唯一;相同 goods_id 再次添加时提示“商品已存在”。
  • 已存在商品允许修改当前 URL,但不自动改变已创建任务的 URL 快照。
  • 最简创建只输入 URL,新商品状态为 pending;人工完整保存或首次成功采集后转为 active,人工可设为 disabled。
  • 商品只保存标题、店铺、数字销量/评价和规格的最新值,不保存价格或字段变更历史。
  • specs_json 使用通用多维结构,角色为 color、size、other;只有颜色规格值保存非负整数分价格,规格值同时保存是否可选择。
  • 人工保存为完整覆盖。completed 采集结果全量覆盖;completed_partial 只合并明确采集到的字段和规格,不删除原有缺失部分;failed 不修改商品。
  • 人工停用的商品不会被后续采集结果自动重新启用;假售罄、临时售罄和采集失败也不会自动停用商品。

虾皮商品

  • shopee_item_id 全局唯一,仅在存活记录之间生效;软删除的记录不占用该唯一性,重新创建或 #41 重新导入均可成功。
  • pdd_product_id 可为空,且不加唯一约束:一个虾皮商品最多关联一个 PDD 商品,但多个虾皮商品可以共用同一个 PDD 商品。
  • 关联 PDD 商品时校验目标存在且非 disabled;不提供手工输入商品 ID 的入口,只能通过搜索选择。
  • 参考售价 sale_price_cent 为整数分,currency 为 ISO 4217 代码;币种取系统配置默认值,不逐商品选择,缺省回退为 TWD。
  • 规格值来源分 import(SYB 导入,不可人工删除,只能清除映射)与 manual(人工添加,可删除);导入与人工值按「维度 + 名称」合并,不重复创建。
  • 映射来源分 manual(人工,允许创建时即为已确认)、exact_match(名称标准化后唯一一致)、ai_match(AI 建议)。通用 SetMapping 入口仍将 exact_match 与 ai_match 一律写为 pending,必须人工确认后才生效;#188 的 SYB 商品页批量 AI 匹配与 #194 的 Admin 蝦皮商品详情一键匹配是两个独立例外。#188 的进入条件已由 #190 放开:只要蝦皮与 PDD 关联完整、PDD 当前为 active 且能给出可选颜色/尺码候选、并且已解析出至少一个目标颜色或尺码,即可进入批量匹配。解析状态(含 parse_status=uncertain 与 failed)、PDD 含颜色尺码之外的可选规格、蝦皮档案中未找到目标颜色或尺码、缺少完整可售 SKU 组合证据,自 #190 起都不再阻断匹配;本项目为内部系统,由此产生的“以错误目标规格进行匹配并保存映射”的风险由人工承担。唯一确定性 exact_match 不调用外部 AI,可直接保存为 confirmed;SYB 商品页批量 ai_match 只要 Provider 成功返回规格结果且理由非空、返回值属于当前可选候选即可直接持久化为 confirmed,置信度仅记录供审计、不作为放行门槛。若当前 PDD 档案存在完整可售颜色+尺码 SKU 组合证据,结果还必须命中其中同一个组合;人工录入或外部导入导致组合证据缺失时不阻断保存或创建采购。无结果、已有组合证据中的无效组合或 Provider 异常不得改写现有映射。
  • 颜色映射只能从关联 PDD 商品当前可选颜色中选择,不允许自由输入;未使用颜色优先显示,已被其他蝦皮颜色使用的颜色仍可选择并显示占用者,因此支持多对一。
  • Admin 蝦皮商品详情只保留一个“一键匹配颜色和尺码”入口。已确认且目标仍存在的映射保留;名称标准化后的唯一确定结果直接写为 exact_match + confirmed;其余只有在 AI 置信度达到服务端当前阈值、理由非空、返回值仍属于当前可选候选时才写为 ai_match + confirmed。低置信度或无结果保持未匹配;Provider 失败、AI 未启用、关联或规格上下文变化时本次不写入。操作前有未保存的人工修改时禁用一键匹配;保存只改映射,不改蝦皮或 PDD 原始规格。
  • PDD 重新采集或更换关联后,目标规格仍存在则映射继续有效;目标规格消失时详情标记“已失效”,服务端拒绝保存不存在的目标,采购预检和创建也拒绝使用失效映射并提示重新选择。
  • 批量软删除逐条校验引用(虾皮商品被 SYB 明细或采购任务引用时不可删除)并逐条返回结果;已删除商品默认不出现在列表,可筛选查看并恢复。

SYB 商品明细

  • 一行对应 SYB 一条明确的商品/颜色/尺码/数量明细;唯一键为「蝦皮订单号 code + 来源明细 id」组合,不是全局唯一 ID(未在多货运单样本中验证过全局唯一性)。

  • productSpec 自由文本解析:按最后一个逗号切分为颜色/尺码 → 剥离【】备注 → 判断残留分隔符;解析状态分 success/uncertain/failed,永不猜测原文中不存在的颜色或尺码。

  • 采购放行不以 uncertain 单独阻断:success 与已提取出至少一个非空颜色或尺码的 uncertain 明细,都可继续进入规格匹配和采购预检;只有 failed 或颜色、尺码均为空的异常明细才要求人工处理。uncertain 状态与解析说明继续保留供审计,不会自动猜测规格。

  • 只有 success 状态的解析结果会合并进虾皮商品档案的规格值(来源标记 import);uncertain/failed 只停留在明细行上供人工复核,不污染共享档案。

  • 金额单位按接口分别定义:/am/stock/detail/listByStock 的 productPrice 是十进制金额,与 /am/stock/list 的 amtOrder(×100 整数)不是同一套换算,不可共用。

  • 关联虾皮商品档案:命中存活记录直接关联;命中软删除记录则复活并保留原有人工映射;均不存在时创建最小档案。命中既有档案时只补写为空的参考图与售价,不覆盖人工修改过的标题、店铺和映射。

  • 重新解析只读取已保存的原始 JSON,不请求 SYB 接口,永不改写 RawJSON;标记 manuallyConfirmed 的明细默认跳过重新解析,除非显式指定强制覆盖。

  • 人工修正的颜色/尺码视为与解析成功同等可信,同样会合并进虾皮商品档案;标记为已人工确认。

  • Admin 商品列表的订单号筛选每行一个、去空去重后精确匹配,最多 100 个且单项最长 64 字符;店铺名称使用包含匹配。店铺、订单号与解析状态之间使用 AND,不再用该筛选框搜索蝦皮商品 ID 或商品标题。

  • SYB 商品数据本身不保存 PDD 订单号、快递单号、支付或有效订单状态;Admin 的采购任务创建入口位于 SYB 商品列表,任务事实仍写入独立采购域。

SYB 商品处理阶段

  • SYB 商品页保留“解析状态”,另按 SYB、蝦皮、PDD、采集任务和采购任务的当前事实动态派生唯一“处理阶段”;不在 syb_product 保存容易过期的阶段字段。
  • 对采购人员展示的阶段固定为:待人工处理、未关联 PDD、PDD 待采集、PDD 采集中、PDD 采集失败、规格待匹配、可创建采购、已创建任务、采购成功、待人工核对。
  • 主阶段优先级为:待人工核对 → 采购成功 → 已创建任务 → 待人工处理 → 未关联 PDD → PDD 待采集/采集中/采集失败 → 规格待匹配 → 可创建采购。每行只显示一个阶段和对应下一步。
  • “待人工核对”表示订单结果不明确,必须先人工核查并禁止自动重试;“采购成功”表示已取得 PDD 订单号和下单时间,不代表已经支付。
  • 一个 PDD 订单号只能属于一个采购任务,该唯一性在采购任务保存路径上全局强制(#241)。人工处理结果未知、取消及 lifecycle 保存路径撞号时返回 PURCHASE_ORDER_NUMBER_ALREADY_USED,提示订单号已属于哪个任务,由采购员人工核对,不静默覆盖原值。
  • 不可逆边界之后的 order_created 结果回传是上述规则的例外:此时 PDD 真单已创建,发现订单号已属于其他任务时不回滚、不判失败,而是把任务降级为 order_result_unknown,冲突订单号以「读到订单号 X,但该号已属于任务 CG-yy」保存在任务与 attempt 的 error_message,pdd_order_no 留空以维持唯一性,保留下单时间与不可逆时间,进入既有人工处理结果未知通道。首要目标是保住「真单已存在」这一事实,不制造无记录的真实订单。
  • Agent 可按收货地址后缀 _cg<任务号> 批量回填订单号与下单时间(#241)。后缀只承载任务号,请求不含地址全文或收件人信息;只允许回填该设备自己的正式采购任务;页面下单时间优先,缺失时回落该任务的 irreversible_at 并标记时间来源,两者皆空则该条失败。
  • 已失败、已取消或演练完成的旧采购任务不单独占用主阶段;当前数据仍满足条件时恢复显示“可创建采购”,旧任务继续在采购管理留痕和按既有规则处理。
  • 未选择处理阶段时,商品列表仍先返回,当前页阶段和采购准备继续异步批量读取且不调用 AI Provider;选择阶段筛选时,服务端必须先对完整查询结果派生并筛选阶段,再计算总数和分页,不能只过滤当前页。

SYB 店铺过滤

  • syb_shop 保存允许导入的 SYB 店铺;店铺名比较前统一去除首尾空白、转换全角/半角字符并忽略大小写。规范化后同名的店铺只能保留一条有效记录。
  • 版本迁移会对历史存活店铺回填 normalized_name = Normalize(display_name);回填只改匹配键且可重复执行。若两个存活店铺回填后会得到同一键,迁移必须整体失败并保留原数据,管理员先人工消除歧义后再执行,不能静默合并、删除或改变店铺启用状态。
  • 店铺可以从 SYB 真实货运单列表发现,也允许管理员手工补充。只有管理员可以新增、改名、启停和软删除,采购员等其他角色只读。
  • 没有任何启用店铺时,导入必须在读取凭据、建立会话、验证码 OCR 和任意 SYB 网络请求之前失败,并给出“请先启用店铺”的可读提示。
  • 同步先预检全范围总数及上限,每页校验原始列表条数、合法 ID 和重复,再按冻结店铺快照获取明细并页事务保存;整日结束核对总数。过滤不能降低完整性校验范围,已保存不能冒充整日完整(#239,c6a962d,已于 2026-09-08 随 d403f3b 部署线上)。
  • 只有列表与明细响应的店铺名都非空且命中启用快照时才允许写入。明细店铺名为空、变化为未启用店铺或无法匹配时跳过,并计入跳过数量。
  • 停用或软删除店铺只影响后续导入,不删除历史 SYB 商品、虾皮商品或任务数据。已有错误导入数据的清理必须先给出精确 SQL 和影响行数,再由用户单独确认。

SYB 后台导入记录

  • 导入允许管理员和采购员(purchaser)创建,创建成功后立即转入后台执行;页面关闭不取消任务。其他已登录角色只能查看同步记录,不能开始导入(#236)。
  • 系统同一时刻只运行一个 SYB 导入任务。syb_sync_run 的唯一执行槽负责跨进程互斥,内存锁减少同一进程内的竞争;服务重启后遗留的执行中记录标记为“已中断”。
  • 导入失败或中断时保留已写入商品,记录明确的失败原因和已处理进度;重新导入相同范围按「订单号 + 明细 ID」覆盖,不产生重复商品。
  • 创建同步记录时冻结本次启用店铺的规范化匹配集合、展示名称快照及 SHA-256 哈希;后台执行必须只使用这一份快照,不得在开始后重新读取 syb_shop。同步详情保存并返回快照可用标记、快照店铺名称、哈希及各店铺“已导入/已跳过”数量。#212 之前的历史记录只有哈希和统计,明确标记为无完整快照。上述记录不保存账号、密码、Cookie、Token、验证码图片或 SYB 原始响应。
  • 后台任务创建前的内部失败仍向普通用户显示“服务端处理失败”,但使用稳定错误码区分阶段:店铺预检为 SYNC_SHOP_PREFLIGHT_FAILED,同步记录创建为 SYNC_RUN_CREATE_FAILED。服务端只记录阶段和经过脱敏、截断的底层原因,不记录请求体、凭据、Cookie、Token、验证码或原始响应。

采集规则

  • 规则创建后立即可用,不存在草稿、发布、版本或停用流程。

  • 规则允许编辑;新任务读取编辑后的当前内容。

  • 创建任务时保存完整 rule_snapshot;规则编辑不影响正在执行的当前 attempt。人工重新采集会归档旧 attempt,并按来源刷新规则:Admin 来源读取原 rule_id 的当前存活内容,Agent 当前页来源读取当前手动采集默认规则;规则已删除、不可用或设备能力不兼容时拒绝重采且不修改原任务。

  • 删除采用软删除;删除后不能创建新任务,但已有任务继续执行自身快照。

  • 商品详情步骤应声明精确 activityName,并与包名和唯一控件共同作为页面证据;进入 PDD 登录 Activity 必须返回 PDD_LOGIN_REQUIRED,不能提交采集成功。

  • 唯一文字节点不可点击时,Agent 只可点击其最近的可点击父容器;不得改点兄弟节点或相似文字。

  • 商品页规格入口只接受带明确选择语义的规格摘要,或底部真实“购买/拼单”文字按钮。若“请选择”和颜色/尺码语义分散在同一可点击父容器的子节点中,也只能在该容器唯一、位于非底部动作区且同时具备两类语义时作为规格入口;规则别名只能收窄已识别的安全候选,不能按页面原始文字扩张。底部购买入口在通过全部安全过滤后仍存在多个候选时,按最右优先(centerX 降序,并列时可点击面积升序)确定性选出唯一入口,不再因候选不唯一直接失败;该情形记为 bottom_purchase_rightmost,唯一候选仍记为 bottom_purchase。“单独购买”与“发起拼单”打开同一规格面板,但对应不同成交形态与价格,最右优先是经人工确认的取舍。评价、评论、晒单、问答、订单、提交订单、支付和付款区域及其父容器一律排除。商品评价页与详情页共用 Activity 时,首次误触只允许安全返回并重新定位一次,重复误触明确失败;点击无变化、误入评价页和面板结构无法确认使用不同错误码。

  • v2 规则使用类型化动作和固定阶段钩子。已由 Agent 支持的选择器、别名、超时、滑动方向和有限次数可以只更新规则;新增动作类型或页面算法才需要升级 Agent。

  • v2 任务首次未进入精确商品详情页时,可以按规则显式重开同一浏览器 URL 一次;登录、验证码、风控、无效链接和详情页内采集失败不触发该恢复。

  • 假售罄恢复只使用主商品规格/购买强证据判断页面是否正常;顶部“相似商品”可以作为受控兜底证据,推荐卡片的标题、价格和销量不得冒充主商品证据。

  • 商品规格遍历必须用已识别规格节点锁定横向颜色容器和纵向面板容器;颜色按视觉行蛇形遍历,滑动完成后重新读取节点,尺码只读并允许在标题滚出后沿已锁定容器续页。

  • PDD 已选规格的订单确认形态只可由详情页、选择摘要、唯一数量控件、支付区、唯一底部提交动作和唯一主要滚动容器的组合证据确认;底部提交动作只读且永久禁止点击。Agent 只在该已确认容器内最多三次向下拖动回顶,每次重新读取节点;“参考分类”作为尺码的精确标题别名处理。

  • PDD 完整规格选择器若无主滚动容器且尚未选择规格而没有已选摘要,仍可识别为非滚动规格面板,但必须同时出现至少两个已解析维度、至少两个可选项、唯一数量控件和唯一底部订单动作;缺少其中任一强证据时保持未识别。该订单动作仍仅作页面证据,永久禁止点击。

  • Agent 可扩展,但规则必须按任务类型授权:采集规则不能创建订单,采购规则只能使用独立审核的创建订单能力。当前项目不实现支付动作、入口或测试;支付、下单和订单相关文字可以作为只读页面证据配置,但不得成为点击目标。后续支付能力必须单独评估并至少具备显式能力位、服务端开关、单笔金额上限和人工授权。

采集任务

  • 任务与结果共用 collection_task 主表,不建立独立 collection_result 主表。
  • 创建任务时固化 url_snapshot、goods_id_snapshot 和 rule_snapshot。
  • 设备默认人工指定;未指定时由在线空闲设备原子领取。
  • 一台设备同时只执行一个任务。
  • 同一 PDD 商品不能同时存在多个 pending 或 running 任务。
  • 手机离线时运行中任务失败;默认不自动重试、不自动换机。
  • 所有 failed 任务,无论由 Admin 还是 Agent 当前页创建,都允许采购员人工“重新采集”;必须复用原 collection_task.id,不得为同一次重采新建任务。Admin 来源继续允许重置 completed、completed_partial,Agent 当前页来源只允许失败后重采;running 禁止重置和删除。
  • collection_task.attempt_number 表示当前执行次数。重采事务先把旧终态执行归档到 collection_task_attempt,保留当次来源、设备、规则 ID/快照、终态、结构化错误、结果摘要与时间,再递增 attempt、清理主表当前错误/结果/租约并恢复为 pending;不保存原始控件树、截图、Token 或个人数据。
  • 重采使用最新有效规则:Admin 来源刷新原规则当前内容,Agent 当前页来源刷新当前手动采集默认规则。全部资格、规则、设备、商品冲突和幂等检查必须在事务写入前通过;相同 requestId 重放不得重复归档或递增。
  • Agent 当前页任务在身份识别前失败时,下一 attempt 允许首次绑定商品;已经绑定商品时必须重新识别为相同 goods_id,不同商品明确失败且不得覆盖原身份。当前页发起重采前仍要求无障碍就绪、最近 PDD 前台证据、设备在线空闲及本地冷却通过。
  • 任务自身结果仍只在任务详情查看;任务完成后会按完整/部分完成规则更新 PDD 商品最新档案,商品页不替代任务结果审计。
  • PDD 商品列表批量操作只选择当前页,最多 100 个商品;每个商品仍创建一个独立采集任务。
  • 已停用、没有可用采集规则或已有 pending/running 任务的商品不能勾选,并显示普通人可理解的原因。
  • 一批商品统一选择一个规则和一个可选设备;设备留空时仍由空闲设备领取。服务端提交时逐商品重新校验。
  • 批量创建按商品分别执行现有单任务事务,允许部分成功;失败项返回稳定错误码和可读原因,不回滚已成功任务。
  • 批次 requestId 为每个商品派生稳定的创建请求标识,同一批次重放不会重复创建任务。
  • 批量采集不创建采购任务、PDD 订单或支付动作。

采集字段

  • PDD 标题、店铺名、销量、评价数量。
  • 通用规格维度和值,当前重点是颜色和尺码。
  • 采集时按颜色读取价格;同一颜色下不同尺码默认价格相同。
  • 逐颜色价格只在精确点击后取得目标选中、已选摘要或规格面板变化证据,并等待候选价格连续稳定后保存;其他颜色残留的选中标记不能阻塞当前颜色。点击无效果时不能沿用旧价格,相同价格允许保存;无法确认选择、找不到价格和价格不稳定只记录结构化原因并按缺失价格提交。
  • 存储时展开 SKU 组合,将颜色价格复制到该颜色各尺码 SKU。
  • SKU 不完整仍提交已有结果并标记 completed_partial。

采购任务契约

  • 采购域使用独立的 purchase_task、purchase_task_attempt 和可选 pdd_account 引用;PDD、虾皮和 SYB 商品表不保存采购订单、支付、物流或回填字段。
  • purchase_task.task_type 区分 syb_order 与 stock。旧任务迁移为 syb_order;备货任务只引用已完成采集且处于 active 的 PDD 商品,颜色/尺码必须逐字命中当前可选规格,规格来源固定为 direct_select,SYB/虾皮身份快照为空。
  • 备货任务不占用 SYB 活动槽,同一 PDD 商品可存在多个待执行备货任务,但设备、可选账号和执行期互斥仍沿用采购安全边界。备货任务不参与商品替换、批量重试、重新采购授权或 SYB 回填;失败后由人员重新创建备货任务。
  • Admin 在处于 active 且具有当前可选颜色价格(有尺码维度时还须有可选尺码)的 PDD 商品详情创建备货任务;颜色、尺码只能从最新采集档案选择,不允许自由输入,颜色切换后按已采集价格更新默认上下限。采购管理列表和详情用“订单采购 / 备货采购”区分类型;备货任务的 SYB/虾皮字段显示为空、失败任务不提供重试,并明确提示“备货采购不参与库存扣减与订单关联。”
  • 正式任务必须引用一条 SYB 商品明细;演练任务可以从 PDD 商品人工创建且不引用 SYB。
  • 创建时固化三个商品身份、蝦皮订单号、目标和映射规格、数量、价格区间、币种、URL、goods_id、规则、设备和可选账号引用。商品档案后续修改不改变任务解释。正式任务的蝦皮订单号来自 SYB 商品 order_code,同一订单号可以对应多条商品和多个采购任务,不作为唯一键。
  • Android 无法可靠识别登录中的 PDD 账号,因此账号引用可空;已知账号才参与账号级串行,未知账号不会阻止采购任务。
  • 同一 SYB 明细可以保留多个历史采购任务,但最多只能有一个活动任务。重新采购新建任务,旧订单不删除、不覆盖。
  • execution_mode 创建后不可变:rehearsal 只能完成商品、规格、数量和价格复核;live 才可能获得改地址和创建订单能力。任何模式都不支持可执行支付动作;规则中的支付相关文字只可作为只读识别信号。
  • 演练规则在服务端契约层拒绝改地址、创建订单和核单动作;正式动作还必须通过版本化能力协商。规则只包含类型化动作,禁止任意脚本。
  • 价格保护保存参考单价、最低单价、最高单价和币种,执行时以 PDD App 实际单价判断;价格越界明确失败,不考虑优惠券。
  • Admin 从 SYB 当前页选择商品,可在“创建采购”和“重新解析”两种批量用途间切换;采购模式只允许选择预检合格行,表头全选不跨页。批量预检和正式创建均最多 100 条并逐条重新校验,每条 SYB 明细只创建一个独立任务;部分失败不回滚其他成功项。
  • SYB 商品列表在列表数据返回后立即展示,采购准备状态独立异步加载;只读批量预检只执行批量数据库读取和本地确定性识别,禁止调用 AI Provider。自 #215 起,未保存或已失效的长期规格映射不再阻断创建采购;满足商品关联、PDD 状态、价格、规则、设备和订单安全门禁后即可创建任务,每个新 SYB 采购任务都在首个 attempt 以当次 PDD 页面候选重新决策。
  • SYB 商品页的 PDD 采集资格独立于采购处理阶段:只要已关联的 PDD 商品未停用、没有 pending / running 采集任务且存在可用采集规则,即可创建采集任务;因此已完成采集并进入“可创建采购”的商品也可以重新采集。相同 PDD 商品在批量创建前按商品去重,服务端创建时仍按最新状态复核。
  • 批量创建读取管理员选定的当前采购规则并重新执行契约校验,每条任务保存不可变快照;当前规则缺失或无效时明确阻断,不回退到代码常量。设备默认人工指定,也可以留空由符合能力的空闲设备领取。
  • 批量创建的价格保护来自 PDD 商品档案而不是 SYB/Shopee 的 TWD 售价:当前采购规则可用 priceGuard.minRatio(0.1~1.0)和 maxRatio(1.0~3.0)配置比例,缺省仍为 0.2 / 1.5;最低价向下取整、最高价向上取整到人民币分。已确认颜色映射时按该颜色计算,待规格探测时以全部可用颜色的最低/最高价计算,参考价取最高价;没有可用颜色价格时不能创建。
  • 地址后缀为 _cg{purchase_task.id}。精确规格、数量、价格和摘要核验通过后,若仍处于已识别的规格面板,Agent 只允许点击唯一、可见、启用、可点击且文案精确命中“确定/确认”别名的规格确认控件;不得点击提交订单、确认购买、付款、支付、地址修改或地址保存控件,也不使用中心手势兜底。点击后必须重新读取并确认已出现订单确认页或地址入口强证据,否则明确失败。进入订单确认页后,若收货地址被面板裁切,只允许在唯一、可见且占据主要宽度的纵向滚动容器内有限向下拉动来显示地址,禁止按页面最大滚动区域盲目滑动。Agent 只在唯一地址入口、唯一修改按钮和唯一详细地址输入框均成立时修改;脱敏手机号文字本身不可点击时,仍以该唯一文字节点的中心坐标执行一次精确手势点击,不沿用可能覆盖整个下单面板的可点击祖先。“修改”“保存”和“提交订单”等文字节点即使依赖可点击父节点,也必须保留原始文字节点作为每次重新定位的锚点,父节点只用于验证存在可点击路径。近乎完全重叠的无障碍重复节点按一个目标处理,仍有多个独立目标或页面切换超时则明确失败。按首个 - 或 _ 截取地址主体后追加当前后缀,保存后必须回读完整新地址。修改或回读失败时禁止创建订单,地址全文和控件树不落库。
  • 地址编辑页可以同时存在收货人、手机号和详细地址等多个输入框;Agent 只选择与“详细地址”标签纵向重叠且位于其右侧的唯一输入框,不能用页面输入框总数或顺序猜测。
  • 点击创建订单前,Agent 必须先在本地事务保存 order_submit_started、不可逆时间、稳定请求 ID 和不含地址全文的最终确认快照,再用同一请求 ID通知服务端;两侧成功后才允许精确点击唯一创建订单按钮一次。
  • 进入不可逆边界后,进程重启、断网、点击结果不明或无法取得唯一订单号/下单时间时只允许只读核单并进入 order_result_unknown,禁止再次点击;任务与订单正式关联仍以完整 PDD 订单号为准。
  • 创建订单后出现 Android 多微信应用选择器时,Agent 只有在系统包和 ChooserActivity / ResolverActivity 白名单、已知选择器标题、微信候选三类证据同时成立时,才允许按一次返回,绝不点击微信候选。若已进入真实微信包 com.tencent.mm,Agent 不点击、不输入、不登录、不支付、不强制停止微信,只允许用一次无参数 PDD 启动 Intent 把既有 PDD 任务栈拉回前台;第二次仍见微信或拉起失败即保持结果未知。回到 PDD 已知支付 Activity 或明确支付动作页面后最多再返回一次,再只读读取唯一订单号和下单时间;下单成功页仅可点击唯一、精确的“查看订单”或“订单详情”入口一次,进入 PDD 订单详情后才允许有限向上手势下翻读取折叠内容。PDD 页面出现“待付款”“待支付”“订单编号”或“下单时间”等订单结果信号时,该只读信号优先于复用的支付 Activity 名称:允许在唯一主要纵向容器内有限下翻并重新读取,仍不得点击支付;没有任何订单结果信号的支付页或未知页面不得盲目滑动。入口缺失或不唯一、点击后未出现详情证据、任一页面不在白名单、恢复动作重复或结果不唯一时保持 order_result_unknown,禁止重下单或支付。
  • Agent 本地 SQLite/Outbox 负责断网和重启恢复,服务端以 task_id + task_attempt_id 幂等接收并保存最终事实。
  • 人工支付复核只记录 paid / unpaid;系统不执行或识别支付。快递单号与回填状态属于采购任务,后续物流工单实现。
  • 采购任务领取时同时占用设备租约和可选 PDD 账号租约;租约过期后才可释放并重新领取。设备还存在采集任务时不能领取采购任务。
  • 自 #215 起,每个新 SYB 采购任务无论是否存在已确认长期映射,都先由 Agent 在当次 PDD 规格面板内有界遍历颜色和尺码并回传原始候选。服务端只以任务冻结的 SYB 目标规格与当次候选先做唯一确定性匹配(繁体转简体、空格/全半角/大小写统一,以及公斤/斤换算),仍无唯一结果才调用已启用的服务端 AI。AI 必须逐字返回当次候选集中的原始标签;候选不完整、集合外返回、歧义、AI 无结果或服务不可用均明确失败,不派发第二趟、更不创建订单。
  • Agent 选择服务端下发的精确颜色或尺码时,只能在已确认打开的规格面板内有限纵向滑动、每次重新读取可选节点并按完整原始文字点击;连续没有新证据或达到上限即停止,不得点击相近规格。第一趟探测并固化规格后,第二趟仍无法精确选择而再次提交探测时,服务端必须明确失败并释放活动槽,保留第一次决策证据,禁止清空决策、循环派发或进入地址与创建订单动作。
  • 采购 Agent 在确认进入 PDD 商品页后、打开规格前,复用采集侧的假售罄识别;规格面板已打开且当前解析到的规格值全部不可选时也按售罄处理。两种情况都只允许关闭规格面板后对商品页执行一次有界恢复(默认下拉 2 次、间隔 1000 毫秒、等待 2000 毫秒),恢复动作失败或恢复后仍售罄时返回 PDD_GOODS_SOLD_OUT,恢复后商品页证据丢失时按页面规则不匹配失败;不得继续选择规格、修改地址或创建订单。该失败码继续进入既有替代商品资格判定。
  • 所有新 SYB 采购任务的规则都必须具有 purchase.spec-probe.v1;创建时任务级 mappedColor / mappedSize 为空且 spec_source=unresolved,长期映射和 PDD 档案候选都不能跳过首趟探测。第一趟只探测规格并释放租约,服务端固化同一 attempt 的决策后才派发第二趟;探测阶段从服务端拒绝进入 order_submit_started。Android 不自行匹配或猜测,只在第二趟接收并精确选择服务端固化的当次 PDD 原始标签。
  • Agent 提交的相同 attempt 最终结果只能写入一次;相同请求重放返回原事实,不同内容拒绝覆盖。order_result_unknown 不参与自动派发,只能人工解除。
  • 已创建订单默认禁止再次采购;管理员或采购员可以做一次性重新采购授权,新任务创建成功时在同一事务消耗授权,旧任务和旧订单保留。已标记为已支付的订单不能授权或创建重新采购任务。
  • 人工回填候选只允许从已支付订单选择;同一 SYB 明细后来选择的订单覆盖旧候选,但不删除旧订单事实。
  • Admin 采购管理只查看和处理已有任务,不提供创建入口或支付按钮;单条和批量采购任务都从 SYB 商品列表发起。订单结果未知时必须先人工核对并解除;处于该状态时页面不提供重新采购授权。
  • 采购失败任务可在采购管理当前页批量勾选重试,最多 100 条。重试不修改旧任务,而是用当前 SYB/PDD 档案、目标规格、当前价格保护和当前采购规则创建新的 pending 任务,并生成新任务编号与地址后缀;来源蝦皮订单号沿用失败任务的不可变快照。新任务不复用旧任务或长期档案的执行规格,仍必须先完成当次真机规格探测。
  • 只有正式采购、未进入不可逆边界、没有订单号或下单时间、且仍是同一 SYB 最新记录的 failed 任务可重试。原设备离线、停用、忙碌或能力不足时该项失败且不自动换机;未指定设备时仍由空闲设备领取。
  • 批量重试逐项处理并允许部分成功;同一请求幂等重放不会重复创建。失败任务不再使用一次性重新采购授权,该授权只保留给已经创建过订单且满足条件的任务。

管理端角色与权限

  • 管理端固定支持 admin(管理员)和 purchaser(采购员)两类业务角色;用户必须绑定一个存在且启用的角色,role_id=0 或停用角色不能创建或保存。
  • 采购员可读取设备状态,维护 PDD/虾皮商品和规格映射,查看与修正 SYB 商品,读取 SYB 店铺及同步记录,读取采集规则,创建/重置/删除采集任务,并创建、查看、重试及人工处理采购任务。
  • 仅管理员可管理用户、角色、菜单、接口、部门和岗位;停用设备或吊销 Device Token;新增、改名、启停、删除或发现 SYB 店铺;新增、编辑或删除采集规则;保存或测试 AI Provider 配置。
  • AI 规格匹配菜单对采购员硬排除:采购员不显示该菜单,角色配置也不能为采购员选中该模块;既有 API 权限不变,仍只允许读取是否启用,不得读取 Provider 地址、模型、API Key,也不得保存或测试。
  • GoAuto 菜单由代码维护的模块定义幂等写入系统菜单和菜单/API 关联;迁移只为采购员追加首次引入且默认开放的模块,不会把采购员人工取消勾选的既有模块重新加回。
  • 采购员 Casbin API 白名单由代码权限矩阵全量重建,不从角色菜单勾选反推;减少权限时旧策略必须删除。菜单勾选只控制可见模块,不能扩大采购员 API 权限。
  • GoAuto 管理接口使用 Casbin 按 HTTP 方法和路径授权;设备凭据、规则和外部服务配置等高风险写操作另有管理员角色守卫,前端隐藏入口不能替代服务端授权。
  • 管理员继续使用 admin 旁路;采购员必须由明确的 purchaser 策略授权,不得通过赋予管理员角色临时解决登录或权限问题。
  • 任何角色都不得执行自动支付。

自动化边界

  • 浏览器“打开拼多多APP”和系统确认框“打开”属于允许动作。
  • 登录失效、验证码、风控、人机验证和找不到唯一控件时失败并给出具体错误。
  • Android Agent 到 GoAuto 服务端默认使用 HTTPS。管理员可在明确接受 Device Token、任务内容、设备状态和执行结果被链路监听或篡改的风险后,通过服务端 GOAUTO_ALLOW_INSECURE_AGENT_HTTP=true 显式允许全部 /api/agent/v1/** 使用 HTTP;该例外不放宽 PDD、SYB、OCR 或其他第三方服务约束。
  • Android Agent 端不使用 OCR/VLM 兜底,不保存原始控件树或截图。采集阶段不猜测缺失数据。
  • 服务端顺云宝(SYB)登录例外:允许调用配置的线上 OCR 服务识别登录验证码(见 #48)。验证码图片会离开本项目发送到该服务,更换服务地址前必须重新评估。此例外只适用于 SYB 登录,不扩大到 Agent 端或任何 PDD 相关流程。
  • 采购阶段的规格匹配由服务端决策(见 #46、#62):Agent 本地不得自行猜测规格或点击相近候选,只执行服务端下发的精确规格;AI Provider 只有一个 OpenAI-compatible 配置,由管理员维护。根据 #62 已确认的内部部署例外,API Key 明文保存在专用设置表,并只向管理员设置接口返回以便查看和替换;它仍不得写入代码、日志、工单、Wiki、任务快照、采购员接口或 Android 接口。Provider Base URL 不限制内网或公网,支持 HTTP/HTTPS;HTTP 不加密传输中的 API Key,生产环境建议 HTTPS。
  • 采购规则的 openSpecPanel 默认不写死页面文字。Agent 只在已由页面语义确认的规格入口或底部购买入口中选择;规则若提供 textAliases,只能进一步缩小这些安全候选,不能把任意同名页面文字变成可点击入口。
  • 采购规则的 probeSpecs.dimensionAliases 是只读规格维度标题的服务端下发事实源;颜色别名可由管理员增加“组合”等 PDD 页面文案,尺码别名单独维护。该字段只影响探测和 AI 匹配输入,不能改变 selectSpec 的精确点击目标;旧任务快照缺省时才使用 Agent 内置兼容值。
  • PDD 采集规则的 collector.textAliases 是规格面板、维度标题、选择摘要、评价入口、售罄主商品证据和购买入口等只读识别文案的服务端下发事实源;缺省字段只为旧快照兼容使用 Agent 内置默认值。颜色/尺码分类不得再用代码字面量扩大 dimensionAliases。订单和支付文字可以参与只读页面判定,但 Agent 内不可配置的创建订单/确认订单/支付/付款点击拒绝清单始终优先,规则不能放宽;修改地址和收货地址在只读及点击字段中都禁止。
  • PDD 颜色采集对首屏已识别为多行或网格的颜色区执行动态行发现:每次动作后重新解析全部可见行,单列不做无效横向滑动,并复用规则中的 specVerticalSwipes 与 stableEdgeReads 有界纵向翻页;颜色结束后规格面板归顶,再进入尺码发现。选项重排或已选项从无障碍节点消失时,不得静默跳过仍未尝试的可用颜色。
  • 正式采购规则可以调用独立审核的改地址、创建待付款订单和只读核单动作;采集规则和演练规则不能调用。真机首次安装或验证仍需独立人工授权。
  • 系统当前不提供自动支付、实时屏幕或管理端远程控制。付款、免密支付及任何等价动作不能配置为点击目标;只读识别字段可以包含支付或订单文字。后续若新增支付能力,必须由独立工单和显式控制重新评估。

设备身份与认证

  • Android Agent 首次安装生成唯一 install_id;服务端收到合法设备信息即注册或更新设备,不使用硬件标识作为唯一键。
  • install_id 在设备表中唯一,不存在注册码、注册申请或设备审核记录。
  • Device Token 明文只返回给客户端,服务端数据库只保存不可逆摘要。
  • 设备状态只保存在线、离线或停用;是否忙碌由运行中的任务关系确定。
  • Agent 默认每 15 秒心跳一次,45 秒没有心跳即离线;离线扫描每 15 秒执行。
  • 心跳上报的 currentTaskId 必须与服务端该设备唯一运行任务一致;采集任务和采购任务共用这一设备级忙碌事实,异常出现跨域同时运行时按服务端一致性错误处理。
  • 设备超时离线时,运行中的采集任务和尚未提交订单的采购任务立即以 DEVICE_OFFLINE 失败,清除租约及运行槽且不自动重试;采购 attempt 同步结束并标为失败。
  • 采购任务已进入 order_submit_started 后设备离线时,任务转为 order_result_unknown 并释放设备/账号运行槽,必须人工核对,禁止自动重派或再次点击创建订单。

术语

术语 含义
规则快照 创建任务时复制到任务中的完整规则内容
URL 快照 创建任务时复制到任务中的 PDD URL 和 goods_id
空闲领取 未指定设备的待执行任务由在线且无活动任务的设备原子领取
部分完成 结果已提交,但一个或多个规格/SKU 缺失
重置任务 保留任务输入快照,清除原结果后重新进入待执行状态
Portal/Agent Android 端注册、保活、执行规则和提交结果的程序
虾皮 Shopee 的中文展示名。管理端界面一律用「虾皮」,数据库表名、字段名、API 路径等程序标识符保持 shopee_product(单数)/ shopee_item_id 不变
SYB 顺云宝 ERP(ShunYunBao,域名 shunyunbaoerp.com),虾皮订单与货运单的外部来源系统。管理端界面一律用「SYB」,不再使用「货运宝」「顺云宝」等别名;数据库表名与字段保持 syb_products
货运单 SYB 中的一张单据(code,如 260728TB95MJTQ),下挂一条或多条商品明细。与系统名「SYB」区分,不可混用
AI 规格匹配 人工映射后仍无法以确定性标准化唯一匹配时,服务端才调用单一 OpenAI-compatible Provider,把虾皮目标颜色尺码匹配到 PDD 实际可选规格;结果必须是候选原始标签,无结果、歧义或 Provider 不可用即失败
快路径 / 慢路径 采购执行的两种路径:Agent 能直接定位到下发的目标规格为快路径;定位不到则触发全量遍历采集并重新匹配,为慢路径
两趟执行 慢路径的实现方式:第一趟采集规格后结束并释放设备,服务端离线匹配,第二趟重新派发下单,复用 task_attempt 机制
采购探测 采购时对 PDD 商品页的实时规格采集,同时作为一次商品信息更新写回档案,按 completed / completed_partial 语义处理
spec_source 采购任务的规格来源标记:manual_mapping / exact_match / ai_match,用于事后批量追溯

SYB 自动同步

  • 服务端内置 go-admin 定时任务“SYB 每小时自动同步”,默认每小时第 5 分钟执行;同步日期按 Asia/Shanghai 计算,覆盖当天和前一天。
  • 定时同步与保留的手动导入 API 共用同一个导入服务和 syb_sync_run 记录;定时任务的操作人显示为“系统定时同步”。
  • 同一时刻只允许一个 SYB 同步任务运行。上一次仍在运行时,本次定时触发直接跳过,不排队、不并发,也不立即重试;等待下一小时再次触发。
  • 定时任务失败时明确记录失败原因,不自动重试。服务重启后由既有启动恢复逻辑处理遗留的运行中记录。
  • 单次同步内部的 SYB 只读请求(货运单总数、列表和明细)遇到暂时网络故障、5xx 或异常响应时最多执行 3 次,分别退避 1 秒、2 秒,单次 HTTP 总超时 60 秒;这不等于失败任务自动重试。明确未登录、业务失败、数据完整性错误以及任何写操作均不自动重试。
  • SYB 商品页不再提供“导入”和“同步记录”快捷按钮,也不查询、展示或轮询同步状态;后台同步成功、失败或中断均不在商品页弹出消息,商品数据由用户主动查询或刷新获取。
  • 独立“SYB 同步记录”页面是同步结果的唯一 Web 展示位置,保留运行状态、进度、数量、失败原因和店铺统计;go-admin 定时任务中的 GoAutoSYBHourlySync 提供“执行记录”入口。管理员和采购员可在同步记录页人工发起覆盖昨天和今天的同步,其他角色只读(#236);人工与定时同步共用导入服务、执行记录和互斥,不排队、不并发,也不立即重试。

cmautobuy 商品导入

  • 这是人工触发的单向离线导入,不是持续双写或双库同步;不随服务启动执行。
  • 来源只读取未软删除的 PDD、蝦皮商品及蝦皮 SKU;不导入 SYB、任务、订单、物流、设备、用户、规则和旧组合规格映射。
  • 目标已有相同 goods_id 或存活 shopee_item_id 时,按用户确认由来源商品档案覆盖;PDD 人工 disabled 状态保留,不能被导入自动启用。
  • PDD 销量和评价、蝦皮参考售价在来源没有对应值时覆盖为空;蝦皮币种读取 GoAuto 系统设置,缺省 TWD。
  • 同一颜色只有唯一有效价格时才保存颜色价格;出现多个价格时价格留空、PDD 商品保持 pending 并报告,禁止取最低价、最高价或平均价。
  • 蝦皮只聚合来源已解析的颜色和尺码,未解析内容不猜测。来源 PDD 关联不存在、已删除或无法转换时,蝦皮记录作为冲突跳过,不能静默关联其他商品。
  • 默认 dry-run 不写数据库;--apply 前必须查看精确影响并再次人工确认。apply 在目标单事务中执行,提交前校验 JSON、唯一键和关联完整性。

Agent 当前设备历史

  • Agent 只可查看当前 Device Token 对应设备最近 30 天的采集和采购任务,不能跨设备查看。
  • 采集历史可以查看结构化采集结果和错误;采购历史可以查看结构化采购数据和错误。采购记录不提供取消订单、修改订单或支付入口;只有服务端明确标记可重试的当前设备失败任务,才提供受控“重试采购”。
  • 历史接口遵循数据最小化:不下发 Device Token、规则快照、PDD URL、收货地址、原始控件树或截图。
  • 实际采购单价只在 Agent 确实观察到时保存;旧任务或未观察到价格时显示“未记录”,不推算、不回填。

Agent 受控重新采集

  • 当前设备可以从自身采集任务详情重新采集已完成、部分完成或失败任务。

Agent 受控重试采购

  • 当前设备只可重试自身最近 30 天内、服务端标记 retryable=true 的正式采购失败任务;列表和详情都只能发起单任务重试,不支持多选、批量或自动重试。
  • 普通“重试采购”调用就地 /reset:复用原 purchase_task.id,只新增 attempt;新 attempt 使用当前有效采购规则和最新版 Agent 代码,商品、目标规格、执行规格、数量、价格、地址及既有规格决策等业务快照保持不变。
  • 就地重试不恢复已经消耗的真机规格探测资格;目标规格存在但对应执行规格为空时必须拒绝,不能进入正式采购阶段。需要按替代商品或已变化业务规格重新决策时,必须走明确的新任务流程。
  • 已出现 order_submit_started 证据,或存在不可逆时间、订单提交请求、PDD 订单号、下单时间的任务一律拒绝重试,并提示走既有“授权重新采购”流程,防止重复下单。
  • requestId 按“任务 + 重置请求”幂等;相同请求重放返回同一 task ID 和 attempt,不重复递增。
  • Android 只在服务端 retryable=true 且状态为 failed 时显示普通“重试采购”。确认和成功反馈必须说明复用原任务、新增一次执行、使用当前规则但业务快照不变、可能创建待付款订单且系统不会支付。
  • /reset 不得把“目标规格存在但对应执行规格为空”的任务恢复到正式采购阶段;此类异常快照必须拒绝,并提示使用明确的新任务流程。
  • 替代商品匹配完成后的“继续采购”继续调用 AgentRetry → BatchRetry → Create,按当前档案创建不同 task ID;Admin 批量重试也保持新任务语义。取消订单、修改既有订单和支付仍禁止。真机重试可能进入创建待付款订单流程,执行前必须再次取得人工授权。

Agent 状态页手动检查任务

  • Agent 保留既有每 15 秒自动检查。状态 Tab 顶部下拉只触发一次合并到现有调度器的立即检查,不新增轮询器、不改变采购优先和单设备串行。
  • 当前任务执行中、无障碍未就绪、未配置服务端或设备身份异常时不领取新任务,并显示普通人可理解的恢复提示。
  • 检查中合并重复请求;无任务、领取采集、领取采购、设备忙和网络失败都有文字反馈。网络失败后退出手动刷新状态,既有自动检查继续运行。
  • 状态 Tab 只读显示无障碍状态;“打开无障碍设置”只保留在设置 Tab。
  • 手动检查不创建、重置或重试任务,不修改任务资格,不打开 PDD、不修改地址、不创建订单、不支付。

Agent 任务记录刷新与同步

  • 采集和采购 Tab 顶部下拉只刷新当前 Tab、当前筛选、当前编号搜索和当前页;不领取新任务,也不执行、重置、重新采集或重新采购。加载失败页必须保留可见重试入口,空列表也允许下拉。
  • 设置页记录范围支持手动输入任意 1~30 天整数,默认 7 天、最大 30 天;空值、非整数或越界时不发起同步且就近提示。同步只读取当前 Device Token 对应设备的采集与采购摘要。
  • 两类记录可以独立成功;界面必须明确显示同步完成、范围内无记录、部分完成或失败以及最近同步时间。
  • 本地仅保存列表摘要和同步时间,详情仍按需读取;不缓存 Token、完整规则快照、PDD URL、地址、控件树或截图。
  • 记录同步是服务端到 Agent 的单向只读能力,不打开 PDD、不修改地址、不创建订单、不支付。

Agent 采集任务间隔

  • Agent 设置页提供设备本地“采集任务执行间隔”,起止值均只接受 0~600 秒整数,默认 15~15;每次在闭区间内等概率随机一个整数秒。0~0 表示不等待,范围包含 0 时允许本次抽到 0。设置只影响之后结束的采集任务,已开始的间隔不随设置修改。
  • 只有采集任务已经开始且成功向服务端提交完成、部分完成或失败结果后,Agent 才按当时保存的范围随机一次并开始间隔;领取前失败、配置/认证错误或结果未安全提交不随机也不开始间隔。采购任务结束不开始采集间隔。
  • 间隔只阻止下一次采集任务的请求、领取和开始;心跳、采购任务优先领取与执行、采购 Outbox、历史刷新和同步继续运行。间隔结束只触发现有调度器一次,不新增轮询器。
  • 状态页下拉检查和采集记录“重新采集”不得绕过间隔,统一提示“采集间隔中,还需 N 秒”。
  • 本次抽中的秒数、开始时间和截止时间作为同一间隔票据持久保存在设备本地;Agent 进程或前台服务重启、设置修改都只恢复剩余时间,不重新随机。系统时间回拨时最多按该次已抽中的原始秒数截断,避免无限等待。
  • 间隔期间保持屏幕常亮;既有“任务结束 5 秒后返回 Agent”是独立机制,返回 Agent 不清除采集间隔。采购任务接管执行时不重复持有间隔亮屏锁,采购完成后若间隔尚未结束则恢复。
  • 该设置不上传服务端,不改变采集任务状态、租约、规则快照或服务端接口,不打开 PDD、不修改地址、不创建订单、不支付。

Agent 当前 PDD 商品页临时采集

  • 操作员先人工在 PDD App 打开并停留在目标商品详情页,再从 Agent 采集 Tab 点击“采集”;该入口采集当前页面,不是重置历史任务。
  • Agent 在请求服务端前取得采集/采购共用的本地互斥锁。服务端原子校验设备在线、空闲、跨域活动任务、默认规则和能力,创建固定当前设备且已进入 running 的标准采集任务。
  • Agent 启动当前页面采集前先保持自身在前台并启动既有前台服务。恢复时若 PDD 已在前台则不返回;若 Agent 仍在前台且近期见过 PDD,只尝试一次系统返回;仍未恢复时只使用 PDD 自身的不带参数启动 Intent 拉回现有任务,不附加清栈/重置标志。恢复后必须重新验证包名、精确 Activity 与页面强证据;不得启动浏览器、构造深链、自动搜索或自动选择相似商品。
  • 恢复详情页后先按规则唯一点击“分享”与“复制链接”,只读取本次复制后的单条、有限长度剪贴板文本。Android 优先选择含 goods_id 的白名单长链;短链只在手机侧以无 Cookie、无项目凭据、逐跳白名单校验的有限请求展开,失败时可把原短链交给服务端兜底。服务端始终重新校验链接、裁决并规范化 goods_id;Agent 不建档、不猜测商品身份。原始剪贴板、分享文案、链接、响应正文、控件树和截图都不保存。
  • goods_id 已存在时复用唯一 PDD 商品,成功或部分成功结果按既有最新档案覆盖规则更新;不存在时创建 PDD 商品。该流程不自动停用或替换旧商品,也不修改虾皮到 PDD 的关联。
  • 管理员必须配置一条存活的 PDD 商品详情 v2 规则作为 Agent 手动采集默认规则;迁移只做一次安全初选,创建任务时仍实时验证规则与设备 collector.pdd.current-page-share.v1 能力。
  • 当前页面任务身份确认前允许 pdd_product_id 为空、URL/goods_id 快照为空;普通管理端任务不放宽。身份确认后不可改成其他商品,结果 goods_id 必须与任务一致。
  • 当前页面任务不能使用“重新采集”重置;失败后重新打开目标商品并新建任务。成功提交完成、部分完成或失败结果后,继续进入设备的采集任务执行间隔。
  • 分享入口、复制链接、剪贴板、链接、页面或身份不唯一时明确失败并释放任务槽;不使用 OCR/VLM,不猜测商品身份。
  • 该能力只采集商品资料;不创建采购任务、不选择采购规格、不修改地址、不创建订单,也不执行支付动作。

SYB 档口入库码导入、匹配与回写

  • 只接受不超过 10 MB、最多 5000 条非空数据行且包含“标签入库码映射”工作表的 Excel。一次文件只能包含一个营业日期;同日单件入库码必须唯一,同一业务键按营业日期、订单号、档口和规范化规格合并并保留 Excel 顺序。
  • 导入事务提交后自动创建并启动只读匹配任务,不提供独立“匹配”按钮。再次导入同日数据只允许整体替换仍处于等待匹配的数据;存在匹配或回写证据时拒绝覆盖。
  • 匹配必须按精确订单号取得唯一货运单,再以规格、原始 SKU 和档口证据确定唯一商品;歧义、冲突或数量不一致均不猜测。匹配阶段不能调用任何 SYB 写接口。
  • 回写前弹窗展示业务记录数、入库码总数、预计占位明细数和替换旧码数。只有 ready 记录可提交;所有服务实例共用数据库租约全局串行执行。
  • 每个远端写动作只发送一次,动作前重读整张货运单并校验匹配计划未漂移;每件写入后重读确认目标码唯一位于预期明细。超时、5xx、响应无法确认或服务在写入期间重启时转为 needs_check,禁止自动重试;“只读复核”只能读取远端状态。
  • 列表支持勾选后批量物理删除。删除必须再次确认;选中项包含 queued、applying 或 needs_check 时整批拒绝,不做部分删除。其余选中业务记录、逐件码、计划和终态执行证据在同一事务中物理删除;已写入 SYB 的远端值不会撤销。

PDD 失效或售罄商品替换(#129)

  • 商品替换是“失效的旧 PDD 商品 → 已成功采集的替代 PDD 商品”的即时生效审计事实,可由失败采集任务或失败采购任务发起;Agent 只提交明确的来源类型、任务编号和采集结果,服务端负责最终校验和登记。
  • 替换记录不删除。同一源商品同时只允许一条生效记录;替代商品必须为 active,不得与源商品相同,不得形成替换环,并必须由同一发起设备的一条 completed 或 completed_partial 采集任务证明。
  • 一个 PDD 商品可能被多个虾皮商品共用,因此规格匹配按受影响的每个虾皮商品分项记录。主表只表达总体进度;Agent 展示和“继续采购”资格必须读取当前任务对应虾皮商品的分项状态。
  • 选错替代商品时,连续执行 B→C 不等于撤销 A→B,因为 B 可能还关联其他虾皮商品。正确纠错语义是把原 A→B 记录置为 superseded,再建立 A→C,并只处理原记录分项中冻结的影响集合。
  • 创建请求按 create_request_id 幂等;重放时源商品、替代商品、来源类型、来源任务、采集证据和发起设备必须一致,否则返回幂等冲突,不能静默覆盖。
  • created_by_device_id 只代表 Agent 设备。当前系统没有设备到采购员账号的绑定,多人多机场景若需要个人责任追踪,必须另建工单实现设备绑定操作员。

PDD 商品替换生效与规格匹配(#131)

  • 替代商品采集成功后,服务端自动、原子生效,无人工审批。受影响虾皮商品改指替代商品并清除旧规格映射;旧 PDD 商品置为停用但不删除。
  • 原有 pending / spec_probe_pending 采购任务取消并标记 PDD_PRODUCT_REPLACED,释放租约与运行守卫,之后只能由既有重试流程按最新档案创建新任务;不得把新商品外键与旧 URL、goods_id、价格或规格快照拼在同一任务中。
  • running / order_submit_started 与所有终态采购任务继续保留原商品外键和全部快照,按原任务事实收敛或留作历史;TargetColorSnapshot / TargetSizeSnapshot 始终是虾皮需求,不因商品替换而清除。
  • 规格匹配按虾皮商品分项持久执行。AI 开关关闭、无结果或未通过自动确认门槛时转人工;确定性唯一 exact_match 可不带置信度自动确认。
  • 用户于 2026-08-28 确认放宽 #46 的 AI 口径:ai_match 仅在置信度存在且不低于服务端阈值(默认 0.9)、结果严格属于当前候选、颜色/尺码角色唯一完整、原因非空且写入前输入版本未变化时自动确认。否则不得猜测或选择相近候选,转 manual_required。
  • 自动确认必须保存来源、实际置信度和脱敏限长原因;人工确认完成后同步对应分项及主表总体状态。worker 不得覆盖已由人工改变的映射。
  • 纠错不能简单执行 B→C;必须把原 A→B 记录置为 superseded,建立 A→C,并只处理原记录冻结的虾皮商品影响集合。

历史:创建采购任务时的异步规格匹配(#148,#215 后仅兼容存量)

  • #215 起,新建 SYB 采购任务不再根据 PDD 档案创建 purchase_spec_match_work_item,也不在首次派发前调用外部 AI;规格决策统一来自首趟真机探测的当次候选。
  • 部署前已存在的匹配工作项继续保留审计、恢复、重试和人工处理能力;其 AI 封闭候选、置信度、输入指纹、退避和最长 60 秒调用边界不变,但不能成为新任务跳过当次探测的依据。

SYB 采购强制当次规格探测(#215)

  • 每个新 SYB 采购任务固定执行“首趟只读探测 → 服务端确定性优先/必要时 AI → 固化任务级精确规格 → 第二趟正式采购”。首趟只打开一次浏览器商品链接;匹配期间当前设备保留给同一任务,不领取其他采购或采集任务。连续进入第二趟且当前仍有 PDD 商品页或规格面板强证据时复用当前页、不再次打开链接;手动同任务重试,或当前处于 Agent、其他应用及缺少上述强证据时,重新打开任务固化的商品 URL。复用或重开均不严格核验标题、goodsId 或页面指纹,但仍要求 PDD 包名与商品/规格/订单页面结构安全证据。已有长期映射只作商品档案事实,不直接进入任务执行规格。
  • 首趟候选与 taskId、taskAttemptId、deviceId、规则快照哈希和幂等结果哈希关联;第二趟失败不得回到首趟循环探测。备货 stock/direct_select 没有 SYB 目标规格,继续使用用户逐字选择的档案规格,不进入本规则。
  • 候选和 Provider 结果仅保存颜色、尺码原始标签及结构化决策,不保存控件树、整屏截图、账号、地址、订单或支付数据;付款仍永久禁止。

Agent 手动采集替代商品(#130)

  • 采集来源不再按任务状态或错误码白名单限制“采集替代商品”:同一设备的采集任务只要仍关联 PDD 商品、该商品没有进行中的替换,且名下不存在 running、order_submit_started、order_result_unknown 采购任务,即可由人工判断是否替换。命中这三种采购状态时必须硬拦截并提示等待任务结束,不提供强制绕过。采购来源仍只允许失败任务且错误码逐字等于 PDD_LINK_INVALID 或 PDD_GOODS_SOLD_OUT;Android 只呈现服务端资格,不自行放宽。
  • Agent 创建当前页面采集任务时携带 replacementOrigin.type(collection / purchase)和来源 taskId。服务端再次校验设备、来源对应的资格边界、源商品、既有替换与进行中的替换流程,并把来源和激活状态持久化到采集任务,保证进程重启后仍可恢复。采集来源确认替换时必须明确提示:所有关联虾皮商品会改指新商品并清空规格映射、尚未开始的采购任务会取消、原商品会停用且暂不能自动撤销。
  • 替代商品采集结果先按普通采集事务完整保存。随后调用 #131 的原子生效流程;生效失败不得回滚或覆盖已采集商品、规格和 SKU,而是记录稳定的 failed 激活状态与限长错误,服务启动后可按同一幂等键仅重试生效,不重新采集。
  • 任务详情的 replacementMappingStatus 必须由来源任务对应的替换分项推导,不能只读取主表总体状态。状态为 matching 时等待自动匹配,manual_required 时由 Admin 人工处理,matched 后才进入 #132 的继续采购流程。
  • 替换采集沿用设备级单任务互斥、采集间隔、无障碍安全边界和禁止支付规则;不会增加轮询,也不会创建采购任务或订单。

替换匹配完成后继续采购(#132)

  • 只有采购来源对应的替换分项为 matched,且既有采购重试的任务终态、最新任务、不可逆边界、当前档案、持久化规格映射、PDD 候选、价格、设备在线/空闲与能力门禁全部通过时,Agent 详情才返回 continuePurchaseEligible=true。
  • 继续资格的详情查询不调用 AI,也不把当前可重新推导的确定性匹配当作已确认映射;映射被人工清空、PDD 重新采集导致候选变化或价格缺失时返回服务端原因。点击时再次执行同一前置门禁,防止详情读取后的状态漂移。
  • Agent 的“继续采购”复用既有 AgentRetry → BatchRetry → Create,请求仍只有来源任务号和 requestId;不新增采购创建接口。旧失败任务保持不可变,创建的新任务重新固化当前替代商品、规格、价格、规则和设备快照。
  • matching / manual_required 只展示匹配状态;matched 但资格不通过时展示服务端下发原因。Admin 批量重试行为不变。
  • 真机点击“继续采购”可能创建新的正式采购任务,必须先取得独立人工授权;永久禁止支付。

颜色规格图片(#133)

  • 颜色图片是 PDD 商品最新档案的可选数据;缺失、截图不支持、定位、裁剪、压缩或上传失败均不得加入 missing,也不得改变 completed / completed_partial 或既有规格、价格结果。
  • Android Agent 仅在既有颜色遍历中,在颜色卡片子树内查找与该卡片同 content-desc 的 ImageView;禁止全局查找同名图片节点,不新增颜色点击、页面跳转或用户操作。
  • API 30 及以上设备可以在内存中取得整屏位图,并严格按图片节点边界裁剪为 JPEG(质量 85);整屏位图用后立即回收,不落盘、不上传、不入库。低于 API 30 或截图受限时安全跳过。
  • 单张 JPEG 最大 512 KiB、最长边不超过 1024 像素;Agent 单任务最多保留 64 张、总量最多 8 MiB。结果提交成功后才逐张独立上传,上传不重试到影响任务时长。
  • 服务端只接受该任务已提交颜色维度中的 JPEG,校验 Device Token、任务归属、终态、内容、尺寸和数量;按“PDD 商品 + 颜色值”维护最新一张,记录来源 task、device,并沿任务关联不可变规则快照。
  • 只允许保存裁剪后的商品图片区域;裁剪结果不得包含账号、地址、订单、支付及其他个人数据。原始控件树、XML、整屏截图仍禁止保存。
  • 诊断阶段 COLOR_IMAGE 只记录成功及不支持、定位失败、裁剪失败、压缩失败、上传失败分类,不记录颜色文案、坐标或图片内容。
  • Agent 采集任务详情只返回并展示当前仍以该任务为 source_task_id 的颜色图片,按颜色分组提供缩略图、明确空态/加载失败占位和只读放大查看;同商品同颜色被后续任务覆盖后,旧任务详情不再显示该图。图片仍沿用既有受控商品裁剪文件,不新增整屏截图、原始控件树、下载、分享或编辑能力。

Admin 采集采购与采采管理导航(#142)

  • 「采集采购」固定顺序为:SYB 商品、SYB 同步记录、档口入库码、虾皮商品、PDD 商品、采集任务、采购管理。
  • 「采采管理」固定顺序为:SYB 店铺、采集规则、采购规则、设备列表、AI 规格匹配。
  • Admin 可见两个分组及全部 12 个页面;采购员可见两个分组和除采购规则、AI 规格匹配外的 10 个页面。父组只承担导航结构,不新增业务权限。
  • 分组迁移保留既有页面菜单 ID、URL、组件和 API 权限关联,删除旧的 12 个一级模块根菜单;菜单只保留“分组 → 页面”两级。

采购规则与 Agent 版本管理

  • purchase_rule 保存管理员维护的采购规则;单例 purchase_rule_setting 指向当前规则。迁移以现有默认正式规则原字节播种首条记录。新建、批量预检、批量创建和安全重试读取当前规则;已有采购任务始终执行自身快照。
  • priceGuard 缺省或 enabled=true 时继续按参考价倍率保护:minRatio 为 0.1~1.0,maxRatio 为 1.0~3.0;旧规则未声明 enabled 时按启用处理。
  • 管理员可以设置 priceGuard.enabled=false 关闭参考价倍率保护,但必须同时配置整数分 absoluteMaxUnitPriceCent,范围 1~100000(¥0.01~¥1000.00),且不能混入倍率字段。服务端仍保留参考价用于预检和审计,并把新任务价格范围固化为 0~绝对上限;不存在无金额上限的采购模式。
  • Admin 保存关闭倍率保护的规则前必须二次确认,并在列表摘要和切换当前规则确认中显示绝对上限。规则编辑只影响新任务;既有任务继续使用自身规则和业务价格快照,安全的同任务重试也不得悄悄扩大原价格范围。
  • Android 始终以任务固化的 minUnitPriceCent / maxUnitPriceCent 为执行边界,在核价、订单摘要和创建订单前 fail-closed 校验;价格越界失败应回传实际观察单价供服务端保存和诊断。支付仍永久禁止。
  • Agent 采购历史必须分开显示任务原始目标规格与服务端最终映射的执行规格;映射缺失不等于目标规格缺失。本地历史缓存同时保存两组字段,自动化始终只消费执行规格。
  • “采购规则”是“采采管理”下与“采集规则”同级的管理员菜单,采购员角色没有菜单和 API 权限。
  • Agent APK 版本由管理员在设备页抽屉中上传、核对并显式设为当前。服务端从 APK Manifest 读取整数 versionCode 和 versionName,保存 SHA-256、大小、说明和创建人;APK 位于非公开目录,Admin 与设备下载均需认证。
  • Agent 只以整数 versionCode 判断更新。启动时静默检查一次,设置页可手动检查、显示下载进度并取消;下载完成必须校验大小和 SHA-256。设备有活动任务时禁止检查、下载和安装;安装始终交给 Android 系统确认,项目不绕过未知来源权限。

Android 采购规格动作安全执行(#214)

  • 规格入口与精确规格选择统一按“重新定位唯一目标 → 执行一次无障碍点击 → 读取新页面验证”执行;不得复用旧无障碍节点,不选择相近规格,也不在多候选时默认点击第一个。
  • 无障碍点击后页面完全无变化时,只允许对解析器已确认的安全规格入口或服务端下发且唯一命中的精确规格执行一次中心手势兜底。目标必须可见、启用、边界有效,手势后仍须以规格面板强证据或精确选中证据确认结果。
  • 页面发生变化但规格面板强证据不足时,不再继续手势或猜测页面,明确失败并只记录面板类型、候选数量和证据布尔值等无敏感标量。原始控件树、节点文字集合和整屏截图仍不得保存或上传。
  • 规格已处于精确选中状态时不得重复点击。规格查找只在解析器唯一识别的规格面板容器内有限滚动,每次滚动后重新定位容器与目标;容器缺失、歧义、到边或验证失败均 fail-closed。
  • 中心手势兜底不得用于修改/保存地址、创建或提交订单、订单详情入口以及任何支付/付款目标;正式创建订单的一次性不可逆门禁与永久禁止支付规则不变。

PDD 商品反向关联与继续订单采购(#161)

  • 一个 PDD 商品可被多个虾皮商品共用。PDD 详情返回全部关联虾皮商品摘要;订单行由独立统一分页接口读取,不按虾皮商品伪造嵌套分页。
  • scope=actionable 固定包含 purchase_ready、pdd_pending、pdd_collecting、pdd_collection_failed、color_mapping;scope=all 才显示其他阶段。该集合由服务端维护,前端不复制。
  • 规格映射摘要使用 specMappingStatus=complete|incomplete|not_required、确认数和总数。not_required 只表示虾皮商品没有颜色或尺码维度;商品摘要不替代订单行采购资格。
  • “关联订单继续采购”只处理已有 SYB 订单;“创建备货采购”不关联 SYB 订单。两者入口和文案必须明确区分。继续采购复用既有批量预检和批量创建,价格、映射、并发、订单和不可逆门禁不变。
  • SYB 订单号、目标颜色/尺码、数量和当前采购任务状态只允许管理员与采购员读取;其他角色由服务端拒绝。查询路径不调用 AI Provider。

定时与手动蝦皮规格自动匹配(#195)

  • 系统只扫描存活且已关联 active PDD 商品、两边至少共享颜色或尺码角色、并且至少存在一个未确认或已失效映射的蝦皮商品。
  • 每个商品复用详情页“一键匹配颜色和尺码”的规则:保留当前仍有效的 confirmed 映射;唯一确定匹配和达到服务端阈值、理由非空、候选仍有效的 AI 结果直接保存为 confirmed;低置信度、无结果、Provider 异常或上下文漂移不猜测、不写入错误映射。
  • 定时与管理员手动执行共用全局活动槽和逐商品工作状态。单批默认最多 20 个商品;同一规格上下文与 AI 设置更新时间未变化时,已完成、低置信度或无结果商品不重复调用 AI。
  • Provider 临时失败最多尝试 3 次,间隔至少 60 分钟;输入变化后重新计算指纹并允许重新处理。运行记录只保存结构化计数和脱敏限长错误,不保存 API Key、Provider 原始响应、商品原始 JSON 或个人数据。
  • 系统定时任务迁移后默认关闭,须由管理员明确启用。该能力仅维护蝦皮与 PDD 颜色/尺码映射,不创建采购任务、PDD 订单,不触发 Agent,也不执行付款。

SYB 异常采购规格 AI 解析(#198)

  • SYB 采购规格采用两阶段流程:先把货运单明细 productSpec 解析为目标颜色/尺码,再由 #195 把蝦皮规格匹配到 PDD 规格;两阶段不得混为同一匹配事实。
  • 定时任务只处理未人工确认且确定性解析为 uncertain / failed 的明细。每条先重跑确定性解析;空 productSpec、无关联蝦皮商品、无颜色/尺码候选或同一角色存在多个候选维度时不调用 AI,继续人工处理。
  • AI 只在关联蝦皮商品的封闭候选集合中返回原始颜色/尺码,并必须提供达到当前自动确认阈值的置信度和非空理由;集合外值、缺失角色、低置信度、歧义、无结果和输入漂移都不得确认。
  • parse_status 保留确定性解析器结论;AI 与人工确认分别记录,人工优先级最高。重复同步不得覆盖人工值;完全相同输入保留 AI 值,来源或关联变化会清除旧 AI 确认。
  • 同一输入的低置信度或无结果不重复调用 Provider;临时故障至少 60 分钟后重试,最多 3 次。任务不创建采集/采购任务、订单,不执行 Android 动作或付款。

设备身份恢复

  • 管理员可在设备管理对未停用设备发起“重置设备身份”。此动作不删除设备记录、不改变设备 ID、能力或已绑定的待领取任务;它立即使旧 Token 无效,并只生成一次、有效期 10 分钟的恢复码。

  • 恢复码仅显示给发起操作的管理员一次,服务端只保存摘要;不得进入列表、日志、任务记录、Android 持久化或普通接口。手机操作员必须在同一安装实例的 Agent 设置中手动输入。

  • 服务端只接受同一 installId、未过期且尚未使用的恢复码完成重新注册,成功后签发新 Token 并使恢复码失效。过期、重复使用、installId 不符或停用均明确失败;不能通过清空数据、直接改库或“吊销 Token”恢复原任务归属。

  • 自 #223 起,任务创建时把与冻结 SYB 目标对应的已确认商品规格映射保存为不可变的探测指导快照,但仍不得跳过首趟真机探测。探测完成后,每个角色先验证快照映射能否按既有规范化规则唯一对应当次候选,能对应时固化当次候选原文;不能对应时只对该未解决角色执行确定性匹配,仍无结果才调用 AI。已解决角色不重复交给 AI,任一最终值仍必须逐字属于当次候选;历史映射失效、规范化后歧义或角色不符时不得复用。候选完整但无法决策时提示“已采集到当前规格,但未能确定颜色或尺码映射”,不再误报候选不存在。

采购商品深链入口(#232)

  • Android 采购新任务(含探测与人工重试)打开商品时,优先使用指定 PDD 包名的 ACTION_VIEW,并设置 NEW_TASK 与 CLEAR_TASK,以清理旧任务栈后交付该任务链接。清理的是 Activity 返回历史,不是清除应用数据或强制停止进程。
  • 直接启动失败(包括无可处理 Activity)时回退既有浏览器入口;启动请求被接受后仍由执行器验证稳定商品页面,停留首页不会仅因启动成功而判定完成。
  • 清栈不用于改地址后返回、下单后回到 PDD、订单核查;采集入口继续使用既有浏览器流程,避免绕过规则中的浏览器步骤。
  • 当前通用商品页面结构验证不能独立证明页面 goods_id;解析结果携带的任务 goodsId 不是页面回读证据。首次直接深链上线仍需以实际目标商品真机核对,ADB 实验不替代 Agent 上下文验证。

SYB 批量采购设备偏好(#233)

  • SYB 商品页“批量创建采购任务”按当前登录用户 ID、当前浏览器来源与 API 环境记住最近一次设备选择;主动清空也记忆为不指定设备。只保存设备 ID,不保存 Token、账号凭据或订单信息。
  • 弹窗打开后先按现有在线/可选/采购能力条件加载设备,再恢复选择并以相同设备预检。记忆设备当前不可用时保留偏好并提示用户重新选择或明确清空,不静默切换设备或自动领取。
  • 预检加载中、失败或记忆设备不可用时不能提交;过期预检结果不覆盖新的设备选择。服务端原有设备及采购资格校验不变。
  • 偏好只作用于此入口,不影响采集、其他创建入口和采购重试。浏览器存储失败时仍允许手动操作;刷新或关闭再打开浏览器可恢复,清理浏览器数据或沿用现有退出登录清理存储行为后需重新选择。

客户端密钥与可编辑模块授权(#237)

以下为提交 71f7751 已实现的规则;2026-09-07 本机已迁移并验证管理页面可用,2026-09-08 已随 d403f3b 完成线上迁移与部署,真实客户端密钥执行闭环尚未验证。

  • 仅管理员创建、查看、编辑授权或停用密钥。首版不提供密钥改名、到期、轮换、恢复启用、删除或任意接口授权。
  • 模块选择复用“采集采购/采采管理”现有 12 个业务模块;分组勾选只影响当前子模块,新菜单不会自动获得授权。客户端密钥管理、系统账号权限及支付不在可授权模块中。
  • 勾选模块默认只读,至少保留一个模块。读写仅开放清单中的普通写操作;同步、采集、采购、删除、导入、重解析、匹配、回写及切换当前采购规则分别独立授权,默认关闭。没有普通写接口的模块不允许勾选读写。
  • 编辑既有密钥不会更换密钥,名称和前缀只读;移除模块同时移除其动作。取消保留原授权;失败保留输入;版本冲突要求刷新重开。停用不可编辑或恢复。
  • 保存后新请求按最新授权校验,已经通过校验的在途请求可能完成,不追溯回滚。模块授权不是行级、店铺级或租户隔离,授予读取即允许读取该模块明确接口可返回的业务范围。
  • 用户于 2026-09-07 明确接受明文风险:密钥管理及客户端接口默认兼容 HTTP/HTTPS,无需开关。HTTP 会明文传输密钥与业务数据,建议优先使用 HTTPS;兼容不改变管理员身份与模块授权边界。
  • 客户端与 Admin 登录 JWT、Agent Device Token 独立。响应排除凭据及原始载荷字段;AI 设置只返回 enabled,不开放 Provider 配置读写或连接测试。设备仅开放列表,不开放身份重置、令牌或解锁接口。
  • 执行动作复用既有业务门禁、幂等参数及状态机;客户端采购 batch-retry 沿用 Admin 原有语义,不等同于 Agent 就地 reset。授权重采购、支付复核、取消订单等未列入接口不开放;永久禁止付款。
  • 创建响应丢失时不可找回完整密钥,应核对列表并停用可能已创建的记录,再明确创建新密钥,不能盲目自动重试。完整密钥只在创建结果弹窗内存中显示,关闭或离开页面清空,不写浏览器持久存储。

打开采购规格面板后按需滚动(#238)

  • Android 0.9.60 / versionCode 73,代码 58a6c1c 起,规则 openSpecPanel.swipeAfter 保留格式校验与旧快照兼容,但不执行打开面板后的固定次数预滑动;不以“必须滑两次成功”作为进入规格探测/选择的条件。动作后的 waitAfterMs 仍生效。
  • 首趟规格探测和第二趟精确选择仍使用各自既有的按需横向/纵向、有界与稳定终止策略。取消预滑动不等于不探测隐藏规格,也不等于只看首屏。目标不存在、歧义、页面证据不足或必要的有界查找失败时仍明确失败。
  • 此调整覆盖所有已经安全识别打开的面板,不再仅特判 NON_SCROLLABLE_CONFIRMATION;不弱化面板验证、精确选中、地址、价格、任务租约、创建订单边界或禁止支付规则。
  • 其他动作的后置滑动沿用原行为,必需滑动失败仍返回 RULE_ACTION_FAILED。旧规则 JSON 不回写、不迁移;原任务 ID、历史 attempt、商品与规格快照不变。旧 APK 行为不变,需升级 Agent;本单未改线上规则或执行 CG68 真机采购。

SYB 逐页保存与部分成功(#239)

实现绑定 c6a962d;2026-09-08 已随 d403f3b 部署线上,未手动触发真实同步验收;#240 上游尾页超时尚未修复。每页完整明细在外部请求结束后按页事务保存;页回滚不累计明细/新增/覆盖数,已提交页保留。日期局部读取失败继续下一日期,全局数据库/进度/会话/取消故障停止。当天漂移不在一次运行内重扫;后续运行重新扫描并幂等补齐。

同步状态增加 partial_success(部分成功,15 字符,复用现有 varchar(16),无需迁移)。有错误且 created+updated>0 为部分成功;有错误无已提交明细为 failed;完整且无错误为 succeeded(包括无符合店铺的数据)。中断仍为 interrupted,不把中断追认为成功。所有终态沿用活动槽释放规则。

orderCount 是已验证页的原始列表读取数量;detailCount、created、updated 为已提交明细及其新增/覆盖数量;daysProcessed 是完整通过的日期数,不是已尝试日期数。失败日期/页码/阶段写入现有脱敏限长 errorMessage。部分成功不刷新店铺的完整同步统计。

Web 唯一展示位置为“采集采购 → SYB 同步记录”:列表状态、状态筛选及详情支持部分成功,详情保留已保存数量、错误原因与重新同步补齐提示。定时任务日志只表示异步任务受理,不等于最终业务同步成功。