@triedotdev/mcp 1.0.113 → 1.0.114
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/auto-fix-apply-PCAHWLXF.js +10 -0
- package/dist/autonomy-config-O4H3Z7YV.js +30 -0
- package/dist/chunk-2GIAROBF.js +173 -0
- package/dist/chunk-2GIAROBF.js.map +1 -0
- package/dist/{chunk-33WL3D7A.js → chunk-2SIFK7OW.js} +7 -419
- package/dist/chunk-2SIFK7OW.js.map +1 -0
- package/dist/chunk-43X6JBEM.js +36 -0
- package/dist/chunk-43X6JBEM.js.map +1 -0
- package/dist/{chunk-2764KZZQ.js → chunk-4SBZXIMG.js} +133 -595
- package/dist/chunk-4SBZXIMG.js.map +1 -0
- package/dist/chunk-55DOQNHJ.js +772 -0
- package/dist/chunk-55DOQNHJ.js.map +1 -0
- package/dist/chunk-6LXSA2OZ.js +425 -0
- package/dist/chunk-6LXSA2OZ.js.map +1 -0
- package/dist/{chunk-SDS3UVFY.js → chunk-AOFYU6T3.js} +113 -559
- package/dist/chunk-AOFYU6T3.js.map +1 -0
- package/dist/{chunk-6QR6QZIX.js → chunk-D3EXBJE2.js} +25 -658
- package/dist/chunk-D3EXBJE2.js.map +1 -0
- package/dist/chunk-DJ2YAGHK.js +50 -0
- package/dist/chunk-DJ2YAGHK.js.map +1 -0
- package/dist/chunk-DRDEEF6G.js +328 -0
- package/dist/chunk-DRDEEF6G.js.map +1 -0
- package/dist/chunk-DZREHOGW.js +706 -0
- package/dist/chunk-DZREHOGW.js.map +1 -0
- package/dist/chunk-KRH642MT.js +947 -0
- package/dist/chunk-KRH642MT.js.map +1 -0
- package/dist/{chunk-QYOACM2C.js → chunk-MVNJPJBK.js} +22 -252
- package/dist/chunk-MVNJPJBK.js.map +1 -0
- package/dist/chunk-NS2MSZMB.js +394 -0
- package/dist/chunk-NS2MSZMB.js.map +1 -0
- package/dist/chunk-SWSK7ANT.js +340 -0
- package/dist/chunk-SWSK7ANT.js.map +1 -0
- package/dist/chunk-VRLMTOB6.js +566 -0
- package/dist/chunk-VRLMTOB6.js.map +1 -0
- package/dist/chunk-YR4BMGYO.js +130 -0
- package/dist/chunk-YR4BMGYO.js.map +1 -0
- package/dist/chunk-ZV2K6M7T.js +74 -0
- package/dist/chunk-ZV2K6M7T.js.map +1 -0
- package/dist/cli/main.js +107 -375
- package/dist/cli/main.js.map +1 -1
- package/dist/cli/yolo-daemon.js +18 -8
- package/dist/cli/yolo-daemon.js.map +1 -1
- package/dist/client-7XZHCMD3.js +28 -0
- package/dist/client-7XZHCMD3.js.map +1 -0
- package/dist/{goal-manager-AP4LTE6U.js → goal-manager-LMS6ZJB7.js} +7 -3
- package/dist/goal-manager-LMS6ZJB7.js.map +1 -0
- package/dist/goal-validator-7UPLOVAZ.js +184 -0
- package/dist/goal-validator-7UPLOVAZ.js.map +1 -0
- package/dist/graph-U5JWSAB5.js +10 -0
- package/dist/graph-U5JWSAB5.js.map +1 -0
- package/dist/guardian-agent-EXP7APLC.js +25 -0
- package/dist/guardian-agent-EXP7APLC.js.map +1 -0
- package/dist/hypothesis-KGC3P54C.js +19 -0
- package/dist/hypothesis-KGC3P54C.js.map +1 -0
- package/dist/incident-index-PNIVT47T.js +11 -0
- package/dist/incident-index-PNIVT47T.js.map +1 -0
- package/dist/index.js +285 -16
- package/dist/index.js.map +1 -1
- package/dist/ledger-SR6OEBLO.js +15 -0
- package/dist/ledger-SR6OEBLO.js.map +1 -0
- package/dist/output-manager-BOTMXSND.js +13 -0
- package/dist/output-manager-BOTMXSND.js.map +1 -0
- package/dist/pattern-discovery-F7LU5K6E.js +8 -0
- package/dist/pattern-discovery-F7LU5K6E.js.map +1 -0
- package/package.json +1 -1
- package/dist/chunk-2764KZZQ.js.map +0 -1
- package/dist/chunk-33WL3D7A.js.map +0 -1
- package/dist/chunk-6JPPYG7F.js +0 -1813
- package/dist/chunk-6JPPYG7F.js.map +0 -1
- package/dist/chunk-6QR6QZIX.js.map +0 -1
- package/dist/chunk-QYOACM2C.js.map +0 -1
- package/dist/chunk-SDS3UVFY.js.map +0 -1
- package/dist/guardian-agent-XEYNG7RH.js +0 -18
- /package/dist/{goal-manager-AP4LTE6U.js.map → auto-fix-apply-PCAHWLXF.js.map} +0 -0
- /package/dist/{guardian-agent-XEYNG7RH.js.map → autonomy-config-O4H3Z7YV.js.map} +0 -0
|
@@ -0,0 +1,394 @@
|
|
|
1
|
+
import {
|
|
2
|
+
getTrieDirectory
|
|
3
|
+
} from "./chunk-R4AAPFXC.js";
|
|
4
|
+
|
|
5
|
+
// src/context/graph.ts
|
|
6
|
+
import crypto from "crypto";
|
|
7
|
+
import path2 from "path";
|
|
8
|
+
|
|
9
|
+
// src/context/store.ts
|
|
10
|
+
import Database from "better-sqlite3";
|
|
11
|
+
import fs from "fs";
|
|
12
|
+
import path from "path";
|
|
13
|
+
var ContextStore = class {
|
|
14
|
+
db;
|
|
15
|
+
dbFilePath;
|
|
16
|
+
constructor(projectPath, dbFilePath) {
|
|
17
|
+
this.dbFilePath = dbFilePath ?? path.join(getTrieDirectory(projectPath), "context.db");
|
|
18
|
+
this.ensureDirectory();
|
|
19
|
+
this.db = new Database(this.dbFilePath);
|
|
20
|
+
this.configure();
|
|
21
|
+
this.prepareSchema();
|
|
22
|
+
}
|
|
23
|
+
get databasePath() {
|
|
24
|
+
return this.dbFilePath;
|
|
25
|
+
}
|
|
26
|
+
addNode(node) {
|
|
27
|
+
const stmt = this.db.prepare(
|
|
28
|
+
`INSERT INTO nodes (id, type, data, created_at, updated_at)
|
|
29
|
+
VALUES (@id, @type, @data, @created_at, @updated_at)`
|
|
30
|
+
);
|
|
31
|
+
stmt.run({
|
|
32
|
+
id: node.id,
|
|
33
|
+
type: node.type,
|
|
34
|
+
data: JSON.stringify(node.data),
|
|
35
|
+
created_at: node.created_at,
|
|
36
|
+
updated_at: node.updated_at
|
|
37
|
+
});
|
|
38
|
+
return node;
|
|
39
|
+
}
|
|
40
|
+
upsertNode(node) {
|
|
41
|
+
const stmt = this.db.prepare(
|
|
42
|
+
`INSERT INTO nodes (id, type, data, created_at, updated_at)
|
|
43
|
+
VALUES (@id, @type, @data, @created_at, @updated_at)
|
|
44
|
+
ON CONFLICT(id) DO UPDATE SET
|
|
45
|
+
type=excluded.type,
|
|
46
|
+
data=excluded.data,
|
|
47
|
+
updated_at=excluded.updated_at`
|
|
48
|
+
);
|
|
49
|
+
stmt.run({
|
|
50
|
+
id: node.id,
|
|
51
|
+
type: node.type,
|
|
52
|
+
data: JSON.stringify(node.data),
|
|
53
|
+
created_at: node.created_at,
|
|
54
|
+
updated_at: node.updated_at
|
|
55
|
+
});
|
|
56
|
+
return node;
|
|
57
|
+
}
|
|
58
|
+
getNode(id) {
|
|
59
|
+
const row = this.db.prepare("SELECT * FROM nodes WHERE id = ?").get(id);
|
|
60
|
+
return row ? this.mapNodeRow(row) : null;
|
|
61
|
+
}
|
|
62
|
+
getNodeByType(type, id) {
|
|
63
|
+
const row = this.db.prepare("SELECT * FROM nodes WHERE id = ? AND type = ?").get(id, type);
|
|
64
|
+
return row ? this.mapNodeRow(row) : null;
|
|
65
|
+
}
|
|
66
|
+
updateNode(id, updates, updatedAt) {
|
|
67
|
+
const existing = this.getNode(id);
|
|
68
|
+
if (!existing) {
|
|
69
|
+
return null;
|
|
70
|
+
}
|
|
71
|
+
const merged = {
|
|
72
|
+
...existing,
|
|
73
|
+
data: { ...existing.data, ...updates },
|
|
74
|
+
updated_at: updatedAt
|
|
75
|
+
};
|
|
76
|
+
this.db.prepare(
|
|
77
|
+
`UPDATE nodes SET data = @data, updated_at = @updated_at
|
|
78
|
+
WHERE id = @id`
|
|
79
|
+
).run({
|
|
80
|
+
id,
|
|
81
|
+
data: JSON.stringify(merged.data),
|
|
82
|
+
updated_at: merged.updated_at
|
|
83
|
+
});
|
|
84
|
+
return merged;
|
|
85
|
+
}
|
|
86
|
+
deleteNode(id) {
|
|
87
|
+
const deleteEdges = this.db.prepare("DELETE FROM edges WHERE from_id = ? OR to_id = ?");
|
|
88
|
+
const deleteNodeStmt = this.db.prepare("DELETE FROM nodes WHERE id = ?");
|
|
89
|
+
const transaction = this.db.transaction((nodeId) => {
|
|
90
|
+
deleteEdges.run(nodeId, nodeId);
|
|
91
|
+
deleteNodeStmt.run(nodeId);
|
|
92
|
+
});
|
|
93
|
+
transaction(id);
|
|
94
|
+
}
|
|
95
|
+
listNodes() {
|
|
96
|
+
const rows = this.db.prepare("SELECT * FROM nodes").all();
|
|
97
|
+
return rows.map((row) => this.mapNodeRow(row));
|
|
98
|
+
}
|
|
99
|
+
findNodesByType(type) {
|
|
100
|
+
const rows = this.db.prepare("SELECT * FROM nodes WHERE type = ?").all(type);
|
|
101
|
+
return rows.map((row) => this.mapNodeRow(row));
|
|
102
|
+
}
|
|
103
|
+
addEdge(edge) {
|
|
104
|
+
const stmt = this.db.prepare(
|
|
105
|
+
`INSERT INTO edges (id, from_id, to_id, type, weight, metadata, created_at)
|
|
106
|
+
VALUES (@id, @from_id, @to_id, @type, @weight, @metadata, @created_at)`
|
|
107
|
+
);
|
|
108
|
+
stmt.run({
|
|
109
|
+
id: edge.id,
|
|
110
|
+
from_id: edge.from_id,
|
|
111
|
+
to_id: edge.to_id,
|
|
112
|
+
type: edge.type,
|
|
113
|
+
weight: edge.weight,
|
|
114
|
+
metadata: JSON.stringify(edge.metadata ?? {}),
|
|
115
|
+
created_at: edge.created_at
|
|
116
|
+
});
|
|
117
|
+
return edge;
|
|
118
|
+
}
|
|
119
|
+
upsertEdge(edge) {
|
|
120
|
+
const stmt = this.db.prepare(
|
|
121
|
+
`INSERT INTO edges (id, from_id, to_id, type, weight, metadata, created_at)
|
|
122
|
+
VALUES (@id, @from_id, @to_id, @type, @weight, @metadata, @created_at)
|
|
123
|
+
ON CONFLICT(id) DO UPDATE SET
|
|
124
|
+
from_id=excluded.from_id,
|
|
125
|
+
to_id=excluded.to_id,
|
|
126
|
+
type=excluded.type,
|
|
127
|
+
weight=excluded.weight,
|
|
128
|
+
metadata=excluded.metadata`
|
|
129
|
+
);
|
|
130
|
+
stmt.run({
|
|
131
|
+
id: edge.id,
|
|
132
|
+
from_id: edge.from_id,
|
|
133
|
+
to_id: edge.to_id,
|
|
134
|
+
type: edge.type,
|
|
135
|
+
weight: edge.weight,
|
|
136
|
+
metadata: JSON.stringify(edge.metadata ?? {}),
|
|
137
|
+
created_at: edge.created_at
|
|
138
|
+
});
|
|
139
|
+
return edge;
|
|
140
|
+
}
|
|
141
|
+
getEdge(id) {
|
|
142
|
+
const row = this.db.prepare("SELECT * FROM edges WHERE id = ?").get(id);
|
|
143
|
+
return row ? this.mapEdgeRow(row) : null;
|
|
144
|
+
}
|
|
145
|
+
getEdges(nodeId, direction = "both") {
|
|
146
|
+
let rows;
|
|
147
|
+
if (direction === "in") {
|
|
148
|
+
rows = this.db.prepare("SELECT * FROM edges WHERE to_id = ?").all(nodeId);
|
|
149
|
+
} else if (direction === "out") {
|
|
150
|
+
rows = this.db.prepare("SELECT * FROM edges WHERE from_id = ?").all(nodeId);
|
|
151
|
+
} else {
|
|
152
|
+
rows = this.db.prepare("SELECT * FROM edges WHERE from_id = ? OR to_id = ?").all(nodeId, nodeId);
|
|
153
|
+
}
|
|
154
|
+
return rows.map((row) => this.mapEdgeRow(row));
|
|
155
|
+
}
|
|
156
|
+
listEdges() {
|
|
157
|
+
const rows = this.db.prepare("SELECT * FROM edges").all();
|
|
158
|
+
return rows.map((row) => this.mapEdgeRow(row));
|
|
159
|
+
}
|
|
160
|
+
deleteEdge(id) {
|
|
161
|
+
this.db.prepare("DELETE FROM edges WHERE id = ?").run(id);
|
|
162
|
+
}
|
|
163
|
+
close() {
|
|
164
|
+
this.db.close();
|
|
165
|
+
}
|
|
166
|
+
ensureDirectory() {
|
|
167
|
+
fs.mkdirSync(path.dirname(this.dbFilePath), { recursive: true });
|
|
168
|
+
}
|
|
169
|
+
configure() {
|
|
170
|
+
this.db.pragma("journal_mode = WAL");
|
|
171
|
+
this.db.pragma("busy_timeout = 5000");
|
|
172
|
+
this.db.pragma("synchronous = NORMAL");
|
|
173
|
+
}
|
|
174
|
+
prepareSchema() {
|
|
175
|
+
this.db.exec(`
|
|
176
|
+
CREATE TABLE IF NOT EXISTS nodes (
|
|
177
|
+
id TEXT PRIMARY KEY,
|
|
178
|
+
type TEXT NOT NULL,
|
|
179
|
+
data TEXT NOT NULL,
|
|
180
|
+
created_at TEXT NOT NULL,
|
|
181
|
+
updated_at TEXT NOT NULL
|
|
182
|
+
);
|
|
183
|
+
|
|
184
|
+
CREATE TABLE IF NOT EXISTS edges (
|
|
185
|
+
id TEXT PRIMARY KEY,
|
|
186
|
+
from_id TEXT NOT NULL,
|
|
187
|
+
to_id TEXT NOT NULL,
|
|
188
|
+
type TEXT NOT NULL,
|
|
189
|
+
weight REAL NOT NULL DEFAULT 1,
|
|
190
|
+
metadata TEXT DEFAULT '{}',
|
|
191
|
+
created_at TEXT NOT NULL
|
|
192
|
+
);
|
|
193
|
+
|
|
194
|
+
CREATE INDEX IF NOT EXISTS idx_nodes_type ON nodes(type);
|
|
195
|
+
CREATE INDEX IF NOT EXISTS idx_edges_from ON edges(from_id);
|
|
196
|
+
CREATE INDEX IF NOT EXISTS idx_edges_to ON edges(to_id);
|
|
197
|
+
CREATE INDEX IF NOT EXISTS idx_edges_type ON edges(type);
|
|
198
|
+
`);
|
|
199
|
+
}
|
|
200
|
+
mapNodeRow(row) {
|
|
201
|
+
return {
|
|
202
|
+
id: row.id,
|
|
203
|
+
type: row.type,
|
|
204
|
+
data: JSON.parse(row.data),
|
|
205
|
+
created_at: row.created_at,
|
|
206
|
+
updated_at: row.updated_at
|
|
207
|
+
};
|
|
208
|
+
}
|
|
209
|
+
mapEdgeRow(row) {
|
|
210
|
+
return {
|
|
211
|
+
id: row.id,
|
|
212
|
+
from_id: row.from_id,
|
|
213
|
+
to_id: row.to_id,
|
|
214
|
+
type: row.type,
|
|
215
|
+
weight: row.weight,
|
|
216
|
+
created_at: row.created_at,
|
|
217
|
+
metadata: row.metadata ? JSON.parse(row.metadata) : {}
|
|
218
|
+
};
|
|
219
|
+
}
|
|
220
|
+
};
|
|
221
|
+
|
|
222
|
+
// src/context/graph.ts
|
|
223
|
+
var ContextGraph = class {
|
|
224
|
+
store;
|
|
225
|
+
projectPath;
|
|
226
|
+
constructor(projectPath, dbPath, store) {
|
|
227
|
+
this.projectPath = projectPath;
|
|
228
|
+
this.store = store ?? new ContextStore(projectPath, dbPath);
|
|
229
|
+
}
|
|
230
|
+
get projectRoot() {
|
|
231
|
+
return this.projectPath;
|
|
232
|
+
}
|
|
233
|
+
async addNode(type, data) {
|
|
234
|
+
const now = (/* @__PURE__ */ new Date()).toISOString();
|
|
235
|
+
const id = this.generateNodeId(type, data);
|
|
236
|
+
const node = {
|
|
237
|
+
id,
|
|
238
|
+
type,
|
|
239
|
+
data,
|
|
240
|
+
created_at: now,
|
|
241
|
+
updated_at: now
|
|
242
|
+
};
|
|
243
|
+
this.store.addNode(node);
|
|
244
|
+
return node;
|
|
245
|
+
}
|
|
246
|
+
async getNode(type, id) {
|
|
247
|
+
return this.store.getNodeByType(type, id);
|
|
248
|
+
}
|
|
249
|
+
async updateNode(type, id, updates) {
|
|
250
|
+
const updated = this.store.updateNode(id, updates, (/* @__PURE__ */ new Date()).toISOString());
|
|
251
|
+
if (updated && updated.type !== type) {
|
|
252
|
+
throw new Error(`Type mismatch for node ${id}: expected ${type} but found ${updated.type}`);
|
|
253
|
+
}
|
|
254
|
+
}
|
|
255
|
+
async deleteNode(_type, id) {
|
|
256
|
+
this.store.deleteNode(id);
|
|
257
|
+
}
|
|
258
|
+
async addEdge(fromId, toId, type, metadata = {}, weight = 1) {
|
|
259
|
+
const edge = {
|
|
260
|
+
id: crypto.randomUUID(),
|
|
261
|
+
from_id: fromId,
|
|
262
|
+
to_id: toId,
|
|
263
|
+
type,
|
|
264
|
+
weight,
|
|
265
|
+
metadata,
|
|
266
|
+
created_at: (/* @__PURE__ */ new Date()).toISOString()
|
|
267
|
+
};
|
|
268
|
+
this.store.addEdge(edge);
|
|
269
|
+
return edge;
|
|
270
|
+
}
|
|
271
|
+
async getEdges(nodeId, direction = "both") {
|
|
272
|
+
return this.store.getEdges(nodeId, direction);
|
|
273
|
+
}
|
|
274
|
+
async getIncidentsForFile(filePath) {
|
|
275
|
+
const fileNode = this.findFileNode(filePath);
|
|
276
|
+
if (!fileNode) return [];
|
|
277
|
+
const incidents = /* @__PURE__ */ new Map();
|
|
278
|
+
const affectEdges = this.store.getEdges(fileNode.id, "in").filter((edge) => edge.type === "affects");
|
|
279
|
+
for (const edge of affectEdges) {
|
|
280
|
+
const changeId = edge.from_id;
|
|
281
|
+
const leadEdges = this.store.getEdges(changeId, "out").filter((e) => e.type === "leadTo");
|
|
282
|
+
const causedByEdges = this.store.getEdges(changeId, "in").filter((e) => e.type === "causedBy");
|
|
283
|
+
for (const le of leadEdges) {
|
|
284
|
+
const incident = this.store.getNodeByType("incident", le.to_id);
|
|
285
|
+
if (incident) incidents.set(incident.id, incident);
|
|
286
|
+
}
|
|
287
|
+
for (const ce of causedByEdges) {
|
|
288
|
+
const incident = this.store.getNodeByType("incident", ce.from_id);
|
|
289
|
+
if (incident) incidents.set(incident.id, incident);
|
|
290
|
+
}
|
|
291
|
+
}
|
|
292
|
+
return Array.from(incidents.values());
|
|
293
|
+
}
|
|
294
|
+
async getPatternsForFile(filePath) {
|
|
295
|
+
const normalized = this.normalizePath(filePath);
|
|
296
|
+
const nodes = this.store.findNodesByType("pattern");
|
|
297
|
+
return nodes.filter(
|
|
298
|
+
(node) => node.data.appliesTo.some((pattern) => normalized.includes(pattern) || filePath.includes(pattern))
|
|
299
|
+
);
|
|
300
|
+
}
|
|
301
|
+
async getRecentChanges(limit) {
|
|
302
|
+
const nodes = this.store.findNodesByType("change");
|
|
303
|
+
return nodes.sort((a, b) => new Date(b.data.timestamp).getTime() - new Date(a.data.timestamp).getTime()).slice(0, limit);
|
|
304
|
+
}
|
|
305
|
+
async calculateFileRisk(filePath) {
|
|
306
|
+
const fileNode = this.findFileNode(filePath);
|
|
307
|
+
if (!fileNode) return "low";
|
|
308
|
+
const incidentScore = Math.min(fileNode.data.incidentCount * 2, 6);
|
|
309
|
+
const changeScore = Math.min(fileNode.data.changeCount, 4);
|
|
310
|
+
const baseScore = this.riskLevelToScore(fileNode.data.riskLevel);
|
|
311
|
+
const total = baseScore + incidentScore + changeScore;
|
|
312
|
+
if (total >= 10) return "critical";
|
|
313
|
+
if (total >= 7) return "high";
|
|
314
|
+
if (total >= 4) return "medium";
|
|
315
|
+
return "low";
|
|
316
|
+
}
|
|
317
|
+
async listNodes() {
|
|
318
|
+
return this.store.listNodes();
|
|
319
|
+
}
|
|
320
|
+
async listEdges() {
|
|
321
|
+
return this.store.listEdges();
|
|
322
|
+
}
|
|
323
|
+
async deleteEdge(id) {
|
|
324
|
+
this.store.deleteEdge(id);
|
|
325
|
+
}
|
|
326
|
+
async getSnapshot() {
|
|
327
|
+
return {
|
|
328
|
+
nodes: this.store.listNodes(),
|
|
329
|
+
edges: this.store.listEdges(),
|
|
330
|
+
exported_at: (/* @__PURE__ */ new Date()).toISOString()
|
|
331
|
+
};
|
|
332
|
+
}
|
|
333
|
+
async applySnapshot(snapshot) {
|
|
334
|
+
for (const node of snapshot.nodes) {
|
|
335
|
+
const existing = this.store.getNode(node.id);
|
|
336
|
+
if (!existing || this.isNewer(node.updated_at, existing.updated_at)) {
|
|
337
|
+
this.store.upsertNode(node);
|
|
338
|
+
}
|
|
339
|
+
}
|
|
340
|
+
for (const edge of snapshot.edges) {
|
|
341
|
+
const existing = this.store.getEdge(edge.id);
|
|
342
|
+
if (!existing) {
|
|
343
|
+
this.store.upsertEdge(edge);
|
|
344
|
+
}
|
|
345
|
+
}
|
|
346
|
+
}
|
|
347
|
+
generateNodeId(type, data) {
|
|
348
|
+
if (type === "file") {
|
|
349
|
+
const fileData = data;
|
|
350
|
+
return this.normalizePath(fileData.path);
|
|
351
|
+
}
|
|
352
|
+
if (type === "change") {
|
|
353
|
+
const changeData = data;
|
|
354
|
+
if (changeData.commitHash) {
|
|
355
|
+
return changeData.commitHash;
|
|
356
|
+
}
|
|
357
|
+
}
|
|
358
|
+
if (type === "linear-ticket") {
|
|
359
|
+
const ticketData = data;
|
|
360
|
+
return `linear:${ticketData.ticketId}`;
|
|
361
|
+
}
|
|
362
|
+
return crypto.randomUUID();
|
|
363
|
+
}
|
|
364
|
+
findFileNode(filePath) {
|
|
365
|
+
const normalized = this.normalizePath(filePath);
|
|
366
|
+
const nodes = this.store.findNodesByType("file");
|
|
367
|
+
return nodes.find(
|
|
368
|
+
(node) => node.id === normalized || this.normalizePath(node.data.path) === normalized || node.data.path === filePath
|
|
369
|
+
) ?? null;
|
|
370
|
+
}
|
|
371
|
+
normalizePath(filePath) {
|
|
372
|
+
return path2.resolve(this.projectPath, filePath);
|
|
373
|
+
}
|
|
374
|
+
riskLevelToScore(level) {
|
|
375
|
+
switch (level) {
|
|
376
|
+
case "critical":
|
|
377
|
+
return 6;
|
|
378
|
+
case "high":
|
|
379
|
+
return 4;
|
|
380
|
+
case "medium":
|
|
381
|
+
return 2;
|
|
382
|
+
default:
|
|
383
|
+
return 0;
|
|
384
|
+
}
|
|
385
|
+
}
|
|
386
|
+
isNewer(incoming, existing) {
|
|
387
|
+
return new Date(incoming).getTime() >= new Date(existing).getTime();
|
|
388
|
+
}
|
|
389
|
+
};
|
|
390
|
+
|
|
391
|
+
export {
|
|
392
|
+
ContextGraph
|
|
393
|
+
};
|
|
394
|
+
//# sourceMappingURL=chunk-NS2MSZMB.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/context/graph.ts","../src/context/store.ts"],"sourcesContent":["import crypto from 'node:crypto';\nimport path from 'node:path';\n\nimport type { RiskLevel } from '../types/index.js';\nimport { ContextStore } from './store.js';\nimport type {\n ChangeNode,\n ChangeNodeData,\n ContextSnapshot,\n DecisionNode,\n DecisionNodeData,\n Edge,\n EdgeDirection,\n EdgeType,\n FileNode,\n FileNodeData,\n FixNode,\n FixNodeData,\n IncidentNode,\n IncidentNodeData,\n IssueNode,\n IssueNodeData,\n LinearTicketNode,\n LinearTicketNodeData,\n Node,\n NodeData,\n NodeType,\n PatternNode,\n PatternNodeData\n} from './types.js';\n\nexport class ContextGraph {\n private readonly store: ContextStore;\n private readonly projectPath: string;\n\n constructor(projectPath: string, dbPath?: string, store?: ContextStore) {\n this.projectPath = projectPath;\n this.store = store ?? new ContextStore(projectPath, dbPath);\n }\n\n get projectRoot(): string {\n return this.projectPath;\n }\n\n async addNode(type: 'file', data: FileNodeData): Promise<FileNode>;\n async addNode(type: 'change', data: ChangeNodeData): Promise<ChangeNode>;\n async addNode(type: 'incident', data: IncidentNodeData): Promise<IncidentNode>;\n async addNode(type: 'issue', data: IssueNodeData): Promise<IssueNode>;\n async addNode(type: 'pattern', data: PatternNodeData): Promise<PatternNode>;\n async addNode(type: 'fix', data: FixNodeData): Promise<FixNode>;\n async addNode(type: 'decision', data: DecisionNodeData): Promise<DecisionNode>;\n async addNode(type: 'linear-ticket', data: LinearTicketNodeData): Promise<LinearTicketNode>;\n async addNode(type: NodeType, data: NodeData): Promise<Node> {\n const now = new Date().toISOString();\n const id = this.generateNodeId(type, data);\n const node = {\n id,\n type,\n data,\n created_at: now,\n updated_at: now\n } as Node;\n\n this.store.addNode(node);\n return node;\n }\n\n async getNode(type: NodeType, id: string): Promise<Node | null> {\n return this.store.getNodeByType(type, id);\n }\n\n async updateNode(type: NodeType, id: string, updates: Partial<NodeData>): Promise<void> {\n const updated = this.store.updateNode(id, updates, new Date().toISOString());\n if (updated && updated.type !== type) {\n throw new Error(`Type mismatch for node ${id}: expected ${type} but found ${updated.type}`);\n }\n }\n\n async deleteNode(_type: NodeType, id: string): Promise<void> {\n this.store.deleteNode(id);\n }\n\n async addEdge(\n fromId: string,\n toId: string,\n type: EdgeType,\n metadata: Record<string, unknown> = {},\n weight = 1\n ): Promise<Edge> {\n const edge: Edge = {\n id: crypto.randomUUID(),\n from_id: fromId,\n to_id: toId,\n type,\n weight,\n metadata,\n created_at: new Date().toISOString()\n };\n\n this.store.addEdge(edge);\n return edge;\n }\n\n async getEdges(nodeId: string, direction: EdgeDirection = 'both'): Promise<Edge[]> {\n return this.store.getEdges(nodeId, direction);\n }\n\n async getIncidentsForFile(filePath: string): Promise<IncidentNode[]> {\n const fileNode = this.findFileNode(filePath);\n if (!fileNode) return [];\n\n const incidents = new Map<string, IncidentNode>();\n\n const affectEdges = this.store.getEdges(fileNode.id, 'in').filter((edge) => edge.type === 'affects');\n for (const edge of affectEdges) {\n const changeId = edge.from_id;\n const leadEdges = this.store.getEdges(changeId, 'out').filter((e) => e.type === 'leadTo');\n const causedByEdges = this.store.getEdges(changeId, 'in').filter((e) => e.type === 'causedBy');\n\n for (const le of leadEdges) {\n const incident = this.store.getNodeByType('incident', le.to_id);\n if (incident) incidents.set(incident.id, incident as IncidentNode);\n }\n\n for (const ce of causedByEdges) {\n const incident = this.store.getNodeByType('incident', ce.from_id);\n if (incident) incidents.set(incident.id, incident as IncidentNode);\n }\n }\n\n return Array.from(incidents.values());\n }\n\n async getPatternsForFile(filePath: string): Promise<PatternNode[]> {\n const normalized = this.normalizePath(filePath);\n const nodes = this.store.findNodesByType('pattern') as PatternNode[];\n\n return nodes.filter((node) =>\n node.data.appliesTo.some((pattern) => normalized.includes(pattern) || filePath.includes(pattern))\n );\n }\n\n async getRecentChanges(limit: number): Promise<ChangeNode[]> {\n const nodes = this.store.findNodesByType('change') as ChangeNode[];\n return nodes\n .sort((a, b) => new Date(b.data.timestamp).getTime() - new Date(a.data.timestamp).getTime())\n .slice(0, limit);\n }\n\n async calculateFileRisk(filePath: string): Promise<RiskLevel> {\n const fileNode = this.findFileNode(filePath);\n if (!fileNode) return 'low';\n\n // Simple heuristic based on incidents and changes\n const incidentScore = Math.min(fileNode.data.incidentCount * 2, 6);\n const changeScore = Math.min(fileNode.data.changeCount, 4);\n const baseScore = this.riskLevelToScore(fileNode.data.riskLevel);\n const total = baseScore + incidentScore + changeScore;\n\n if (total >= 10) return 'critical';\n if (total >= 7) return 'high';\n if (total >= 4) return 'medium';\n return 'low';\n }\n\n async listNodes(): Promise<Node[]> {\n return this.store.listNodes();\n }\n\n async listEdges(): Promise<Edge[]> {\n return this.store.listEdges();\n }\n\n async deleteEdge(id: string): Promise<void> {\n this.store.deleteEdge(id);\n }\n\n async getSnapshot(): Promise<ContextSnapshot> {\n return {\n nodes: this.store.listNodes(),\n edges: this.store.listEdges(),\n exported_at: new Date().toISOString()\n };\n }\n\n async applySnapshot(snapshot: ContextSnapshot): Promise<void> {\n for (const node of snapshot.nodes) {\n const existing = this.store.getNode(node.id);\n if (!existing || this.isNewer(node.updated_at, existing.updated_at)) {\n this.store.upsertNode(node);\n }\n }\n\n for (const edge of snapshot.edges) {\n const existing = this.store.getEdge(edge.id);\n if (!existing) {\n this.store.upsertEdge(edge);\n }\n }\n }\n\n private generateNodeId(type: NodeType, data: NodeData): string {\n if (type === 'file') {\n const fileData = data as FileNodeData;\n return this.normalizePath(fileData.path);\n }\n\n if (type === 'change') {\n const changeData = data as ChangeNodeData;\n if (changeData.commitHash) {\n return changeData.commitHash;\n }\n }\n\n if (type === 'linear-ticket') {\n const ticketData = data as LinearTicketNodeData;\n return `linear:${ticketData.ticketId}`;\n }\n\n return crypto.randomUUID();\n }\n\n private findFileNode(filePath: string): FileNode | null {\n const normalized = this.normalizePath(filePath);\n const nodes = this.store.findNodesByType('file') as FileNode[];\n return (\n nodes.find(\n (node) =>\n node.id === normalized ||\n this.normalizePath(node.data.path) === normalized ||\n node.data.path === filePath\n ) ?? null\n );\n }\n\n private normalizePath(filePath: string): string {\n return path.resolve(this.projectPath, filePath);\n }\n\n private riskLevelToScore(level: RiskLevel): number {\n switch (level) {\n case 'critical':\n return 6;\n case 'high':\n return 4;\n case 'medium':\n return 2;\n default:\n return 0;\n }\n }\n\n private isNewer(incoming: string, existing: string): boolean {\n return new Date(incoming).getTime() >= new Date(existing).getTime();\n }\n}\n","import Database, { type Database as DatabaseType } from 'better-sqlite3';\nimport fs from 'node:fs';\nimport path from 'node:path';\nimport { getTrieDirectory } from '../utils/workspace.js';\n\nimport type { Edge, EdgeDirection, EdgeType, Node, NodeData, NodeType } from './types.js';\n\ntype NodeRow = {\n id: string;\n type: NodeType;\n data: string;\n created_at: string;\n updated_at: string;\n};\n\ntype EdgeRow = {\n id: string;\n from_id: string;\n to_id: string;\n type: EdgeType;\n weight: number;\n metadata: string | null;\n created_at: string;\n};\n\nexport class ContextStore {\n private db: DatabaseType;\n private readonly dbFilePath: string;\n\n constructor(projectPath: string, dbFilePath?: string) {\n this.dbFilePath = dbFilePath ?? path.join(getTrieDirectory(projectPath), 'context.db');\n this.ensureDirectory();\n\n this.db = new Database(this.dbFilePath);\n this.configure();\n this.prepareSchema();\n }\n\n get databasePath(): string {\n return this.dbFilePath;\n }\n\n addNode(node: Node): Node {\n const stmt = this.db.prepare(\n `INSERT INTO nodes (id, type, data, created_at, updated_at)\n VALUES (@id, @type, @data, @created_at, @updated_at)`\n );\n\n stmt.run({\n id: node.id,\n type: node.type,\n data: JSON.stringify(node.data),\n created_at: node.created_at,\n updated_at: node.updated_at\n });\n\n return node;\n }\n\n upsertNode(node: Node): Node {\n const stmt = this.db.prepare(\n `INSERT INTO nodes (id, type, data, created_at, updated_at)\n VALUES (@id, @type, @data, @created_at, @updated_at)\n ON CONFLICT(id) DO UPDATE SET\n type=excluded.type,\n data=excluded.data,\n updated_at=excluded.updated_at`\n );\n\n stmt.run({\n id: node.id,\n type: node.type,\n data: JSON.stringify(node.data),\n created_at: node.created_at,\n updated_at: node.updated_at\n });\n\n return node;\n }\n\n getNode(id: string): Node | null {\n const row = this.db.prepare('SELECT * FROM nodes WHERE id = ?').get(id) as NodeRow | undefined;\n return row ? this.mapNodeRow(row) : null;\n }\n\n getNodeByType(type: NodeType, id: string): Node | null {\n const row = this.db\n .prepare('SELECT * FROM nodes WHERE id = ? AND type = ?')\n .get(id, type) as NodeRow | undefined;\n return row ? this.mapNodeRow(row) : null;\n }\n\n updateNode(id: string, updates: Partial<NodeData>, updatedAt: string): Node | null {\n const existing = this.getNode(id);\n if (!existing) {\n return null;\n }\n\n const merged = {\n ...existing,\n data: { ...existing.data, ...updates },\n updated_at: updatedAt\n } as Node;\n\n this.db\n .prepare(\n `UPDATE nodes SET data = @data, updated_at = @updated_at\n WHERE id = @id`\n )\n .run({\n id,\n data: JSON.stringify(merged.data),\n updated_at: merged.updated_at\n });\n\n return merged;\n }\n\n deleteNode(id: string): void {\n const deleteEdges = this.db.prepare('DELETE FROM edges WHERE from_id = ? OR to_id = ?');\n const deleteNodeStmt = this.db.prepare('DELETE FROM nodes WHERE id = ?');\n\n const transaction = this.db.transaction((nodeId: string) => {\n deleteEdges.run(nodeId, nodeId);\n deleteNodeStmt.run(nodeId);\n });\n\n transaction(id);\n }\n\n listNodes(): Node[] {\n const rows = this.db.prepare('SELECT * FROM nodes').all() as NodeRow[];\n return rows.map((row) => this.mapNodeRow(row));\n }\n\n findNodesByType(type: NodeType): Node[] {\n const rows = this.db.prepare('SELECT * FROM nodes WHERE type = ?').all(type) as NodeRow[];\n return rows.map((row) => this.mapNodeRow(row));\n }\n\n addEdge(edge: Edge): Edge {\n const stmt = this.db.prepare(\n `INSERT INTO edges (id, from_id, to_id, type, weight, metadata, created_at)\n VALUES (@id, @from_id, @to_id, @type, @weight, @metadata, @created_at)`\n );\n\n stmt.run({\n id: edge.id,\n from_id: edge.from_id,\n to_id: edge.to_id,\n type: edge.type,\n weight: edge.weight,\n metadata: JSON.stringify(edge.metadata ?? {}),\n created_at: edge.created_at\n });\n\n return edge;\n }\n\n upsertEdge(edge: Edge): Edge {\n const stmt = this.db.prepare(\n `INSERT INTO edges (id, from_id, to_id, type, weight, metadata, created_at)\n VALUES (@id, @from_id, @to_id, @type, @weight, @metadata, @created_at)\n ON CONFLICT(id) DO UPDATE SET\n from_id=excluded.from_id,\n to_id=excluded.to_id,\n type=excluded.type,\n weight=excluded.weight,\n metadata=excluded.metadata`\n );\n\n stmt.run({\n id: edge.id,\n from_id: edge.from_id,\n to_id: edge.to_id,\n type: edge.type,\n weight: edge.weight,\n metadata: JSON.stringify(edge.metadata ?? {}),\n created_at: edge.created_at\n });\n\n return edge;\n }\n\n getEdge(id: string): Edge | null {\n const row = this.db.prepare('SELECT * FROM edges WHERE id = ?').get(id) as EdgeRow | undefined;\n return row ? this.mapEdgeRow(row) : null;\n }\n\n getEdges(nodeId: string, direction: EdgeDirection = 'both'): Edge[] {\n let rows: EdgeRow[];\n\n if (direction === 'in') {\n rows = this.db.prepare('SELECT * FROM edges WHERE to_id = ?').all(nodeId) as EdgeRow[];\n } else if (direction === 'out') {\n rows = this.db.prepare('SELECT * FROM edges WHERE from_id = ?').all(nodeId) as EdgeRow[];\n } else {\n rows = this.db\n .prepare('SELECT * FROM edges WHERE from_id = ? OR to_id = ?')\n .all(nodeId, nodeId) as EdgeRow[];\n }\n\n return rows.map((row) => this.mapEdgeRow(row));\n }\n\n listEdges(): Edge[] {\n const rows = this.db.prepare('SELECT * FROM edges').all() as EdgeRow[];\n return rows.map((row) => this.mapEdgeRow(row));\n }\n\n deleteEdge(id: string): void {\n this.db.prepare('DELETE FROM edges WHERE id = ?').run(id);\n }\n\n close(): void {\n this.db.close();\n }\n\n private ensureDirectory(): void {\n fs.mkdirSync(path.dirname(this.dbFilePath), { recursive: true });\n }\n\n private configure(): void {\n this.db.pragma('journal_mode = WAL');\n this.db.pragma('busy_timeout = 5000');\n this.db.pragma('synchronous = NORMAL');\n }\n\n private prepareSchema(): void {\n this.db.exec(`\n CREATE TABLE IF NOT EXISTS nodes (\n id TEXT PRIMARY KEY,\n type TEXT NOT NULL,\n data TEXT NOT NULL,\n created_at TEXT NOT NULL,\n updated_at TEXT NOT NULL\n );\n\n CREATE TABLE IF NOT EXISTS edges (\n id TEXT PRIMARY KEY,\n from_id TEXT NOT NULL,\n to_id TEXT NOT NULL,\n type TEXT NOT NULL,\n weight REAL NOT NULL DEFAULT 1,\n metadata TEXT DEFAULT '{}',\n created_at TEXT NOT NULL\n );\n\n CREATE INDEX IF NOT EXISTS idx_nodes_type ON nodes(type);\n CREATE INDEX IF NOT EXISTS idx_edges_from ON edges(from_id);\n CREATE INDEX IF NOT EXISTS idx_edges_to ON edges(to_id);\n CREATE INDEX IF NOT EXISTS idx_edges_type ON edges(type);\n `);\n }\n\n private mapNodeRow(row: NodeRow): Node {\n return {\n id: row.id,\n type: row.type,\n data: JSON.parse(row.data),\n created_at: row.created_at,\n updated_at: row.updated_at\n } as Node;\n }\n\n private mapEdgeRow(row: EdgeRow): Edge {\n return {\n id: row.id,\n from_id: row.from_id,\n to_id: row.to_id,\n type: row.type,\n weight: row.weight,\n created_at: row.created_at,\n metadata: row.metadata ? (JSON.parse(row.metadata) as Record<string, unknown>) : {}\n };\n }\n}\n"],"mappings":"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","names":["path","path"]}
|