@fingerskier/augment 0.1.9 → 0.2.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/README.md +20 -2
- package/dist/cli.d.ts +6 -0
- package/dist/cli.js +43 -2
- package/dist/cli.js.map +1 -1
- package/dist/constants.d.ts +6 -0
- package/dist/constants.js +46 -6
- package/dist/constants.js.map +1 -1
- package/dist/daemon/client.d.ts +5 -0
- package/dist/daemon/client.js +15 -6
- package/dist/daemon/client.js.map +1 -1
- package/dist/daemon/http.d.ts +1 -1
- package/dist/daemon/http.js +159 -53
- package/dist/daemon/http.js.map +1 -1
- package/dist/daemon/main.js +15 -1
- package/dist/daemon/main.js.map +1 -1
- package/dist/daemon/scheduler.d.ts +17 -0
- package/dist/daemon/scheduler.js +77 -0
- package/dist/daemon/scheduler.js.map +1 -0
- package/dist/daemon/single-instance.d.ts +32 -0
- package/dist/daemon/single-instance.js +131 -0
- package/dist/daemon/single-instance.js.map +1 -0
- package/dist/db.d.ts +13 -1
- package/dist/db.js +166 -105
- package/dist/db.js.map +1 -1
- package/dist/embeddings.js +8 -0
- package/dist/embeddings.js.map +1 -1
- package/dist/hooks.js +28 -3
- package/dist/hooks.js.map +1 -1
- package/dist/install.d.ts +2 -0
- package/dist/install.js +41 -7
- package/dist/install.js.map +1 -1
- package/dist/mcp/server.js +30 -4
- package/dist/mcp/server.js.map +1 -1
- package/dist/recall.d.ts +2 -0
- package/dist/recall.js +1 -0
- package/dist/recall.js.map +1 -1
- package/dist/service.d.ts +64 -1
- package/dist/service.js +298 -38
- package/dist/service.js.map +1 -1
- package/dist/sleep.d.ts +43 -0
- package/dist/sleep.js +129 -0
- package/dist/sleep.js.map +1 -0
- package/dist/tally.d.ts +46 -0
- package/dist/tally.js +94 -0
- package/dist/tally.js.map +1 -0
- package/dist/types.d.ts +6 -0
- package/dist/util/text.d.ts +3 -0
- package/dist/util/text.js +26 -2
- package/dist/util/text.js.map +1 -1
- package/docs/FEATURES.md +161 -51
- package/docs/verify-memory-flow.md +28 -9
- package/package.json +2 -1
package/dist/daemon/http.js
CHANGED
|
@@ -1,65 +1,121 @@
|
|
|
1
1
|
import { writeFile } from "node:fs/promises";
|
|
2
2
|
import http from "node:http";
|
|
3
|
+
import path from "node:path";
|
|
3
4
|
import chokidar from "chokidar";
|
|
4
5
|
import { EMBEDDING_MODEL_ID } from "../constants.js";
|
|
5
6
|
import { cytoscapeBundleJs, dashboardAsset } from "../dashboard/assets.js";
|
|
7
|
+
import { ensureConfigDirs } from "../config.js";
|
|
8
|
+
import { appendTallyEvent, appendTallyRating, isTallyVerdict, readTallyRatings, renderTallySummary, summarizeTally, TALLY_VERDICTS, } from "../tally.js";
|
|
9
|
+
import { createIndexScheduler } from "./scheduler.js";
|
|
10
|
+
import { acquireSingleInstance } from "./single-instance.js";
|
|
6
11
|
export async function startHttpDaemon(config, service) {
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
12
|
+
// The daemon file and watcher need the state/memory dirs before the (now
|
|
13
|
+
// backgrounded) initial index gets a chance to create them.
|
|
14
|
+
await ensureConfigDirs(config);
|
|
15
|
+
// Single-instance guard: refuse to start if a healthy daemon already owns this
|
|
16
|
+
// state dir, so two daemons never co-open the sqlite index (SQLITE_BUSY). The
|
|
17
|
+
// db handle is lazy, so throwing here means the duplicate never touches it.
|
|
18
|
+
const instanceLock = await acquireSingleInstance(config);
|
|
19
|
+
// Everything past the slot claim runs under one guard: any startup failure
|
|
20
|
+
// (bind error, daemon.json write, watcher wiring) must release the slot and
|
|
21
|
+
// close whatever we opened, or a stranded pidfile would wrongly block the next
|
|
22
|
+
// start (and, once its pid is reused, block it forever).
|
|
23
|
+
let server;
|
|
24
|
+
try {
|
|
25
|
+
// Listen first, index in the background: on a cold corpus the initial index
|
|
26
|
+
// can take minutes of embedding, and clients (hooks especially) must not time
|
|
27
|
+
// out against an unbound port. /index/status reports readiness.
|
|
28
|
+
const indexState = { ready: false };
|
|
29
|
+
const initPromise = service
|
|
30
|
+
.init()
|
|
31
|
+
.then(() => {
|
|
32
|
+
indexState.ready = true;
|
|
33
|
+
})
|
|
34
|
+
.catch((error) => {
|
|
35
|
+
indexState.error = errorMessage(error);
|
|
36
|
+
console.error("augment: initial index failed:", error);
|
|
11
37
|
});
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
38
|
+
server = http.createServer((request, response) => {
|
|
39
|
+
handleRequest(service, indexState, config, request, response).catch((error) => {
|
|
40
|
+
sendJson(response, 500, { error: errorMessage(error) });
|
|
41
|
+
});
|
|
42
|
+
});
|
|
43
|
+
const boundServer = server;
|
|
44
|
+
const port = config.daemonPort ?? 0;
|
|
45
|
+
await new Promise((resolve, reject) => {
|
|
46
|
+
boundServer.once("error", reject);
|
|
47
|
+
boundServer.listen(port, "127.0.0.1", () => {
|
|
48
|
+
boundServer.off("error", reject);
|
|
49
|
+
resolve();
|
|
50
|
+
});
|
|
19
51
|
});
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
throw new Error("Failed to determine daemon address");
|
|
24
|
-
}
|
|
25
|
-
const info = {
|
|
26
|
-
pid: process.pid,
|
|
27
|
-
endpoint: `http://127.0.0.1:${address.port}`,
|
|
28
|
-
memoryRoot: config.memoryRoot,
|
|
29
|
-
model: EMBEDDING_MODEL_ID,
|
|
30
|
-
startedAt: new Date().toISOString(),
|
|
31
|
-
};
|
|
32
|
-
await writeFile(config.daemonFile, JSON.stringify(info, null, 2), "utf8");
|
|
33
|
-
let rebuildTimer;
|
|
34
|
-
const watcher = chokidar.watch(config.memoryRoot, {
|
|
35
|
-
ignoreInitial: true,
|
|
36
|
-
awaitWriteFinish: { stabilityThreshold: 250, pollInterval: 50 },
|
|
37
|
-
});
|
|
38
|
-
const scheduleRebuild = () => {
|
|
39
|
-
if (rebuildTimer) {
|
|
40
|
-
clearTimeout(rebuildTimer);
|
|
52
|
+
const address = boundServer.address();
|
|
53
|
+
if (!address || typeof address === "string") {
|
|
54
|
+
throw new Error("Failed to determine daemon address");
|
|
41
55
|
}
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
56
|
+
const info = {
|
|
57
|
+
pid: process.pid,
|
|
58
|
+
endpoint: `http://127.0.0.1:${address.port}`,
|
|
59
|
+
memoryRoot: config.memoryRoot,
|
|
60
|
+
model: EMBEDDING_MODEL_ID,
|
|
61
|
+
startedAt: new Date().toISOString(),
|
|
62
|
+
};
|
|
63
|
+
await writeFile(config.daemonFile, JSON.stringify(info, null, 2), "utf8");
|
|
64
|
+
const scheduler = createIndexScheduler(async (paths) => {
|
|
65
|
+
for (const relativePath of paths) {
|
|
66
|
+
await service.indexPath(relativePath).catch((error) => {
|
|
67
|
+
console.error(`augment: incremental index failed for ${relativePath}:`, error);
|
|
68
|
+
});
|
|
54
69
|
}
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
70
|
+
});
|
|
71
|
+
const watcher = chokidar.watch(config.memoryRoot, {
|
|
72
|
+
ignoreInitial: true,
|
|
73
|
+
ignored: /(^|[\\/])\.git([\\/]|$)/,
|
|
74
|
+
awaitWriteFinish: { stabilityThreshold: 250, pollInterval: 50 },
|
|
75
|
+
});
|
|
76
|
+
const onWatchEvent = (eventPath) => {
|
|
77
|
+
const relativePath = path.relative(config.memoryRoot, eventPath).split(path.sep).join("/");
|
|
78
|
+
if (!relativePath || relativePath.startsWith("..") || !relativePath.endsWith(".md")) {
|
|
79
|
+
return;
|
|
80
|
+
}
|
|
81
|
+
// Echoes of the service's own writes are already indexed inline; only
|
|
82
|
+
// external edits (editor saves, Dropbox sync) need the incremental pass.
|
|
83
|
+
if (service.consumeSelfWrite(relativePath)) {
|
|
84
|
+
return;
|
|
85
|
+
}
|
|
86
|
+
scheduler.schedule(relativePath);
|
|
87
|
+
};
|
|
88
|
+
watcher.on("add", onWatchEvent);
|
|
89
|
+
watcher.on("change", onWatchEvent);
|
|
90
|
+
watcher.on("unlink", onWatchEvent);
|
|
91
|
+
return {
|
|
92
|
+
info,
|
|
93
|
+
async close() {
|
|
94
|
+
// Release the slot no matter how teardown goes, so a failing watcher or
|
|
95
|
+
// server close can't strand the pidfile.
|
|
96
|
+
try {
|
|
97
|
+
await watcher.close();
|
|
98
|
+
await scheduler.close();
|
|
99
|
+
await initPromise;
|
|
100
|
+
await new Promise((resolve, reject) => {
|
|
101
|
+
boundServer.close((error) => (error ? reject(error) : resolve()));
|
|
102
|
+
});
|
|
103
|
+
}
|
|
104
|
+
finally {
|
|
105
|
+
await instanceLock.release();
|
|
106
|
+
}
|
|
107
|
+
},
|
|
108
|
+
};
|
|
109
|
+
}
|
|
110
|
+
catch (error) {
|
|
111
|
+
await instanceLock.release().catch(() => { });
|
|
112
|
+
if (server) {
|
|
113
|
+
await new Promise((resolve) => server.close(() => resolve()));
|
|
114
|
+
}
|
|
115
|
+
throw error;
|
|
116
|
+
}
|
|
61
117
|
}
|
|
62
|
-
async function handleRequest(service, request, response) {
|
|
118
|
+
async function handleRequest(service, indexState, config, request, response) {
|
|
63
119
|
const url = new URL(request.url ?? "/", "http://127.0.0.1");
|
|
64
120
|
if (request.method === "GET" && url.pathname === "/health") {
|
|
65
121
|
sendJson(response, 200, { ok: true, pid: process.pid, title: process.title });
|
|
@@ -103,7 +159,26 @@ async function handleRequest(service, request, response) {
|
|
|
103
159
|
return;
|
|
104
160
|
}
|
|
105
161
|
if (request.method === "POST" && url.pathname === "/memories/search") {
|
|
106
|
-
|
|
162
|
+
const body = (await readJson(request));
|
|
163
|
+
const output = await service.search(body);
|
|
164
|
+
try {
|
|
165
|
+
// Phase-2 dogfood instrumentation. Best-effort by design: search must
|
|
166
|
+
// never fail because the tally could not be written.
|
|
167
|
+
await appendTallyEvent(config.stateDir, {
|
|
168
|
+
ts: new Date().toISOString(),
|
|
169
|
+
surface: body.surface ?? "unknown",
|
|
170
|
+
project: body.project_name,
|
|
171
|
+
query: String(body.query ?? "").slice(0, 200),
|
|
172
|
+
abstained: output.results.length === 0,
|
|
173
|
+
result_count: output.results.length,
|
|
174
|
+
...(output.results[0] ? { top_score: output.results[0].score } : {}),
|
|
175
|
+
paths: output.results.map((result) => result.memory.relative_path),
|
|
176
|
+
});
|
|
177
|
+
}
|
|
178
|
+
catch {
|
|
179
|
+
// fail open
|
|
180
|
+
}
|
|
181
|
+
sendJson(response, 200, output);
|
|
107
182
|
return;
|
|
108
183
|
}
|
|
109
184
|
if (request.method === "POST" && url.pathname === "/memories/upsert") {
|
|
@@ -139,7 +214,34 @@ async function handleRequest(service, request, response) {
|
|
|
139
214
|
return;
|
|
140
215
|
}
|
|
141
216
|
if (request.method === "GET" && url.pathname === "/index/status") {
|
|
142
|
-
sendJson(response, 200, {
|
|
217
|
+
sendJson(response, 200, {
|
|
218
|
+
ok: indexState.error === undefined,
|
|
219
|
+
ready: indexState.ready,
|
|
220
|
+
...(indexState.error !== undefined ? { error: indexState.error } : {}),
|
|
221
|
+
});
|
|
222
|
+
return;
|
|
223
|
+
}
|
|
224
|
+
if (request.method === "POST" && url.pathname === "/tally") {
|
|
225
|
+
const body = (await readJson(request));
|
|
226
|
+
if (!isTallyVerdict(body.verdict)) {
|
|
227
|
+
sendJson(response, 400, { error: `verdict must be one of: ${TALLY_VERDICTS.join(", ")}` });
|
|
228
|
+
return;
|
|
229
|
+
}
|
|
230
|
+
await appendTallyRating(config.stateDir, {
|
|
231
|
+
ts: new Date().toISOString(),
|
|
232
|
+
verdict: body.verdict,
|
|
233
|
+
surface: typeof body.surface === "string" && body.surface ? body.surface : "unknown",
|
|
234
|
+
...(typeof body.note === "string" && body.note ? { note: body.note } : {}),
|
|
235
|
+
});
|
|
236
|
+
await sendTallySummary(response, config.stateDir);
|
|
237
|
+
return;
|
|
238
|
+
}
|
|
239
|
+
if (request.method === "GET" && url.pathname === "/tally") {
|
|
240
|
+
await sendTallySummary(response, config.stateDir);
|
|
241
|
+
return;
|
|
242
|
+
}
|
|
243
|
+
if (request.method === "POST" && url.pathname === "/sleep/candidates") {
|
|
244
|
+
sendJson(response, 200, await service.sleepCandidates(await readJson(request)));
|
|
143
245
|
return;
|
|
144
246
|
}
|
|
145
247
|
sendJson(response, 404, { error: "not found" });
|
|
@@ -156,6 +258,10 @@ function sendJson(response, status, body) {
|
|
|
156
258
|
response.writeHead(status, { "content-type": "application/json; charset=utf-8" });
|
|
157
259
|
response.end(JSON.stringify(body));
|
|
158
260
|
}
|
|
261
|
+
async function sendTallySummary(response, stateDir) {
|
|
262
|
+
const summary = summarizeTally(await readTallyRatings(stateDir));
|
|
263
|
+
sendJson(response, 200, { ...summary, text: renderTallySummary(summary) });
|
|
264
|
+
}
|
|
159
265
|
function sendText(response, status, contentType, body) {
|
|
160
266
|
response.writeHead(status, { "content-type": contentType });
|
|
161
267
|
response.end(body);
|
package/dist/daemon/http.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"http.js","sourceRoot":"","sources":["../../src/daemon/http.ts"],"names":[],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"http.js","sourceRoot":"","sources":["../../src/daemon/http.ts"],"names":[],"mappings":"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"}
|
package/dist/daemon/main.js
CHANGED
|
@@ -1,10 +1,24 @@
|
|
|
1
1
|
import { loadConfig } from "../config.js";
|
|
2
2
|
import { AugmentService } from "../service.js";
|
|
3
3
|
import { startHttpDaemon } from "./http.js";
|
|
4
|
+
import { DaemonAlreadyRunningError } from "./single-instance.js";
|
|
4
5
|
export async function startDaemonFromCli(_args) {
|
|
5
6
|
const config = await loadConfig();
|
|
6
7
|
const service = new AugmentService(config);
|
|
7
|
-
|
|
8
|
+
let daemon;
|
|
9
|
+
try {
|
|
10
|
+
daemon = await startHttpDaemon(config, service);
|
|
11
|
+
}
|
|
12
|
+
catch (error) {
|
|
13
|
+
if (error instanceof DaemonAlreadyRunningError) {
|
|
14
|
+
// Not a failure: another daemon already serves this state. Exit cleanly
|
|
15
|
+
// without co-opening its sqlite index.
|
|
16
|
+
console.error(`augment-daemon: ${error.message}; exiting`);
|
|
17
|
+
await service.close();
|
|
18
|
+
process.exit(0);
|
|
19
|
+
}
|
|
20
|
+
throw error;
|
|
21
|
+
}
|
|
8
22
|
console.error(`augment-daemon listening at ${daemon.info.endpoint}`);
|
|
9
23
|
const close = async () => {
|
|
10
24
|
await daemon.close();
|
package/dist/daemon/main.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"main.js","sourceRoot":"","sources":["../../src/daemon/main.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAC1C,OAAO,EAAE,cAAc,EAAE,MAAM,eAAe,CAAC;AAC/C,OAAO,EAAE,eAAe,EAAE,MAAM,WAAW,CAAC;
|
|
1
|
+
{"version":3,"file":"main.js","sourceRoot":"","sources":["../../src/daemon/main.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAC1C,OAAO,EAAE,cAAc,EAAE,MAAM,eAAe,CAAC;AAC/C,OAAO,EAAE,eAAe,EAAE,MAAM,WAAW,CAAC;AAC5C,OAAO,EAAE,yBAAyB,EAAE,MAAM,sBAAsB,CAAC;AAEjE,MAAM,CAAC,KAAK,UAAU,kBAAkB,CAAC,KAAe;IACtD,MAAM,MAAM,GAAG,MAAM,UAAU,EAAE,CAAC;IAClC,MAAM,OAAO,GAAG,IAAI,cAAc,CAAC,MAAM,CAAC,CAAC;IAE3C,IAAI,MAAM,CAAC;IACX,IAAI,CAAC;QACH,MAAM,GAAG,MAAM,eAAe,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IAClD,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,IAAI,KAAK,YAAY,yBAAyB,EAAE,CAAC;YAC/C,wEAAwE;YACxE,uCAAuC;YACvC,OAAO,CAAC,KAAK,CAAC,mBAAmB,KAAK,CAAC,OAAO,WAAW,CAAC,CAAC;YAC3D,MAAM,OAAO,CAAC,KAAK,EAAE,CAAC;YACtB,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;QAClB,CAAC;QACD,MAAM,KAAK,CAAC;IACd,CAAC;IACD,OAAO,CAAC,KAAK,CAAC,+BAA+B,MAAM,CAAC,IAAI,CAAC,QAAQ,EAAE,CAAC,CAAC;IAErE,MAAM,KAAK,GAAG,KAAK,IAAI,EAAE;QACvB,MAAM,MAAM,CAAC,KAAK,EAAE,CAAC;QACrB,OAAO,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IAClB,CAAC,CAAC;IACF,OAAO,CAAC,EAAE,CAAC,QAAQ,EAAE,GAAG,EAAE,CAAC,KAAK,KAAK,EAAE,CAAC,CAAC;IACzC,OAAO,CAAC,EAAE,CAAC,SAAS,EAAE,GAAG,EAAE,CAAC,KAAK,KAAK,EAAE,CAAC,CAAC;AAC5C,CAAC"}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Single-flight, debounced batcher between the filesystem watcher and the indexer.
|
|
3
|
+
*
|
|
4
|
+
* Watcher events arrive in bursts (editors write temp+rename, Dropbox syncs whole
|
|
5
|
+
* directories). The scheduler coalesces a burst into one batch of unique paths and
|
|
6
|
+
* guarantees the runner is never invoked concurrently with itself: events that land
|
|
7
|
+
* while a run is in flight are queued and processed in one follow-up run.
|
|
8
|
+
*/
|
|
9
|
+
export interface IndexScheduler {
|
|
10
|
+
/** Queue a path for (re)indexing. Duplicate paths within a batch collapse. */
|
|
11
|
+
schedule(relativePath: string): void;
|
|
12
|
+
/** Resolves once no run is in flight, no timer is armed, and nothing is queued. */
|
|
13
|
+
idle(): Promise<void>;
|
|
14
|
+
/** Cancels pending work and waits for any in-flight run to finish. */
|
|
15
|
+
close(): Promise<void>;
|
|
16
|
+
}
|
|
17
|
+
export declare function createIndexScheduler(run: (paths: string[]) => Promise<void>, debounceMs?: number): IndexScheduler;
|
|
@@ -0,0 +1,77 @@
|
|
|
1
|
+
export function createIndexScheduler(run, debounceMs = 250) {
|
|
2
|
+
const pending = new Set();
|
|
3
|
+
let timer;
|
|
4
|
+
let inFlight;
|
|
5
|
+
let closed = false;
|
|
6
|
+
const waiters = [];
|
|
7
|
+
function settleIfIdle() {
|
|
8
|
+
if (timer === undefined && inFlight === undefined && pending.size === 0) {
|
|
9
|
+
while (waiters.length > 0) {
|
|
10
|
+
waiters.shift()?.();
|
|
11
|
+
}
|
|
12
|
+
}
|
|
13
|
+
}
|
|
14
|
+
function arm() {
|
|
15
|
+
if (closed || timer !== undefined) {
|
|
16
|
+
return;
|
|
17
|
+
}
|
|
18
|
+
timer = setTimeout(() => {
|
|
19
|
+
timer = undefined;
|
|
20
|
+
drain();
|
|
21
|
+
}, debounceMs);
|
|
22
|
+
timer.unref?.();
|
|
23
|
+
}
|
|
24
|
+
function drain() {
|
|
25
|
+
if (inFlight !== undefined || pending.size === 0) {
|
|
26
|
+
settleIfIdle();
|
|
27
|
+
return;
|
|
28
|
+
}
|
|
29
|
+
const batch = [...pending];
|
|
30
|
+
pending.clear();
|
|
31
|
+
inFlight = run(batch)
|
|
32
|
+
.catch((error) => {
|
|
33
|
+
// A failed run must not wedge the scheduler; the next event retries naturally.
|
|
34
|
+
console.error("augment: index run failed:", error);
|
|
35
|
+
})
|
|
36
|
+
.finally(() => {
|
|
37
|
+
inFlight = undefined;
|
|
38
|
+
if (pending.size > 0 && !closed) {
|
|
39
|
+
arm();
|
|
40
|
+
}
|
|
41
|
+
settleIfIdle();
|
|
42
|
+
});
|
|
43
|
+
}
|
|
44
|
+
return {
|
|
45
|
+
schedule(relativePath) {
|
|
46
|
+
if (closed) {
|
|
47
|
+
return;
|
|
48
|
+
}
|
|
49
|
+
pending.add(relativePath);
|
|
50
|
+
if (inFlight === undefined) {
|
|
51
|
+
arm();
|
|
52
|
+
}
|
|
53
|
+
// With a run in flight, its finally() arms the follow-up drain.
|
|
54
|
+
},
|
|
55
|
+
async idle() {
|
|
56
|
+
if (timer === undefined && inFlight === undefined && pending.size === 0) {
|
|
57
|
+
return;
|
|
58
|
+
}
|
|
59
|
+
await new Promise((resolve) => waiters.push(resolve));
|
|
60
|
+
},
|
|
61
|
+
async close() {
|
|
62
|
+
closed = true;
|
|
63
|
+
if (timer !== undefined) {
|
|
64
|
+
clearTimeout(timer);
|
|
65
|
+
timer = undefined;
|
|
66
|
+
}
|
|
67
|
+
if (inFlight !== undefined) {
|
|
68
|
+
await inFlight;
|
|
69
|
+
}
|
|
70
|
+
pending.clear();
|
|
71
|
+
while (waiters.length > 0) {
|
|
72
|
+
waiters.shift()?.();
|
|
73
|
+
}
|
|
74
|
+
},
|
|
75
|
+
};
|
|
76
|
+
}
|
|
77
|
+
//# sourceMappingURL=scheduler.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"scheduler.js","sourceRoot":"","sources":["../../src/daemon/scheduler.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
import type { AugmentConfig } from "../config.js";
|
|
2
|
+
/**
|
|
3
|
+
* Thrown when a healthy daemon already owns this state dir. The daemon process
|
|
4
|
+
* itself (not just the connect-or-start client) must refuse to start a second
|
|
5
|
+
* time: two daemons co-opening the same sqlite index race on writes and produce
|
|
6
|
+
* intermittent SQLITE_BUSY. Callers that spawn the daemon treat this as a clean
|
|
7
|
+
* "already up" exit, not a failure.
|
|
8
|
+
*/
|
|
9
|
+
export declare class DaemonAlreadyRunningError extends Error {
|
|
10
|
+
readonly endpoint: string;
|
|
11
|
+
readonly pid: number;
|
|
12
|
+
constructor(endpoint: string, pid: number);
|
|
13
|
+
}
|
|
14
|
+
/** Handle to the single-instance slot; release() frees it for the next start. */
|
|
15
|
+
export interface InstanceLock {
|
|
16
|
+
release(): Promise<void>;
|
|
17
|
+
}
|
|
18
|
+
/**
|
|
19
|
+
* Claim the sole-daemon slot for `config.stateDir`, or throw
|
|
20
|
+
* {@link DaemonAlreadyRunningError} if another daemon already holds it.
|
|
21
|
+
*
|
|
22
|
+
* Two independent signals guard the slot:
|
|
23
|
+
* - the recorded daemon's /health endpoint (authoritative — a daemon that
|
|
24
|
+
* answers /health for this memoryRoot is unambiguously already serving), and
|
|
25
|
+
* - an exclusive `daemon.pid` lockfile that closes the cold-start window before
|
|
26
|
+
* the winner becomes healthy. A pidfile is reclaimed when its holder is
|
|
27
|
+
* provably dead, or when it has aged past the grace window (a crash-stranded
|
|
28
|
+
* orphan, possibly with a since-reused pid); a live, recent holder is honored.
|
|
29
|
+
* Reclamation is atomic — an orphan is renamed aside, so of two racing starts
|
|
30
|
+
* at most one reclaims and the loser honors whoever recreates the slot.
|
|
31
|
+
*/
|
|
32
|
+
export declare function acquireSingleInstance(config: AugmentConfig): Promise<InstanceLock>;
|
|
@@ -0,0 +1,131 @@
|
|
|
1
|
+
import { constants } from "node:fs";
|
|
2
|
+
import { open, readFile, rename, rm, stat } from "node:fs/promises";
|
|
3
|
+
import path from "node:path";
|
|
4
|
+
import { isDaemonHealthy, readDaemonInfo } from "./client.js";
|
|
5
|
+
/**
|
|
6
|
+
* A pidfile whose holder is not provably dead is honored only this long. Past
|
|
7
|
+
* this age it is treated as an orphan and reclaimed — covering an unclean death
|
|
8
|
+
* (SIGKILL / `taskkill /F` / power loss) that stranded the file, and the case
|
|
9
|
+
* where the OS has since reused the dead daemon's pid for an unrelated live
|
|
10
|
+
* process. The window must exceed a real cold start (acquire → bind →
|
|
11
|
+
* write-daemon.json, sub-second under listen-first) so a genuinely-starting peer
|
|
12
|
+
* is never reclaimed out from under itself; 30s sits well above that and matches
|
|
13
|
+
* the client's existing daemon timeouts.
|
|
14
|
+
*/
|
|
15
|
+
const STALE_PIDFILE_GRACE_MS = 30_000;
|
|
16
|
+
/**
|
|
17
|
+
* Thrown when a healthy daemon already owns this state dir. The daemon process
|
|
18
|
+
* itself (not just the connect-or-start client) must refuse to start a second
|
|
19
|
+
* time: two daemons co-opening the same sqlite index race on writes and produce
|
|
20
|
+
* intermittent SQLITE_BUSY. Callers that spawn the daemon treat this as a clean
|
|
21
|
+
* "already up" exit, not a failure.
|
|
22
|
+
*/
|
|
23
|
+
export class DaemonAlreadyRunningError extends Error {
|
|
24
|
+
endpoint;
|
|
25
|
+
pid;
|
|
26
|
+
constructor(endpoint, pid) {
|
|
27
|
+
super(`augment daemon already running at ${endpoint} (pid ${pid})`);
|
|
28
|
+
this.endpoint = endpoint;
|
|
29
|
+
this.pid = pid;
|
|
30
|
+
this.name = "DaemonAlreadyRunningError";
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
/**
|
|
34
|
+
* Claim the sole-daemon slot for `config.stateDir`, or throw
|
|
35
|
+
* {@link DaemonAlreadyRunningError} if another daemon already holds it.
|
|
36
|
+
*
|
|
37
|
+
* Two independent signals guard the slot:
|
|
38
|
+
* - the recorded daemon's /health endpoint (authoritative — a daemon that
|
|
39
|
+
* answers /health for this memoryRoot is unambiguously already serving), and
|
|
40
|
+
* - an exclusive `daemon.pid` lockfile that closes the cold-start window before
|
|
41
|
+
* the winner becomes healthy. A pidfile is reclaimed when its holder is
|
|
42
|
+
* provably dead, or when it has aged past the grace window (a crash-stranded
|
|
43
|
+
* orphan, possibly with a since-reused pid); a live, recent holder is honored.
|
|
44
|
+
* Reclamation is atomic — an orphan is renamed aside, so of two racing starts
|
|
45
|
+
* at most one reclaims and the loser honors whoever recreates the slot.
|
|
46
|
+
*/
|
|
47
|
+
export async function acquireSingleInstance(config) {
|
|
48
|
+
const pidPath = path.join(config.stateDir, "daemon.pid");
|
|
49
|
+
for (let attempt = 0; attempt < 50; attempt += 1) {
|
|
50
|
+
// Authoritative check: is a daemon for this memoryRoot already answering?
|
|
51
|
+
const recorded = await readDaemonInfo(config);
|
|
52
|
+
if (recorded && (await isDaemonHealthy(recorded, config))) {
|
|
53
|
+
throw new DaemonAlreadyRunningError(recorded.endpoint, recorded.pid);
|
|
54
|
+
}
|
|
55
|
+
let handle;
|
|
56
|
+
try {
|
|
57
|
+
handle = await open(pidPath, constants.O_CREAT | constants.O_EXCL | constants.O_RDWR);
|
|
58
|
+
}
|
|
59
|
+
catch (error) {
|
|
60
|
+
if (error.code !== "EEXIST") {
|
|
61
|
+
throw error;
|
|
62
|
+
}
|
|
63
|
+
// A pidfile exists but no healthy daemon answered above.
|
|
64
|
+
const holder = await classifyPidfile(pidPath);
|
|
65
|
+
if (!holder.reclaim) {
|
|
66
|
+
throw new DaemonAlreadyRunningError(recorded?.endpoint ?? "unknown", recorded?.pid ?? holder.pid);
|
|
67
|
+
}
|
|
68
|
+
// Reclaim atomically: only one racer can rename the orphan away, so two
|
|
69
|
+
// concurrent starts can never both delete-and-recreate the slot. The loser
|
|
70
|
+
// gets ENOENT and re-evaluates, then honors whoever recreated the pidfile.
|
|
71
|
+
const parked = `${pidPath}.${process.pid}.${attempt}.reclaim`;
|
|
72
|
+
try {
|
|
73
|
+
await rename(pidPath, parked);
|
|
74
|
+
}
|
|
75
|
+
catch (renameError) {
|
|
76
|
+
if (renameError.code === "ENOENT") {
|
|
77
|
+
continue;
|
|
78
|
+
}
|
|
79
|
+
throw renameError;
|
|
80
|
+
}
|
|
81
|
+
await rm(parked, { force: true });
|
|
82
|
+
continue;
|
|
83
|
+
}
|
|
84
|
+
try {
|
|
85
|
+
await handle.writeFile(String(process.pid), "utf8");
|
|
86
|
+
}
|
|
87
|
+
finally {
|
|
88
|
+
await handle.close();
|
|
89
|
+
}
|
|
90
|
+
return {
|
|
91
|
+
async release() {
|
|
92
|
+
await rm(pidPath, { force: true });
|
|
93
|
+
},
|
|
94
|
+
};
|
|
95
|
+
}
|
|
96
|
+
throw new Error(`Could not acquire daemon single-instance lock: ${pidPath}`);
|
|
97
|
+
}
|
|
98
|
+
/**
|
|
99
|
+
* Decide whether an existing pidfile may be reclaimed. A provably-dead holder is
|
|
100
|
+
* always safe. Otherwise the pidfile is honored only until it ages out: a real
|
|
101
|
+
* cold-start peer writes its pid and becomes healthy within the grace window, so
|
|
102
|
+
* anything older is a crash-stranded orphan (empty, or a since-reused pid).
|
|
103
|
+
*/
|
|
104
|
+
async function classifyPidfile(pidPath) {
|
|
105
|
+
let ageMs = Infinity;
|
|
106
|
+
try {
|
|
107
|
+
ageMs = Date.now() - (await stat(pidPath)).mtimeMs;
|
|
108
|
+
}
|
|
109
|
+
catch {
|
|
110
|
+
// Vanished between the failed O_EXCL create and now — free to take.
|
|
111
|
+
return { reclaim: true, pid: -1 };
|
|
112
|
+
}
|
|
113
|
+
const raw = (await readFile(pidPath, "utf8").catch(() => "")).trim();
|
|
114
|
+
const pid = Number(raw);
|
|
115
|
+
const parsed = raw !== "" && Number.isInteger(pid) && pid > 0;
|
|
116
|
+
if (parsed && !isProcessAlive(pid)) {
|
|
117
|
+
return { reclaim: true, pid };
|
|
118
|
+
}
|
|
119
|
+
return { reclaim: ageMs > STALE_PIDFILE_GRACE_MS, pid: parsed ? pid : -1 };
|
|
120
|
+
}
|
|
121
|
+
/** True if `pid` names a live process (including one we lack permission to signal). */
|
|
122
|
+
function isProcessAlive(pid) {
|
|
123
|
+
try {
|
|
124
|
+
process.kill(pid, 0);
|
|
125
|
+
return true;
|
|
126
|
+
}
|
|
127
|
+
catch (error) {
|
|
128
|
+
return error.code === "EPERM";
|
|
129
|
+
}
|
|
130
|
+
}
|
|
131
|
+
//# sourceMappingURL=single-instance.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"single-instance.js","sourceRoot":"","sources":["../../src/daemon/single-instance.ts"],"names":[],"mappings":"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"}
|
package/dist/db.d.ts
CHANGED
|
@@ -12,7 +12,10 @@ export declare class AugmentDatabase {
|
|
|
12
12
|
getProjectByName(name: string): Promise<ProjectRecord | undefined>;
|
|
13
13
|
upsertMemory(memory: ParsedMemory): Promise<MemoryRecord>;
|
|
14
14
|
deleteMemory(id: number): Promise<void>;
|
|
15
|
-
|
|
15
|
+
deleteMemoryByPath(relativePath: string): Promise<void>;
|
|
16
|
+
/** relative_path → stored file mtime (ms), for change detection without reading file bodies. */
|
|
17
|
+
listMemoryFileStats(): Promise<Map<string, number>>;
|
|
18
|
+
removeMissingMemories(relativePaths: string[]): Promise<number>;
|
|
16
19
|
rebuildLinks(): Promise<void>;
|
|
17
20
|
getMemoryById(id: number): Promise<MemoryRecord | undefined>;
|
|
18
21
|
getMemoryByPath(relativePath: string): Promise<MemoryRecord | undefined>;
|
|
@@ -28,7 +31,16 @@ export declare class AugmentDatabase {
|
|
|
28
31
|
getAllEmbeddings(): Promise<Map<number, number[]>>;
|
|
29
32
|
upsertEmbedding(memory: ParsedMemory | MemoryRecord, provider: EmbeddingProvider, vector: number[]): Promise<void>;
|
|
30
33
|
embeddingText(memory: ParsedMemory | MemoryRecord): string;
|
|
34
|
+
/**
|
|
35
|
+
* Incremental link maintenance for one re-indexed memory: replaces its outbound links from its
|
|
36
|
+
* frontmatter, then materializes inbound links other memories declare toward its path (they may
|
|
37
|
+
* have been dangling if this file was just created). Equivalent to {@link rebuildLinks} for the
|
|
38
|
+
* subgraph touching this memory, without paying the full O(memories × links) sweep.
|
|
39
|
+
*/
|
|
40
|
+
rebuildLinksForMemory(memory: MemoryRecord): Promise<void>;
|
|
31
41
|
private execute;
|
|
32
42
|
private batch;
|
|
43
|
+
/** Parameterized statements in one transaction: one commit, all-or-nothing. */
|
|
44
|
+
private batchExecute;
|
|
33
45
|
private getClient;
|
|
34
46
|
}
|