Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion Agent.md
Original file line number Diff line number Diff line change
Expand Up @@ -119,14 +119,15 @@ Community needs voiced in HN agent-UI discussions map directly to EMRG's design:
pkill -f "emrg.server"; rm -f ~/.emrg/emrgd.token; python -m emrg
```

Python: `uv run pytest tests/ -v` (1410) — import check: `uv run python -c "from emrg.client.app import run_client"
Python: `uv run pytest tests/ -v` (1433) — import check: `uv run python -c "from emrg.client.app import run_client"
GUI: `cd emrg/gui && npm test` (100: 44 daemon_client + 20 conn-manager + 7 integration + 7 nav-policy + 7 gui-state + 6 build-config + 4 boot-contract + 3 preload-api + 2 theme-guard) — syntax: `node --check main.js preload.js daemon_client.js`
Renderer: `cd emrg/gui/renderer && npm run typecheck && npm test` (514: 5 snapshot-store + 9 utils + 3 ErrorBoundary + 2 App smoke + 11 commands + 4 copywriting + 11 i18n + 13 markdown + 21 transcript + 11 TranscriptView + 15 history + 31 composer + 41 Composer + 6 LinkDialog + 16 sidebar + 17 Sidebar + 9 fileTree + 9 FileTree + 16 resultPanel + 8 ResultPanel + 27 workspaceView + 10 WorkspaceView + 10 dialog + 6 Dialog + 9 ConfirmDialog + 9 RenameDialog + 10 dialogLists + 3 HelpDialog + 9 MemoryDialog + 6 SkillsDialog + 8 openSession + 6 WelcomeDialog + 9 OpenSessionDialog + 7 NewSessionDialog + 7 rewind + 8 RewindDialog + 7 GithubDeviceDialog + 18 daemonBridge + 7 DaemonBridgeProvider + 30 Shell + 15 DialogHost + 20 SettingsPanel + 6 TaskFormDialog + 5 RantDialog + 4 vendorMarkdown) + `npm run build` → `renderer/dist/`
CI: `uv run pytest` (ubuntu + **windows-2025 matrix** — Windows pytest 回归在 PR CI 即失败,v0.2.29 教训 #725) + GUI tests + **actionlint workflow lint** (`rhysd/actionlint@v1.7.12` gate, #444 — workflow 解析错误在 PR CI 即失败,如 `if:` secrets 上下文)
Re-trigger: `scripts/re-trigger-ci.sh [branch]` (workflow_dispatch, #527 — 替代空 commit 重触发:Actions outage 会整段丢弃 push 事件,dispatch 走 API 路径不受影响)
Release bump: `python3 scripts/bump-version.py <x.y.z>` — 一次改齐 8 处版本声明(`emrg/__init__.py`、`pyproject.toml`、`emrg/gui/package.json`、`emrg/gui/package-lock.json` 根 + `packages[""]`、`uv.lock`、`packaging/{build-runtime,make-installer,make-run-installer}.sh`);`--check` 只报告漂移(宿主侧自检,与 CI 的 test_version_sync 对称),`--dry-run` 预览不落盘。锚点缺失/数量不符即 fail-loud,绝不猜测;`uv.lock` 只改 `name = "emrg"` 那一行(v0.2.94 教训:直接 `uv run` 会把 lock 里所有 registry URL 重写成镜像,556 行环境噪声)。bump 后用 `uv run --no-sync pytest` 避免 uv 重生成 lock。详见 Agent.md「Releasing」
Doc count sync: `uv run --no-sync python3 scripts/check-doc-count.py [--write|--dry-run|--resolve-conflict]` — 测量当前树的 pytest 收集数并校验 Agent.md 的 Python 测试数(宿主侧自检,与 CI 的 test_python_count_matches_docs 对称);`--write` 仅单 token 替换那个数字(前后遮罩对比,其余字节不变),锚点缺失/出现多次/收集失败均 fail-loud(exit 2)。`--resolve-conflict` 专治合并冲突态:冲突块的**两侧按构造都是陈旧的**,`--write` 会(正确地)拒绝猜哪一侧为真;该模式去掉冲突标记后**在合并后的树上重新测量**写入,绝不选边——实测两侧写 1335/1337 而合并树实收 1339。冲突出现在计数行以外的位置即拒绝(不是什么通用「删标记」按钮)。用途:合并冲突解决后一条命令同步(#1119/#1120/#1121/#1122 四次冲突均在这一行;2026-09-11 #1130 落地后三个 PR 转 DIRTY,逐个解冲突都靠这条)
Node count sync: `uv run --no-sync python3 scripts/check-node-test-count.py [--write|--dry-run]` — 直接问**真实运行器**(vitest / node --test)并校验 Agent.md 的 Renderer 与 GUI 两个总数:`tests/test_doc_counts.py` 只能**静态**数 `it(`/`test(` 定义(pytest 作业没有 node_modules),而静态计数只是运行器的**模型**——R2254(445→448)、#1120(同 stem 文件整份被吞)、#1125(`it.each`/`test.skip` 正则看不见)三次都是模型与实践脱节。GUI 侧按 CI 环境(EMRG_SKIP_INTEGRATION=1)运行后减去 1 个模块级 `skip()` 原因条目(该条目数会先断言为 1,形状变了就停手而不是报个看着像对的数)。缺 node_modules 即报该原因,绝不报假数
Vote count: `uv run --no-sync python3 scripts/check-vote-count.py <PR>...` — 合并前数**仍然算数**的 LGTM 票,而不是评论里看得见的 ✅ 行数。三条规则让手工计数每次都错:① **票早于 head push 即作废**(rebase/解冲突推新 head 后,旧 ✅ 说的是已经不存在的 commit,而评论历史照样显示五六行 ✅,PR 看着能合实则零票——2026-09-11 实测 #1133/#1134/#1136/#1137 各显示 4-6 张 LGTM,解锁后**有效票全为 0**);② **❌ 重置计数**(三次 ✅ 后一个 needs-fix,再一个 ✅ 只算一票);③ **同一周期只算一票**(否则一个周期独自把 PR 送过门槛)。判票读正文**首字符**(`gh pr review --comment` 让 GitHub 把 ✅ 和 ❌ 都记成 `COMMENTED`,state 字段在这里毫无用处),周期号从正文里取(`cyc20260911-091230`)。push 时间取**该 SHA 上最早一次 workflow run 的创建时间**(就是 GitHub 收到 push 事件的时刻);没有 run 时退回 commit 日期并**在输出里注明**(commit 日期可能早于 push,是乐观方向,不许默默采信)。exit 0 每张 PR 都够票 / 1 有 PR 缺票 / 2 问不出来(gh 失败、响应不可解析)——问不出来的问题绝不报数。评论**逐页取全**(reviews 端点默认只给 30 条且**按时间正序**,超限时丢掉的正是**最新的**票,也就是唯一算数的那几张;#1134 解锁一次就有 7 条评论),并在本地按时间排序(「❌ 重置计数」和「同周期只算一票」都是**位置相关**的规则,依赖服务端返回顺序等于把判决权外包)。两个自暴露的坑:① gh 的 `--jq` **后者覆盖前者**,helper 若自己追加 `--jq` 会吃掉调用方投影,字段名退回原名、`at` 读成空串,而 `"" <= push_time` 恒真 ⇒ **全部票作废**、有 2 票的 PR 显示 0/3(计数方向偏「安全」,没人会去查);故 helper 只管 `--paginate`,投影归调用方,并对载荷形状**运行时断言**(缺 `at` 即 exit 2,不报数)
Git-over-https 兜底: `python scripts/sync-master-from-api.py [--repo owner/name] [--ref master]` — 受限网络下 github.com:443 不可达而 api.github.com 可达时,用 Git Data API 的 verification payload + signature 字节级重建上游 commit(含 web-flow GPG 签名 squash merge,reconstruct_commit 经 hermetic 测试验证 sha 一致)并推进本地 refs;内容对象缺失时 fail-loud 提示改用 git fetch(10+ 周期实证的恢复路径)
Git-over-https push 兜底: `python scripts/push-branch-from-api.py --branch feature/x [--ref HEAD] [--force]` — 同一宕机场景下的 push 方向(#988 配对):从本地 ref 沿一父链找到远端基点(已有分支头或首个远端已知祖先),自底向上上传 blobs(原始字节)/trees(`git mktree` 语义复算)/commits(结构化创建,author/committer 携带原始 +0800 偏移、消息去尾随换行——GitHub 规范化行为),更新远端 ref 后把本地分支 ref 重写为远端 sha 并 `git diff` 验证内容一致;失败即止不触碰 refs(hermetic 测试经忠实假 API 验证字节级 sha 一致)

Expand Down
Loading
Loading