loki-mode 11.3.0 → 11.3.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (215) hide show
  1. package/README.md +68 -650
  2. package/SKILL.md +4 -4
  3. package/VERSION +1 -1
  4. package/autonomy/completion-council.sh +2 -2
  5. package/autonomy/context-tracker.py +4 -4
  6. package/autonomy/council-v2.sh +1 -1
  7. package/autonomy/grill.sh +1 -1
  8. package/autonomy/lib/done-recognition.sh +1 -1
  9. package/autonomy/lib/prd-enrich.sh +1 -1
  10. package/autonomy/lib/voter-agents.sh +1 -1
  11. package/autonomy/loki +99 -75
  12. package/autonomy/run.sh +30 -18
  13. package/autonomy/sandbox.sh +1 -1
  14. package/autonomy/tui.sh +6 -5
  15. package/autonomy/verify.sh +1 -1
  16. package/bin/loki +166 -59
  17. package/completions/_loki +2 -0
  18. package/completions/loki.bash +2 -2
  19. package/dashboard/__init__.py +1 -1
  20. package/dashboard/server.py +25 -31
  21. package/docs/ARCHITECTURE.md +337 -0
  22. package/docs/BRANDING.md +124 -0
  23. package/docs/CLI-REFERENCE.md +7 -1
  24. package/docs/COMPONENTS.md +447 -0
  25. package/docs/DEPLOYMENT.md +9 -9
  26. package/docs/DOCKER.md +469 -0
  27. package/docs/INSTALLATION.md +67 -1045
  28. package/docs/KNOWN-ISSUES.md +11 -35
  29. package/docs/TESTING.md +161 -0
  30. package/docs/air-gapped.md +1 -2
  31. package/docs/alternative-installations.md +14 -24
  32. package/docs/architecture/DECISIONS.md +333 -0
  33. package/docs/audit-logging.md +7 -7
  34. package/docs/authentication.md +3 -3
  35. package/docs/authorization.md +1 -1
  36. package/docs/certification/04-production-deployment/lab.md +6 -6
  37. package/docs/certification/04-production-deployment/lesson.md +4 -4
  38. package/docs/certification/README.md +1 -1
  39. package/docs/control-plane-container.md +2 -2
  40. package/docs/dev/real-run.md +34 -0
  41. package/docs/dev/release-checklist.md +2 -2
  42. package/docs/exit-codes.md +3 -3
  43. package/docs/git-workflow.md +3 -3
  44. package/docs/metrics.md +37 -55
  45. package/docs/network-security.md +1 -1
  46. package/docs/siem-integration.md +5 -5
  47. package/docs/v10/CLI-MODERN.md +4 -3
  48. package/docs/v10/DECISIONS.md +44 -0
  49. package/docs/v10/DEPS.md +22 -22
  50. package/docs/v10/ENGINE.md +1 -1
  51. package/docs/v10/FAILURE-CLASSES.md +118 -1
  52. package/docs/v10/FOUNDER-QUEUE.md +1 -0
  53. package/docs/v10/GUARDS.md +13 -0
  54. package/docs/v10/LEGACY-REMOVAL.md +4 -6
  55. package/docs/v10/METRICS.md +2 -2
  56. package/docs/v10/MODERNIZE.md +1 -1
  57. package/docs/v10/OPERATING-MODEL.md +2 -1
  58. package/docs/v10/PROGRESS.md +29 -0
  59. package/docs/v11/COST-HALF.md +352 -0
  60. package/docs/v11/MARKET-SLICES.md +315 -0
  61. package/docs/v11/REGISTRIES.md +730 -0
  62. package/loki-ts/data/model-pricing.json +52 -24
  63. package/loki-ts/dist/loki.js +1036 -957
  64. package/mcp/__init__.py +1 -1
  65. package/package.json +1 -1
  66. package/packages/control-plane/dist/server.js +2467 -736
  67. package/plugins/loki-mode/.claude-plugin/plugin.json +1 -1
  68. package/src/protocols/mcp-client.js +6 -2
  69. package/src/protocols/mcp-server.js +13 -3
  70. package/tools/audit-docs.py +1 -1
  71. package/web-app/dist/assets/{AdminPage-D_e45uTw.js → AdminPage-CMkHNJbF.js} +1 -1
  72. package/web-app/dist/assets/{Avatar-T3nIpoaf.js → Avatar-BJyjV7Zi.js} +1 -1
  73. package/web-app/dist/assets/{Badge-BKqb59pP.js → Badge-D572l0uq.js} +1 -1
  74. package/web-app/dist/assets/{Button-DjVlkh8_.js → Button-T4BnOZgl.js} +1 -1
  75. package/web-app/dist/assets/{CockpitPage-DXJgLGmh.js → CockpitPage-Cj_GFsNn.js} +1 -1
  76. package/web-app/dist/assets/{ComparePage-BRP_eVc_.js → ComparePage-A8m4ZXak.js} +1 -1
  77. package/web-app/dist/assets/{ErrorBoundary-CLjpGLjC.js → ErrorBoundary-hugCg5yg.js} +1 -1
  78. package/web-app/dist/assets/{EvidenceReceiptPanel-DX-vb4Xy.js → EvidenceReceiptPanel-CuJKDC2G.js} +1 -1
  79. package/web-app/dist/assets/{GitHubIssuesPanel-214HVHtX.js → GitHubIssuesPanel-BYGKjarC.js} +1 -1
  80. package/web-app/dist/assets/{GitHubPRsPanel-BEiZKc4t.js → GitHubPRsPanel-c7sFIJlf.js} +1 -1
  81. package/web-app/dist/assets/{HomePage-VvMHS5ga.js → HomePage-A1MIkG2P.js} +2 -2
  82. package/web-app/dist/assets/{LoginPage-5WD-v7n3.js → LoginPage-8KQMRhtR.js} +1 -1
  83. package/web-app/dist/assets/{MagicPage-DUQT_Jye.js → MagicPage-C05QW2Lx.js} +1 -1
  84. package/web-app/dist/assets/{MetricsPage-lga-z79v.js → MetricsPage-Oukv5hme.js} +1 -1
  85. package/web-app/dist/assets/{NotFoundPage-CGhBX3G1.js → NotFoundPage-DKIwsawz.js} +1 -1
  86. package/web-app/dist/assets/{ProjectPage-CdzF2GzZ.js → ProjectPage-DwFRPLCG.js} +3 -3
  87. package/web-app/dist/assets/{ProjectsPage-DRG64N8s.js → ProjectsPage-CgY4YYDX.js} +1 -1
  88. package/web-app/dist/assets/{SettingsPage-5fzW9Frb.js → SettingsPage-BpfcSjUA.js} +1 -1
  89. package/web-app/dist/assets/{ShowcasePage-DrTdxO4y.js → ShowcasePage-BqBakC4K.js} +1 -1
  90. package/web-app/dist/assets/{SystemSettingsPage-C9Mqs6Rd.js → SystemSettingsPage-CZLu5VB0.js} +1 -1
  91. package/web-app/dist/assets/{TeamsPage-CUGPdSWo.js → TeamsPage-D55S1jKz.js} +1 -1
  92. package/web-app/dist/assets/{TemplatesPage-CNraDY0F.js → TemplatesPage-D3SydvxN.js} +1 -1
  93. package/web-app/dist/assets/{TerminalOutput-BIu_6Pea.js → TerminalOutput-hNg8G1-e.js} +1 -1
  94. package/web-app/dist/assets/{activity-Bk-kgqaf.js → activity-D2C0VagO.js} +1 -1
  95. package/web-app/dist/assets/{bell-BXmUdmo8.js → bell-CMvYi36w.js} +1 -1
  96. package/web-app/dist/assets/{bot-CiuzXxUR.js → bot-BvtQ6lmo.js} +1 -1
  97. package/web-app/dist/assets/{check-BEzjXppd.js → check-B13xkXed.js} +1 -1
  98. package/web-app/dist/assets/{chevron-left-AYWCXHf8.js → chevron-left-emu6r49E.js} +1 -1
  99. package/web-app/dist/assets/{circle-alert-BNg2uSRq.js → circle-alert-CExlwjuy.js} +1 -1
  100. package/web-app/dist/assets/{clock-DTj0kkGT.js → clock-D7Uas3oL.js} +1 -1
  101. package/web-app/dist/assets/{cloud-x4nTDBLT.js → cloud-CkB4S86C.js} +1 -1
  102. package/web-app/dist/assets/{code-xml-BVh_MLrk.js → code-xml-SL9IIWIn.js} +1 -1
  103. package/web-app/dist/assets/{database-DdfBaowG.js → database-BQFkd7t1.js} +1 -1
  104. package/web-app/dist/assets/{dollar-sign-XuYFmAOY.js → dollar-sign-qHmnNYsU.js} +1 -1
  105. package/web-app/dist/assets/{file-code-corner-D4cRnmeL.js → file-code-corner-C2YUDP0K.js} +1 -1
  106. package/web-app/dist/assets/{file-plus-CyoVlHc_.js → file-plus-C_ooIkDe.js} +1 -1
  107. package/web-app/dist/assets/{globe-Y6IK2RPW.js → globe-CQ-GL485.js} +1 -1
  108. package/web-app/dist/assets/{hammer-BKzr9VZI.js → hammer-U05L_D7V.js} +1 -1
  109. package/web-app/dist/assets/{index-B20cSx5G.js → index-CooHd7I-.js} +3 -3
  110. package/web-app/dist/assets/{layers-DebNOhGS.js → layers-Buo17rjW.js} +1 -1
  111. package/web-app/dist/assets/{loader-circle-DyGbrEgd.js → loader-circle-15vK3oV1.js} +1 -1
  112. package/web-app/dist/assets/{lock-BKPpyt20.js → lock-BeXLebuJ.js} +1 -1
  113. package/web-app/dist/assets/{package-egF5Wi4y.js → package-MVh_6-6R.js} +1 -1
  114. package/web-app/dist/assets/{plus-OiEgKIc-.js → plus-Dh_nd9vS.js} +1 -1
  115. package/web-app/dist/assets/{refresh-cw-CzKvrONq.js → refresh-cw-C9cBJEAT.js} +1 -1
  116. package/web-app/dist/assets/{rotate-ccw-Bu2mII0p.js → rotate-ccw-D3PAtzST.js} +1 -1
  117. package/web-app/dist/assets/{scroll-text-CSkiyax8.js → scroll-text-DZCoXQjo.js} +1 -1
  118. package/web-app/dist/assets/{server-DlPthJFw.js → server-OCOLI5J_.js} +1 -1
  119. package/web-app/dist/assets/{shield-alert-CbpHWQQX.js → shield-alert-oVhmf1_h.js} +1 -1
  120. package/web-app/dist/assets/{thumbs-up-DgGpZe-Q.js → thumbs-up-B-kbX4vN.js} +1 -1
  121. package/web-app/dist/assets/{trash-2-BV3GlCB-.js → trash-2-EL6moveW.js} +1 -1
  122. package/web-app/dist/assets/{trending-down-Y4TJtXhD.js → trending-down-Cl3kjpsx.js} +1 -1
  123. package/web-app/dist/assets/{trending-up-DsDNoHZY.js → trending-up-DST7I6M2.js} +1 -1
  124. package/web-app/dist/assets/{upload-gkThrc_I.js → upload-CUOT780G.js} +1 -1
  125. package/web-app/dist/assets/{usePolling-jpNSeNAe.js → usePolling-Djmt90eb.js} +1 -1
  126. package/web-app/dist/assets/{user-3Zez1WOK.js → user-BRBohA6J.js} +1 -1
  127. package/web-app/dist/index.html +1 -1
  128. package/docs/ARCHITECTURE-OVERVIEW.md +0 -209
  129. package/docs/AUTONOMI-ECOSYSTEM.md +0 -107
  130. package/docs/COCKPIT-SPEC.md +0 -72
  131. package/docs/COCKPIT-UX-MANDATE.md +0 -53
  132. package/docs/COMPETITIVE-ANALYSIS.md +0 -303
  133. package/docs/COMPETITIVE-NEXT-10.md +0 -316
  134. package/docs/COMPETITIVE-RALPH-ZEROSHOT-2026-07-08.md +0 -81
  135. package/docs/DASHBOARD-9.12-EVIDENCE.md +0 -97
  136. package/docs/DASHBOARD-ARCHITECTURE.md +0 -425
  137. package/docs/DASHBOARD_V2_CHECKLIST.md +0 -243
  138. package/docs/DEMOS.md +0 -63
  139. package/docs/ENTERPRISE-IDENTITY-ROADMAP.md +0 -206
  140. package/docs/EVIDENCE-RECEIPT-BUILD-APPLICABILITY.md +0 -79
  141. package/docs/FEAT-PRDREUSE-DOCKER-PLAN.md +0 -144
  142. package/docs/GATE-FAILURE-TRIAGE.md +0 -254
  143. package/docs/HANDOFF-2026-08-03.md +0 -439
  144. package/docs/LOOP-CANDIDATE-PROPOSAL-v1.md +0 -167
  145. package/docs/LOOP-HARNESS-AUDIT.md +0 -684
  146. package/docs/MERGE-DEDUP-MAP.md +0 -420
  147. package/docs/MERGE-ROUTE-MAP.md +0 -139
  148. package/docs/MODEL-REGISTRY-PLAN.md +0 -155
  149. package/docs/OUTCOME-FRONTIER.md +0 -536
  150. package/docs/P2-SPEC-ROBUSTNESS-PLAN.md +0 -192
  151. package/docs/PLANS-INDEX.md +0 -32
  152. package/docs/PRD-REUSE-DONE-RECOGNITION-PLAN.md +0 -536
  153. package/docs/PROMPT-ABLATION-RESULT.md +0 -97
  154. package/docs/R4-TRUST-TRAJECTORY-DESIGN.md +0 -127
  155. package/docs/R5-AUTO-WIKI-DESIGN.md +0 -137
  156. package/docs/R6-ROLLBACK-CHECKPOINT-PLAN.md +0 -107
  157. package/docs/R7-ZERO-CONFIG-FIRST-RUN-PLAN.md +0 -137
  158. package/docs/R8-SHAREABLE-TEAM-ASSETS-PLAN.md +0 -129
  159. package/docs/R9-OPEN-CORE-HOOKS-PLAN.md +0 -113
  160. package/docs/RARV-C-100X-PLAN.md +0 -286
  161. package/docs/RARV-C-LOOP-EFFICIENCY-PLAN.md +0 -470
  162. package/docs/SHAREABLE-PROOF-PLAN.md +0 -194
  163. package/docs/SONNET5-DEFAULT-PLAN.md +0 -157
  164. package/docs/SPEED-AND-FIRST-PASS-PLAN.md +0 -281
  165. package/docs/STALE-STATE-AUDIT.md +0 -174
  166. package/docs/SYNERGY-TASKS.md +0 -143
  167. package/docs/TASKLIST-ACCURACY-PLAN.md +0 -355
  168. package/docs/TOP-100-BACKLOG.md +0 -159
  169. package/docs/V8-ACCEPTANCE-TRIAGE-2026-07-24.md +0 -114
  170. package/docs/V8-COMPLEXITY-AUDIT-2026-07-24.md +0 -45
  171. package/docs/V8-MAJOR-RELEASE-PLAN.md +0 -137
  172. package/docs/V8-OVERNIGHT-PLAN-2026-07-25.md +0 -82
  173. package/docs/V8-SDK-RESEARCH-RAW.md +0 -129
  174. package/docs/WELCOME-OPENER-PLAN.md +0 -106
  175. package/docs/adoption-baseline-2026-07-31.md +0 -84
  176. package/docs/architecture/bmad-integration-epic.md +0 -271
  177. package/docs/architecture/bmad-integration-review.md +0 -86
  178. package/docs/architecture/bmad-integration-validation.md +0 -249
  179. package/docs/architecture/bmad-loki-voice-agent-council-analysis.md +0 -61
  180. package/docs/auto-claude-comparison.md +0 -250
  181. package/docs/bug-fixes/agent-01-cli-fixes.md +0 -101
  182. package/docs/bug-fixes/agent-02-purplelab-fixes.md +0 -88
  183. package/docs/bug-fixes/agent-03-dashboard-fixes.md +0 -119
  184. package/docs/bug-fixes/agent-04-memory-fixes.md +0 -105
  185. package/docs/bug-fixes/agent-05-provider-fixes.md +0 -86
  186. package/docs/bug-fixes/agent-06-integration-fixes.md +0 -101
  187. package/docs/bug-fixes/agent-07-dash-run-fixes.md +0 -101
  188. package/docs/bug-fixes/agent-08-docker-fixes.md +0 -164
  189. package/docs/bug-fixes/agent-09-e2e-build-fixes.md +0 -69
  190. package/docs/bug-fixes/agent-10-e2e-fullstack-fixes.md +0 -102
  191. package/docs/bug-fixes/agent-11-e2e-session-fixes.md +0 -70
  192. package/docs/bug-fixes/agent-12-scenario-fixes.md +0 -120
  193. package/docs/bug-fixes/agent-13-enterprise-fixes.md +0 -143
  194. package/docs/bug-fixes/agent-14-uat-newuser-fixes.md +0 -88
  195. package/docs/bug-fixes/agent-15-uat-poweruser-fixes.md +0 -132
  196. package/docs/bug-fixes/agent-19-code-review.md +0 -316
  197. package/docs/bug-fixes/agent-20-architecture-review.md +0 -331
  198. package/docs/competitive/bolt-new-analysis.md +0 -579
  199. package/docs/competitive/emergence-others-analysis.md +0 -605
  200. package/docs/competitive/replit-lovable-analysis.md +0 -622
  201. package/docs/dashboard-guide.md +0 -487
  202. package/docs/enterprise/migration.md +0 -265
  203. package/docs/history/one-run-audit.md +0 -304
  204. package/docs/plans/FORGE-AUTONOMOUS-QUEUE.md +0 -312
  205. package/docs/plans/ULTRAPLAN-FORGE-BAAS.md +0 -612
  206. package/docs/plans/UT2-6-LSP-DIAGNOSTIC-BROADCAST.md +0 -394
  207. package/docs/prd-purple-lab-ide.md +0 -152
  208. package/docs/prd-purple-lab-platform-v2.md +0 -223
  209. package/docs/prd-purple-lab-platform.md +0 -319
  210. package/docs/retrospectives/v7.5.15-fleet-postmortem.md +0 -325
  211. package/docs/retrospectives/v7.5.15-honesty-audit.md +0 -136
  212. package/docs/retrospectives/v7.5.15-llm-failure-modes.md +0 -49
  213. package/docs/show-hn-post.md +0 -46
  214. package/docs/test-scenarios/enterprise-scenarios.md +0 -732
  215. package/docs/thick2thin.md +0 -173
@@ -1,144 +0,0 @@
1
- # FEAT-PRDREUSE-DOCKER-PLAN
2
-
3
- Implementation plan for the PRD-reuse + Docker feature batch. Anchored to verified file:line.
4
- Designed for 4-5 parallel dev agents with zero file overlap. Founder scope locks:
5
- - Docker dashboard: publish on a HOST PORT and AUTO-OPEN (like local loki start); show BOTH local and docker runs.
6
- - Image cleanup: after pull, prune ONLY dangling/old asklokesh/loki-mode images NOT in use by a running container.
7
- - loki stop: ALSO stops/removes the loki-mode docker container for this project (tracked via .loki docker state).
8
-
9
- ## Context: wave-4 uncommitted edits (build on top, do NOT revert)
10
- Uncommitted W4 work in: autonomy/run.sh, autonomy/sandbox.sh, autonomy/prd-checklist.sh,
11
- autonomy/spec-interrogation.sh, dashboard/migration_engine.py, dashboard/server.py,
12
- loki-ts/src/council/voter_agents.ts, loki-ts/src/runner/build_prompt.ts, loki-ts/src/runner/council.ts.
13
- Relevant: build_prompt.ts buildPromptForRunner now passes ctx.prdPath (a PATH). PRD-reuse Bun work depends
14
- on this and must NOT touch build_prompt.ts.
15
-
16
- ## Existing scaffolding (EXTEND, not duplicate)
17
- Bash route already implements generated-PRD reuse for the no-file case:
18
- - .loki/generated-prd.md is the canonical generated-PRD path, byte-locked for parity (run.sh ANALYSIS_INSTRUCTION,
19
- build_prompt.ts:208, resume lines).
20
- - decide_generated_prd_action() (run.sh:4892) returns reuse | update | generate | user_owned.
21
- - persist_prd_signature_if_present() (run.sh:4983) writes .loki/state/prd-signature.json.
22
- - run_autonomous() (run.sh:~13824) auto-detect block handles the empty prd_path case only.
23
- - Bun route: runAutonomous (autonomous.ts:230) -> makeContext (autonomous.ts:641) sets ctx.prdPath = opts.prdPath. No reuse/persist.
24
-
25
- Docker route already has host-aggregating dashboard:
26
- - cmd_docker (autonomy/loki:~28748) -> docker-run.sh helpers.
27
- - _loki_docker_register_host running/stopped brackets the blocking run; registers $(pwd) in ~/.loki/dashboard/projects.json.
28
- - Dashboard /api/projects (server.py:~2623) aggregates local + docker; pid=None reads bind-mounted .loki/session.json.
29
- - Dashboard Stop for docker works via STOP file (server.py:~2970).
30
- - cmd_dashboard_start (autonomy/loki:~4038) + cmd_dashboard_open (~3982) are standalone host dashboard entries.
31
-
32
- ## Design decision locks
33
- LOCK 1: Canonical PRD path = .loki/generated-prd.md (do NOT invent .loki/prd/current.md). Persist user content INTO it;
34
- record provenance in .loki/state/prd-signature.json via a new `source` field.
35
- LOCK 2: User PRDs resolve to reuse/user_owned, NEVER update. Stamp source:"user" at persist; short-circuit
36
- decide_generated_prd_action to user_owned when source=user (except --fresh-prd). Signature-diff `update` stays scoped to source=generated.
37
- This answers "update only if needed": user PRD = always as-is; generated PRD = existing signature logic.
38
- LOCK 3: DOCKER-DASH uses the HOST dashboard, not the published container port. Container mounts only workspace; an
39
- in-container dashboard sees ONE project and cannot satisfy "shows BOTH." Host dashboard already aggregates both.
40
- Local loki start runs the dashboard on host port 57374 + auto-opens (run.sh:~10081-10099), so host dashboard IS "like local loki start."
41
- LOCK 4: Ownership deconflicted by FILE with an interface contract (matrix below).
42
-
43
- ## FEATURE 1 - FEAT-PRD-REUSE
44
- Semantics (both routes identical):
45
- | Run | File arg? | Persisted PRD? | Behavior |
46
- | 1st | yes | no | use file; persist to .loki/generated-prd.md, source=user |
47
- | 1st | no | no | codebase-analysis generates .loki/generated-prd.md, source=generated (existing) |
48
- | 2nd+ | no | yes | continue from persisted PRD (reuse; generated may update on drift, user never) |
49
- | 2nd+ | yes | yes | new file overwrites .loki/generated-prd.md, source reset to user (brownfield) |
50
-
51
- Bash (Agent C, autonomy/run.sh ONLY):
52
- - New persistence branch for explicit user PRD: when prd_path non-empty and not already .loki/generated-prd.md:
53
- mkdir -p .loki .loki/state; atomic copy prd_path -> .loki/generated-prd.md; write prd-signature.json with
54
- source:"user", prd_sha (reuse _loki_prd_file_hash run.sh:4869), generated_at, signature (compute_codebase_signature),
55
- origin_path; repoint prd_path=".loki/generated-prd.md"; export GENERATED_PRD_ACTION="user_owned".
56
- - Extend decide_generated_prd_action (4892): read source from prd-signature.json. Precedence:
57
- --fresh-prd/LOKI_PRD_REGEN -> generate > source=user -> user_owned > existing generated logic.
58
-
59
- Bun (Agent D, loki-ts/src/runner/autonomous.ts + NEW loki-ts/src/runner/prd_reuse.ts; NOT build_prompt.ts):
60
- - New helper resolvePrdForRun(opts) called at top of runAutonomous (autonomous.ts:233 before makeContext). Mirrors 1a/1b:
61
- user file -> copy + persist source:user -> return generated path; empty + generated exists -> decideGeneratedPrdAction
62
- TS port -> return generated path for reuse/update/user_owned, undefined for generate; empty + none -> undefined.
63
- Set resolved path onto opts.prdPath before makeContext (autonomous.ts:655). No build_prompt.ts edit.
64
- - Parity: TS prd-signature.json schema + decideGeneratedPrdAction must match bash exactly.
65
-
66
- .loki state additions: .loki/generated-prd.md also holds persisted user PRD. prd-signature.json adds
67
- source ("user"|"generated"), origin_path (when source=user).
68
-
69
- AC: AC1 user file persists byte-equal + source:user. AC2 no-arg rerun reuses, no codebase analysis. AC3 new file
70
- overwrites, source stays user, origin_path updates. AC4 no-arg first run still generates source:generated. AC5
71
- --fresh-prd re-analyzes -> source:generated. AC6 bash/Bun identical source+action (parity test). AC7 no-arg rerun
72
- after user PRD never enters GENERATED_PRD_UPDATE_MODE even if codebase changed.
73
-
74
- ## FEATURE 2 - FEAT-DOCKER-DASH (host dashboard auto-open)
75
- Architecture (LOCK 3): host dashboard, auto-opened.
76
- Agent A (autonomy/loki, inside cmd_docker, start path): between _loki_docker_register_host running and the blocking run:
77
- 1. Start/reuse host dashboard via cmd_dashboard_start (idempotent). Port: DASHBOARD_DEFAULT_PORT 57374 with fallback
78
- (Agent B loki_docker_pick_host_port). 2. Auto-open gated like run.sh:~10088 ([ -t 1 ] && not background && LOKI_NO_AUTO_OPEN!=1)
79
- via cmd_dashboard_open. 3. Container stays dashboard-OFF (docker-run.sh LOKI_DASHBOARD=false), no container port publish.
80
- Agent B (autonomy/docker-run.sh): loki_docker_pick_host_port - probe 57374, increment to free port if bound, echo chosen port.
81
- server.py (Agent E only IF a gap appears): /api/projects already aggregates docker, Stop already handles docker. Default: no change.
82
-
83
- AC: AC8 loki docker start in TTY starts host dashboard + opens browser. AC9 dashboard lists docker run alongside local.
84
- AC10 LOKI_NO_AUTO_OPEN=1/non-TTY/--bg no browser. AC11 second docker start reuses dashboard, both runs listed.
85
-
86
- ## FEATURE 3 - FEAT-DOCKER-PRUNE (scoped image cleanup after pull)
87
- No explicit docker pull today (run auto-pulls only if absent). PRUNE needs explicit pull.
88
- Agent B (docker-run.sh helpers) + Agent A (call site in cmd_docker): loki_docker_pull_and_prune, called from cmd_docker before run (start path):
89
- 1. docker pull $LOKI_DOCKER_IMAGE (default asklokesh/loki-mode:latest), capture image ID.
90
- 2. In-use set: docker ps --format '{{.Image}} {{.ImageID}}'.
91
- 3. Enumerate ONLY asklokesh/loki-mode: docker images --filter 'reference=asklokesh/loki-mode' --format '{{.ID}} ...'
92
- + dangling: --filter 'reference=asklokesh/loki-mode' --filter 'dangling=true' -q.
93
- 4. docker rmi each ID NOT the just-pulled :latest AND NOT in-use (best-effort).
94
- 5. NEVER docker image prune -a. Scope strictly reference=asklokesh/loki-mode.
95
- 6. Honest output: reclaimed count/bytes or "nothing to reclaim."
96
- Gate: LOKI_DOCKER_PRUNE=${LOKI_DOCKER_PRUNE:-1} (default on, =0 opt-out; =0 also skips explicit pull).
97
-
98
- AC: AC12 old asklokesh/loki-mode IDs removed, :latest remains. AC13 in-use image never removed. AC14 non-loki-mode
99
- image never touched (decoy survives). AC15 LOKI_DOCKER_PRUNE=0 skips; honest output.
100
-
101
- ## FEATURE 4 - FIX-DOCKER-STOP (loki stop reaps the container)
102
- Repro: container loki-<sha12> Up but loki stop says "No active session." cmd_stop (autonomy/loki:~2242) only checks .loki.
103
- Container name deterministic: loki-<sha12 of workspace> (docker-run.sh:~204-214).
104
- Agent A (autonomy/loki write+read) + Agent B (docker-run.sh helpers):
105
- Write: before blocking run write .loki/docker/run.json {container, image, project_dir, started_at}; clear after.
106
- Helpers loki_docker_write_runstate / loki_docker_clear_runstate.
107
- Read/reap (cmd_stop folder-scoped default, before "No active session"):
108
- 1. Read .loki/docker/run.json -> container; fallback recompute loki-<sha12 of $(pwd)> (loki_docker_container_name).
109
- 2. If docker ps -q -f name=^${container}$ non-empty -> docker stop then docker rm (best-effort; --rm may auto-remove).
110
- 3. Remove run.json. 4. Report reap, no "No active session" when docker run Up.
111
- 5. loki stop --all: also docker ps -q --filter ancestor=asklokesh/loki-mode -> stop/rm all (machine-wide, parity with --all PID).
112
- Folder-scoped default stays folder-scoped. Preserves v7.7.30-34 stop-scoping.
113
-
114
- .loki state additions: .loki/docker/run.json (NEW) {container, image, project_dir, started_at}.
115
-
116
- AC: AC16 docker start then stop (same folder) stops+removes container, names it, no "No active session". AC17 run.json
117
- deleted -> still reaps via recomputed name. AC18 stop in folder X does not stop docker run in folder Y. AC19 stop --all
118
- stops every loki-mode container. AC20 no docker run + no local session -> existing "No active session" (no regression).
119
-
120
- ## FILE-OWNERSHIP MATRIX (zero overlap)
121
- - Agent A (Docker orchestration): autonomy/loki ONLY. cmd_docker (dashboard start/open F2, pull+prune F3, write/clear
122
- run.json F4), cmd_stop (docker reconcile+reap F4). Calls Agent-B helpers by name; uses cmd_dashboard_start/open.
123
- - Agent B (Docker helpers): autonomy/docker-run.sh ONLY. loki_docker_pick_host_port, loki_docker_pull_and_prune,
124
- loki_docker_write_runstate, loki_docker_clear_runstate, loki_docker_container_name. No call-site edits in autonomy/loki.
125
- - Agent C (PRD-reuse bash): autonomy/run.sh ONLY. User-PRD persistence in run_autonomous, extend decide_generated_prd_action.
126
- - Agent D (PRD-reuse Bun): loki-ts/src/runner/autonomous.ts + NEW loki-ts/src/runner/prd_reuse.ts. MUST NOT edit build_prompt.ts.
127
- - Agent E (Tests + server.py iff needed): tests/** new files, loki-ts/tests/** new files; server.py only if a real DASH gap appears.
128
- Do not edit existing W4-touched test files.
129
-
130
- A<->B: disjoint files, share function-boundary contract. C<->A: PRD-reuse-bash entirely in run_autonomous; cmd_start
131
- already passes file arg to run.sh. D<->W4: D sets ctx.prdPath upstream; build_prompt.ts read-only for D.
132
-
133
- Sequencing: B, C, D independent -> parallel immediately. A depends on B helper signatures (contract fixed up-front, A can
134
- start against signatures). E writes tests against contracts in parallel, finalizes after A-D land.
135
-
136
- ## RISKS
137
- R1 (DASH architecture): host dashboard satisfies host-port + auto-open + shows-both; container-port publish breaks shows-both. Host chosen (LOCK 3).
138
- R2 (host-port conflict): cmd_dashboard_start idempotent; loki_docker_pick_host_port fallback. Container-port publish was already disabled for 57374 collision.
139
- R3 (PRD update-only-if-needed): LOCK 2 source field. source=user always reuse/user_owned; source=generated existing signature logic. Hand-edited persisted PRD -> still user_owned.
140
- R4 (prune over-aggression): triple-scoped (reference filter + exclude :latest ID + exclude in-use). AC14 decoy survives. rmi best-effort.
141
- R5 (pull latency): pull-always v1, gated by LOKI_DOCKER_PRUNE. OQ: pull-always vs only-on-digest-change; recommend pull-always v1.
142
- R6 (--rm + stop): docker stop triggers auto-removal; docker rm best-effort (already-gone = success).
143
- OQ1: run.json write BEFORE blocking run, clear AFTER. Deterministic-name fallback covers the window.
144
- OQ2: confirm Bun runAutonomous reached with opts.prdPath set from same arg as bash; parity test guards decision logic regardless.
@@ -1,254 +0,0 @@
1
- # Gate failure triage: exact-SHA classification
2
-
3
- Ordered by the steer: reproduce locally against exact HEAD, classify each
4
- failure as environment / baseline / candidate regression, evidence every claim
5
- with a command and its output. Nothing here was pushed.
6
-
7
- | Field | Value |
8
- |---|---|
9
- | HEAD at triage | `d230a3b2` (the steer named `09138e26`; that SHA is not in this worktree) |
10
- | baseline compared | `dda8beec` = origin/main |
11
- | held commits | `22199024`, `94315f35`, `d230a3b2`, plus `94f7639a` from this triage |
12
- | pushed | **nothing** |
13
-
14
- ## Classification
15
-
16
- | Failure | Class | Evidence |
17
- |---|---|---|
18
- | `test-onboard-command` (6 of 9) | **BASELINE**, now FIXED | `autonomy/loki` byte-identical to origin/main; `git diff --name-only dda8beec..HEAD` returns zero matches for that path |
19
- | `test-model-override` | **BASELINE**, 1 of 66, still open | identical failure at `dda8beec` and at HEAD: `Results: 65 passed, 1 failed (of 66)`, `EXIT=1` |
20
- | `bun run typecheck` | **ENVIRONMENT** | `tsc` not installed locally; unchanged |
21
-
22
- ## The onboard defect
23
-
24
- `loki onboard --stdout` exited **141** and wrote **0 bytes** on this repo,
25
- while passing on small fixtures.
26
-
27
- ```
28
- EXIT=141
29
- STDOUT bytes: 0
30
- STDERR bytes: 242
31
- ```
32
-
33
- 141 = 128+13 = SIGPIPE. `cmd_onboard`'s find fallback ends
34
- `| sed | sort | head -200`. Under the file's `set -euo pipefail` (line 22),
35
- `head` exits after 200 lines; `sort` -- which must consume ALL input before it
36
- emits anything -- then takes SIGPIPE, the pipeline returns 141, and `-e` aborts
37
- before a byte is written. The sibling `git ls-files` branch two lines above was
38
- already guarded with `|| true`. The find branch never was.
39
-
40
- `sort`, not `find`, is the process that dies. That distinction sets the test
41
- size: see below.
42
-
43
- ### Why no existing test caught it
44
-
45
- **1. Every fixture was too small.** The residual output has to exceed the 64KB
46
- pipe buffer before the signal lands. Measured:
47
-
48
- | Fixture | Result vs unfixed code |
49
- |---|---|
50
- | 250 files | **passes** -- ~50 lines left after the cut, fits the buffer |
51
- | 3000 files | **exit 141**, deterministic |
52
-
53
- A 250-file regression test would have been worthless. I wrote one first,
54
- confirmed it passed against the pre-fix binary, and resized it.
55
-
56
- **2. This worktree never reached the guarded branch.** The check was
57
- `[ -d "$target_path/.git" ]`, and in a git **worktree** `.git` is a pointer
58
- **file**, not a directory:
59
-
60
- ```
61
- -rw-r--r-- 1 lokesh staff 83 Jul 31 19:25 .git
62
- gitdir: /Users/lokesh/git/lokimode-anthropic/.git/worktrees/pre-push-scoped-pytest
63
- ```
64
-
65
- So every worktree silently fell through to the find path. Proven by trace:
66
-
67
- ```
68
- PRE-FIX ++ find ... -maxdepth 4
69
- FIXED ++ git ls-files
70
- ```
71
-
72
- ### The fix
73
-
74
- `-e` instead of `-d`, and `|| true` matching the sibling branch. Two lines.
75
-
76
- ### Two sibling sites, quieter symptom
77
-
78
- `cmd_explain` and `_docs_scan_project` carry the same pipeline at `head -500`.
79
- Fixed alongside -- patching only the path the failure named would leave the
80
- siblings broken.
81
-
82
- They fail *differently*, which is why nothing ever caught them: both assign via
83
- `local x=$(...)`, and `local` resets `$?`, swallowing the 141. Demonstrated:
84
-
85
- ```
86
- $ f() { local x=$(false | head -1); echo "rc=$?"; }
87
- rc=0
88
- ```
89
-
90
- So they **silently truncate** their file tree instead of aborting. Same root
91
- cause, no visible symptom.
92
-
93
- ### Sweep
94
-
95
- Three unguarded `sort | head -N` sites existed; zero remain. The sweep pattern
96
- is not vacuous -- it matches 3 in the pre-fix file and 0 now.
97
-
98
- The other two `-d .../.git` checks in the file (`loki:11113`, `loki:13473`) are
99
- CORRECT as `-d`: one detects a clone (a worktree is not one), the other guards
100
- `git init` on a fresh demo dir. Left alone.
101
-
102
- ## Verification
103
-
104
- | Check | Before | After |
105
- |---|---|---|
106
- | `test-onboard-command.sh` | 3/9 | **10/10** |
107
- | new Test 10 vs pre-fix binary | **FAIL** (exit 141) | PASS |
108
- | `test-onboard-json-injection-wave10.sh` | 2/2 | 2/2 |
109
- | `test-contradiction-detection.sh` | 19/19 | 19/19 |
110
- | `bash -n autonomy/loki` | OK | OK |
111
-
112
- Test 10 was mutation-tested against `dda8beec`: it fails with the exact
113
- diagnostic `exit 141 (SIGPIPE)` on the old code and passes on the new. It also
114
- carries a vacuity guard rejecting exit 0 with under 100 bytes of output -- the
115
- precise shape of the bug, since the abort produced exit 141 *and* silence.
116
-
117
- ## Correction: I called test-model-override a non-failure before it finished
118
-
119
- An earlier revision of THIS FILE classified `test-model-override` as "NOT A
120
- FAILURE -- slow suite, mis-measured". That was wrong, and it was wrong in the
121
- worst available way: I wrote the classification while the run was still
122
- executing, from a partial log that showed 50 PASS and no failures yet.
123
-
124
- The completed run:
125
-
126
- ```
127
- FAIL: architect no-cap mismatch: estimator='Opus' runner-dispatch='opus'
128
- runner-tier='fable' (expected Opus,Sonnet / opus / fable)
129
- Results: 65 passed, 1 failed (of 66)
130
- EXIT=1
131
- ```
132
-
133
- The slowness was real -- a 224-cell parity matrix, each cell spawning a
134
- `python3` that imports the FastAPI dashboard at ~0.46s -- and it was NOT the
135
- explanation for the failure. Both things were true and I reported only the
136
- convenient one.
137
-
138
- The rule this violates is one already written down in this repo: an absent
139
- measurement is not a measurement. A log with no FAIL line yet is not a log with
140
- no failures; it is an unfinished log. I should have blocked on the EXIT marker
141
- before classifying, exactly as I did for the onboard suite.
142
-
143
- ### The actual failure
144
-
145
- `tests/test-model-override.sh:827`. A three-way coherence assertion; two of the
146
- three legs are correct:
147
-
148
- | Leg | Expected | Actual |
149
- |---|---|---|
150
- | runner dispatch | `opus` | `opus` -- correct |
151
- | runner tier (pre-collapse) | `fable` | `fable` -- correct |
152
- | estimator quote | `Opus,Sonnet` | `Opus` -- **mismatch** |
153
-
154
- So the runtime routing is right and only the cost QUOTE disagrees: the
155
- estimator names one model where the run actually uses two. Per the test's own
156
- comment (line 800), this is the known "estimator needs the sonnet5-default
157
- update" case -- iter-1 collapses fable to opus, later iterations run the
158
- development tier which defaults to sonnet since v7.104.0, so an honest quote
159
- must name both.
160
-
161
- It under-quotes cost. It does not mis-route a model.
162
-
163
- ### Root cause: the fixture stopped producing enough iterations
164
-
165
- The estimator is CORRECT. The expectation is only reachable when the estimate
166
- spans more than one iteration, and the suite's fixture no longer does.
167
-
168
- `autonomy/loki:18342` prices iteration 0 as Opus (the fable architect pass
169
- collapsing to opus), and every LATER iteration through
170
- `_priced_model_for(_dispatched_model)`, which defaults to Sonnet since
171
- v7.104.0. So `Opus,Sonnet` requires **iterations >= 2**.
172
-
173
- Measured on the suite's own fixture (`# PRD\nBuild a small todo API with one
174
- endpoint.`, byte-identical to v7.104.0):
175
-
176
- | Binary | tier | estimated iterations | nonzero models |
177
- |---|---|---|---|
178
- | `766219ac` (v7.104.0, where this was written and passed 66/0) | simple | **4** | `Opus,Sonnet` |
179
- | HEAD | simple | **1** | `Opus` |
180
-
181
- The complexity TIER is unchanged (`simple` in both). Only the iteration count
182
- for that tier fell, 4 -> 1, and with a single iteration the loop never reaches
183
- the branch where Sonnet appears.
184
-
185
- Confirmed causal by holding the binary fixed and enlarging the input: a 24-
186
- feature PRD at HEAD estimates 4 iterations and returns exactly `Opus,Sonnet`
187
- (`{"Fable":0,"Opus":1,"Sonnet":3,"Haiku":0}`). Same code, more iterations,
188
- expected answer.
189
-
190
- So the assertion is a **stale coupling**: it encodes "a simple PRD takes
191
- several iterations", which stopped being true. The v7.104.0 commit message
192
- claims "locked by tests/test-model-override.sh (66/0)" -- that lock silently
193
- came undone when the iteration estimate for simple PRDs changed.
194
-
195
- ### Classification: BASELINE
196
-
197
- Run against `dda8beec`'s `autonomy/loki` (my onboard fix reverted), the failure
198
- is **identical**:
199
-
200
- ```
201
- FAIL: architect no-cap mismatch: estimator='Opus' ...
202
- Results: 65 passed, 1 failed (of 66)
203
- EXIT=1
204
- ```
205
-
206
- Not caused by any held commit. My `autonomy/loki` diff touches only three
207
- tree-building sites and no pricing or routing code.
208
-
209
- ### Not fixed here, deliberately
210
-
211
- Two candidate fixes, and choosing between them is a product call I should not
212
- make unilaterally:
213
-
214
- 1. **Enlarge the fixture** so a multi-iteration estimate is exercised. Restores
215
- the assertion's original intent (verify the architect collapse across a
216
- real multi-iteration run) and keeps its coverage.
217
- 2. **Weaken the assertion** to accept `Opus`. Cheaper, and wrong: it would
218
- stop testing the later-iteration Sonnet attribution entirely.
219
-
220
- (1) is almost certainly right, but it changes what the test measures, and the
221
- prior instruction excluded runtime changes without an evidenced deterministic
222
- requirement. The evidence is now here; the decision is not mine.
223
-
224
- `docs/LOOP-CANDIDATE-PROPOSAL-v1.md` states the onboard defect "cannot be
225
- addressed by any of [the six cheaper surfaces]" because it is a bash command
226
- that never calls a model. That reasoning was right, and the conclusion drawn
227
- from it was too weak: it is not a model-loop problem, it is a **two-line shell
228
- bug**, and the correct action was to fix it rather than to route around it.
229
-
230
- It also claimed the failure needed "a runtime fix to `autonomy/loki`" of
231
- unknown size. Measured: 28 lines changed across three sites, all mechanical.
232
-
233
- ## Gate status
234
-
235
- Still not green, and this triage does not make it so.
236
-
237
- - `test-onboard-command`: **RESOLVED** (3/9 -> 10/10)
238
- - `test-model-override`: **1 of 66 still failing, BASELINE** -- a stale test
239
- coupling, not an estimator defect. Root-caused (fixture no longer produces a
240
- multi-iteration estimate); two candidate fixes named, neither applied.
241
- - `bun run typecheck`: **unchanged**, `tsc` still absent
242
-
243
- Two items remain, not one. Both are pre-existing at `dda8beec`; neither was
244
- introduced by a held commit.
245
-
246
- | Item | Needs |
247
- |---|---|
248
- | `bun run typecheck` | install the TS toolchain -- the environment fix already named |
249
- | `test-model-override` | a decision between enlarging the fixture and weakening the assertion |
250
-
251
- Neither is unblocked by the other, so "install tsc" was never sufficient on its
252
- own. That was an error in the earlier proposal, which named a single
253
- gate-closing action while a second real failure sat unclassified behind a
254
- measurement I had cut short.