vibe-coding-master 0.5.0 → 0.5.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.
- package/README.md +1 -1
- package/package.json +1 -2
- package/scripts/verify-package.mjs +0 -1
- package/docs/ARCHITECTURE.md +0 -124
- package/docs/TESTING.md +0 -130
- package/docs/cc-best-practices.md +0 -2465
- package/docs/known-issues.md +0 -156
- package/docs/product-design.md +0 -891
- package/docs/v0.5-custom-workflow-plan.md +0 -788
- package/docs/vcm-cc-best-practices.md +0 -528
package/docs/known-issues.md
DELETED
|
@@ -1,156 +0,0 @@
|
|
|
1
|
-
# Known Issues
|
|
2
|
-
|
|
3
|
-
Durable open issues and accepted limitations for VibeCodingMaster (VCM). This is
|
|
4
|
-
a current open-issue snapshot, not a task log. Each entry is architect-owned and
|
|
5
|
-
should be removed or rewritten once the underlying gap is resolved.
|
|
6
|
-
|
|
7
|
-
Issues are grouped by category. Severity reflects architectural/correctness/
|
|
8
|
-
security risk, not delivery priority.
|
|
9
|
-
|
|
10
|
-
---
|
|
11
|
-
|
|
12
|
-
## Security & Exposure
|
|
13
|
-
|
|
14
|
-
### KI-001 — Unauthenticated HTTP API and `/ws` terminal surface
|
|
15
|
-
|
|
16
|
-
- **Status**: Open (accepted limitation by design; needs explicit user/PM decision before any non-loopback use).
|
|
17
|
-
- **Category**: Product / security.
|
|
18
|
-
- **Affected modules / surfaces**: `src/backend/server.ts` (no auth hook, no CORS/origin policy), all `src/backend/api/*` routes, `src/backend/ws/terminal-ws.ts`, `src/main.ts` (`--host=` flag).
|
|
19
|
-
- **Current gap**: The backend registers every `/api/*` route and the `/ws/terminal/:id` WebSocket with no authentication, authorization, or origin/CSRF check. These surfaces can spawn processes (`runtime.createSession`), run `git`, read/write the filesystem and `vcmDataDir`, manage gateway tokens, and write raw bytes directly into role PTYs (`runtime.write` via the terminal WebSocket). The default bind is `127.0.0.1`, but `--host=` lets a user bind to `0.0.0.0`/LAN, and the WS upgrade path performs no `Origin` validation (cross-site WebSocket hijacking is possible if a browser session is open).
|
|
20
|
-
- **Impact**: Binding to any non-loopback interface exposes a powerful, fully unauthenticated remote-code-execution-equivalent surface to the local network. Even on loopback, the lack of `Origin` checks means a malicious web page in the user's browser could drive the API/terminal.
|
|
21
|
-
- **Mitigation / workaround**: Keep the default `127.0.0.1` bind; do not pass `--host=` with a routable address; do not run VCM on shared/untrusted machines.
|
|
22
|
-
- **Resolution condition**: Either (a) document and enforce loopback-only as a hard product constraint, or (b) add an auth/token + `Origin` allowlist before allowing non-loopback binds. Requires a product decision (route through the full code-change flow if a fix is chosen).
|
|
23
|
-
- **Related**: KI-002, KI-007.
|
|
24
|
-
|
|
25
|
-
### KI-002 — Gateway bot token and app secret stored in plaintext at rest
|
|
26
|
-
|
|
27
|
-
- **Status**: Open (accepted limitation).
|
|
28
|
-
- **Category**: Product / security.
|
|
29
|
-
- **Affected modules / surfaces**: `src/backend/gateway/gateway-settings-service.ts` (`writeJsonAtomic(settingsPath, cachedSettings)`), gateway channel credentials (`binding.token`, `binding.appSecret`).
|
|
30
|
-
- **Current gap**: Gateway channel credentials (Weixin iLink bot token, Lark app secret) are persisted unencrypted as JSON under `vcmDataDir`. Status responses correctly expose only `tokenConfigured`/`appSecretConfigured` booleans, so the leak is at-rest only, not over the status API.
|
|
31
|
-
- **Impact**: Anyone with read access to the user's `vcmDataDir` (backups, sync tools, other local users) can recover live chat-platform bot credentials.
|
|
32
|
-
- **Mitigation / workaround**: Protect `vcmDataDir` filesystem permissions; rotate tokens if the data dir is exposed.
|
|
33
|
-
- **Resolution condition**: Encrypt secrets at rest or delegate to an OS keychain; or formally accept and document the plaintext-at-rest model.
|
|
34
|
-
- **Related**: KI-001.
|
|
35
|
-
|
|
36
|
-
---
|
|
37
|
-
|
|
38
|
-
## Correctness & Robustness
|
|
39
|
-
|
|
40
|
-
### KI-003 — Spawn failures are indistinguishable from real `git` exit code 1
|
|
41
|
-
|
|
42
|
-
- **Status**: Open.
|
|
43
|
-
- **Category**: Product / correctness.
|
|
44
|
-
- **Affected modules / surfaces**: `src/backend/adapters/command-runner.ts` (catch branch returns `{ exitCode: 1, stderr: error.message }`), `src/backend/adapters/git-adapter.ts` (`isIgnored`, `branchExists` treat `exitCode === 1` as a definitive "false").
|
|
45
|
-
- **Current gap**: `command-runner.run` collapses every `execa` failure — including a spawn error such as `git` not being installed/launchable (ENOENT) — into `exitCode: 1`. Several git-adapter methods (`isIgnored`, `branchExists`) interpret `exitCode === 1` as a meaningful negative result ("not ignored" / "branch does not exist"). A missing or unspawnable `git` therefore returns a confident wrong answer instead of surfacing the real failure.
|
|
46
|
-
- **Impact**: Downstream logic (worktree creation, ignore checks, branch existence gating) can silently make wrong decisions when `git` is absent or the spawn fails, masking the root cause and producing confusing secondary errors.
|
|
47
|
-
- **Mitigation / workaround**: Ensure `git` is installed and on `PATH` before use.
|
|
48
|
-
- **Resolution condition**: Distinguish spawn/launch errors from non-zero process exits in `command-runner` (e.g., a sentinel exit code or a typed `spawnFailed` flag) and have git-adapter treat spawn failure as an error rather than a `false` result. Requires a cross-file contract change → route through the full code-change flow.
|
|
49
|
-
- **Related**: none.
|
|
50
|
-
|
|
51
|
-
### KI-010 — Translation queue stuck-head recovery is enqueue-triggered, not continuous
|
|
52
|
-
|
|
53
|
-
- **Status**: Open (accepted limitation; the primary issue #13 case is resolved).
|
|
54
|
-
- **Category**: Product / robustness (operability).
|
|
55
|
-
- **Affected modules / surfaces**: `src/backend/services/translation-worker-service.ts` (`dispatchNext` / `reconcileStuckActiveItem` / `STALE_CONVERSATION_ITEM_MS`), `src/backend/services/translation-service.ts` (`waitForConversationResult` poll loop).
|
|
56
|
-
- **Current gap**: Recovery of a stuck active queue item (whose Translator `Stop`/`StopFailure` hook was lost) runs only when `dispatchNext` is invoked — i.e. when a new item is enqueued or a hook arrives. The request poll loop (`waitForConversationResult` -> `getState`) does not call `dispatchNext`. The primary case (the result already written to disk, hook lost) self-heals immediately on the next enqueue: conversation output lives in a single shared, self-describing `runtime/conversations/result.json`, and the recovery association key is the in-file `batchId` validated all-or-nothing (`conversationResultAvailable` requires the file to exist, parse, have `batchId` equal to the active item's `batchId`, and contain every expected `batchIndex`). The secondary case (Translator session gone with no result written) is only released after the item passes the 90s `STALE_CONVERSATION_ITEM_MS` window *and* a subsequent enqueue occurs; if the stuck head is still younger than 90s when the next translation is requested, that request can still time out once.
|
|
57
|
-
- **Impact**: Low. A narrow window can still produce a single `translation timed out` (HTTP 502) for the "session gone, no result, head <90s old, no further enqueue" case; it self-heals on the next translation attempt after the stale window. No permanent queue block remains, and a backend restart with a pre-existing stuck item recovers immediately (its `updatedAt` is already stale, or the result is on disk).
|
|
58
|
-
- **Mitigation / workaround**: Retry the translation once; the retry's enqueue triggers reconciliation.
|
|
59
|
-
- **Resolution condition**: Add a periodic / poll-driven reconcile (e.g. reconcile on `getState` or a timer) so stuck heads are released without depending on a new enqueue. Requires a code change → route through the full code-change flow if pursued.
|
|
60
|
-
- **Related**: KI-011.
|
|
61
|
-
|
|
62
|
-
### KI-011 — Conversation result cleanup deletes the shared dir without a batchId guard
|
|
63
|
-
|
|
64
|
-
- **Status**: Open (accepted limitation; harm effectively unreachable today).
|
|
65
|
-
- **Category**: Product / robustness (operability).
|
|
66
|
-
- **Affected modules / surfaces**: `src/backend/services/translation-worker-service.ts` (`validateConversationResult` cleanup of the shared `runtime/conversations/` directory holding `result.json`).
|
|
67
|
-
- **Current gap**: Because conversation translation now uses one shared `result.json` (KI-010), cleanup after a consumed result removes the shared `conversations/` directory (the `batchResultPath` dirname) rather than a per-batch directory, and it is not guarded by a `batchId` match against the file actually on disk. In principle a delete could race a newly written `result.json` for a later batch.
|
|
68
|
-
- **Impact**: Negligible in practice. Cleanup fires on the ~500ms consumer poll, far ahead of when a subsequent batch's Translator (LLM latency ≫ 500ms) could write a new `result.json`; and the all-or-nothing in-file `batchId` validation means the worst case is a recoverable dropped result, never a mis-assignment — within the design's accepted "drop over mis-assign" tolerance.
|
|
69
|
-
- **Mitigation / workaround**: None needed; a dropped conversation result self-recovers via re-translate / stale-release.
|
|
70
|
-
- **Resolution condition**: Optional hardening — scope the cleanup to delete only when the on-disk `result.json` `batchId` matches the just-consumed batch (or delete the file, not the directory). Requires a small code change → full code-change flow if pursued.
|
|
71
|
-
- **Related**: KI-010.
|
|
72
|
-
|
|
73
|
-
### KI-004 — Claude transcript project-directory hashing does not match Claude Code's encoding
|
|
74
|
-
|
|
75
|
-
- **Status**: Open.
|
|
76
|
-
- **Category**: Product / correctness (external coupling to Claude Code's on-disk format).
|
|
77
|
-
- **Affected modules / surfaces**: `src/backend/services/claude-transcript-service.ts` (`projectHash`, `projectsTranscriptDir`, `claudeTranscriptPath`, `resolveExistingClaudeTranscriptPath`), translation panel and question/todo extraction that depend on it.
|
|
78
|
-
- **Current gap**: `projectHash` only replaces `[/\s]+` with `-`, which does not reproduce Claude Code's actual project-directory encoding (which also encodes `.` and other path characters). The primary path lookup can therefore miss; correctness currently leans on the fallback full scan `findClaudeTranscriptPathBySessionId`, which picks the most-recently-modified `<sessionId>.jsonl` across all project dirs.
|
|
79
|
-
- **Impact**: If Claude changes its encoding, or two project directories produce a colliding hash / share a session-id filename, transcript resolution can attach to the wrong file or fail to find one, breaking translation feed and question/todo surfacing. The fallback masks the brittleness rather than fixing it.
|
|
80
|
-
- **Mitigation / workaround**: Rely on the `session.transcriptPath` / `claudeSessionId` resolution path; the mtime-sorted fallback usually recovers the right file.
|
|
81
|
-
- **Resolution condition**: Mirror Claude Code's real directory-encoding scheme (or resolve transcript paths via a documented Claude API/contract) instead of an approximate replace. Treat the encoding as an external-contract assumption to re-verify on Claude Code upgrades.
|
|
82
|
-
- **Related**: KI-005.
|
|
83
|
-
|
|
84
|
-
---
|
|
85
|
-
|
|
86
|
-
## Performance & Scalability
|
|
87
|
-
|
|
88
|
-
### KI-005 — Synchronous filesystem I/O and full-file replay on the event loop in `TranscriptTail`
|
|
89
|
-
|
|
90
|
-
- **Status**: Open.
|
|
91
|
-
- **Category**: Product / performance.
|
|
92
|
-
- **Affected modules / surfaces**: `src/backend/services/claude-transcript-service.ts` (`TranscriptTail.start/flush/replayHistory/replaySince`), translation worker/feed consumers.
|
|
93
|
-
- **Current gap**: Transcript tailing uses synchronous `statSync`/`openSync`/`readSync` on every flush and `readFileSync` for replay, all on the main event-loop thread, with a 1s poll timer per subscribed session. Replay (`replayHistory`/`replaySince`) reads the entire JSONL transcript into memory and parses every line synchronously.
|
|
94
|
-
- **Impact**: Long-lived sessions accumulate large transcripts; with multiple concurrent role sessions each tailing + replaying, synchronous reads can stall the event loop and spike memory, degrading API/WS responsiveness.
|
|
95
|
-
- **Mitigation / workaround**: Practical session/transcript sizes are usually small; impact is bounded by transcript length and session count.
|
|
96
|
-
- **Resolution condition**: Move to async/streamed reads, bound replay (cap bytes/lines read), and/or offload tailing; treat as a scalability hardening item.
|
|
97
|
-
- **Related**: KI-004, KI-006.
|
|
98
|
-
|
|
99
|
-
### KI-006 — O(n)-per-chunk terminal replay buffer recomputation
|
|
100
|
-
|
|
101
|
-
- **Status**: Open.
|
|
102
|
-
- **Category**: Product / performance.
|
|
103
|
-
- **Affected modules / surfaces**: `src/backend/runtime/node-pty-runtime.ts` (`appendTerminalReplay`, `tailTerminalReplay`, invoked on every `child.onData`).
|
|
104
|
-
- **Current gap**: On every PTY output chunk, `appendTerminalReplay` concatenates the existing buffer with the new data and re-tails to the 2 MB cap, and `tailTerminalReplay` recomputes `Buffer.byteLength` inside a trimming loop. This is O(buffer size) per chunk regardless of chunk size.
|
|
105
|
-
- **Impact**: Chatty/high-throughput Claude sessions trigger repeated multi-MB string copies and byte-length scans, a measurable CPU hotspot under sustained output.
|
|
106
|
-
- **Mitigation / workaround**: Output bursts are typically short; the 2 MB cap bounds memory.
|
|
107
|
-
- **Resolution condition**: Use a chunked/ring buffer or amortized trimming so per-chunk cost is proportional to the new data, not the whole buffer.
|
|
108
|
-
- **Related**: KI-005.
|
|
109
|
-
|
|
110
|
-
---
|
|
111
|
-
|
|
112
|
-
## Maintainability
|
|
113
|
-
|
|
114
|
-
### KI-007 — Non-matching `/ws` upgrade requests leak the socket
|
|
115
|
-
|
|
116
|
-
- **Status**: Open.
|
|
117
|
-
- **Category**: Product / robustness.
|
|
118
|
-
- **Affected modules / surfaces**: `src/backend/ws/terminal-ws.ts` (`app.server.on("upgrade", ...)`).
|
|
119
|
-
- **Current gap**: When an upgrade request's path does not match `/ws/terminal/:id`, the handler `return`s without calling `socket.destroy()` (or writing a `400`/`426` response). The half-upgraded socket is left hanging until a timeout. There is also no `Origin` check at the upgrade boundary (see KI-001).
|
|
120
|
-
- **Impact**: Low — stray/unrelated `/ws` upgrade attempts hold a connection open instead of being cleanly rejected; minor resource pressure, no correct rejection signal to the client.
|
|
121
|
-
- **Mitigation / workaround**: Only the intended `/ws/terminal/:id` path is used by the shipped frontend.
|
|
122
|
-
- **Resolution condition**: Destroy (or explicitly reject) the socket on non-matching upgrade paths and add an `Origin` allowlist.
|
|
123
|
-
- **Related**: KI-001.
|
|
124
|
-
|
|
125
|
-
### KI-008 — Oversized service modules concentrate orchestration complexity
|
|
126
|
-
|
|
127
|
-
- **Status**: Open (maintainability hazard, not a defect).
|
|
128
|
-
- **Category**: Product / maintainability.
|
|
129
|
-
- **Affected modules / surfaces**: `src/backend/services/harness-service.ts` (~2160 lines), `translation-worker-service.ts` (~2155), `translation-service.ts` (~1721), `session-service.ts` (~1682), `gate-review-service.ts` (~980), `claude-hook-service.ts` (~769).
|
|
130
|
-
- **Current gap**: Several service files greatly exceed comfortable single-file cohesion and bundle orchestration, retry/error handling, and side-effect coordination together. This makes the intended `api -> services -> (runtime | adapters | gateway | templates)` boundary harder to reason about and raises regression risk on edits.
|
|
131
|
-
- **Impact**: Higher change cost and review/regression risk in the highest-traffic backend logic; harder to localize behavior and test seams.
|
|
132
|
-
- **Mitigation / workaround**: Existing unit tests cover many of these services; keep edits narrowly scoped.
|
|
133
|
-
- **Resolution condition**: Incrementally extract cohesive sub-modules (with explicit cross-file contracts captured in module `ARCHITECTURE.md`) when these areas are next changed. No standalone refactor mandated.
|
|
134
|
-
- **Related**: none.
|
|
135
|
-
|
|
136
|
-
### KI-009 — Error responses surface raw subprocess stderr and runtime diagnostics to clients
|
|
137
|
-
|
|
138
|
-
- **Status**: Open (low risk on loopback; compounds with KI-001).
|
|
139
|
-
- **Category**: Product / information exposure.
|
|
140
|
-
- **Affected modules / surfaces**: `src/backend/server.ts` global error handler (returns `hint` and `runtime` diagnostics), `src/backend/adapters/git-adapter.ts` (sets `hint: result.stderr`).
|
|
141
|
-
- **Current gap**: API error payloads include `hint` (often raw `git` stderr) and `diagnosticsService.getErrorRuntimeInfo()`. On loopback this is acceptable developer feedback, but it leaks local paths/environment detail to any caller — which matters if combined with a non-loopback bind (KI-001).
|
|
142
|
-
- **Impact**: Low in the default configuration; an information-exposure amplifier when the API is exposed beyond loopback.
|
|
143
|
-
- **Mitigation / workaround**: Keep the loopback bind (KI-001).
|
|
144
|
-
- **Resolution condition**: Gate verbose `hint`/`runtime` detail behind a dev flag, or sanitize before returning, if non-loopback exposure is ever supported.
|
|
145
|
-
- **Related**: KI-001, KI-007.
|
|
146
|
-
|
|
147
|
-
### KI-012 — `flowPause.role` / `flowPause.since` are emitted but unused by the GUI
|
|
148
|
-
|
|
149
|
-
- **Status**: Open (accepted minor redundancy; not a defect).
|
|
150
|
-
- **Category**: Product / maintainability (cleanup).
|
|
151
|
-
- **Affected modules / surfaces**: `src/shared/types/round.ts` (`VcmFlowPauseState`), `src/backend/services/round-service.ts` (`computeFlowPause`), `src/frontend/app.tsx` (flow-pause alert mechanics).
|
|
152
|
-
- **Current gap**: The authoritative `roundState.flowPause` carries `role` and `since`, but the GUI alert mechanics still read equivalent round-level fields — `roundState.activeRole` for the pause-notice label and `getFlowPauseDurationMs(roundState)` for sound severity. Both sources derive from the same `currentRound`, so the values are equivalent and the redundancy is harmless.
|
|
153
|
-
- **Impact**: None functionally; mild contract over-provisioning (fields provided that no consumer reads), which can confuse future maintainers ("why does `flowPause` carry `role`/`since`?").
|
|
154
|
-
- **Mitigation / workaround**: None needed.
|
|
155
|
-
- **Resolution condition**: Either point the GUI label/severity at `flowPause.role`/`flowPause.since` (consume what the signal already provides), or drop the two fields from `VcmFlowPauseState`. Small, optional.
|
|
156
|
-
- **Related**: none.
|