19 KiB
19 KiB
当前关键发现
2026-08-24 — ERP 异常状态链接刷新加固(已完成)
- 用户描述的是插件长时间待机后的偶发 ERP 未连接告警;当前源码已有
chrome.alarms待机保活,但runErpSessionKeepalive()在session_expired/failed后只写入erpKeepaliveState,没有恢复动作。 - 当前保活默认首次约 1 分钟、之后每 5 分钟;只查找现有
https://lwlt.hisy.cc/*标签页,执行主世界带 Cookie 的只读GET /System/Mainlt.asp,执行中跳过,不新开标签、不刷新页面、不写 ERP。 findExistingErpTabForKeepalive()会拒绝非完整加载或非 allowlisted origin;因此长待机后页面已被导航到登录/异常路径、页面注入链路失效或标签页状态异常时,保活只能报告skipped/failed/session_expired,不能自愈。readErpSessionStatus()、business-bridge.js和 popup 已能展示最近保活状态;平台/业务 operation、Schema 与 Skill 不承载此宿主维护能力,当前活动约束来自mappings/lifecycle.mapping.json。- 本轮拟保持 fail-closed:仅在无活动 ERP 执行、自动化与保活开关开启且已存在 allowlisted ERP 标签页时,执行受控同源 Mainlt 导航/刷新后再次只读探测;不自动打开新标签、不重交任务、不跨越 ERP 写入边界。
- 已实现
performErpLinkRecovery()与单飞请求锁:异常时对现有 ERP 标签页执行chrome.tabs.reload(..., { bypassCache: true }),等待加载完成,再复用只读 probe;2 分钟冷却内最多一次,执行中二次检查并跳过。 readErpSessionStatus()在登录/权限页面或页面注入异常时异步触发恢复,不阻塞平台 PING;桥接和平台状态新增session_ready、恢复状态、恢复次数和最近恢复时间。平台在会话异常/恢复中保持告警并阻止新的任务下发,恢复失败要求人工确认,不自动重交。- lifecycle mapping、插件 README、popup 文案和
tools/erp-session-keepalive.test.mjs已同步;定向保活回归 4/4、生命周期契约 47/47、相关 JS 语法检查通过。 - 扩展已递增到
0.5.140;dist/ltjt-order-assistant-0.5.140.zip已通过unzip -t,SHA-256 为5d2eceb77a337849bd20bc3e03dea4c86b617c789dd196b8a47bbb33c0da0338;0.5.139已归档到archive/releases/2026-08-24/。 - 完整门禁最终通过:
check:repo9/9、check、串行test:control-plane66/66、test:legacy214/214、build、git diff --check;未进行真实 ERP 写入、任务重试、外部发送、重启或部署。
2026-08-22 — 取消产品/客户来源地强制匹配
- 用户日志中的阻断发生在
shared_child_order_create的浏览器只读阶段,唯一失败项为product_customer_source_region:产品关键字识别出“贵阳”,客户来源信息未命中;客户、OP、销售和领队候选本身均已唯一,且no_erp_write=true。 - 当前 Schema 没有要求产品与客户来源地相同;强制关系来自插件
inpage.js、team-batch-inpage.js的运行时来源地兼容门禁,以及客户候选的产品来源地消歧 fallback。 - 活动规则已收敛为:产品和客户分别进行 ERP 唯一解析;客户关键词在精确/唯一包含失败后仍可用客户自身来源词做唯一 fallback,但该 fallback 不读取产品;产品/客户来源地不一致不阻断
DoInfoJH、DoInfoJHs或DoInfoSPs。 - 已移除来源地兼容函数和跨产品/客户候选消歧;保留产品候选唯一、客户候选唯一、人员/领队校验、写入前门禁、明确 ERP 回执及 fresh requery。
source-region.js仅保留客户侧候选辅助接口。 - 扩展已递增到
0.5.139,平台最低版本、生命周期 mapping、运行时版本断言、业务页、mapping、夹具和说明同步;dist/ltjt-order-assistant-0.5.139.zipSHA-256 为d3ad25b6c22f5269a2fa713441f3b2aebf4cbcf3dff96bdafcef15d29d810353。 - 上一版
0.5.138已保存在archive/releases/2026-08-22/;本轮未重试用户任务、未写入 ERP、未重启、未部署、未向外部渠道发送消息。
2026-08-20 — ERP 会话待机保活实现
- 现有插件已有执行期间的 MV3 worker/page keepalive,但没有空闲时的 ERP 会话请求;
lwlt-confirmationSkill 明确“定时和外发”不属于业务 action,因此本次只修改插件宿主维护逻辑,不扩展 operation、Schema 或 Skill 输入契约。 - 安全实现采用
chrome.alarms,默认首次约 1 分钟、之后每 5 分钟触发;只查找现存且 allowlisted 的https://lwlt.hisy.cc/*标签页,不自动新开标签、不调用tabs.reload()。 - 页面侧通过主世界
fetch('/System/Mainlt.asp', { method: 'GET', credentials: 'include', cache: 'no-store' })发送轻量只读请求;检查最终 URL、HTTP 状态和登录/权限页面特征,结果写入本地状态并通过插件面板展示。 - 当 ERP 自动化或单独保活开关关闭、执行中任务存在、没有已加载 ERP 标签页或权限不可用时,保活跳过/失败且不触碰业务写入;浏览器或操作系统休眠会延迟 alarm,不能保证休眠期间持续请求。
- 扩展已递增到
0.5.138,同步manifest.json、平台最低版本、生命周期 mapping、页面运行时版本和定向回归;版本化 ZIP SHA-256 为751dfe6022d61c7388c602089c703b88a9bfeebf67f81edacea1555545d7bcd0。
2026-08-19 — AgentBus 无状态消息但任务成功(诊断进行中)
- 已确认本轮是只读诊断;工作区存在大量既有未提交改动,不能回退或覆盖。
- 当前尚未取得该次成功任务的任务 ID、渠道 ID 或运行时发送日志;先以当前契约、源码、测试和已有控制面证据定位确定性条件。
- 待核对:任务状态事件生成、回复路由是否持久化、AgentBus 渠道是否启用/握手、accepted/processing/result 是否进入 durable outbox,以及失败/重试语义。
- 登记表列出的
agent设计规范/businesses/confirmation_export.md当前不存在;已转用行为注册表、lwlt-confirmationSkill、AgentBus 回复契约和源码作为活动规则来源。 - 当前
control-plane/README.md明确用户侧只持久化发送一次task.progress(status=accepted)和一次task.result;不会发送“解析完成/等待确认/进入 ERP”的中间进度,因此“processing”不是当前 AgentBus 对外消息。 lwlt-confirmationSkill 与标准 operation Schema 只描述业务解析/执行事实,不承诺定时或主动外发;lifecycle.mapping.json的scheduled=false/sent=false属于业务附件外发字段,不能单独证明 AgentBus 回执已发送或未发送。- AgentBus 回复契约明确用户侧预期是“受理通知 + 最终返回通知”,但执行阶段、页面打开、提交中和回查等中间状态只进入平台生命周期/审计;因此本次“没有处理消息”首先是契约预期与实现定义不一致,仍需查清 accepted/result 为何也未达渠道。
- 生产数据库渠道走 durable delivery:
AgentBusListener.processInboundTask()将channel_id、入站 frame 路由和 accepted payload 一起交给TaskService.ingestMessage();只有这些路由字段存在时,事务才插入agentbus_deliveries(delivery_kind='accepted')。 - durable 模式下不会直接发送 accepted;listener 每秒/
session.ready后 flush outbox。只有 accepted delivery 已标记delivered,且任务进入终态,才会创建delivery_kind='result';因此 accepted 没投递成功时,result 会被有意延后,而任务本身仍可继续完成。 - 手工操作台/API 任务没有 AgentBus
channel_id/agentBusRoute,recordAgentBusAcceptedDelivery()会直接跳过;该任务可以成功,但不会生成任何 AgentBus delivery。判断“任务来自 AgentBus”必须看tasks.source='agentbus'、tasks.channel_id和入站回执行。 - listener 只有在
agentBusEnabled、渠道enabled=true、全局 WebSocket URL/渠道 key/bot address 可用并收到session.ready后才会发送;连接断开会把sending释放回pending,失败按退避重试。当前源码测试覆盖 legacy 直发和数据库渠道 durable accepted/result 两种路径。 tasks.source仅允许manual/agentbus,tasks.channel_id可为空;agentbus_deliveries对 accepted/result 做唯一约束,默认pending,失败会重试。数据库设计本身允许“任务已成功但 delivery 未送达”的中间状态。TaskService的执行结果路径只更新任务、写task_events/通用outbox_events并发出内部events;AgentBus result 不是在任务成功事务内直接发送,而由 listener 的 durable flush 后置生成。因此仅看到控制面“任务成功”日志,不等于看到outbound_durable_delivery_sent。- 最终诊断:
processing缺失是设计行为;accepted/result 同时缺失则不是“ERP 任务成功”能够覆盖的成功条件,优先检查该任务是否为source=agentbus且绑定channel_id,再检查对应 accepted/result delivery 是否存在及其pending/failed/delivered状态。没有任务 ID 和任务时段日志,无法在“手工任务无路由”与“AgentBus delivery 未投递”之间做历史唯一归因。 - 当前只读
/health/ready探针返回数据库/schema 正常,4 个启用渠道均connected=true、session_ready=true;未执行外部发送、任务重试、重启或部署。 - 现场日志已捕获用户刚发的成功任务
TASK-20260819102429-R13bn8w:入站 frame 为wechat-task-c6540dcf293678ec2d76dfeb#1,控制面先发送 accepted(delivery4d447c5b-1012-437c-9e00-2854429a91d3),后发送 completed result(deliverye4b3db12-abc2-49b8-b97f-a1674fe876a8),两条均有outbound_durable_delivery_sent。 - 同一 result frame 之后收到 AgentBus server 的
accepted-177与delivered-178确认帧;日志没有outbound_durable_delivery_failed、socket_error或socket_close与该任务相邻。因此“控制面未给 AgentBus 返回”已被排除;“delivered”只能证明 AgentBus WebSocket/网关接收,不证明微信客户端已经渲染。 - 该任务的
processing仍不会发送,这是契约设计;本次 accepted/result 已实际发送却用户不可见,剩余故障域是 AgentBus 网关到微信适配器/会话的下游路由、事件类型渲染或会话展示。
2026-08-19 — confirmation_export Chrome host 权限阻断
- 两份用户粘贴日志内容结构相同但任务编号/时间不同;外部 Agent SSE 正常完成,标准 operation 校验通过,action 为
confirmation_export,文件类型为xingyou-confirm。 - 两次都在插件浏览器执行阶段阻断,错误完全一致:
Cannot access contents of the page. Extension manifest must request permission to access the respective host.;agent_returned=true、plugin_dispatch_started=true、erp_write_started=false、no_erp_write=true,没有 ERP 写入或导出源回执。 - 当前扩展
manifest.json已递增到0.5.137,仍只允许登记的https://lwlt.hisy.cc/*;background.js用同一固定 origin 查找/打开 ERP tab,随后通过chrome.scripting.executeScript注入页面脚本。 runPageAction()的业务动作执行使用主框架;resolveOperationInErp()也使用主框架,但前置/只读探针路径有allFrames=true调用。Chrome 原始错误没有在源码中硬编码,说明需要区分固定 ERP host、重定向 host 和受限 frame 三种触发条件。- 对固定 ERP URL 的外部只读 HEAD/重定向探测因连接超时未得到网络证据;不读取秘密配置,不重试外部业务任务。
- 修复已在后台增加
chrome.permissions.containshost 前检、tab origin 复核、同源导航竞态的一次安全重试和结构化权限错误;平台桥接状态现在展示 ERP 页面权限,并在权限不可用时阻止新的自动 handoff。 - 定向验证已通过:扩展/平台语法检查、operation plan 40/40、生命周期契约 47/47;
check:repo9/9 通过,0.5.137 ZIP 与源码逐文件一致。
2026-08-18 — visitor-list XLSX 转换失败日志
- 用户提供的运行记录中,外部 Agent 解析完成并进入插件只读阶段;没有 ERP 写入。
- 最终阻断原因为
artifact_delivery_failed:visitor_xlsx_conversion_failed:conversion_failed:游客信息已读取,但移动端.xlsx派生文件生成失败。 - 系统按 fail-closed 规则没有把原始 HTML-in-XLS
.xls回传 AgentBus,因此不能把前面的confirmed自动化事件当作最终成功;最终任务状态是blocked。 - 当前需要继续核对转换器的输入路径、LibreOffice 调用/退出码、输出发现与 XLSX ZIP/magic 校验;在得到根因前不执行 ERP 重试。
- 已用当前 bundled
soffice对脱敏 HTML-in-XLS fixture 复现:输入被识别为Writer/Web document,执行xlsx:Calc MS Excel 2007 XML时退出信号为SIGABRT,stderr 为Unspecified Application Error;输出目录仅有锁文件和临时文件,没有有效 XLSX。该崩溃是当前conversion_failed的直接根因候选。
2026-08-18 — 散拼母团创建写后回查假阴性修复
- 用户已人工确认本次 2027 年三个母团实际创建成功;本次错误因此确定为写后回查假阴性,而非 ERP 创建失败。
- ERP 成功响应完整返回 3 个团号,精确回查却全部为
parent_group_not_found;最终错误为erp_result_uncertain,系统未自动重试。 - 当前
createSplitParentLive()仅在groupNumbers.length < dates.length或启用事实探针时调用reconcileSplitParentByRequest()。本次 3 个返回团号等于 3 个日期,导致精确回查全部失败时仍跳过按日期兜底。 - 精确回查调用
searchMainPage()时只设置日期范围与团号,没有显式清空客户、产品、游客/领队和状态筛选;列表复用现有文档,因此残留筛选可能隐藏已创建行。 - 修复范围已确认:清空非目标筛选、有限延迟只读重试、任一精确团号未命中即触发按日期兜底;不得再次提交创建请求,持续缺失或歧义仍保持不确定态。
- 当前实现使用
0/750/2000ms三次精确只读查询;每次查询都设置日期与团号,并清空客户、产品、游客/领队和状态筛选。 - 恢复判定现在同时检查保存响应、团号数量、精确回查完整性和事实探针;任一条件需要恢复时调用现有逐日期唯一匹配。回查行合并会让成功的日期兜底结果覆盖先前空结果,但不会覆盖歧义或缺失门禁。
- 定向测试已通过:
split-plan-reconciliation14/14;生命周期静态门禁 1/1。测试确认首次全空、第二次可见可收敛,持续缺失会耗尽有限预算并保持未确认,且createSplitParentLive()仍只有一次captureAjaxSubmit()保存捕获调用。 - 扩展已递增到
0.5.135,当前 ZIP SHA-256 为9f49f5529083cb1cc497bfc52c56d0142076394c034552fcdd77e34e70ce7f14;旧0.5.134已进入日期归档。 - 完整验证中,本次回查相关代码、legacy 214/214、类型检查、构建、仓库与发布物门禁均通过。控制面唯一失败来自任务开始前已有的游客 XLSX 并行改动:
convertDocumentToXlsx()期待.xlsx,测试假soffice仍只生成team.pdf;本轮未改动该策略或测试。
2026-08-18 — visitor-list AgentBus XLSX 交付
- 用户日志中的源文件为
LW-260816Z-A Visitor.xls,源大小 9,377 字节,源 MIME 为application/vnd.ms-excel; Charset=UTF-8,并带有独立 SHA-256。 - 历史 ERP 实时采集记录确认
/System/Business/orders_Visitor.asp的响应虽然声明application/vnd.ms-excel,但首字节是 HTML 文档头,属于 HTML-in-XLS wrapper,不是标准 BIFF/OLE.xls。 - 桌面 Excel 会兼容解析这种 HTML 表格;手机 Office/微信通常同时检查扩展名与文件签名,遇到“
.xls文件名 + HTML 内容”会提示格式不支持。这与用户“电脑能开、手机和微信打不开”的现象一致。 - 插件
chrome-extension/ltjt-order-assistant/inpage.js用response.arrayBuffer()读取 ERP 响应,再计算 SHA-256/base64;没有文本转码或重写。 - 控制面
prepareExecutionArtifacts()对visitor-list直接沿用源字节、源文件名和源 MIME;OSS 写入设置attachmentdisposition 并保留 MIME。当前证据不支持平台或微信链路把文件内容损坏,问题边界在 ERP 源格式。 - 仅把扩展名改成
.xlsx或只改 MIME 不能修复;要在手机/微信打开,必须生成真实.xlsx(保留表格语义)或 PDF。 - 用户已确认双文件方案:原始
.xls仅作为平台源归档,真实.xlsx作为移动端/AgentBus 交付文件;其他类型仍按 PDF 规则处理。 convertDocumentToXlsx()识别 HTML-in-XLS,调用 LibreOfficeCalc MS Excel 2007 XML,校验 ZIP/XLSX magic;转换失败返回source_fallback,任务层对 visitor-list fail-closed,不把原始 XLS 发送给 AgentBus。- 游客导出报告现在同时记录
source_artifact_count=1、derived_artifact_count=1、xlsx_count=1和delivered_artifact_count=2;原始 artifact 标记artifact_role=source_archive、agentbus_visible=false,XLSX 标记artifact_role=mobile_delivery、agentbus_visible=true。 reply-contract.ts和agentbus.ts均过滤agentbus_visible=false,因此用户回执文本、普通附件元数据、直连与耐久 AgentBus outbox 都只暴露 XLSX。- 已用 artifact-tool 导入并检查真实 XLSX:工作表单元格可读取,渲染预览正常,文件头为 ZIP/XLSX;验证使用 LibreOffice 实际转换路径而非仅改扩展名。
- 本轮复现进一步确认:同一 HTML 内容临时文件名为
.xls时,LibreOffice 将其识别为Calc document并成功生成 6KB 有效 XLSX;临时文件名为.html时则识别为Writer/Web document并SIGABRT。修复已将 HTML 源临时扩展名固定为.xls,并让回归测试断言该导入路径。 - 修复后的完整门禁全部通过:
check:repo9/9、类型检查、控制面 66/66、legacy 214/214、build、git diff --check;面板已重启,新 PID24717监听127.0.0.1:8786,live/ready 与 4 个 AgentBus 渠道均正常。
已完成的相关交付
confirmation_export已按类型交付:visitor-list源 XLS 归档并生成真实 XLSX,AgentBus/微信只返回 XLSX;其余类型 PDF;转换失败回退源文件。- 已同步控制面、Skill、输出契约、Schema、mapping、插件提示、测试、版本化 Skill/扩展包、运营 DOCX 和发布清单。
- 散拼子单导出二次查询已移除固定“收客中”过滤,仍保留母团/子单/
ddid/tid唯一核验。 - 上一轮验证全部通过:
check:repo9/9、check、控制面 61/61、legacy 208/208、build、git diff --check;Skill 官方校验和 DOCX 15 页渲染检查通过。
约束与证据边界
- 当前证据是脱敏的响应摘要(路径、状态、MIME、长度、内容特征、哈希),未保存真实游客资料或完整源文件;不能在本地对用户这一个 9,377 字节样本再运行
file/移动端实测。 - 未读取或输出秘密配置;未执行 ERP 写入、重试、重启、部署或外部发送。
- 压缩前完整 findings 已冻结到 visitor 移动端诊断前 findings;更早历史事实仍在同目录日期归档中。