@smartmemory/stratum 0.3.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.
Files changed (81) hide show
  1. package/dist/cli/guard.js +91 -0
  2. package/dist/cli/guard.js.map +1 -0
  3. package/dist/cli/mcp_install.js +302 -0
  4. package/dist/cli/mcp_install.js.map +1 -0
  5. package/dist/cli/query_gate.js +316 -0
  6. package/dist/cli/query_gate.js.map +1 -0
  7. package/dist/cli/stratum.js +291 -0
  8. package/dist/cli/stratum.js.map +1 -0
  9. package/dist/connectors/background.js +531 -0
  10. package/dist/connectors/background.js.map +1 -0
  11. package/dist/connectors/base.js +12 -0
  12. package/dist/connectors/base.js.map +1 -0
  13. package/dist/connectors/claude-bg-worker.js +99 -0
  14. package/dist/connectors/claude-bg-worker.js.map +1 -0
  15. package/dist/connectors/claude.js +170 -0
  16. package/dist/connectors/claude.js.map +1 -0
  17. package/dist/connectors/codex.js +319 -0
  18. package/dist/connectors/codex.js.map +1 -0
  19. package/dist/connectors/index.js +7 -0
  20. package/dist/connectors/index.js.map +1 -0
  21. package/dist/connectors/proc_identity.js +90 -0
  22. package/dist/connectors/proc_identity.js.map +1 -0
  23. package/dist/connectors/runner.js +63 -0
  24. package/dist/connectors/runner.js.map +1 -0
  25. package/dist/contracts/events.json +65 -0
  26. package/dist/contracts/mcp-surface.json +215 -0
  27. package/dist/engine/checkpoint.js +50 -0
  28. package/dist/engine/checkpoint.js.map +1 -0
  29. package/dist/engine/engine.js +2356 -0
  30. package/dist/engine/engine.js.map +1 -0
  31. package/dist/engine/ledger.js +36 -0
  32. package/dist/engine/ledger.js.map +1 -0
  33. package/dist/engine/state.js +42 -0
  34. package/dist/engine/state.js.map +1 -0
  35. package/dist/eval/expr.js +679 -0
  36. package/dist/eval/expr.js.map +1 -0
  37. package/dist/eval/files.js +130 -0
  38. package/dist/eval/files.js.map +1 -0
  39. package/dist/guard/canonical.js +116 -0
  40. package/dist/guard/canonical.js.map +1 -0
  41. package/dist/guard/errors.js +80 -0
  42. package/dist/guard/errors.js.map +1 -0
  43. package/dist/guard/evidence.js +475 -0
  44. package/dist/guard/evidence.js.map +1 -0
  45. package/dist/guard/fingerprint.js +13 -0
  46. package/dist/guard/fingerprint.js.map +1 -0
  47. package/dist/guard/lock.js +360 -0
  48. package/dist/guard/lock.js.map +1 -0
  49. package/dist/guard/store.js +396 -0
  50. package/dist/guard/store.js.map +1 -0
  51. package/dist/guard/transition.js +477 -0
  52. package/dist/guard/transition.js.map +1 -0
  53. package/dist/ir/refs.js +69 -0
  54. package/dist/ir/refs.js.map +1 -0
  55. package/dist/ir/schema.js +123 -0
  56. package/dist/ir/schema.js.map +1 -0
  57. package/dist/ir/validate.js +595 -0
  58. package/dist/ir/validate.js.map +1 -0
  59. package/dist/judge/codex_judged.js +85 -0
  60. package/dist/judge/codex_judged.js.map +1 -0
  61. package/dist/judge/fixture_judged.js +62 -0
  62. package/dist/judge/fixture_judged.js.map +1 -0
  63. package/dist/judge/judged.js +89 -0
  64. package/dist/judge/judged.js.map +1 -0
  65. package/dist/judge/pricing.js +22 -0
  66. package/dist/judge/pricing.js.map +1 -0
  67. package/dist/mcp/contracts.js +162 -0
  68. package/dist/mcp/contracts.js.map +1 -0
  69. package/dist/mcp/main.js +7 -0
  70. package/dist/mcp/main.js.map +1 -0
  71. package/dist/mcp/server.js +370 -0
  72. package/dist/mcp/server.js.map +1 -0
  73. package/dist/migrate/check.js +164 -0
  74. package/dist/migrate/check.js.map +1 -0
  75. package/dist/parallel/certificate.js +37 -0
  76. package/dist/parallel/certificate.js.map +1 -0
  77. package/dist/parallel/evaluate.js +73 -0
  78. package/dist/parallel/evaluate.js.map +1 -0
  79. package/dist/speckit/compiler.js +162 -0
  80. package/dist/speckit/compiler.js.map +1 -0
  81. package/package.json +47 -0
@@ -0,0 +1,360 @@
1
+ /** Per-resource in-process and cross-process guard locking. */
2
+ import { execFile } from "node:child_process";
3
+ import { randomUUID } from "node:crypto";
4
+ import { constants } from "node:fs";
5
+ import { link, mkdir, open, readFile, unlink } from "node:fs/promises";
6
+ import { performance } from "node:perf_hooks";
7
+ import { join } from "node:path";
8
+ import { promisify } from "node:util";
9
+ import { resourceDir } from "./store.js";
10
+ const execFileAsync = promisify(execFile);
11
+ const DEFAULT_TIMEOUT_MS = 10_000;
12
+ const DEFAULT_MIN_RETRY_DELAY_MS = 10;
13
+ const DEFAULT_MAX_RETRY_DELAY_MS = 250;
14
+ const SAFE_TOKEN = /^[A-Za-z0-9_-]+$/;
15
+ function isErrno(error, code) {
16
+ return error instanceof Error && "code" in error && error.code === code;
17
+ }
18
+ function pidIsAlive(pid) {
19
+ if (!Number.isSafeInteger(pid) || pid <= 0)
20
+ return false;
21
+ try {
22
+ process.kill(pid, 0);
23
+ return true;
24
+ }
25
+ catch (error) {
26
+ // EPERM proves that the pid exists even though it cannot be signalled.
27
+ if (isErrno(error, "EPERM"))
28
+ return true;
29
+ if (isErrno(error, "ESRCH"))
30
+ return false;
31
+ // An unfamiliar probe failure cannot safely establish death.
32
+ return true;
33
+ }
34
+ }
35
+ async function linuxStartTime(pid) {
36
+ try {
37
+ const stat = await readFile(`/proc/${pid}/stat`, "utf8");
38
+ // The command name is parenthesized and may itself contain spaces or ')'.
39
+ const close = stat.lastIndexOf(")");
40
+ if (close < 0)
41
+ return null;
42
+ const fieldsFromThree = stat.slice(close + 2).trim().split(/\s+/);
43
+ return fieldsFromThree[19] || null; // Linux procfs field 22: starttime.
44
+ }
45
+ catch {
46
+ return null;
47
+ }
48
+ }
49
+ async function darwinStartTime(pid) {
50
+ try {
51
+ const { stdout } = await execFileAsync("ps", ["-o", "lstart=", "-p", String(pid)], { timeout: 5_000 });
52
+ return stdout.trim() || null;
53
+ }
54
+ catch {
55
+ return null;
56
+ }
57
+ }
58
+ /**
59
+ * Return a same-host pid identity. `alive: true, startTime: null` means the
60
+ * process exists but its stable identity is unverifiable and must be protected.
61
+ */
62
+ export async function processIdentity(pid) {
63
+ if (!Number.isSafeInteger(pid) || pid <= 0)
64
+ return { alive: false, startTime: null };
65
+ if (!pidIsAlive(pid))
66
+ return { alive: false, startTime: null };
67
+ let startTime = null;
68
+ if (process.platform === "linux")
69
+ startTime = await linuxStartTime(pid);
70
+ else if (process.platform === "darwin")
71
+ startTime = await darwinStartTime(pid);
72
+ // Re-probe after reading the identity. Disappearance is verified death; an
73
+ // unreadable start time for a still-live process remains fail-closed.
74
+ if (!pidIsAlive(pid))
75
+ return { alive: false, startTime: null };
76
+ return { alive: true, startTime };
77
+ }
78
+ export class LockTimeoutError extends Error {
79
+ constructor(resourceId, timeoutMs) {
80
+ super(`timed out after ${timeoutMs}ms waiting for guard lock ${JSON.stringify(resourceId)}`);
81
+ this.name = "LockTimeoutError";
82
+ }
83
+ }
84
+ export class LockFenceError extends Error {
85
+ constructor(resourceId) {
86
+ super(`guard lock for ${JSON.stringify(resourceId)} is no longer held by this token`);
87
+ this.name = "LockFenceError";
88
+ }
89
+ }
90
+ export class ProcessIdentityUnverifiableError extends Error {
91
+ constructor(pid) {
92
+ super(`cannot acquire guard lock: process identity for pid ${pid} is unverifiable`);
93
+ this.name = "ProcessIdentityUnverifiableError";
94
+ }
95
+ }
96
+ function parseOwner(value) {
97
+ if (value === null || typeof value !== "object" || Array.isArray(value))
98
+ return null;
99
+ const record = value;
100
+ if (typeof record.token !== "string" || !SAFE_TOKEN.test(record.token))
101
+ return null;
102
+ if (!Number.isSafeInteger(record.pid) || Number(record.pid) <= 0)
103
+ return null;
104
+ if (typeof record.procStartTime !== "string" || record.procStartTime.length === 0)
105
+ return null;
106
+ if (record.since !== undefined && typeof record.since !== "string")
107
+ return null;
108
+ return {
109
+ token: record.token,
110
+ pid: Number(record.pid),
111
+ procStartTime: record.procStartTime,
112
+ ...(typeof record.since === "string" ? { since: record.since } : {}),
113
+ };
114
+ }
115
+ async function readOwner(path) {
116
+ let body;
117
+ try {
118
+ body = await readFile(path, "utf8");
119
+ }
120
+ catch (error) {
121
+ if (isErrno(error, "ENOENT"))
122
+ return { kind: "missing" };
123
+ throw error;
124
+ }
125
+ let owner = null;
126
+ try {
127
+ owner = parseOwner(JSON.parse(body));
128
+ }
129
+ catch {
130
+ // Atomic publication below makes a malformed canonical file impossible for
131
+ // this implementation. Fail loudly on legacy/external corruption instead
132
+ // of classifying it as permanent contention and wedging every claimant.
133
+ }
134
+ if (owner === null)
135
+ throw new Error(`invalid guard lock file at ${path}`);
136
+ return { kind: "owner", owner };
137
+ }
138
+ async function createExclusive(path, owner) {
139
+ const temporaryPath = `${path}.tmp.${randomUUID()}`;
140
+ const handle = await open(temporaryPath, constants.O_WRONLY | constants.O_CREAT | constants.O_EXCL, 0o600);
141
+ try {
142
+ try {
143
+ await handle.writeFile(`${JSON.stringify(owner)}\n`, "utf8");
144
+ await handle.sync();
145
+ }
146
+ finally {
147
+ await handle.close();
148
+ }
149
+ // The hard link publishes an already-complete inode and retains O_EXCL's
150
+ // EEXIST arbitration. A crash can leave only an ignored unique temp name.
151
+ try {
152
+ await link(temporaryPath, path);
153
+ return true;
154
+ }
155
+ catch (error) {
156
+ if (isErrno(error, "EEXIST"))
157
+ return false;
158
+ throw error;
159
+ }
160
+ }
161
+ finally {
162
+ try {
163
+ await unlink(temporaryPath);
164
+ }
165
+ catch (error) {
166
+ // Cleanup is best-effort: a truly failed unlink leaves only an inert uniquely-named orphan.
167
+ if (!isErrno(error, "ENOENT")) {
168
+ void error;
169
+ }
170
+ }
171
+ }
172
+ }
173
+ function sameOwner(left, right) {
174
+ return left.token === right.token
175
+ && left.pid === right.pid
176
+ && left.procStartTime === right.procStartTime;
177
+ }
178
+ async function delay(milliseconds) {
179
+ await new Promise((resolve) => setTimeout(resolve, milliseconds));
180
+ }
181
+ export class ResourceLockManager {
182
+ pid;
183
+ identityProvider;
184
+ tokenFactory;
185
+ timeoutMs;
186
+ minRetryDelayMs;
187
+ maxRetryDelayMs;
188
+ inProcessLocks = new Map();
189
+ constructor(options = {}) {
190
+ this.pid = options.pid ?? process.pid;
191
+ this.identityProvider = options.processIdentity ?? processIdentity;
192
+ this.tokenFactory = options.token ?? randomUUID;
193
+ this.timeoutMs = options.timeoutMs ?? DEFAULT_TIMEOUT_MS;
194
+ this.minRetryDelayMs = options.minRetryDelayMs ?? DEFAULT_MIN_RETRY_DELAY_MS;
195
+ this.maxRetryDelayMs = options.maxRetryDelayMs ?? DEFAULT_MAX_RETRY_DELAY_MS;
196
+ if (!Number.isFinite(this.timeoutMs) || this.timeoutMs < 0)
197
+ throw new TypeError("timeoutMs must be non-negative");
198
+ if (!Number.isFinite(this.minRetryDelayMs) || this.minRetryDelayMs < 0) {
199
+ throw new TypeError("minRetryDelayMs must be non-negative");
200
+ }
201
+ if (!Number.isFinite(this.maxRetryDelayMs) || this.maxRetryDelayMs < this.minRetryDelayMs) {
202
+ throw new TypeError("maxRetryDelayMs must be at least minRetryDelayMs");
203
+ }
204
+ }
205
+ newToken() {
206
+ const token = this.tokenFactory();
207
+ if (!SAFE_TOKEN.test(token))
208
+ throw new TypeError("guard lock token must contain only letters, digits, '_' or '-'");
209
+ return token;
210
+ }
211
+ async acquireInProcess(resourceId) {
212
+ const previous = this.inProcessLocks.get(resourceId) ?? Promise.resolve();
213
+ let signal;
214
+ const current = new Promise((resolve) => { signal = resolve; });
215
+ const tail = previous.then(() => current);
216
+ this.inProcessLocks.set(resourceId, tail);
217
+ await previous;
218
+ let released = false;
219
+ return () => {
220
+ if (released)
221
+ return;
222
+ released = true;
223
+ signal();
224
+ void tail.then(() => {
225
+ if (this.inProcessLocks.get(resourceId) === tail)
226
+ this.inProcessLocks.delete(resourceId);
227
+ });
228
+ };
229
+ }
230
+ async ownerIsProtected(owner) {
231
+ const identity = await this.identityProvider(owner.pid);
232
+ if (!identity.alive)
233
+ return false;
234
+ // A live pid with unreadable start time is explicitly unverifiable.
235
+ if (identity.startTime === null)
236
+ return true;
237
+ return identity.startTime === owner.procStartTime;
238
+ }
239
+ async unlinkIfStillOwned(path, expected) {
240
+ const reread = await readOwner(path);
241
+ if (reread.kind !== "owner" || !sameOwner(reread.owner, expected))
242
+ return false;
243
+ try {
244
+ await unlink(path);
245
+ return true;
246
+ }
247
+ catch (error) {
248
+ if (isErrno(error, "ENOENT"))
249
+ return false;
250
+ throw error;
251
+ }
252
+ }
253
+ async tryRecover(lockPath, staleOwner, ownLock, attemptedTokens) {
254
+ if (attemptedTokens.has(staleOwner.token))
255
+ return false;
256
+ // A claimant that loses this token-keyed name never retries it during this
257
+ // acquisition. A future acquisition is a new claimant and may recover a
258
+ // recovery file whose creator has subsequently died.
259
+ attemptedTokens.add(staleOwner.token);
260
+ const recoveryPath = `${lockPath}.recovery.${staleOwner.token}`;
261
+ const existingRecovery = await readOwner(recoveryPath);
262
+ if (existingRecovery.kind === "owner") {
263
+ if (await this.ownerIsProtected(existingRecovery.owner))
264
+ return false;
265
+ // Verify the exact dead creator again immediately before removing its
266
+ // recovery claim. A live or changed creator is never unlinked.
267
+ if (!await this.unlinkIfStillOwned(recoveryPath, existingRecovery.owner))
268
+ return false;
269
+ }
270
+ const recoveryOwner = {
271
+ token: this.newToken(),
272
+ pid: this.pid,
273
+ procStartTime: ownLock.procStartTime,
274
+ };
275
+ if (!await createExclusive(recoveryPath, recoveryOwner))
276
+ return false;
277
+ try {
278
+ const current = await readOwner(lockPath);
279
+ if (current.kind !== "owner" || current.owner.token !== staleOwner.token)
280
+ return false;
281
+ // Holding recovery.<T> is the sole authority to unlink a main lock named T.
282
+ if (!await this.unlinkIfStillOwned(lockPath, current.owner))
283
+ return false;
284
+ // A contender may legitimately win the now-empty main name first. The
285
+ // atomic link decides; this claimant never removes that replacement.
286
+ return await createExclusive(lockPath, ownLock);
287
+ }
288
+ finally {
289
+ await this.unlinkIfStillOwned(recoveryPath, recoveryOwner);
290
+ }
291
+ }
292
+ async acquireFileLock(resourceId, options) {
293
+ const identity = await this.identityProvider(this.pid);
294
+ if (!identity.alive || identity.startTime === null) {
295
+ throw new ProcessIdentityUnverifiableError(this.pid);
296
+ }
297
+ const directory = resourceDir(resourceId);
298
+ await mkdir(directory, { recursive: true });
299
+ const lockPath = join(directory, ".lock.ts");
300
+ const ownLock = {
301
+ token: this.newToken(),
302
+ pid: this.pid,
303
+ procStartTime: identity.startTime,
304
+ since: new Date().toISOString(),
305
+ };
306
+ const timeoutMs = options.timeoutMs ?? this.timeoutMs;
307
+ const minDelay = options.minRetryDelayMs ?? this.minRetryDelayMs;
308
+ const maxDelay = options.maxRetryDelayMs ?? this.maxRetryDelayMs;
309
+ const started = performance.now();
310
+ const attemptedTokens = new Set();
311
+ let retryDelay = minDelay;
312
+ for (;;) {
313
+ if (await createExclusive(lockPath, ownLock))
314
+ return ownLock;
315
+ const observed = await readOwner(lockPath);
316
+ if (observed.kind === "owner" && !await this.ownerIsProtected(observed.owner)) {
317
+ if (await this.tryRecover(lockPath, observed.owner, ownLock, attemptedTokens))
318
+ return ownLock;
319
+ }
320
+ if (performance.now() - started >= timeoutMs)
321
+ throw new LockTimeoutError(resourceId, timeoutMs);
322
+ await delay(retryDelay);
323
+ retryDelay = Math.min(maxDelay, Math.max(minDelay, retryDelay * 2 || 1));
324
+ }
325
+ }
326
+ async assertStillHeld(resourceId, token) {
327
+ const current = await readOwner(join(resourceDir(resourceId), ".lock.ts"));
328
+ if (current.kind !== "owner" || current.owner.token !== token)
329
+ throw new LockFenceError(resourceId);
330
+ }
331
+ /** Acquire, yield the fence token to the callback, and always release. */
332
+ async resourceLock(resourceId, action, options = {}) {
333
+ // resourceDir validates the raw id; the mutex key intentionally remains raw.
334
+ resourceDir(resourceId);
335
+ const releaseInProcess = await this.acquireInProcess(resourceId);
336
+ let owner;
337
+ try {
338
+ owner = await this.acquireFileLock(resourceId, options);
339
+ return await action({ token: owner.token });
340
+ }
341
+ finally {
342
+ try {
343
+ if (owner !== undefined) {
344
+ await this.unlinkIfStillOwned(join(resourceDir(resourceId), ".lock.ts"), owner);
345
+ }
346
+ }
347
+ finally {
348
+ releaseInProcess();
349
+ }
350
+ }
351
+ }
352
+ }
353
+ const defaultManager = new ResourceLockManager();
354
+ export function resourceLock(resourceId, action, options = {}) {
355
+ return defaultManager.resourceLock(resourceId, action, options);
356
+ }
357
+ export function assertStillHeld(resourceId, token) {
358
+ return defaultManager.assertStillHeld(resourceId, token);
359
+ }
360
+ //# sourceMappingURL=lock.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"lock.js","sourceRoot":"","sources":["../../src/guard/lock.ts"],"names":[],"mappings":"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"}