wicked-crew 0.5.0 → 0.7.0
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/dist/api/audit.d.ts +70 -0
- package/dist/api/audit.d.ts.map +1 -0
- package/dist/api/audit.js +131 -0
- package/dist/api/audit.js.map +1 -0
- package/dist/api/auth.d.ts +192 -0
- package/dist/api/auth.d.ts.map +1 -0
- package/dist/api/auth.js +515 -0
- package/dist/api/auth.js.map +1 -0
- package/dist/api/gate-cache.d.ts +8 -0
- package/dist/api/gate-cache.d.ts.map +1 -1
- package/dist/api/gate-cache.js +10 -0
- package/dist/api/gate-cache.js.map +1 -1
- package/dist/api/guidance-index.d.ts +39 -0
- package/dist/api/guidance-index.d.ts.map +1 -0
- package/dist/api/guidance-index.js +67 -0
- package/dist/api/guidance-index.js.map +1 -0
- package/dist/api/open-path.d.ts +34 -0
- package/dist/api/open-path.d.ts.map +1 -0
- package/dist/api/open-path.js +101 -0
- package/dist/api/open-path.js.map +1 -0
- package/dist/api/retry-index.d.ts +30 -0
- package/dist/api/retry-index.d.ts.map +1 -0
- package/dist/api/retry-index.js +45 -0
- package/dist/api/retry-index.js.map +1 -0
- package/dist/api/routes.d.ts +164 -1
- package/dist/api/routes.d.ts.map +1 -1
- package/dist/api/routes.js +769 -21
- package/dist/api/routes.js.map +1 -1
- package/dist/api/run-files.d.ts +63 -0
- package/dist/api/run-files.d.ts.map +1 -0
- package/dist/api/run-files.js +271 -0
- package/dist/api/run-files.js.map +1 -0
- package/dist/api/seat-health.d.ts +55 -0
- package/dist/api/seat-health.d.ts.map +1 -0
- package/dist/api/seat-health.js +273 -0
- package/dist/api/seat-health.js.map +1 -0
- package/dist/api/seat-signin.d.ts +27 -0
- package/dist/api/seat-signin.d.ts.map +1 -0
- package/dist/api/seat-signin.js +143 -0
- package/dist/api/seat-signin.js.map +1 -0
- package/dist/api/server.d.ts +190 -3
- package/dist/api/server.d.ts.map +1 -1
- package/dist/api/server.js +365 -11
- package/dist/api/server.js.map +1 -1
- package/dist/api/stall-watchdog.d.ts +62 -0
- package/dist/api/stall-watchdog.d.ts.map +1 -0
- package/dist/api/stall-watchdog.js +138 -0
- package/dist/api/stall-watchdog.js.map +1 -0
- package/dist/cli/index.js +171 -12
- package/dist/cli/index.js.map +1 -1
- package/dist/cli/mcp.d.ts +14 -0
- package/dist/cli/mcp.d.ts.map +1 -0
- package/dist/cli/mcp.js +119 -0
- package/dist/cli/mcp.js.map +1 -0
- package/dist/core/adapter.d.ts +87 -10
- package/dist/core/adapter.d.ts.map +1 -1
- package/dist/core/adapter.js +347 -28
- package/dist/core/adapter.js.map +1 -1
- package/dist/core/bridge-reaper.d.ts +134 -0
- package/dist/core/bridge-reaper.d.ts.map +1 -0
- package/dist/core/bridge-reaper.js +286 -0
- package/dist/core/bridge-reaper.js.map +1 -0
- package/dist/core/deliver.d.ts +118 -0
- package/dist/core/deliver.d.ts.map +1 -0
- package/dist/core/deliver.js +241 -0
- package/dist/core/deliver.js.map +1 -0
- package/dist/core/deliverable-floor.d.ts +103 -0
- package/dist/core/deliverable-floor.d.ts.map +1 -0
- package/dist/core/deliverable-floor.js +173 -0
- package/dist/core/deliverable-floor.js.map +1 -0
- package/dist/core/exec.d.ts +2 -0
- package/dist/core/exec.d.ts.map +1 -1
- package/dist/core/exec.js.map +1 -1
- package/dist/core/types.d.ts +92 -352
- package/dist/core/types.d.ts.map +1 -1
- package/dist/core/types.js +14 -4
- package/dist/core/types.js.map +1 -1
- package/dist/interactive/bridge-pool.d.ts +99 -0
- package/dist/interactive/bridge-pool.d.ts.map +1 -0
- package/dist/interactive/bridge-pool.js +244 -0
- package/dist/interactive/bridge-pool.js.map +1 -0
- package/dist/interactive/bridge-root.d.ts +36 -0
- package/dist/interactive/bridge-root.d.ts.map +1 -0
- package/dist/interactive/bridge-root.js +48 -0
- package/dist/interactive/bridge-root.js.map +1 -0
- package/dist/interactive/chat-events.d.ts +207 -0
- package/dist/interactive/chat-events.d.ts.map +1 -0
- package/dist/interactive/chat-events.js +769 -0
- package/dist/interactive/chat-events.js.map +1 -0
- package/dist/interactive/demo-events.d.ts +283 -0
- package/dist/interactive/demo-events.d.ts.map +1 -0
- package/dist/interactive/demo-events.js +889 -0
- package/dist/interactive/demo-events.js.map +1 -0
- package/dist/interactive/draft-events.d.ts +224 -0
- package/dist/interactive/draft-events.d.ts.map +1 -0
- package/dist/interactive/draft-events.js +793 -0
- package/dist/interactive/draft-events.js.map +1 -0
- package/dist/interactive/edit-events.d.ts +194 -0
- package/dist/interactive/edit-events.d.ts.map +1 -0
- package/dist/interactive/edit-events.js +601 -0
- package/dist/interactive/edit-events.js.map +1 -0
- package/dist/interactive/ledger.d.ts +39 -0
- package/dist/interactive/ledger.d.ts.map +1 -0
- package/dist/interactive/ledger.js +93 -0
- package/dist/interactive/ledger.js.map +1 -0
- package/dist/interactive/proxy-routes.d.ts +39 -0
- package/dist/interactive/proxy-routes.d.ts.map +1 -0
- package/dist/interactive/proxy-routes.js +189 -0
- package/dist/interactive/proxy-routes.js.map +1 -0
- package/dist/interactive/repo-snapshot.d.ts +100 -0
- package/dist/interactive/repo-snapshot.d.ts.map +1 -0
- package/dist/interactive/repo-snapshot.js +289 -0
- package/dist/interactive/repo-snapshot.js.map +1 -0
- package/dist/interactive/ws-relay.d.ts +85 -0
- package/dist/interactive/ws-relay.d.ts.map +1 -0
- package/dist/interactive/ws-relay.js +191 -0
- package/dist/interactive/ws-relay.js.map +1 -0
- package/dist/projects/activity.d.ts +29 -0
- package/dist/projects/activity.d.ts.map +1 -0
- package/dist/projects/activity.js +172 -0
- package/dist/projects/activity.js.map +1 -0
- package/dist/projects/charter.d.ts +28 -0
- package/dist/projects/charter.d.ts.map +1 -0
- package/dist/projects/charter.js +53 -0
- package/dist/projects/charter.js.map +1 -0
- package/dist/projects/events.d.ts +55 -0
- package/dist/projects/events.d.ts.map +1 -0
- package/dist/projects/events.js +141 -0
- package/dist/projects/events.js.map +1 -0
- package/dist/projects/graph-paths.d.ts +92 -0
- package/dist/projects/graph-paths.d.ts.map +1 -0
- package/dist/projects/graph-paths.js +130 -0
- package/dist/projects/graph-paths.js.map +1 -0
- package/dist/projects/graph.d.ts +179 -0
- package/dist/projects/graph.d.ts.map +1 -0
- package/dist/projects/graph.js +775 -0
- package/dist/projects/graph.js.map +1 -0
- package/dist/projects/membership-index.d.ts +25 -0
- package/dist/projects/membership-index.d.ts.map +1 -0
- package/dist/projects/membership-index.js +46 -0
- package/dist/projects/membership-index.js.map +1 -0
- package/dist/projects/routes.d.ts +97 -0
- package/dist/projects/routes.d.ts.map +1 -0
- package/dist/projects/routes.js +510 -0
- package/dist/projects/routes.js.map +1 -0
- package/dist/projects/settings.d.ts +32 -0
- package/dist/projects/settings.d.ts.map +1 -0
- package/dist/projects/settings.js +64 -0
- package/dist/projects/settings.js.map +1 -0
- package/dist/qe/acceptance.d.ts +137 -0
- package/dist/qe/acceptance.d.ts.map +1 -0
- package/dist/qe/acceptance.js +249 -0
- package/dist/qe/acceptance.js.map +1 -0
- package/dist/qe/gate-events.d.ts +111 -0
- package/dist/qe/gate-events.d.ts.map +1 -0
- package/dist/qe/gate-events.js +168 -0
- package/dist/qe/gate-events.js.map +1 -0
- package/dist/qe/ledger.d.ts +100 -0
- package/dist/qe/ledger.d.ts.map +1 -0
- package/dist/qe/ledger.js +154 -0
- package/dist/qe/ledger.js.map +1 -0
- package/dist/studio/assets/index-8p8uwCxG.js +530 -0
- package/dist/studio/assets/index-D6S9zUtO.css +32 -0
- package/dist/studio/index.html +5 -3
- package/package.json +10 -4
- package/dist/studio/assets/index-DaaUU8Ep.css +0 -32
- package/dist/studio/assets/index-Fu5DRC00.js +0 -423
|
@@ -0,0 +1,130 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Where a PROJECT's co-located code graph lives, and what each member repo is called inside it.
|
|
3
|
+
*
|
|
4
|
+
* # Why a module instead of a `join()` at each call site
|
|
5
|
+
*
|
|
6
|
+
* This is `repoPaths.ts`'s posture applied one level up (see that module's header for the bill:
|
|
7
|
+
* five spellings of the per-repo graph path against a sixth inside wicked-core, and every graph
|
|
8
|
+
* query answering "nothing found" about a repo full of code). One producer, one consumer. Nothing
|
|
9
|
+
* outside this module spells a project-graph path or mints a repo label.
|
|
10
|
+
*
|
|
11
|
+
* # Why NOT inside a repo checkout
|
|
12
|
+
*
|
|
13
|
+
* The per-repo graph lives at `<repo>/.codegraph/estate.db` — inside the working tree — and we have
|
|
14
|
+
* just spent the effort removing that directory from six checkouts it had polluted. A PROJECT graph
|
|
15
|
+
* is worse on that axis, not better: it holds N repos, so there is no one checkout it belongs to,
|
|
16
|
+
* and writing it into the first member's tree would make repo A's working directory grow with repo
|
|
17
|
+
* B's symbols. It goes in the daemon's own state directory.
|
|
18
|
+
*
|
|
19
|
+
* # Why `~/.wicked-crew/project-graphs/<projectId>/`
|
|
20
|
+
*
|
|
21
|
+
* `~/.wicked-crew/` is already where this package keeps crew-side per-project state that the engine
|
|
22
|
+
* does not own — `project-settings.json` (DES-MERGE-001 §7.1) sits there today. The project graph is
|
|
23
|
+
* exactly that kind of thing: crew-owned, per-project, derived, and rebuildable. A directory per
|
|
24
|
+
* project (rather than `<projectId>.db` files in one flat folder) keeps the db and the refresh
|
|
25
|
+
* manifest that describes it together, so removing a project's graph is one `rm -rf` that cannot
|
|
26
|
+
* leave a manifest describing a database that is gone.
|
|
27
|
+
*
|
|
28
|
+
* Overridable with `WICKED_CREW_PROJECT_GRAPH_ROOT` — the same escape hatch
|
|
29
|
+
* `WICKED_CREW_PROJECT_SETTINGS` gives the settings store, and what lets the tests and the proof
|
|
30
|
+
* scripts run without touching a developer's real home.
|
|
31
|
+
*/
|
|
32
|
+
import { createHash } from 'node:crypto';
|
|
33
|
+
import { homedir } from 'node:os';
|
|
34
|
+
import { join } from 'node:path';
|
|
35
|
+
/**
|
|
36
|
+
* The estate label charset, copied from the rule that enforces it
|
|
37
|
+
* (`wicked-estate/src/repo_scope.rs::validate_label`): 1–64 chars of `[A-Za-z0-9._-]`, and never
|
|
38
|
+
* `.` or `..`.
|
|
39
|
+
*
|
|
40
|
+
* The constraint is not cosmetic and not ours to relax. estate splices the label into `files.path`
|
|
41
|
+
* AND into every SymbolId derived from it, so a `/` or a `..` in a label would forge paths inside
|
|
42
|
+
* another repo's namespace — the exact collision the whole labelling mechanism exists to prevent.
|
|
43
|
+
* A label that fails this test is refused by estate before a single row is written; we mint labels
|
|
44
|
+
* that pass it instead of discovering that at index time.
|
|
45
|
+
*/
|
|
46
|
+
export function isValidRepoLabel(label) {
|
|
47
|
+
return (label.length > 0 &&
|
|
48
|
+
label.length <= 64 &&
|
|
49
|
+
label !== '.' &&
|
|
50
|
+
label !== '..' &&
|
|
51
|
+
/^[A-Za-z0-9._-]+$/.test(label));
|
|
52
|
+
}
|
|
53
|
+
/** Sanitized-label budget: 51 + `-` + 12 hex = exactly estate's 64-character ceiling. */
|
|
54
|
+
const HASH_LEN = 12;
|
|
55
|
+
const STEM_LEN = 64 - 1 - HASH_LEN;
|
|
56
|
+
/**
|
|
57
|
+
* The label one registered repo carries inside a project graph — its REGISTRY ID when that id is
|
|
58
|
+
* already a legal estate label, and a deterministic sanitized form when it is not.
|
|
59
|
+
*
|
|
60
|
+
* WHY the registry id. The label becomes a path prefix on every row the repo writes and shows up in
|
|
61
|
+
* every result this surface returns, so it has to be a name an operator can map back to a repo
|
|
62
|
+
* without a lookup table. It also has to be STABLE: estate binds a label to a repo permanently
|
|
63
|
+
* (re-indexing under a second label is refused as a duplicate; re-using a label for a different repo
|
|
64
|
+
* is refused as a collision), so a label derived from anything mutable — the repo's display name,
|
|
65
|
+
* its root path, its position in the member list — would break the next refresh after a rename or a
|
|
66
|
+
* move. The registry id is the one identifier that is both stable and already unique per repo.
|
|
67
|
+
*
|
|
68
|
+
* Every repo id in the live registry today (`wicked-ledger`, `wicked-vault`, `pageindex-proof`, …)
|
|
69
|
+
* satisfies estate's rule as-is, so the common path is the identity function and the label IS the
|
|
70
|
+
* id. That is not guaranteed for ids minted later, so the fallback is real rather than theoretical:
|
|
71
|
+
* illegal characters collapse to `-`, the stem is capped, and a 12-hex digest of the FULL id is
|
|
72
|
+
* appended — the digest is what keeps `a/b` and `a:b` (which sanitize identically) apart, and what
|
|
73
|
+
* keeps a truncated 200-character id distinct from another that shares its first 51 characters.
|
|
74
|
+
*
|
|
75
|
+
* The mapping is a pure function of the id, which is what makes it safe against estate's permanent
|
|
76
|
+
* binding: the same repo resolves to the same label on every refresh, for the life of the graph.
|
|
77
|
+
*/
|
|
78
|
+
export function repoLabel(repoId) {
|
|
79
|
+
if (isValidRepoLabel(repoId))
|
|
80
|
+
return repoId;
|
|
81
|
+
const digest = createHash('sha256').update(repoId).digest('hex').slice(0, HASH_LEN);
|
|
82
|
+
const stem = repoId.replace(/[^A-Za-z0-9._-]/g, '-').slice(0, STEM_LEN);
|
|
83
|
+
return `${stem}-${digest}`;
|
|
84
|
+
}
|
|
85
|
+
/**
|
|
86
|
+
* Project ids are REJECTED, never sanitized.
|
|
87
|
+
*
|
|
88
|
+
* A sanitizing map is what would let two distinct project ids land in one directory and share one
|
|
89
|
+
* database — the same class of silent collision that made a multi-repo graph impossible in the first
|
|
90
|
+
* place, reintroduced at the project level. It is also the traversal guard: the id is a path
|
|
91
|
+
* segment, so `../../x` must never be spelled into a path. Engine-minted ids (`proj_1787…`) and the
|
|
92
|
+
* synthesized `default` both pass; anything that does not is a bug worth hearing about.
|
|
93
|
+
*/
|
|
94
|
+
export function assertProjectIdIsPathSafe(projectId) {
|
|
95
|
+
if (!isValidRepoLabel(projectId)) {
|
|
96
|
+
// Name the ACTUAL rule that rejected it (Copilot on #326). `.` and `..` match the stated
|
|
97
|
+
// character set, so a message quoting only the charset tells an operator their id is legal
|
|
98
|
+
// and rejected in the same breath — and sends them looking for an illegal character that
|
|
99
|
+
// is not there.
|
|
100
|
+
const why = projectId === '.' || projectId === '..'
|
|
101
|
+
? `${JSON.stringify(projectId)} is a relative path segment, so it cannot name a directory`
|
|
102
|
+
: `expected 1-64 chars of [A-Za-z0-9._-]`;
|
|
103
|
+
throw new Error(`project id ${JSON.stringify(projectId)} cannot address a project graph directory: ${why}`);
|
|
104
|
+
}
|
|
105
|
+
}
|
|
106
|
+
/** The root every project graph directory hangs off. */
|
|
107
|
+
export function projectGraphRoot(env = process.env) {
|
|
108
|
+
return env['WICKED_CREW_PROJECT_GRAPH_ROOT'] ?? join(homedir(), '.wicked-crew', 'project-graphs');
|
|
109
|
+
}
|
|
110
|
+
/** One project's graph directory — holds the database and the manifest that describes it. */
|
|
111
|
+
export function projectGraphDir(projectId, env = process.env) {
|
|
112
|
+
assertProjectIdIsPathSafe(projectId);
|
|
113
|
+
return join(projectGraphRoot(env), projectId);
|
|
114
|
+
}
|
|
115
|
+
/** The ONE database holding every member repo of this project, co-located under their labels. */
|
|
116
|
+
export function projectGraphDb(projectId, env = process.env) {
|
|
117
|
+
return join(projectGraphDir(projectId, env), 'code-graph.db');
|
|
118
|
+
}
|
|
119
|
+
/**
|
|
120
|
+
* What the last refresh put in that database, per repo — the record incremental refresh reads.
|
|
121
|
+
*
|
|
122
|
+
* Deliberately a SIDECAR rather than a read of estate's own `repo:<label>:commit` meta: estate
|
|
123
|
+
* exposes that only through `stats`, whose output is human text with no `--json`, and deciding
|
|
124
|
+
* whether to re-index a repo by regex-matching a report is the kind of coupling that breaks on a
|
|
125
|
+
* formatting change with no test to catch it.
|
|
126
|
+
*/
|
|
127
|
+
export function projectGraphManifest(projectId, env = process.env) {
|
|
128
|
+
return join(projectGraphDir(projectId, env), 'manifest.json');
|
|
129
|
+
}
|
|
130
|
+
//# sourceMappingURL=graph-paths.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"graph-paths.js","sourceRoot":"","sources":["../../src/projects/graph-paths.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA8BG;AAEH,OAAO,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AACzC,OAAO,EAAE,OAAO,EAAE,MAAM,SAAS,CAAC;AAClC,OAAO,EAAE,IAAI,EAAE,MAAM,WAAW,CAAC;AAEjC;;;;;;;;;;GAUG;AACH,MAAM,UAAU,gBAAgB,CAAC,KAAa;IAC5C,OAAO,CACL,KAAK,CAAC,MAAM,GAAG,CAAC;QAChB,KAAK,CAAC,MAAM,IAAI,EAAE;QAClB,KAAK,KAAK,GAAG;QACb,KAAK,KAAK,IAAI;QACd,mBAAmB,CAAC,IAAI,CAAC,KAAK,CAAC,CAChC,CAAC;AACJ,CAAC;AAED,yFAAyF;AACzF,MAAM,QAAQ,GAAG,EAAE,CAAC;AACpB,MAAM,QAAQ,GAAG,EAAE,GAAG,CAAC,GAAG,QAAQ,CAAC;AAEnC;;;;;;;;;;;;;;;;;;;;;GAqBG;AACH,MAAM,UAAU,SAAS,CAAC,MAAc;IACtC,IAAI,gBAAgB,CAAC,MAAM,CAAC;QAAE,OAAO,MAAM,CAAC;IAC5C,MAAM,MAAM,GAAG,UAAU,CAAC,QAAQ,CAAC,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC,KAAK,CAAC,CAAC,EAAE,QAAQ,CAAC,CAAC;IACpF,MAAM,IAAI,GAAG,MAAM,CAAC,OAAO,CAAC,kBAAkB,EAAE,GAAG,CAAC,CAAC,KAAK,CAAC,CAAC,EAAE,QAAQ,CAAC,CAAC;IACxE,OAAO,GAAG,IAAI,IAAI,MAAM,EAAE,CAAC;AAC7B,CAAC;AAED;;;;;;;;GAQG;AACH,MAAM,UAAU,yBAAyB,CAAC,SAAiB;IACzD,IAAI,CAAC,gBAAgB,CAAC,SAAS,CAAC,EAAE,CAAC;QACjC,yFAAyF;QACzF,2FAA2F;QAC3F,yFAAyF;QACzF,gBAAgB;QAChB,MAAM,GAAG,GACP,SAAS,KAAK,GAAG,IAAI,SAAS,KAAK,IAAI;YACrC,CAAC,CAAC,GAAG,IAAI,CAAC,SAAS,CAAC,SAAS,CAAC,4DAA4D;YAC1F,CAAC,CAAC,uCAAuC,CAAC;QAC9C,MAAM,IAAI,KAAK,CACb,cAAc,IAAI,CAAC,SAAS,CAAC,SAAS,CAAC,8CAA8C,GAAG,EAAE,CAC3F,CAAC;IACJ,CAAC;AACH,CAAC;AAED,wDAAwD;AACxD,MAAM,UAAU,gBAAgB,CAAC,MAAyB,OAAO,CAAC,GAAG;IACnE,OAAO,GAAG,CAAC,gCAAgC,CAAC,IAAI,IAAI,CAAC,OAAO,EAAE,EAAE,cAAc,EAAE,gBAAgB,CAAC,CAAC;AACpG,CAAC;AAED,6FAA6F;AAC7F,MAAM,UAAU,eAAe,CAAC,SAAiB,EAAE,MAAyB,OAAO,CAAC,GAAG;IACrF,yBAAyB,CAAC,SAAS,CAAC,CAAC;IACrC,OAAO,IAAI,CAAC,gBAAgB,CAAC,GAAG,CAAC,EAAE,SAAS,CAAC,CAAC;AAChD,CAAC;AAED,iGAAiG;AACjG,MAAM,UAAU,cAAc,CAAC,SAAiB,EAAE,MAAyB,OAAO,CAAC,GAAG;IACpF,OAAO,IAAI,CAAC,eAAe,CAAC,SAAS,EAAE,GAAG,CAAC,EAAE,eAAe,CAAC,CAAC;AAChE,CAAC;AAED;;;;;;;GAOG;AACH,MAAM,UAAU,oBAAoB,CAAC,SAAiB,EAAE,MAAyB,OAAO,CAAC,GAAG;IAC1F,OAAO,IAAI,CAAC,eAAe,CAAC,SAAS,EAAE,GAAG,CAAC,EAAE,eAAe,CAAC,CAAC;AAChE,CAAC"}
|
|
@@ -0,0 +1,179 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The project code graph — every `crew.repo` member of one project in ONE wicked-estate database.
|
|
3
|
+
*
|
|
4
|
+
* # What changed to make this possible
|
|
5
|
+
*
|
|
6
|
+
* One estate database used to hold exactly one repo. SymbolIds embed the repo-relative path, so two
|
|
7
|
+
* repos that both contain `src/index.ts` mint identical file rows AND identical symbol ids: the
|
|
8
|
+
* second index overwrote the first and said nothing. `wicked-estate index <path> --repo <label>`
|
|
9
|
+
* (wicked-estate#117) namespaces every path as `<label>/…`, so N repos co-exist, each queryable,
|
|
10
|
+
* with a guard that refuses — before a row is written — any index that would overwrite another
|
|
11
|
+
* repo's content.
|
|
12
|
+
*
|
|
13
|
+
* # THE LIMIT
|
|
14
|
+
*
|
|
15
|
+
* CO-LOCATION IS NOT LINKAGE. estate resolves edges within a labelled repo's own nodes, exactly as
|
|
16
|
+
* if each repo sat in its own database. `studio → wicked-crew-api-types → crew` does not traverse.
|
|
17
|
+
* What this module federates is per-repo results into one answer with the repo named on every hit —
|
|
18
|
+
* which is genuinely useful ("who calls `record`, anywhere in this project") and is NOT a cross-repo
|
|
19
|
+
* dependency trace. Every response carries `linkage: 'co-located'` and {@link CO_LOCATION_NOTE} so a
|
|
20
|
+
* consumer cannot mistake one for the other.
|
|
21
|
+
*
|
|
22
|
+
* # Why the estate binary is capability-PROBED before anything is indexed
|
|
23
|
+
*
|
|
24
|
+
* `wicked-estate 0.14.4` — the version installed on this machine while this was written — accepts
|
|
25
|
+
* `--repo`, IGNORES it, and exits 0. Indexing three repos through it produces a database holding
|
|
26
|
+
* only the third, with no error anywhere and results that look perfectly healthy. That is the exact
|
|
27
|
+
* silent-loss failure the labelling work exists to end, reachable by nothing worse than a stale
|
|
28
|
+
* binary on PATH. So the flag's support is established from the binary that will actually run,
|
|
29
|
+
* before the first index (help text), and confirmed from the database afterwards (the labelled repo
|
|
30
|
+
* registry `stats` prints) — a claim, then evidence.
|
|
31
|
+
*
|
|
32
|
+
* # Honest degradation
|
|
33
|
+
*
|
|
34
|
+
* Every path out of here names its cause. A project with no repo members, one whose graph was never
|
|
35
|
+
* built, one whose member repo the registry no longer knows, and an addon too old to publish
|
|
36
|
+
* `code_graph_db` are four different situations with four different remedies; collapsing them into
|
|
37
|
+
* an empty result set is the failure estate's own R3 rule exists to prevent, and it is the failure
|
|
38
|
+
* FINDING-069 actually shipped.
|
|
39
|
+
*/
|
|
40
|
+
import type { CoreAdapter } from '../core/adapter.js';
|
|
41
|
+
import type { ProjectBlastRadius, ProjectGraphHit, ProjectGraphRefreshResult, ProjectGraphRepoCount, ProjectGraphSearch, ProjectGraphStatus } from '../core/types.js';
|
|
42
|
+
/** The sentence every project-graph response carries. Stated on the wire, not just in this file. */
|
|
43
|
+
export declare const CO_LOCATION_NOTE: string;
|
|
44
|
+
/**
|
|
45
|
+
* The second sentence `/graph/search` carries, and only it.
|
|
46
|
+
*
|
|
47
|
+
* `matches: []` from an exact-name resolver against a healthy graph is the empty-result-that-reads-
|
|
48
|
+
* as-an-answer this whole surface is built to refuse: a caller who typed half a name is told
|
|
49
|
+
* "nothing in this project", which is false. estate's `resolve` has no substring mode (the header
|
|
50
|
+
* on {@link projectSymbolSearch} argues why a `nodes --json` dump is not the answer), so the
|
|
51
|
+
* matching RULE goes on the wire instead of a matching mode that does not exist.
|
|
52
|
+
*/
|
|
53
|
+
export declare const EXACT_NAME_NOTE: string;
|
|
54
|
+
/**
|
|
55
|
+
* Does the `wicked-estate` that will actually run support `--repo`?
|
|
56
|
+
*
|
|
57
|
+
* A version comparison would be the obvious probe and the wrong one: it asks a string on disk
|
|
58
|
+
* instead of the binary on PATH, and a locally built or vendored estate can carry any version it
|
|
59
|
+
* likes. The usage banner is printed by the same binary that would do the indexing.
|
|
60
|
+
*/
|
|
61
|
+
export declare function estateSupportsMultiRepo(env?: NodeJS.ProcessEnv): Promise<boolean>;
|
|
62
|
+
/**
|
|
63
|
+
* The evidence check failed: the binary took `--repo` and dropped it.
|
|
64
|
+
*
|
|
65
|
+
* A distinct type because it is NOT a per-repo failure and must not be collected as one. It is the
|
|
66
|
+
* same fact the capability probe establishes — this binary cannot co-locate — discovered one step
|
|
67
|
+
* later, and the only safe response is the probe's: stop, before the next repo's index overwrites
|
|
68
|
+
* the rows just written. Recording it in `failed` and continuing runs a full index per member, each
|
|
69
|
+
* clobbering the last, while the message on every entry claims the opposite.
|
|
70
|
+
*/
|
|
71
|
+
export declare class EstateDroppedRepoLabelError extends Error {
|
|
72
|
+
constructor(message: string);
|
|
73
|
+
}
|
|
74
|
+
/**
|
|
75
|
+
* Thrown when the running addon predates `code_graph_db` on the repo record. Mapped to 501: this is
|
|
76
|
+
* a capability gap in the engine, not a bad request.
|
|
77
|
+
*
|
|
78
|
+
* WHY this surface gates on a field it does not itself use. The project graph lives in crew's own
|
|
79
|
+
* state directory and is built from `root_path`, so it could be built against any addon. But
|
|
80
|
+
* `code_graph_db` is the engine's statement that it can vouch for where a repo's graph lives, and
|
|
81
|
+
* `/repos/:id/graph` HARD-THROWS without it (repoPaths.ts, deliberately — a local re-derivation is
|
|
82
|
+
* what FINDING-069 was). Quietly serving a project graph on a daemon whose per-repo graph surface
|
|
83
|
+
* cannot answer would leave two graph endpoints disagreeing about whether this repo has a graph at
|
|
84
|
+
* all, and the operator's real problem — a stale addon — unmentioned.
|
|
85
|
+
*/
|
|
86
|
+
export declare class ProjectGraphEngineTooOldError extends Error {
|
|
87
|
+
readonly cause: string;
|
|
88
|
+
constructor(cause: string);
|
|
89
|
+
}
|
|
90
|
+
/** Read the project graph's standing without touching it. */
|
|
91
|
+
export declare function projectGraphStatus(adapter: CoreAdapter, projectId: string, env?: NodeJS.ProcessEnv): Promise<ProjectGraphStatus>;
|
|
92
|
+
export declare function refreshProjectGraph(adapter: CoreAdapter, projectId: string, env?: NodeJS.ProcessEnv): Promise<ProjectGraphRefreshResult>;
|
|
93
|
+
/**
|
|
94
|
+
* Passed to the engine as `LaunchOptions.projectGraph`. `repoLabel` names this run's repo inside
|
|
95
|
+
* the co-located graph so the engine can confirm the graph actually holds it; a repo-less run
|
|
96
|
+
* carries no label because it has no own repo to confirm.
|
|
97
|
+
*/
|
|
98
|
+
export interface ProjectGraphBinding {
|
|
99
|
+
dbPath: string;
|
|
100
|
+
repoLabel?: string;
|
|
101
|
+
}
|
|
102
|
+
/**
|
|
103
|
+
* What a launch decided about the project graph, and why. The `reason` is carried on BOTH outcomes
|
|
104
|
+
* because "you got the project graph" and "you got the repo graph instead, because X" are equally
|
|
105
|
+
* worth saying, and the operator asking "why can't this run see the sibling repo" needs the second
|
|
106
|
+
* one to have been recorded somewhere.
|
|
107
|
+
*/
|
|
108
|
+
export interface ProjectGraphBindingDecision {
|
|
109
|
+
/** The binding to hand the engine; `null` ⇒ the run keeps whatever graph it would have had. */
|
|
110
|
+
binding: ProjectGraphBinding | null;
|
|
111
|
+
/** One sentence: what the run got, and what would change it. */
|
|
112
|
+
reason: string;
|
|
113
|
+
}
|
|
114
|
+
/**
|
|
115
|
+
* Decide which code graph a run launched into `projectId` should be bound to.
|
|
116
|
+
*
|
|
117
|
+
* # This never indexes
|
|
118
|
+
*
|
|
119
|
+
* A refresh is `wicked-estate index` per member repo, bounded at ten minutes EACH. Doing that
|
|
120
|
+
* inside a launch would turn "start a run" into an unannounced multi-repo indexing job that blocks
|
|
121
|
+
* the response, and the first thing an operator would learn about it is a request that appears to
|
|
122
|
+
* hang. So a missing or stale graph DEGRADES the run to the per-repo graph and says so; refreshing
|
|
123
|
+
* stays an explicit `POST /projects/:id/graph/refresh`.
|
|
124
|
+
*
|
|
125
|
+
* # Why the run's OWN repo decides it
|
|
126
|
+
*
|
|
127
|
+
* The engine independently verifies whatever it is handed and falls back on its own, so this
|
|
128
|
+
* function cannot make a run unsafe — but it can make one confusing, and it has information the
|
|
129
|
+
* engine does not. `projectGraphStatus` knows a repo was attached after the last refresh, that its
|
|
130
|
+
* registry root moved out from under the label, that its member ref is dangling. Declining HERE,
|
|
131
|
+
* with that cause attached, is the difference between an operator reading "attached since the last
|
|
132
|
+
* refresh — not in the graph yet" and reading the engine's generic "no files under that label".
|
|
133
|
+
*
|
|
134
|
+
* The rule itself is the engine's, restated on this side: bind when the graph holds THIS RUN'S
|
|
135
|
+
* repo. A graph missing some OTHER member is still bound — it is strictly more than the per-repo
|
|
136
|
+
* graph, and the run's own code is described correctly. A graph missing THIS repo is not, because
|
|
137
|
+
* its answers about the worktree the worker is sitting in would all be "nothing found".
|
|
138
|
+
*/
|
|
139
|
+
export declare function resolveProjectGraphBinding(adapter: CoreAdapter, projectId: string, repoRef: string | undefined, env?: NodeJS.ProcessEnv): Promise<ProjectGraphBindingDecision>;
|
|
140
|
+
/**
|
|
141
|
+
* A query can run only against a graph that exists and holds at least one MEMBER repo. Anything
|
|
142
|
+
* else is returned as the status, so the caller gets the cause and the remedy instead of `[]`.
|
|
143
|
+
*/
|
|
144
|
+
export type Queryable = {
|
|
145
|
+
ok: true;
|
|
146
|
+
dbPath: string;
|
|
147
|
+
status: ProjectGraphStatus;
|
|
148
|
+
labels: Map<string, string>;
|
|
149
|
+
} | {
|
|
150
|
+
ok: false;
|
|
151
|
+
status: ProjectGraphStatus;
|
|
152
|
+
};
|
|
153
|
+
export declare function queryable(adapter: CoreAdapter, projectId: string, env?: NodeJS.ProcessEnv): Promise<Queryable>;
|
|
154
|
+
/**
|
|
155
|
+
* estate's raw hit list → attributed hits plus their per-repo counts. THE federation step, and the
|
|
156
|
+
* only place a result acquires its provenance — exported so the attribution rules are testable
|
|
157
|
+
* without a graph on disk, which is what makes the stale-label exclusion below coverable at all.
|
|
158
|
+
*/
|
|
159
|
+
export declare function attributeHits(raw: unknown, labels: Map<string, string>): {
|
|
160
|
+
hits: ProjectGraphHit[];
|
|
161
|
+
byRepo: ProjectGraphRepoCount[];
|
|
162
|
+
};
|
|
163
|
+
/** Dependents of a symbol across every member repo, each hit attributed to the repo it is in. */
|
|
164
|
+
export declare function projectBlastRadius(q: Extract<Queryable, {
|
|
165
|
+
ok: true;
|
|
166
|
+
}>, name: string, env?: NodeJS.ProcessEnv): Promise<ProjectBlastRadius>;
|
|
167
|
+
/**
|
|
168
|
+
* Symbol search across every member repo — exact name, which is what estate's `resolve` answers.
|
|
169
|
+
*
|
|
170
|
+
* Not a substring search on purpose: the only estate primitive that would give one is a full
|
|
171
|
+
* `nodes --json` dump filtered daemon-side, whose cost scales with the whole project rather than
|
|
172
|
+
* with the query, and which would need a cap whose truncation is itself a silent wrong answer.
|
|
173
|
+
* `resolve` is the same primitive the repo-scoped surface uses to turn a name into SymbolIds; run
|
|
174
|
+
* against a co-located graph it returns every repo's matches in one call.
|
|
175
|
+
*/
|
|
176
|
+
export declare function projectSymbolSearch(q: Extract<Queryable, {
|
|
177
|
+
ok: true;
|
|
178
|
+
}>, name: string, env?: NodeJS.ProcessEnv): Promise<ProjectGraphSearch>;
|
|
179
|
+
//# sourceMappingURL=graph.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"graph.d.ts","sourceRoot":"","sources":["../../src/projects/graph.ts"],"names":[],"mappings":"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"}
|