|
|
3 өдөр өмнө | |
|---|---|---|
| build | 4 өдөр өмнө | |
| harness | 3 өдөр өмнө | |
| public | 4 өдөр өмнө | |
| src | 3 өдөр өмнө | |
| .editorconfig | 4 өдөр өмнө | |
| .env.development | 3 өдөр өмнө | |
| .env.production | 3 өдөр өмнө | |
| .env.qingpu | 3 өдөр өмнө | |
| .env.test | 3 өдөр өмнө | |
| .eslintignore | 4 өдөр өмнө | |
| .eslintrc.js | 4 өдөр өмнө | |
| .gitignore | 3 өдөр өмнө | |
| .prettierrc.cjs | 4 өдөр өмнө | |
| CLAUDE.md | 3 өдөр өмнө | |
| README.md | 3 өдөр өмнө | |
| agents.md | 3 өдөр өмнө | |
| index.html | 3 өдөр өмнө | |
| jest.config.js | 4 өдөр өмнө | |
| package-lock.json | 4 өдөр өмнө | |
| package.json | 4 өдөр өмнө | |
| redirect.html | 4 өдөр өмнө | |
| tsconfig.json | 4 өдөр өмнө | |
| tsconfig.node.json | 4 өдөр өмнө | |
| vite.config.ts | 3 өдөр өмнө |
本文件当前只记录按日期的改动。项目概述、技术栈、目录结构、接口说明等内容, 等项目结束时再统一总结。
POST /api/chat(SSE)
src/components/api-chat-coordinator.ts,把 SSE 事件翻译成既有渲染组件
可识别的内容标记,渲染层无需感知新协议{thread_id, question};answer 与 result.response 只展示一次;
未收到 done/error 即断流时按连接中断处理,不自动重试src/components/stream-message-coordinator.ts 保留未用VITE_CHAT_API,新增 dev 代理 /chat-api → http://192.168.2.23:8000thread_busy → 该问题还在处理中)<scope>、<!-- POLICY_TABLE -->、
<ref_links> 等原始标记一起复制出来priority.rank 排序.gitignore 约定不入库)public/merchant-agent/policies_public.v1.json
(262 条申报事项 / 38 个政策),本轮匹配到的惠企政策置顶is_policy_library,缺失时回退到按标题在库中匹配
(已做归一化,容忍《》全半角括号等差异)status 字段判定形态(found / not_found / failed / 无 status),
替掉原先靠"候选数是否为 0"和 input_help 文案正则的猜测式判断
failed(查询服务失败)此前会落进 not_found 分支,文案被填成"未查询到匹配的公司",
等于把失败说成查无公司,已改为独立分支并说明失败原因status(初次询问是否需要公司信息)此前给"跳过公司查询",改为"不需要公司信息"/skip 改为发送选项文本「跳过公司查询」content.trim()
(<scope> 进度块算作有内容),渲染层用 stripScopeBlocks()
(进度块不算内容)。同一段内容,一处认为「有」、一处认为「没有」done 才写入,处理期间内容只有进度块,把这个缝隙
从偶发放大成「一切会话就出现」:归一化认为有内容 → 不替换文案,却把状态翻成
Finish;渲染层认为没内容 → 显示「请求已取消」,而请求其实还在跑hasVisibleMessageContent()(utils/interrupted-message.ts),
归一化与渲染层都改用它harness/tools/verify-empty-content-agreement.mjs,
断言的不变量就是「两处必须一致」,30 项断言ScopeContent 按卡片宽度切样式 —— 没撑满容器时标题 nowrap + 省略号,
撑满时切成 pre-wrap。而阶段文案长度不一(新协议的文案比原来的"正在思考中..."长得多),
切换时表现为「突然换行」且卡片高度跳动nowrap + 省略号data.市级政策id
拼出 https://zwdt.sh.gov.cn/qykj/shell_oc_policy_zq/policy/policy-detail?id=<id>
apply_link 字段 262 条全为空;资源申请备注 里的 URL 是按申报事项
零散对应、且混有内网地址(25 条指向 http://10.235.238.34:7202/imanage/login),
不能作为来源。市级政策id 有 261/262 条,可靠public/merchant-agent/policies_public.v1.json:262 条,data.市级政策id 有 261 条VITE_DOWNLOAD_URL:327 条,该字段一条都没有(它有的 policy_id 是 40 位、
与条目 id 相同,与 24 位的 市级政策id 是两套 id 体系)index.html 原本是远端优先(远端带 CORS 头,浏览器里确实会赢),
于是取不到 id → 拼不出详情地址 → 「政策名称」是纯文本。
此前怀疑的「HMR 状态陈旧」「走了兜底路径」均排除VITE_POLICY_LOCAL_FIRST:仅开发环境打开(本地优先、远端兜底),
生产仍远端优先——生产该问题属后端数据缺失,需远端那份补上 data.市级政策id,
前端无法修harness/tools/check-policy-sources.mjs:对比两个来源的条数与字段覆盖率,
并在「远端也带上 id 了」时提醒可以移除该开关c_session_id upsert:没有就新增、有就更新)与问答记录(先写问题);
回答完成补写回答;停止/断流也补写已生成的内容,避免中断的问答只有问题没有回答c_record_id 定位那一行)访客_<访客id> 归属(访客 id 复用埋点的那个)session.id(它恒等于聊天协议的 thread_id);问答记录标识用
AI 消息 id(同时是反馈组件用的 record.id,因此从 DMS 读回的历史消息点赞仍能命中原始行).env.development.local,按约定不入库),
浏览器产物里没有 token;DMS 不可用时静默降级,聊天与本地历史不受影响delContentById(各种传法都返回参数错误),
而是 POST /content/updateAudit 把状态改成 4(销毁);addContent 会返回记录 uuid?access_token= 或 ?credit_code=harness/)结构对齐
Learn Harness Engineering 的 OpenAI 高级包:
docs/plans/ → docs/exec-plans/(completed/ + tech-debt-tracker.md),
并新增结构校验脚本 harness/tools/validate-harness.mjs(机械约束优先于口头约定:
可检出假 passing、多个 in_progress、游离的计划文件等)harness/、CLAUDE.md、agents.md 纳入版本控制(此前排除)
.env.*.local、.claude/settings.local.json),
以及 esbuild 生成的 harness/tools/_*.mjs(构建产物,入库会与源码漂移);
产物重新生成的命令写在 harness/tools/README.mdtitle 与
declaration_item 都取自 card.name.text(只有政策名),而后端不下发
id/policy_id(实测恒为 undefined)——这些卡片在字段上完全无法区分,
原来的反查只要任一条件命中就返回,于是点第二张也跳到第一张resolvePolicyDetailIndex(),对象同一性优先,
退化的字段比对只在唯一命中时采信,多命中时交给「直接展示被点条目」的兜底
—— 宁可走兜底,也不张冠李戴harness/tools/verify-policy-detail-index.mjs(10 项断言,
含「点第 2 张 → 下标 1」这条针对本 bug 的断言)declaration_item 改用后端每条唯一的 data.title,不再与卡片标题同值;
卡片区标题仍是政策名,观感不变(含一处连带的 panelData.title 取值顺序修正——
否则改详情标题会连带改掉卡片标题)harness/tools/verify-policy-card-fields.mjs(8 项断言:同政策两条必须可区分、
卡片标题不变、无后缀时退化为政策名)cardList,与旧列表共用同一套模板与样式类,未新增 CSS;
旧列表逻辑靠既有守卫自然短路,openPolicyList 一行未动harness/tools/verify-policy-card-list.mjs(31 项断言:聚合并集保序、
坏 JSON/空输入不抛错、首见优先去重、降序+同分稳定、六面关键词过滤)c_record_id,
问题与回答各存一半)。曾一度改成「一个会话一行、整段对话 JSON 塞进 c_answer」,
现按需求改回——更贴近库表原本语义(chat_record 即一行一轮问答),也便于按轮次检索统计。
反馈随之改为写在该轮的 c_feedback_* 列上;会话删除连带清理其名下所有问答行harness/docs/exec-plans/completed/ 开始启用,
已实现的两个计划(DMS 落地、政策列表侧边栏)移入并更新状态;
结构校验脚本新增两条检查(active/ 里状态写着已完成、completed/ 里状态仍写进行中)isGenerating,于是「同一时间只能一个会话在生成」,
并衍生出两个 bug:生成中切到别的会话,发送按钮仍显示「停止」(想发送却停了生成);
停止时目标会话解析错误(同步事件把它提前清空 → 回落到「当前会话」),
会把停止打在看的那条会话上、并凭空造出一条空的「请求已取消」消息tasks Map + 每轮独立协调器实例 + 监听器闭包捕获会话 id),
各会话并行、互不干扰;停止只停自己那一轮;新建会话不再打断正在生成的会话verify-chat-task-utils.mjs(33 项,含把「响应式容器破坏对象同一性」
这个陷阱钉死的断言)、verify-coordinator-multi-instance.mjs
(11 项,验证多实例事件隔离——并行化的地基)VITE_CHAT_TARGET(聊天后端真实地址)——此前它硬编码在 vite.config.ts 的
代理配置里;现由 vite.config.ts 从 env 读取(保留同值兜底)