@omnicross/daemon 0.1.8 → 0.1.10

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/cli.js CHANGED
@@ -1,86 +1,633 @@
1
1
  #!/usr/bin/env node
2
2
 
3
- // src/commands/import-ccr.ts
4
- import { readFileSync as readFileSync3 } from "fs";
3
+ // src/commands/audit.ts
4
+ import { readdirSync as readdirSync3 } from "fs";
5
+ import { join as join5 } from "path";
5
6
  import { parseArgs } from "util";
6
7
 
7
- // src/ccr-import.ts
8
- function parseCcrConfig(raw) {
9
- if (!raw || typeof raw !== "object") {
10
- throw new Error("CCR config: top-level value must be an object");
8
+ // src/audit/auditBodyReader.ts
9
+ import { existsSync as existsSync2, readdirSync as readdirSync2, readFileSync as readFileSync2, statSync as statSync2 } from "fs";
10
+ import { join as join2 } from "path";
11
+ import { gunzipSync } from "zlib";
12
+
13
+ // src/audit/auditBodyStore.ts
14
+ var ANCHOR_EVERY = 64;
15
+ var ANCHOR_DELTA_RATIO = 0.75;
16
+ var DIVERGED_PREFIX_RATIO = 0.25;
17
+ var MAX_BASE_CHARS = 4e6;
18
+ var CACHE_BUDGET_CHARS = 16e6;
19
+ var CACHE_MAX_SESSIONS = 32;
20
+ var MAX_BASES_PER_SESSION = 4;
21
+ var isHighSurrogate = (code) => code >= 55296 && code <= 56319;
22
+ var isLowSurrogate = (code) => code >= 56320 && code <= 57343;
23
+ function computeBodyDelta(prev, next) {
24
+ const shortest = Math.min(prev.length, next.length);
25
+ let pre = 0;
26
+ while (pre < shortest && prev.charCodeAt(pre) === next.charCodeAt(pre)) pre += 1;
27
+ if (pre > 0 && isHighSurrogate(prev.charCodeAt(pre - 1))) pre -= 1;
28
+ const maxSuf = shortest - pre;
29
+ let suf = 0;
30
+ while (suf < maxSuf && prev.charCodeAt(prev.length - 1 - suf) === next.charCodeAt(next.length - 1 - suf)) {
31
+ suf += 1;
32
+ }
33
+ if (suf > 0 && isLowSurrogate(prev.charCodeAt(prev.length - suf))) suf -= 1;
34
+ return { pre, suf, ins: next.slice(pre, next.length - suf) };
35
+ }
36
+ function applyBodyDelta(prev, delta) {
37
+ const head = delta.pre > 0 ? prev.slice(0, delta.pre) : "";
38
+ const tail = delta.suf > 0 ? prev.slice(prev.length - delta.suf) : "";
39
+ return head + delta.ins + tail;
40
+ }
41
+ var SessionBaseCache = class {
42
+ constructor(maxSessions = CACHE_MAX_SESSIONS, budgetChars = CACHE_BUDGET_CHARS, maxBaseChars = MAX_BASE_CHARS, maxHeads = MAX_BASES_PER_SESSION) {
43
+ this.maxSessions = maxSessions;
44
+ this.budgetChars = budgetChars;
45
+ this.maxBaseChars = maxBaseChars;
46
+ this.maxHeads = maxHeads;
47
+ }
48
+ maxSessions;
49
+ budgetChars;
50
+ maxBaseChars;
51
+ maxHeads;
52
+ /** Session key to its retained heads, most-recent first. */
53
+ entries = /* @__PURE__ */ new Map();
54
+ chars = 0;
55
+ /** Retained sessions (tests + diagnostics). */
56
+ get size() {
57
+ return this.entries.size;
58
+ }
59
+ /** A session's retained heads, most-recent first. Refreshes LRU recency. */
60
+ get(sessionKey) {
61
+ const found = this.entries.get(sessionKey);
62
+ if (!found) return [];
63
+ this.entries.delete(sessionKey);
64
+ this.entries.set(sessionKey, found);
65
+ return found;
11
66
  }
12
- const obj = raw;
13
- const Providers = Array.isArray(obj["Providers"]) ? obj["Providers"] : [];
14
- const Router = obj["Router"] && typeof obj["Router"] === "object" ? obj["Router"] : {};
15
- return { Providers, Router };
67
+ /**
68
+ * Retain `base` as a head of `sessionKey`.
69
+ *
70
+ * `replacesId` is the head this turn CONTINUES (its body was preserved whole
71
+ * inside the new one), which is swapped out so a linear conversation keeps
72
+ * exactly one head. Omit it when the turn started a distinct stream %s that
73
+ * head is added alongside, which is what keeps a fork's branches apart.
74
+ *
75
+ * A body larger than `maxBaseChars` is not retained: the next turn anchors
76
+ * rather than letting one oversized session monopolize the budget.
77
+ */
78
+ remember(sessionKey, base, replacesId) {
79
+ const heads = this.entries.get(sessionKey) ?? [];
80
+ if (replacesId !== void 0) {
81
+ const at = heads.findIndex((head) => head.lastId === replacesId);
82
+ if (at >= 0) {
83
+ this.chars -= heads[at].text.length;
84
+ heads.splice(at, 1);
85
+ }
86
+ }
87
+ if (base.text.length <= this.maxBaseChars) {
88
+ heads.unshift(base);
89
+ this.chars += base.text.length;
90
+ }
91
+ while (heads.length > this.maxHeads) {
92
+ const dropped = heads.pop();
93
+ if (dropped) this.chars -= dropped.text.length;
94
+ }
95
+ this.entries.delete(sessionKey);
96
+ if (heads.length > 0) this.entries.set(sessionKey, heads);
97
+ this.evict();
98
+ }
99
+ /** Drop a session's heads (eviction, or a write failure invalidating them). */
100
+ forget(sessionKey) {
101
+ const heads = this.entries.get(sessionKey);
102
+ if (!heads) return;
103
+ for (const head of heads) this.chars -= head.text.length;
104
+ this.entries.delete(sessionKey);
105
+ }
106
+ /** Drop everything (writer disposal / test teardown). */
107
+ clear() {
108
+ this.entries.clear();
109
+ this.chars = 0;
110
+ }
111
+ /** Evict least-recently-used sessions until both bounds hold. */
112
+ evict() {
113
+ while (this.entries.size > this.maxSessions || this.chars > this.budgetChars && this.entries.size > 1) {
114
+ const oldest = this.entries.keys().next();
115
+ if (oldest.done) break;
116
+ this.forget(oldest.value);
117
+ }
118
+ }
119
+ };
120
+ function anchorReason(base, dayDir, delta, nextLength) {
121
+ if (!base || !delta) return "new";
122
+ if (base.dayDir !== dayDir) return "day";
123
+ if (base.chainLen >= ANCHOR_EVERY) return "chain";
124
+ if (delta.pre < base.text.length * DIVERGED_PREFIX_RATIO) return "diverged";
125
+ if (delta.ins.length > nextLength * ANCHOR_DELTA_RATIO) return "costly";
126
+ return null;
16
127
  }
17
- function inferApiFormat(provider) {
18
- const hay = `${provider.api_base_url ?? ""} ${provider.name ?? ""}`.toLowerCase();
19
- if (hay.includes("anthropic") || hay.includes("claude")) {
20
- return { format: "anthropic", ambiguous: false };
128
+ function pickBase(heads, next) {
129
+ let best = null;
130
+ for (const base of heads) {
131
+ const delta = computeBodyDelta(base.text, next);
132
+ if (best !== null && delta.ins.length >= best.delta.ins.length) continue;
133
+ best = { base, delta, continues: delta.pre + delta.suf >= base.text.length };
134
+ }
135
+ return best;
136
+ }
137
+ function encodeBodyEntry(record, sessionKey, dayDir, cache) {
138
+ const requestBody = record.requestBody;
139
+ const responseBody = record.responseBody;
140
+ if (requestBody === void 0 && responseBody === void 0) return null;
141
+ const entry = { id: record.id, ts: record.ts };
142
+ if (requestBody !== void 0) {
143
+ const heads = cache.get(sessionKey);
144
+ const sameDay = heads.filter((head) => head.dayDir === dayDir);
145
+ const chosen = pickBase(sameDay, requestBody);
146
+ const reason = heads.length > 0 && sameDay.length === 0 ? "day" : anchorReason(chosen?.base, dayDir, chosen?.delta ?? null, requestBody.length);
147
+ if (reason !== null) {
148
+ entry.req = { base: null, anchor: reason, pre: 0, suf: 0, ins: requestBody };
149
+ cache.remember(
150
+ sessionKey,
151
+ { dayDir, lastId: record.id, text: requestBody, chainLen: 0 },
152
+ chosen?.continues === true ? chosen.base.lastId : void 0
153
+ );
154
+ } else {
155
+ const picked = chosen;
156
+ entry.req = {
157
+ base: picked.base.lastId,
158
+ ...picked.continues ? { cont: true } : {},
159
+ pre: picked.delta.pre,
160
+ suf: picked.delta.suf,
161
+ ins: picked.delta.ins
162
+ };
163
+ cache.remember(
164
+ sessionKey,
165
+ { dayDir, lastId: record.id, text: requestBody, chainLen: picked.base.chainLen + 1 },
166
+ picked.continues ? picked.base.lastId : void 0
167
+ );
168
+ }
21
169
  }
22
- if (hay.includes("generativelanguage") || hay.includes("gemini") || hay.includes("google")) {
23
- return { format: "gemini", ambiguous: false };
170
+ if (responseBody !== void 0) entry.res = responseBody;
171
+ return JSON.stringify(entry);
172
+ }
173
+ function isAuditBodyEntry(value) {
174
+ if (!value || typeof value !== "object" || Array.isArray(value)) return false;
175
+ const entry = value;
176
+ if (typeof entry["id"] !== "string" || typeof entry["ts"] !== "number") return false;
177
+ if (entry["res"] !== void 0 && typeof entry["res"] !== "string") return false;
178
+ const req = entry["req"];
179
+ if (req === void 0) return true;
180
+ if (!req || typeof req !== "object" || Array.isArray(req)) return false;
181
+ const delta = req;
182
+ if (delta["anchor"] !== void 0 && typeof delta["anchor"] !== "string") return false;
183
+ if (delta["cont"] !== void 0 && typeof delta["cont"] !== "boolean") return false;
184
+ return (delta["base"] === null || typeof delta["base"] === "string") && Number.isSafeInteger(delta["pre"]) && delta["pre"] >= 0 && Number.isSafeInteger(delta["suf"]) && delta["suf"] >= 0 && typeof delta["ins"] === "string";
185
+ }
186
+
187
+ // src/audit/auditDictionary.ts
188
+ import { existsSync, readdirSync, readFileSync, renameSync, unlinkSync, writeFileSync } from "fs";
189
+ import { join } from "path";
190
+
191
+ // src/audit/auditFiles.ts
192
+ var AUDIT_FILE_RE = /^audit-(\d{4})-(\d{2})-(\d{2})\.jsonl$/;
193
+ var AUDIT_DAY_DIR_RE = /^audit-(\d{4})-(\d{2})-(\d{2})$/;
194
+ var AUDIT_META_FILE = "meta.jsonl";
195
+ var AUDIT_BODIES_DIR = "bodies";
196
+ var AUDIT_SESSION_KEY_RE = /^[0-9a-f]{8,64}$/;
197
+ var pad2 = (n) => String(n).padStart(2, "0");
198
+ var localDateStamp = (ts) => {
199
+ const d = new Date(ts);
200
+ return `${d.getFullYear()}-${pad2(d.getMonth() + 1)}-${pad2(d.getDate())}`;
201
+ };
202
+ function auditDayDirName(ts) {
203
+ return `audit-${localDateStamp(ts)}`;
204
+ }
205
+ function isAuditDayDir(name) {
206
+ return AUDIT_DAY_DIR_RE.test(name);
207
+ }
208
+ function isSafeSessionKey(key) {
209
+ return typeof key === "string" && AUDIT_SESSION_KEY_RE.test(key);
210
+ }
211
+ function auditBodyFileName(sessionKey) {
212
+ return `${sessionKey}.jsonl`;
213
+ }
214
+ function auditFileDateMs(name) {
215
+ const m = AUDIT_FILE_RE.exec(name) ?? AUDIT_DAY_DIR_RE.exec(name);
216
+ if (!m) return null;
217
+ const year = Number(m[1]);
218
+ const month = Number(m[2]);
219
+ const day = Number(m[3]);
220
+ const d = new Date(year, month - 1, day);
221
+ if (d.getFullYear() !== year || d.getMonth() !== month - 1 || d.getDate() !== day) {
222
+ return null;
24
223
  }
25
- if (hay.includes("/responses")) {
26
- return { format: "openai-response", ambiguous: false };
224
+ return d.getTime();
225
+ }
226
+
227
+ // src/audit/auditDictionary.ts
228
+ var AUDIT_DICT_FILE = "_dict.jsonl";
229
+ var DICT_BASE_PREFIX = "dict:";
230
+ var DICT_CANDIDATES = 3;
231
+ var MIN_SAVING_RATIO = 0.2;
232
+ function parseEntries(raw) {
233
+ const entries = [];
234
+ for (const line of raw.split("\n")) {
235
+ const trimmed = line.trim();
236
+ if (!trimmed) continue;
237
+ try {
238
+ const parsed = JSON.parse(trimmed);
239
+ if (isAuditBodyEntry(parsed)) entries.push(parsed);
240
+ } catch {
241
+ }
27
242
  }
28
- if (hay.includes("openai") || hay.includes("/v1") || hay.includes("chat/completions")) {
29
- return { format: "openai", ambiguous: false };
243
+ return entries;
244
+ }
245
+ function plainShards(bodiesPath) {
246
+ try {
247
+ return readdirSync(bodiesPath).filter(
248
+ (file) => file.endsWith(".jsonl") && isSafeSessionKey(file.slice(0, -".jsonl".length))
249
+ );
250
+ } catch {
251
+ return [];
30
252
  }
31
- return { format: "openai", ambiguous: true };
32
253
  }
33
- function mapProviders(providers, notes) {
34
- const rows = [];
35
- for (const [i, p] of providers.entries()) {
36
- const id = p.name?.trim();
37
- if (!id) {
38
- notes.push(`Providers[${i}] has no name \u2014 skipped.`);
254
+ function chooseDictionary(anchors) {
255
+ if (anchors.length < 2) return null;
256
+ const total = anchors.reduce((sum, body) => sum + body.length, 0);
257
+ const candidates = [...anchors].sort((a, b) => b.length - a.length).slice(0, DICT_CANDIDATES);
258
+ let best = null;
259
+ for (const candidate of candidates) {
260
+ let cost = candidate.length;
261
+ for (const body of anchors) {
262
+ cost += body === candidate ? 0 : computeBodyDelta(candidate, body).ins.length;
263
+ }
264
+ if (best === null || cost < best.cost) best = { body: candidate, cost };
265
+ }
266
+ if (best === null) return null;
267
+ return total - best.cost >= total * MIN_SAVING_RATIO ? best.body : null;
268
+ }
269
+ var EMPTY = { shards: 0, anchors: 0, savedBytes: 0 };
270
+ function compactAuditDay(dayPath) {
271
+ const bodiesPath = join(dayPath, AUDIT_BODIES_DIR);
272
+ if (!existsSync(bodiesPath)) return EMPTY;
273
+ const dictPath = join(bodiesPath, AUDIT_DICT_FILE);
274
+ if (existsSync(dictPath) || existsSync(`${dictPath}.gz`)) return EMPTY;
275
+ const shardFiles = plainShards(bodiesPath);
276
+ if (shardFiles.length < 2) return EMPTY;
277
+ const loaded = /* @__PURE__ */ new Map();
278
+ const anchors = [];
279
+ for (const file of shardFiles) {
280
+ let entries;
281
+ try {
282
+ entries = parseEntries(readFileSync(join(bodiesPath, file), "utf8"));
283
+ } catch {
39
284
  continue;
40
285
  }
41
- const { format, ambiguous } = inferApiFormat(p);
42
- if (ambiguous) {
43
- notes.push(
44
- `Provider '${id}': could not infer apiFormat from base URL \u2014 defaulted to 'openai'. Edit the config if this provider speaks a different wire format.`
45
- );
286
+ loaded.set(file, entries);
287
+ for (const entry of entries) {
288
+ if (entry.req && entry.req.base === null) anchors.push(entry.req.ins);
46
289
  }
47
- rows.push({
48
- id,
49
- apiFormat: format,
50
- baseUrl: p.api_base_url ?? "",
51
- apiKey: p.api_key ?? "",
52
- models: Array.isArray(p.models) ? p.models : void 0
290
+ }
291
+ if (anchors.length < 2) return EMPTY;
292
+ const dictionary = chooseDictionary(anchors);
293
+ if (dictionary === null) return EMPTY;
294
+ const dictEntry = {
295
+ id: `${DICT_BASE_PREFIX}0`,
296
+ ts: 0,
297
+ req: { base: null, anchor: "dict", pre: 0, suf: 0, ins: dictionary }
298
+ };
299
+ writeFileSync(dictPath, JSON.stringify(dictEntry) + "\n", "utf8");
300
+ const result = { shards: 0, anchors: 0, savedBytes: 0 };
301
+ for (const [file, entries] of loaded) {
302
+ let changed = false;
303
+ let saved = 0;
304
+ const rewritten = entries.map((entry) => {
305
+ if (!entry.req || entry.req.base !== null || entry.req.ins === dictionary) return entry;
306
+ const delta = computeBodyDelta(dictionary, entry.req.ins);
307
+ if (delta.ins.length >= entry.req.ins.length) return entry;
308
+ changed = true;
309
+ saved += entry.req.ins.length - delta.ins.length;
310
+ return {
311
+ ...entry,
312
+ req: { base: dictEntry.id, pre: delta.pre, suf: delta.suf, ins: delta.ins }
313
+ };
53
314
  });
315
+ if (!changed) continue;
316
+ const target = join(bodiesPath, file);
317
+ const temp = `${target}.compacting`;
318
+ try {
319
+ writeFileSync(temp, rewritten.map((e) => JSON.stringify(e)).join("\n") + "\n", "utf8");
320
+ renameSync(temp, target);
321
+ } catch {
322
+ try {
323
+ if (existsSync(temp)) unlinkSync(temp);
324
+ } catch {
325
+ }
326
+ continue;
327
+ }
328
+ result.shards += 1;
329
+ result.anchors += rewritten.filter((e) => e.req?.base === dictEntry.id).length;
330
+ result.savedBytes += saved;
54
331
  }
55
- return rows;
332
+ if (result.shards === 0) {
333
+ try {
334
+ unlinkSync(dictPath);
335
+ } catch {
336
+ }
337
+ }
338
+ return result;
56
339
  }
57
- function noteRouterRoles(router, notes) {
58
- if (router.think) {
59
- notes.push(`Router.think \u2192 folded into 'default' (omnicross has no think slot).`);
340
+ function compactAllClosedAuditDays(auditDir, now = Date.now) {
341
+ const run = { days: 0, shards: 0, savedBytes: 0 };
342
+ if (!existsSync(auditDir)) return run;
343
+ const today = auditDayDirName(now());
344
+ let names;
345
+ try {
346
+ names = readdirSync(auditDir).filter(isAuditDayDir).sort();
347
+ } catch {
348
+ return run;
60
349
  }
61
- if (router.longContext) {
62
- notes.push(
63
- `Router.longContext \u2192 folded into 'default' (no longContext slot; longContextThreshold dropped).`
64
- );
350
+ for (const name of names) {
351
+ if (name === today) continue;
352
+ try {
353
+ const result = compactAuditDay(join(auditDir, name));
354
+ if (result.shards === 0) continue;
355
+ run.days += 1;
356
+ run.shards += result.shards;
357
+ run.savedBytes += result.savedBytes;
358
+ } catch {
359
+ }
65
360
  }
66
- if (router.image) {
67
- notes.push(`Router.image \u2192 mapped to 'vision' (CCR forceUseImageAgent dropped).`);
361
+ return run;
362
+ }
363
+
364
+ // src/audit/auditJsonl.ts
365
+ import { closeSync, openSync, readSync, statSync } from "fs";
366
+ var WINDOW_BYTES = 1 << 20;
367
+ var MAX_LINE_BYTES = 32 * 1024 * 1024;
368
+ var NEWLINE = 10;
369
+ function forEachLineFromTail(path2, onLine) {
370
+ let fd;
371
+ let end;
372
+ try {
373
+ end = statSync(path2).size;
374
+ if (end === 0) return;
375
+ fd = openSync(path2, "r");
376
+ } catch {
377
+ return;
68
378
  }
69
- if (router.webSearch) {
70
- notes.push(
71
- `Router.webSearch \u2192 DROPPED. omnicross injects web search via an interception port rather than routing to a natively-online model; the CCR webSearch model ('${router.webSearch}') was not carried over.`
72
- );
379
+ try {
380
+ let carry = Buffer.alloc(0);
381
+ while (end > 0) {
382
+ const start = Math.max(0, end - WINDOW_BYTES);
383
+ const window = Buffer.allocUnsafe(end - start);
384
+ let read;
385
+ try {
386
+ read = readSync(fd, window, 0, end - start, start);
387
+ } catch {
388
+ return;
389
+ }
390
+ const chunk = carry.length > 0 ? Buffer.concat([window.subarray(0, read), carry]) : window.subarray(0, read);
391
+ let lineEnd = chunk.length;
392
+ let nl = lineEnd > 0 ? chunk.lastIndexOf(NEWLINE, lineEnd - 1) : -1;
393
+ while (nl >= 0) {
394
+ if (nl + 1 < lineEnd) {
395
+ const line = chunk.subarray(nl + 1, lineEnd).toString("utf8").trim();
396
+ if (line && onLine(line)) return;
397
+ }
398
+ lineEnd = nl;
399
+ nl = lineEnd > 0 ? chunk.lastIndexOf(NEWLINE, lineEnd - 1) : -1;
400
+ }
401
+ if (start === 0) {
402
+ if (lineEnd > 0) {
403
+ const line = chunk.subarray(0, lineEnd).toString("utf8").trim();
404
+ if (line) onLine(line);
405
+ }
406
+ return;
407
+ }
408
+ if (lineEnd > MAX_LINE_BYTES) return;
409
+ carry = Buffer.from(chunk.subarray(0, lineEnd));
410
+ end = start;
411
+ }
412
+ } finally {
413
+ try {
414
+ closeSync(fd);
415
+ } catch {
416
+ }
73
417
  }
74
418
  }
75
- function mapCcrToOmnicross(ccr) {
76
- const notes = [];
77
- const providers = mapProviders(ccr.Providers ?? [], notes);
78
- noteRouterRoles(ccr.Router ?? {}, notes);
79
- return { config: { providers }, notes };
419
+
420
+ // src/audit/auditBodyReader.ts
421
+ function candidateDays(auditDir, ts) {
422
+ if (typeof ts === "number" && Number.isFinite(ts)) {
423
+ const named = auditDayDirName(ts);
424
+ if (existsSync2(join2(auditDir, named))) return [named];
425
+ }
426
+ try {
427
+ return readdirSync2(auditDir).filter(isAuditDayDir).sort().reverse();
428
+ } catch {
429
+ return [];
430
+ }
431
+ }
432
+ function readShard(auditDir, day, sessionKey) {
433
+ const base = join2(auditDir, day, AUDIT_BODIES_DIR, auditBodyFileName(sessionKey));
434
+ try {
435
+ if (existsSync2(base)) return readFileSync2(base, "utf8");
436
+ const gz = `${base}.gz`;
437
+ if (existsSync2(gz)) return gunzipSync(readFileSync2(gz)).toString("utf8");
438
+ } catch {
439
+ return null;
440
+ }
441
+ return null;
442
+ }
443
+ function parseShard(raw) {
444
+ const entries = /* @__PURE__ */ new Map();
445
+ for (const line of raw.split("\n")) {
446
+ const trimmed = line.trim();
447
+ if (!trimmed) continue;
448
+ let parsed;
449
+ try {
450
+ parsed = JSON.parse(trimmed);
451
+ } catch {
452
+ continue;
453
+ }
454
+ if (isAuditBodyEntry(parsed)) entries.set(parsed.id, parsed);
455
+ }
456
+ return entries;
457
+ }
458
+ function withDictionary(auditDir, day, entries) {
459
+ let needed = false;
460
+ for (const entry of entries.values()) {
461
+ if (entry.req?.base?.startsWith(DICT_BASE_PREFIX)) {
462
+ needed = true;
463
+ break;
464
+ }
465
+ }
466
+ if (!needed) return entries;
467
+ const base = join2(auditDir, day, AUDIT_BODIES_DIR, AUDIT_DICT_FILE);
468
+ let raw = null;
469
+ try {
470
+ if (existsSync2(base)) raw = readFileSync2(base, "utf8");
471
+ else if (existsSync2(`${base}.gz`)) raw = gunzipSync(readFileSync2(`${base}.gz`)).toString("utf8");
472
+ } catch {
473
+ return entries;
474
+ }
475
+ if (raw === null) return entries;
476
+ for (const [id, entry] of parseShard(raw)) entries.set(id, entry);
477
+ return entries;
478
+ }
479
+ function reconstructRequest(entries, entry) {
480
+ if (!entry.req) return void 0;
481
+ const chain = [];
482
+ const visited = /* @__PURE__ */ new Set();
483
+ let cursor = entry;
484
+ while (cursor?.req) {
485
+ if (visited.has(cursor.id)) return void 0;
486
+ visited.add(cursor.id);
487
+ chain.push(cursor);
488
+ if (cursor.req.base === null) break;
489
+ cursor = entries.get(cursor.req.base);
490
+ }
491
+ const anchor = chain[chain.length - 1];
492
+ if (!anchor?.req || anchor.req.base !== null) return void 0;
493
+ let text = anchor.req.ins;
494
+ for (let i = chain.length - 2; i >= 0; i -= 1) {
495
+ const delta = chain[i]?.req;
496
+ if (!delta) return void 0;
497
+ if (delta.pre > text.length || delta.suf > text.length - delta.pre) return void 0;
498
+ text = applyBodyDelta(text, delta);
499
+ }
500
+ return text;
501
+ }
502
+ function assignStreams(entries) {
503
+ const rootOf = /* @__PURE__ */ new Map();
504
+ for (const entry of entries.values()) {
505
+ const seen = /* @__PURE__ */ new Set();
506
+ let cursor = entry;
507
+ while (cursor?.req?.cont === true && cursor.req.base !== null && !seen.has(cursor.id)) {
508
+ seen.add(cursor.id);
509
+ const next = entries.get(cursor.req.base);
510
+ if (!next) break;
511
+ cursor = next;
512
+ }
513
+ rootOf.set(entry.id, cursor?.id ?? entry.id);
514
+ }
515
+ const firstTs = /* @__PURE__ */ new Map();
516
+ for (const entry of entries.values()) {
517
+ const root = rootOf.get(entry.id);
518
+ const known = firstTs.get(root);
519
+ if (known === void 0 || entry.ts < known) firstTs.set(root, entry.ts);
520
+ }
521
+ const order = [...firstTs.entries()].sort((a, b) => a[1] - b[1]).map(([root]) => root);
522
+ const index = new Map(order.map((root, i) => [root, i]));
523
+ const streams = /* @__PURE__ */ new Map();
524
+ for (const entry of entries.values()) {
525
+ streams.set(entry.id, index.get(rootOf.get(entry.id)) ?? 0);
526
+ }
527
+ return streams;
528
+ }
529
+ function readAuditBody(auditDir, query2) {
530
+ if (!isSafeSessionKey(query2.sessionKey) || !query2.id) return {};
531
+ if (!existsSync2(auditDir)) return {};
532
+ for (const day of candidateDays(auditDir, query2.ts)) {
533
+ const raw = readShard(auditDir, day, query2.sessionKey);
534
+ if (raw === null) continue;
535
+ const entries = withDictionary(auditDir, day, parseShard(raw));
536
+ const entry = entries.get(query2.id);
537
+ if (!entry) continue;
538
+ const result = {};
539
+ const requestBody = reconstructRequest(entries, entry);
540
+ if (requestBody !== void 0) result.requestBody = requestBody;
541
+ if (entry.res !== void 0) result.responseBody = entry.res;
542
+ return result;
543
+ }
544
+ return readLegacyInlineBody(auditDir, query2.id);
545
+ }
546
+ function readLegacyInlineBody(auditDir, id) {
547
+ let names;
548
+ try {
549
+ names = readdirSync2(auditDir).filter((name) => AUDIT_FILE_RE.test(name)).sort().reverse();
550
+ } catch {
551
+ return {};
552
+ }
553
+ const needle = JSON.stringify(id);
554
+ let found = {};
555
+ for (const name of names) {
556
+ forEachLineFromTail(join2(auditDir, name), (line) => {
557
+ if (!line.includes(needle)) return false;
558
+ let parsed;
559
+ try {
560
+ parsed = JSON.parse(line);
561
+ } catch {
562
+ return false;
563
+ }
564
+ const record = parsed;
565
+ if (record.id !== id) return false;
566
+ const result = {};
567
+ if (typeof record.requestBody === "string") result.requestBody = record.requestBody;
568
+ if (typeof record.responseBody === "string") result.responseBody = record.responseBody;
569
+ found = result;
570
+ return true;
571
+ });
572
+ if (found.requestBody !== void 0 || found.responseBody !== void 0) break;
573
+ }
574
+ return found;
575
+ }
576
+ function readAuditSessionTurns(auditDir, sessionKey, ts) {
577
+ if (!isSafeSessionKey(sessionKey) || !existsSync2(auditDir)) return [];
578
+ for (const day of candidateDays(auditDir, ts)) {
579
+ const raw = readShard(auditDir, day, sessionKey);
580
+ if (raw === null) continue;
581
+ const shardEntries = parseShard(raw);
582
+ const streams = assignStreams(shardEntries);
583
+ const entries = withDictionary(auditDir, day, shardEntries);
584
+ const turns = [];
585
+ for (const entry of entries.values()) {
586
+ if (entry.id.startsWith(DICT_BASE_PREFIX)) continue;
587
+ const turn = { id: entry.id, ts: entry.ts, stream: streams.get(entry.id) ?? 0 };
588
+ if (entry.req?.anchor === "diverged") turn.diverged = true;
589
+ const requestBody = reconstructRequest(entries, entry);
590
+ if (requestBody !== void 0) turn.requestBody = requestBody;
591
+ if (entry.res !== void 0) turn.responseBody = entry.res;
592
+ turns.push(turn);
593
+ }
594
+ turns.sort((a, b) => a.stream === b.stream ? a.ts - b.ts : a.stream - b.stream);
595
+ return turns;
596
+ }
597
+ return [];
598
+ }
599
+ function listAuditSessions(auditDir, ts) {
600
+ if (!existsSync2(auditDir)) return [];
601
+ const summaries = [];
602
+ for (const day of candidateDays(auditDir, ts)) {
603
+ const bodiesPath = join2(auditDir, day, AUDIT_BODIES_DIR);
604
+ let files;
605
+ try {
606
+ files = readdirSync2(bodiesPath);
607
+ } catch {
608
+ continue;
609
+ }
610
+ for (const file of files) {
611
+ const compressed = file.endsWith(".jsonl.gz");
612
+ const sessionKey = file.replace(/\.jsonl(\.gz)?$/, "");
613
+ if (!isSafeSessionKey(sessionKey) || !compressed && !file.endsWith(".jsonl")) continue;
614
+ let bytes = 0;
615
+ try {
616
+ bytes = statSync2(join2(bodiesPath, file)).size;
617
+ } catch {
618
+ continue;
619
+ }
620
+ const raw = readShard(auditDir, day, sessionKey);
621
+ const turns = raw === null ? 0 : parseShard(raw).size;
622
+ summaries.push({ sessionKey, day, turns, bytes, compressed });
623
+ }
624
+ }
625
+ summaries.sort((a, b) => a.day === b.day ? b.bytes - a.bytes : a.day < b.day ? 1 : -1);
626
+ return summaries;
80
627
  }
81
628
 
82
- // src/config.ts
83
- import { readFileSync as readFileSync2, writeFileSync as writeFileSync2 } from "fs";
629
+ // src/commands/paths.ts
630
+ import { dirname as dirname2, join as join4 } from "path";
84
631
 
85
632
  // src/secrets/envelope.ts
86
633
  import { createCipheriv, createDecipheriv, randomBytes } from "crypto";
@@ -139,13 +686,13 @@ function decryptValue(envelope, key) {
139
686
 
140
687
  // src/secrets/masterKey.ts
141
688
  import { randomBytes as randomBytes2 } from "crypto";
142
- import { chmodSync, existsSync, mkdirSync, readFileSync, writeFileSync } from "fs";
689
+ import { chmodSync, existsSync as existsSync3, mkdirSync, readFileSync as readFileSync3, writeFileSync as writeFileSync2 } from "fs";
143
690
  import { homedir } from "os";
144
- import { dirname, join } from "path";
691
+ import { dirname, join as join3 } from "path";
145
692
  var MASTER_KEY_ENV = "OMNICROSS_MASTER_KEY";
146
693
  var KEY_BYTES2 = 32;
147
694
  function defaultMasterKeyPath() {
148
- return join(homedir(), ".omnicross", "master.key");
695
+ return join3(homedir(), ".omnicross", "master.key");
149
696
  }
150
697
  function decodeEnvKey(raw) {
151
698
  const trimmed = raw.trim();
@@ -161,7 +708,7 @@ function decodeEnvKey(raw) {
161
708
  return buf;
162
709
  }
163
710
  function readKeyFile(path2) {
164
- const raw = readFileSync(path2);
711
+ const raw = readFileSync3(path2);
165
712
  if (raw.length === KEY_BYTES2) return raw;
166
713
  const text = raw.toString("utf8").trim();
167
714
  if (/^[0-9a-fA-F]{64}$/.test(text)) return Buffer.from(text, "hex");
@@ -174,7 +721,7 @@ function readKeyFile(path2) {
174
721
  function generateKeyFile(path2) {
175
722
  const key = randomBytes2(KEY_BYTES2);
176
723
  mkdirSync(dirname(path2), { recursive: true });
177
- writeFileSync(path2, key, { mode: 384 });
724
+ writeFileSync2(path2, key, { mode: 384 });
178
725
  try {
179
726
  chmodSync(path2, 384);
180
727
  } catch {
@@ -187,7 +734,7 @@ function resolveMasterKey(options = {}) {
187
734
  return decodeEnvKey(envRaw);
188
735
  }
189
736
  const keyFilePath = options.keyFilePath ?? defaultMasterKeyPath();
190
- if (existsSync(keyFilePath)) {
737
+ if (existsSync3(keyFilePath)) {
191
738
  return readKeyFile(keyFilePath);
192
739
  }
193
740
  return generateKeyFile(keyFilePath);
@@ -426,16 +973,243 @@ function transformTokens(tokens, fn) {
426
973
  });
427
974
  }
428
975
  }
429
- return next;
976
+ return next;
977
+ }
978
+ function encryptTokens(tokens, box) {
979
+ return transformTokens(tokens, (v) => box.encryptMaybe(v));
980
+ }
981
+ function decryptTokens(tokens, box) {
982
+ return transformTokens(tokens, (v) => box.decryptMaybe(v));
983
+ }
984
+
985
+ // src/commands/paths.ts
986
+ function defaultKeysPath(configPath) {
987
+ return join4(dirname2(configPath), "keys.json");
988
+ }
989
+ function defaultVouchersPath(configPath) {
990
+ return join4(dirname2(configPath), "vouchers.json");
991
+ }
992
+ function defaultTokensPath(configPath) {
993
+ return join4(dirname2(configPath), "tokens.json");
994
+ }
995
+ function defaultIntegrationsPath(configPath) {
996
+ return join4(dirname2(configPath), "integrations.json");
997
+ }
998
+ function defaultPricingPath(configPath) {
999
+ return join4(dirname2(configPath), "pricing.json");
1000
+ }
1001
+ function defaultPricingRefreshStatePath(configPath) {
1002
+ return join4(dirname2(configPath), "pricing-refresh.json");
1003
+ }
1004
+ function defaultAccountAllowancePath(configPath) {
1005
+ return join4(dirname2(configPath), "allowance-cache.json");
1006
+ }
1007
+ function defaultUsageEventsPath(configPath) {
1008
+ return join4(dirname2(configPath), "usage-events.jsonl");
1009
+ }
1010
+ function defaultAuditDir(configPath) {
1011
+ return join4(dirname2(configPath), "audit");
1012
+ }
1013
+ function defaultBillingDir(configPath) {
1014
+ return join4(dirname2(configPath), "billing");
1015
+ }
1016
+ function resolveSecretBox(masterKeyFilePath) {
1017
+ return new SecretBox(() => resolveMasterKey({ keyFilePath: masterKeyFilePath }));
1018
+ }
1019
+
1020
+ // src/commands/audit.ts
1021
+ function parseDate(value) {
1022
+ if (!value) return void 0;
1023
+ const m = /^(\d{4})-(\d{2})-(\d{2})$/.exec(value.trim());
1024
+ if (!m) throw new Error(`audit: --date must be YYYY-MM-DD (got ${value})`);
1025
+ const d = new Date(Number(m[1]), Number(m[2]) - 1, Number(m[3]));
1026
+ return d.getTime();
1027
+ }
1028
+ function formatBytes(bytes) {
1029
+ if (bytes < 1024) return `${bytes} B`;
1030
+ if (bytes < 1024 * 1024) return `${(bytes / 1024).toFixed(1)} KB`;
1031
+ return `${(bytes / (1024 * 1024)).toFixed(1)} MB`;
1032
+ }
1033
+ async function runAudit(argv) {
1034
+ const { values, positionals } = parseArgs({
1035
+ args: argv,
1036
+ options: {
1037
+ config: { type: "string", short: "c" },
1038
+ session: { type: "string", short: "s" },
1039
+ date: { type: "string", short: "d" },
1040
+ id: { type: "string" }
1041
+ },
1042
+ allowPositionals: true
1043
+ });
1044
+ const configPath = values.config;
1045
+ if (!configPath) throw new Error("audit: --config <path> is required");
1046
+ const auditDir = defaultAuditDir(configPath);
1047
+ const ts = parseDate(values.date);
1048
+ const action = positionals[0];
1049
+ if (action === "sessions") {
1050
+ const sessions2 = listAuditSessions(auditDir, ts);
1051
+ if (sessions2.length === 0) {
1052
+ console.info("No audit body shards found. Is `captureBodies` enabled?");
1053
+ return;
1054
+ }
1055
+ console.info(["DAY", "SESSION", "TURNS", "SIZE", "ARCHIVED"].join(" "));
1056
+ for (const s of sessions2) {
1057
+ console.info(
1058
+ [s.day, s.sessionKey, String(s.turns), formatBytes(s.bytes), s.compressed ? "gz" : "-"].join(" ")
1059
+ );
1060
+ }
1061
+ return;
1062
+ }
1063
+ if (action === "show") {
1064
+ const sessionKey = values.session;
1065
+ if (!sessionKey) throw new Error("audit show: --session <key> is required");
1066
+ if (values.id) {
1067
+ const body = readAuditBody(auditDir, { id: values.id, sessionKey, ...ts !== void 0 ? { ts } : {} });
1068
+ if (body.requestBody === void 0 && body.responseBody === void 0) {
1069
+ throw new Error(`audit show: no body found for record ${values.id}`);
1070
+ }
1071
+ if (body.requestBody !== void 0) console.info(`--- request ${values.id} ---
1072
+ ${body.requestBody}`);
1073
+ if (body.responseBody !== void 0) console.info(`--- response ${values.id} ---
1074
+ ${body.responseBody}`);
1075
+ return;
1076
+ }
1077
+ const turns = readAuditSessionTurns(auditDir, sessionKey, ts);
1078
+ if (turns.length === 0) throw new Error(`audit show: no shard found for session ${sessionKey}`);
1079
+ let stream = -1;
1080
+ for (const turn of turns) {
1081
+ const when = new Date(turn.ts).toISOString();
1082
+ if (turn.stream !== stream) {
1083
+ stream = turn.stream;
1084
+ console.info(`
1085
+ ########## stream ${stream} ##########`);
1086
+ }
1087
+ if (turn.diverged) {
1088
+ console.info("=== prefix diverged here (system prompt changed, or a restart reused this session) ===");
1089
+ }
1090
+ if (turn.requestBody !== void 0) {
1091
+ console.info(`--- request ${turn.id} @ ${when} ---
1092
+ ${turn.requestBody}`);
1093
+ }
1094
+ if (turn.responseBody !== void 0) {
1095
+ console.info(`--- response ${turn.id} @ ${when} ---
1096
+ ${turn.responseBody}`);
1097
+ }
1098
+ }
1099
+ return;
1100
+ }
1101
+ if (action === "compact") {
1102
+ const todayDir = auditDayDirName(Date.now());
1103
+ let names;
1104
+ try {
1105
+ names = readdirSync3(auditDir).filter(isAuditDayDir).sort();
1106
+ } catch {
1107
+ names = [];
1108
+ }
1109
+ const targets = ts !== void 0 ? names.filter((name) => name === auditDayDirName(ts)) : names.filter((name) => name !== todayDir);
1110
+ if (targets.length === 0) {
1111
+ console.info("Nothing to compact (today is skipped; a day is compacted once).");
1112
+ return;
1113
+ }
1114
+ let shards = 0;
1115
+ let saved = 0;
1116
+ for (const name of targets) {
1117
+ if (name === todayDir) {
1118
+ console.info(`Skipping ${name}: the current day is still being written.`);
1119
+ continue;
1120
+ }
1121
+ const result = compactAuditDay(join5(auditDir, name));
1122
+ shards += result.shards;
1123
+ saved += result.savedBytes;
1124
+ console.info(`${name}: ${result.shards} shard(s), ${result.anchors} anchor(s), ${formatBytes(result.savedBytes)} saved`);
1125
+ }
1126
+ console.info(`Done: ${shards} shard(s) rewritten, ${formatBytes(saved)} saved.`);
1127
+ return;
1128
+ }
1129
+ throw new Error("audit: expected `sessions`, `show`, or `compact` (see `omnicross help`)");
1130
+ }
1131
+
1132
+ // src/commands/import-ccr.ts
1133
+ import { readFileSync as readFileSync5 } from "fs";
1134
+ import { parseArgs as parseArgs2 } from "util";
1135
+
1136
+ // src/ccr-import.ts
1137
+ function parseCcrConfig(raw) {
1138
+ if (!raw || typeof raw !== "object") {
1139
+ throw new Error("CCR config: top-level value must be an object");
1140
+ }
1141
+ const obj = raw;
1142
+ const Providers = Array.isArray(obj["Providers"]) ? obj["Providers"] : [];
1143
+ const Router = obj["Router"] && typeof obj["Router"] === "object" ? obj["Router"] : {};
1144
+ return { Providers, Router };
1145
+ }
1146
+ function inferApiFormat(provider) {
1147
+ const hay = `${provider.api_base_url ?? ""} ${provider.name ?? ""}`.toLowerCase();
1148
+ if (hay.includes("anthropic") || hay.includes("claude")) {
1149
+ return { format: "anthropic", ambiguous: false };
1150
+ }
1151
+ if (hay.includes("generativelanguage") || hay.includes("gemini") || hay.includes("google")) {
1152
+ return { format: "gemini", ambiguous: false };
1153
+ }
1154
+ if (hay.includes("/responses")) {
1155
+ return { format: "openai-response", ambiguous: false };
1156
+ }
1157
+ if (hay.includes("openai") || hay.includes("/v1") || hay.includes("chat/completions")) {
1158
+ return { format: "openai", ambiguous: false };
1159
+ }
1160
+ return { format: "openai", ambiguous: true };
1161
+ }
1162
+ function mapProviders(providers, notes) {
1163
+ const rows = [];
1164
+ for (const [i, p] of providers.entries()) {
1165
+ const id = p.name?.trim();
1166
+ if (!id) {
1167
+ notes.push(`Providers[${i}] has no name \u2014 skipped.`);
1168
+ continue;
1169
+ }
1170
+ const { format, ambiguous } = inferApiFormat(p);
1171
+ if (ambiguous) {
1172
+ notes.push(
1173
+ `Provider '${id}': could not infer apiFormat from base URL \u2014 defaulted to 'openai'. Edit the config if this provider speaks a different wire format.`
1174
+ );
1175
+ }
1176
+ rows.push({
1177
+ id,
1178
+ apiFormat: format,
1179
+ baseUrl: p.api_base_url ?? "",
1180
+ apiKey: p.api_key ?? "",
1181
+ models: Array.isArray(p.models) ? p.models : void 0
1182
+ });
1183
+ }
1184
+ return rows;
430
1185
  }
431
- function encryptTokens(tokens, box) {
432
- return transformTokens(tokens, (v) => box.encryptMaybe(v));
1186
+ function noteRouterRoles(router, notes) {
1187
+ if (router.think) {
1188
+ notes.push(`Router.think \u2192 folded into 'default' (omnicross has no think slot).`);
1189
+ }
1190
+ if (router.longContext) {
1191
+ notes.push(
1192
+ `Router.longContext \u2192 folded into 'default' (no longContext slot; longContextThreshold dropped).`
1193
+ );
1194
+ }
1195
+ if (router.image) {
1196
+ notes.push(`Router.image \u2192 mapped to 'vision' (CCR forceUseImageAgent dropped).`);
1197
+ }
1198
+ if (router.webSearch) {
1199
+ notes.push(
1200
+ `Router.webSearch \u2192 DROPPED. omnicross injects web search via an interception port rather than routing to a natively-online model; the CCR webSearch model ('${router.webSearch}') was not carried over.`
1201
+ );
1202
+ }
433
1203
  }
434
- function decryptTokens(tokens, box) {
435
- return transformTokens(tokens, (v) => box.decryptMaybe(v));
1204
+ function mapCcrToOmnicross(ccr) {
1205
+ const notes = [];
1206
+ const providers = mapProviders(ccr.Providers ?? [], notes);
1207
+ noteRouterRoles(ccr.Router ?? {}, notes);
1208
+ return { config: { providers }, notes };
436
1209
  }
437
1210
 
438
1211
  // src/config.ts
1212
+ import { readFileSync as readFileSync4, writeFileSync as writeFileSync3 } from "fs";
439
1213
  var DEFAULT_ADMIN_PORT = 8766;
440
1214
  function validateAdmin(raw) {
441
1215
  if (!raw || typeof raw !== "object" || Array.isArray(raw)) return void 0;
@@ -497,6 +1271,35 @@ function validateApiKeys(raw) {
497
1271
  }
498
1272
  return out.length > 0 ? out : void 0;
499
1273
  }
1274
+ var THINK_LEVELS = /* @__PURE__ */ new Set([
1275
+ "none",
1276
+ "minimal",
1277
+ "low",
1278
+ "medium",
1279
+ "high",
1280
+ "xhigh",
1281
+ "max"
1282
+ ]);
1283
+ function validateThinkingLevels(raw) {
1284
+ if (!Array.isArray(raw)) return void 0;
1285
+ if (!raw.every((level) => typeof level === "string" && THINK_LEVELS.has(level))) {
1286
+ return void 0;
1287
+ }
1288
+ return [...raw];
1289
+ }
1290
+ function validateThinkingTokenLimit(raw) {
1291
+ if (!raw || typeof raw !== "object" || Array.isArray(raw)) return void 0;
1292
+ const bounds = raw;
1293
+ const min = bounds["min"];
1294
+ const max = bounds["max"];
1295
+ if (typeof min !== "number" || !Number.isFinite(min) || !Number.isInteger(min) || min < 0) {
1296
+ return void 0;
1297
+ }
1298
+ if (typeof max !== "number" || !Number.isFinite(max) || !Number.isInteger(max) || max < min) {
1299
+ return void 0;
1300
+ }
1301
+ return { min, max };
1302
+ }
500
1303
  function validateModelConfigs(raw) {
501
1304
  if (!Array.isArray(raw)) return void 0;
502
1305
  const out = [];
@@ -511,6 +1314,10 @@ function validateModelConfigs(raw) {
511
1314
  if (typeof m["enabled"] === "boolean") entry.enabled = m["enabled"];
512
1315
  if (typeof m["vision"] === "boolean") entry.vision = m["vision"];
513
1316
  if (typeof m["reasoning"] === "boolean") entry.reasoning = m["reasoning"];
1317
+ const thinkingLevels = validateThinkingLevels(m["thinkingLevels"]);
1318
+ if (thinkingLevels) entry.thinkingLevels = thinkingLevels;
1319
+ const thinkingTokenLimit = validateThinkingTokenLimit(m["thinkingTokenLimit"]);
1320
+ if (thinkingTokenLimit) entry.thinkingTokenLimit = thinkingTokenLimit;
514
1321
  out.push(entry);
515
1322
  }
516
1323
  return out.length > 0 ? out : void 0;
@@ -695,7 +1502,7 @@ function setSecretBox(box) {
695
1502
  function loadConfig(path2) {
696
1503
  let raw;
697
1504
  try {
698
- raw = readFileSync2(path2, "utf8");
1505
+ raw = readFileSync4(path2, "utf8");
699
1506
  } catch {
700
1507
  throw new Error(`config: cannot read file at '${path2}'`);
701
1508
  }
@@ -710,48 +1517,12 @@ function loadConfig(path2) {
710
1517
  }
711
1518
  function saveConfig(path2, cfg) {
712
1519
  const toWrite = secretBox ? encryptConfigSecrets(cfg, secretBox) : cfg;
713
- writeFileSync2(path2, JSON.stringify(toWrite, null, 2) + "\n", "utf8");
714
- }
715
-
716
- // src/commands/paths.ts
717
- import { dirname as dirname2, join as join2 } from "path";
718
- function defaultKeysPath(configPath) {
719
- return join2(dirname2(configPath), "keys.json");
720
- }
721
- function defaultVouchersPath(configPath) {
722
- return join2(dirname2(configPath), "vouchers.json");
723
- }
724
- function defaultTokensPath(configPath) {
725
- return join2(dirname2(configPath), "tokens.json");
726
- }
727
- function defaultIntegrationsPath(configPath) {
728
- return join2(dirname2(configPath), "integrations.json");
729
- }
730
- function defaultPricingPath(configPath) {
731
- return join2(dirname2(configPath), "pricing.json");
732
- }
733
- function defaultPricingRefreshStatePath(configPath) {
734
- return join2(dirname2(configPath), "pricing-refresh.json");
735
- }
736
- function defaultAccountAllowancePath(configPath) {
737
- return join2(dirname2(configPath), "allowance-cache.json");
738
- }
739
- function defaultUsageEventsPath(configPath) {
740
- return join2(dirname2(configPath), "usage-events.jsonl");
741
- }
742
- function defaultAuditDir(configPath) {
743
- return join2(dirname2(configPath), "audit");
744
- }
745
- function defaultBillingDir(configPath) {
746
- return join2(dirname2(configPath), "billing");
747
- }
748
- function resolveSecretBox(masterKeyFilePath) {
749
- return new SecretBox(() => resolveMasterKey({ keyFilePath: masterKeyFilePath }));
1520
+ writeFileSync3(path2, JSON.stringify(toWrite, null, 2) + "\n", "utf8");
750
1521
  }
751
1522
 
752
1523
  // src/commands/import-ccr.ts
753
1524
  async function runImportCcr(argv) {
754
- const { values, positionals } = parseArgs({
1525
+ const { values, positionals } = parseArgs2({
755
1526
  args: argv,
756
1527
  options: {
757
1528
  out: { type: "string", short: "o" },
@@ -766,7 +1537,7 @@ async function runImportCcr(argv) {
766
1537
  const outPath = values.out ?? "omnicross.config.json";
767
1538
  let raw;
768
1539
  try {
769
- raw = JSON.parse(readFileSync3(ccrPath, "utf8"));
1540
+ raw = JSON.parse(readFileSync5(ccrPath, "utf8"));
770
1541
  } catch {
771
1542
  throw new Error(`import-ccr: cannot read or parse '${ccrPath}'`);
772
1543
  }
@@ -788,24 +1559,24 @@ async function runImportCcr(argv) {
788
1559
 
789
1560
  // src/commands/integrations.ts
790
1561
  import { resolve as resolve2 } from "path";
791
- import { parseArgs as parseArgs2 } from "util";
1562
+ import { parseArgs as parseArgs3 } from "util";
792
1563
 
793
1564
  // src/integrations/IntegrationManager.ts
794
1565
  import { createHash } from "crypto";
795
- import { existsSync as existsSync3, readFileSync as readFileSync5, unlinkSync as unlinkSync2 } from "fs";
1566
+ import { existsSync as existsSync5, readFileSync as readFileSync7, unlinkSync as unlinkSync3 } from "fs";
796
1567
  import { homedir as homedir2 } from "os";
797
- import { dirname as dirname4, join as join3, resolve } from "path";
1568
+ import { dirname as dirname4, join as join6, resolve } from "path";
798
1569
  import { createIntegrationKey } from "@omnicross/core";
799
1570
 
800
1571
  // src/integrations/IntegrationStateStore.ts
801
1572
  import {
802
1573
  chmodSync as chmodSync2,
803
- existsSync as existsSync2,
1574
+ existsSync as existsSync4,
804
1575
  mkdirSync as mkdirSync2,
805
- readFileSync as readFileSync4,
806
- renameSync,
807
- unlinkSync,
808
- writeFileSync as writeFileSync3
1576
+ readFileSync as readFileSync6,
1577
+ renameSync as renameSync2,
1578
+ unlinkSync as unlinkSync2,
1579
+ writeFileSync as writeFileSync4
809
1580
  } from "fs";
810
1581
  import { dirname as dirname3 } from "path";
811
1582
  var EMPTY_STATE = { version: 1, clients: {} };
@@ -817,10 +1588,10 @@ var IntegrationStateStore = class {
817
1588
  path;
818
1589
  box;
819
1590
  load() {
820
- if (!existsSync2(this.path)) return { ...EMPTY_STATE, clients: {} };
1591
+ if (!existsSync4(this.path)) return { ...EMPTY_STATE, clients: {} };
821
1592
  let raw;
822
1593
  try {
823
- raw = JSON.parse(readFileSync4(this.path, "utf8"));
1594
+ raw = JSON.parse(readFileSync6(this.path, "utf8"));
824
1595
  } catch {
825
1596
  throw new Error(`integration state '${this.path}' is not valid JSON`);
826
1597
  }
@@ -890,17 +1661,17 @@ function isManagedFileRecord(value) {
890
1661
  function atomicWrite(path2, content) {
891
1662
  mkdirSync2(dirname3(path2), { recursive: true });
892
1663
  const temp = `${path2}.tmp-${process.pid}-${Date.now()}`;
893
- writeFileSync3(temp, content, { encoding: "utf8", mode: 384 });
1664
+ writeFileSync4(temp, content, { encoding: "utf8", mode: 384 });
894
1665
  try {
895
- renameSync(temp, path2);
1666
+ renameSync2(temp, path2);
896
1667
  } catch (error) {
897
1668
  try {
898
- unlinkSync(temp);
1669
+ unlinkSync2(temp);
899
1670
  } catch {
900
1671
  }
901
1672
  throw error;
902
1673
  } finally {
903
- if (existsSync2(path2)) {
1674
+ if (existsSync4(path2)) {
904
1675
  try {
905
1676
  chmodSync2(path2, 384);
906
1677
  } catch {
@@ -1394,10 +2165,10 @@ var IntegrationManager = class {
1394
2165
  };
1395
2166
  }
1396
2167
  defaultConfigPath(client) {
1397
- return client === "codex" ? join3(this.homeDir, ".codex", "config.toml") : join3(this.homeDir, ".claude", "settings.json");
2168
+ return client === "codex" ? join6(this.homeDir, ".codex", "config.toml") : join6(this.homeDir, ".claude", "settings.json");
1398
2169
  }
1399
2170
  codexAuthPathForConfig(configPath) {
1400
- return join3(dirname4(configPath), "auth.json");
2171
+ return join6(dirname4(configPath), "auth.json");
1401
2172
  }
1402
2173
  renderInstalled(client, base, secret) {
1403
2174
  if (client === "claude") {
@@ -1410,7 +2181,7 @@ var IntegrationManager = class {
1410
2181
  }
1411
2182
  };
1412
2183
  function readOptional(path2) {
1413
- return existsSync3(path2) ? readFileSync5(path2, "utf8") : null;
2184
+ return existsSync5(path2) ? readFileSync7(path2, "utf8") : null;
1414
2185
  }
1415
2186
  function sha256(value) {
1416
2187
  return createHash("sha256").update(value, "utf8").digest("hex");
@@ -1474,7 +2245,7 @@ function writeOptional(path2, content) {
1474
2245
  atomicWrite(path2, content);
1475
2246
  return;
1476
2247
  }
1477
- if (existsSync3(path2)) unlinkSync2(path2);
2248
+ if (existsSync5(path2)) unlinkSync3(path2);
1478
2249
  }
1479
2250
  function assertLoopbackGatewayUrl(value) {
1480
2251
  let url;
@@ -1491,7 +2262,7 @@ function assertLoopbackGatewayUrl(value) {
1491
2262
  }
1492
2263
 
1493
2264
  // src/ports/JsonOutboundKeyDb.ts
1494
- import { existsSync as existsSync4, readFileSync as readFileSync6, writeFileSync as writeFileSync4 } from "fs";
2265
+ import { existsSync as existsSync6, readFileSync as readFileSync8, writeFileSync as writeFileSync5 } from "fs";
1495
2266
  var JsonOutboundKeyDb = class {
1496
2267
  /**
1497
2268
  * @param secretBox OPTIONAL reversible-secret codec. When present, a created
@@ -1624,16 +2395,16 @@ var JsonOutboundKeyDb = class {
1624
2395
  }
1625
2396
  /** Read the key rows, tolerating a missing/corrupt file (→ empty list). */
1626
2397
  readRows() {
1627
- if (!existsSync4(this.keysPath)) return [];
2398
+ if (!existsSync6(this.keysPath)) return [];
1628
2399
  try {
1629
- const parsed = JSON.parse(readFileSync6(this.keysPath, "utf8"));
2400
+ const parsed = JSON.parse(readFileSync8(this.keysPath, "utf8"));
1630
2401
  return Array.isArray(parsed) ? parsed : [];
1631
2402
  } catch {
1632
2403
  return [];
1633
2404
  }
1634
2405
  }
1635
2406
  writeRows(rows) {
1636
- writeFileSync4(this.keysPath, JSON.stringify(rows, null, 2) + "\n", "utf8");
2407
+ writeFileSync5(this.keysPath, JSON.stringify(rows, null, 2) + "\n", "utf8");
1637
2408
  }
1638
2409
  };
1639
2410
  function applyPolicyField(row, field, value) {
@@ -1644,7 +2415,7 @@ function applyPolicyField(row, field, value) {
1644
2415
 
1645
2416
  // src/commands/integrations.ts
1646
2417
  async function runIntegrations(argv) {
1647
- const { values, positionals } = parseArgs2({
2418
+ const { values, positionals } = parseArgs3({
1648
2419
  args: argv,
1649
2420
  options: {
1650
2421
  config: { type: "string", short: "c" },
@@ -1694,10 +2465,10 @@ function isClient(value) {
1694
2465
  }
1695
2466
 
1696
2467
  // src/commands/keys.ts
1697
- import { parseArgs as parseArgs3 } from "util";
2468
+ import { parseArgs as parseArgs4 } from "util";
1698
2469
  import { createNamedKey } from "@omnicross/core/outbound-api";
1699
2470
  async function runKeys(argv) {
1700
- const { values, positionals } = parseArgs3({
2471
+ const { values, positionals } = parseArgs4({
1701
2472
  args: argv,
1702
2473
  options: { config: { type: "string", short: "c" } },
1703
2474
  allowPositionals: true
@@ -1751,9 +2522,9 @@ async function keysRevoke(db, id) {
1751
2522
  // src/commands/launch.ts
1752
2523
  import { spawn as spawn2 } from "child_process";
1753
2524
  import { randomUUID as randomUUID6 } from "crypto";
1754
- import { existsSync as existsSync20 } from "fs";
1755
- import { delimiter as delimiter2, join as join12 } from "path";
1756
- import { parseArgs as parseArgs4 } from "util";
2525
+ import { existsSync as existsSync22 } from "fs";
2526
+ import { delimiter as delimiter2, join as join15 } from "path";
2527
+ import { parseArgs as parseArgs5 } from "util";
1757
2528
  import {
1758
2529
  buildChatCliLaunchConfig as buildChatCliLaunchConfig2,
1759
2530
  buildGeminiCliLaunchConfig as buildGeminiCliLaunchConfig2
@@ -1761,7 +2532,7 @@ import {
1761
2532
  import { ROUTE_LEASE_REQUEST_SCHEMA as ROUTE_LEASE_REQUEST_SCHEMA2 } from "@omnicross/core/provider-proxy";
1762
2533
 
1763
2534
  // src/bootstrap.ts
1764
- import { accessSync, constants as fsConstants, existsSync as existsSync19 } from "fs";
2535
+ import { accessSync, constants as fsConstants, existsSync as existsSync21 } from "fs";
1765
2536
  import { DEFAULT_AUDIT_CONFIG } from "@omnicross/contracts/audit-types";
1766
2537
  import { DEFAULT_BILLING_CONFIG } from "@omnicross/contracts/billing-types";
1767
2538
  import { getGeminiCodeAssistProjectResolver } from "@omnicross/core/auth/GeminiCodeAssistProjectResolver";
@@ -1795,7 +2566,12 @@ import {
1795
2566
  } from "@omnicross/core/provider-proxy";
1796
2567
  import { routeLeaseDescriptorPort } from "@omnicross/cli-launcher";
1797
2568
  import { KeySpendTracker } from "@omnicross/core/outbound-api";
1798
- import { PricingEngine, UsageRecorder } from "@omnicross/core/usage";
2569
+ import {
2570
+ __resetSharedUsageThroughputTrackerForTests,
2571
+ getSharedUsageThroughputTracker as getSharedUsageThroughputTracker2,
2572
+ PricingEngine,
2573
+ UsageRecorder
2574
+ } from "@omnicross/core/usage";
1799
2575
  import {
1800
2576
  setSubscriptionAccountService,
1801
2577
  setSubscriptionProviderRegistry,
@@ -2302,13 +3078,13 @@ var ClaudeAllowanceRefreshScheduler = class {
2302
3078
  // src/allowance/JsonAccountAllowancePersistence.ts
2303
3079
  import { randomUUID } from "crypto";
2304
3080
  import {
2305
- existsSync as existsSync5,
3081
+ existsSync as existsSync7,
2306
3082
  mkdirSync as mkdirSync3,
2307
- readFileSync as readFileSync7,
2308
- renameSync as renameSync2,
3083
+ readFileSync as readFileSync9,
3084
+ renameSync as renameSync3,
2309
3085
  rmSync,
2310
- statSync,
2311
- writeFileSync as writeFileSync5
3086
+ statSync as statSync3,
3087
+ writeFileSync as writeFileSync6
2312
3088
  } from "fs";
2313
3089
  import { dirname as dirname5 } from "path";
2314
3090
  import { normalizeAccountAllowanceSnapshot } from "@omnicross/core/pipeline/AccountAllowanceStore";
@@ -2322,10 +3098,10 @@ var JsonAccountAllowancePersistence = class {
2322
3098
  cachePath;
2323
3099
  /** Read only the `snapshots` payload; all row validation remains defensive. */
2324
3100
  load() {
2325
- if (!existsSync5(this.cachePath)) return [];
3101
+ if (!existsSync7(this.cachePath)) return [];
2326
3102
  try {
2327
- if (statSync(this.cachePath).size > MAX_ALLOWANCE_CACHE_BYTES) return [];
2328
- const raw = readFileSync7(this.cachePath, "utf8");
3103
+ if (statSync3(this.cachePath).size > MAX_ALLOWANCE_CACHE_BYTES) return [];
3104
+ const raw = readFileSync9(this.cachePath, "utf8");
2329
3105
  if (!raw.trim()) return [];
2330
3106
  const parsed = JSON.parse(raw);
2331
3107
  if (Array.isArray(parsed)) return parsed;
@@ -2356,8 +3132,8 @@ var JsonAccountAllowancePersistence = class {
2356
3132
  mkdirSync3(dirname5(this.cachePath), { recursive: true });
2357
3133
  const temporaryPath = `${this.cachePath}.${process.pid}.${randomUUID()}.tmp`;
2358
3134
  try {
2359
- writeFileSync5(temporaryPath, serialized, { encoding: "utf8", flag: "wx" });
2360
- renameSync2(temporaryPath, this.cachePath);
3135
+ writeFileSync6(temporaryPath, serialized, { encoding: "utf8", flag: "wx" });
3136
+ renameSync3(temporaryPath, this.cachePath);
2361
3137
  } finally {
2362
3138
  rmSync(temporaryPath, { force: true });
2363
3139
  }
@@ -2399,6 +3175,37 @@ function handleAuditQuery(req, res, reader) {
2399
3175
  res.writeHead(200, { "Content-Type": "application/json" });
2400
3176
  res.end(JSON.stringify({ records }));
2401
3177
  }
3178
+ function handleAuditBodyQuery(req, res, reader) {
3179
+ const url = new URL(req.url ?? "/", "http://localhost");
3180
+ const id = url.searchParams.get("id")?.trim();
3181
+ const sessionKey = url.searchParams.get("session")?.trim();
3182
+ if (!id || !sessionKey) {
3183
+ res.writeHead(400, { "Content-Type": "application/json" });
3184
+ res.end(JSON.stringify({ error: "id and session are required" }));
3185
+ return;
3186
+ }
3187
+ const query2 = { id, sessionKey };
3188
+ const ts = intParam(url.searchParams.get("ts"));
3189
+ if (ts !== void 0) query2.ts = ts;
3190
+ const body = reader ? reader(query2) : {};
3191
+ res.writeHead(200, { "Content-Type": "application/json" });
3192
+ res.end(JSON.stringify(body));
3193
+ }
3194
+ function handleAuditCompact(res, compact) {
3195
+ if (!compact) {
3196
+ res.writeHead(200, { "Content-Type": "application/json" });
3197
+ res.end(JSON.stringify({ days: 0, shards: 0, savedBytes: 0 }));
3198
+ return;
3199
+ }
3200
+ try {
3201
+ const result = compact();
3202
+ res.writeHead(200, { "Content-Type": "application/json" });
3203
+ res.end(JSON.stringify(result));
3204
+ } catch (error) {
3205
+ res.writeHead(500, { "Content-Type": "application/json" });
3206
+ res.end(JSON.stringify({ error: error instanceof Error ? error.message : "compaction failed" }));
3207
+ }
3208
+ }
2402
3209
  async function handleAuditStatsQuery(req, res, reader) {
2403
3210
  const url = new URL(req.url ?? "/", "http://localhost");
2404
3211
  const query2 = {};
@@ -3144,10 +3951,10 @@ async function exchangeGemini(code, codeVerifier, exchangeFetch) {
3144
3951
  // src/admin/cliLaunch.ts
3145
3952
  import { exec, spawn } from "child_process";
3146
3953
  import { randomUUID as randomUUID2 } from "crypto";
3147
- import { chmodSync as chmodSync3, existsSync as existsSync6, mkdtempSync, rmSync as rmSync2, writeFileSync as writeFileSync6 } from "fs";
3954
+ import { chmodSync as chmodSync3, existsSync as existsSync8, mkdtempSync, rmSync as rmSync2, writeFileSync as writeFileSync7 } from "fs";
3148
3955
  import { createServer } from "net";
3149
3956
  import { tmpdir } from "os";
3150
- import { delimiter, join as join4 } from "path";
3957
+ import { delimiter, join as join7 } from "path";
3151
3958
  import {
3152
3959
  buildChatCliLaunchConfig,
3153
3960
  buildClaudeCliLaunchConfig,
@@ -3204,8 +4011,8 @@ function isLaunchCliId(id) {
3204
4011
  function probeDefault(candidate) {
3205
4012
  const segments = (process.env["PATH"] ?? "").split(delimiter).filter(Boolean);
3206
4013
  for (const seg of segments) {
3207
- const full = join4(seg, candidate);
3208
- if (existsSync6(full)) return full;
4014
+ const full = join7(seg, candidate);
4015
+ if (existsSync8(full)) return full;
3209
4016
  }
3210
4017
  return null;
3211
4018
  }
@@ -3309,10 +4116,10 @@ function openTerminal({ cli, command, extraArgs, env, cwd, platform, onFailure }
3309
4116
  const runLine = [command, ...extraArgs].map(shq).join(" ");
3310
4117
  const script = `${cwd ? `cd ${shq(cwd)}; ` : ""}${runLine}`;
3311
4118
  if (platform === "darwin") {
3312
- const launchDir = mkdtempSync(join4(tmpdir(), "omnicross-terminal-"));
3313
- const commandFile = join4(launchDir, "launch.command");
3314
- const bootstrapFile = join4(launchDir, "bootstrap.cjs");
3315
- const socketPath = macIpc.socketPath ?? join4(launchDir, "descriptor.sock");
4119
+ const launchDir = mkdtempSync(join7(tmpdir(), "omnicross-terminal-"));
4120
+ const commandFile = join7(launchDir, "launch.command");
4121
+ const bootstrapFile = join7(launchDir, "bootstrap.cjs");
4122
+ const socketPath = macIpc.socketPath ?? join7(launchDir, "descriptor.sock");
3316
4123
  const openerEnv = { ...process.env };
3317
4124
  for (const key of Object.keys(env)) delete openerEnv[key];
3318
4125
  let claimed = false;
@@ -3382,8 +4189,8 @@ function openTerminal({ cli, command, extraArgs, env, cwd, platform, onFailure }
3382
4189
  }
3383
4190
  };
3384
4191
  try {
3385
- writeFileSync6(bootstrapFile, MAC_TERMINAL_BOOTSTRAP_SOURCE, { encoding: "utf8", mode: 448 });
3386
- writeFileSync6(commandFile, `#!/bin/bash
4192
+ writeFileSync7(bootstrapFile, MAC_TERMINAL_BOOTSTRAP_SOURCE, { encoding: "utf8", mode: 448 });
4193
+ writeFileSync7(commandFile, `#!/bin/bash
3387
4194
  rm -f -- "$0"
3388
4195
  exec ${shq(process.execPath)} ${shq(bootstrapFile)} ${shq(socketPath)} ${shq(launchDir)} ${shq(cwd ?? "")} ${runLine}
3389
4196
  `, {
@@ -4054,6 +4861,7 @@ function applyAuditConfig(config) {
4054
4861
  } else {
4055
4862
  setAuditCaptureConfig(null);
4056
4863
  setAuditSink(null);
4864
+ writer?.reset();
4057
4865
  if (sweeper) {
4058
4866
  if (config) sweeper.configure(config);
4059
4867
  sweeper.dispose();
@@ -4640,6 +5448,7 @@ async function handleImport(body, deps) {
4640
5448
  }
4641
5449
 
4642
5450
  // src/admin/usagePricing.ts
5451
+ import { getSharedUsageThroughputTracker } from "@omnicross/core/usage";
4643
5452
  var err4 = (status, message) => ({
4644
5453
  status,
4645
5454
  body: { error: { type: "admin_api_error", message } }
@@ -4665,6 +5474,9 @@ var BUCKET_SPAN_MS = {
4665
5474
  };
4666
5475
  var MAX_TIMESERIES_BUCKETS = 2e3;
4667
5476
  async function handleUsageGet(view, query2, deps) {
5477
+ if (view === "throughput") {
5478
+ return { status: 200, body: getSharedUsageThroughputTracker().snapshot() };
5479
+ }
4668
5480
  const range = parseRange(query2);
4669
5481
  if (!isRange(range)) return range;
4670
5482
  switch (view) {
@@ -5470,6 +6282,12 @@ function parseModelConfigsInput(raw, existing) {
5470
6282
  else if (typeof prior?.vision === "boolean") entry.vision = prior.vision;
5471
6283
  if (typeof m["reasoning"] === "boolean") entry.reasoning = m["reasoning"];
5472
6284
  else if (typeof prior?.reasoning === "boolean") entry.reasoning = prior.reasoning;
6285
+ const thinkingLevels = validateThinkingLevels(m["thinkingLevels"]);
6286
+ if (thinkingLevels) entry.thinkingLevels = thinkingLevels;
6287
+ else if (prior?.thinkingLevels) entry.thinkingLevels = prior.thinkingLevels;
6288
+ const thinkingTokenLimit = validateThinkingTokenLimit(m["thinkingTokenLimit"]);
6289
+ if (thinkingTokenLimit) entry.thinkingTokenLimit = thinkingTokenLimit;
6290
+ else if (prior?.thinkingTokenLimit) entry.thinkingTokenLimit = prior.thinkingTokenLimit;
5473
6291
  out.push(entry);
5474
6292
  }
5475
6293
  return out.length > 0 ? out : void 0;
@@ -6295,7 +7113,7 @@ function proxyToOutbound(res, outboundPort, path2, key, body) {
6295
7113
  }
6296
7114
 
6297
7115
  // src/admin/uiStatic.ts
6298
- import { existsSync as existsSync7, statSync as statSync2 } from "fs";
7116
+ import { existsSync as existsSync9, statSync as statSync4 } from "fs";
6299
7117
  import { readFile } from "fs/promises";
6300
7118
  import { createRequire } from "module";
6301
7119
  import path from "path";
@@ -6318,13 +7136,13 @@ var CONTENT_TYPES = {
6318
7136
  function resolveUiDist() {
6319
7137
  const fromEnv = process.env["OMNICROSS_UI_DIST"];
6320
7138
  if (fromEnv) {
6321
- return existsSync7(path.join(fromEnv, "index.html")) ? path.resolve(fromEnv) : null;
7139
+ return existsSync9(path.join(fromEnv, "index.html")) ? path.resolve(fromEnv) : null;
6322
7140
  }
6323
7141
  try {
6324
7142
  const req = createRequire(typeof __filename !== "undefined" ? __filename : import.meta.url);
6325
7143
  const pkgJson = req.resolve("@omnicross/ui/package.json");
6326
7144
  const dist = path.join(path.dirname(pkgJson), "dist");
6327
- return existsSync7(path.join(dist, "index.html")) ? dist : null;
7145
+ return existsSync9(path.join(dist, "index.html")) ? dist : null;
6328
7146
  } catch {
6329
7147
  return null;
6330
7148
  }
@@ -6373,7 +7191,7 @@ async function handleUiStatic(req, res, urlPath, uiDist) {
6373
7191
  return true;
6374
7192
  }
6375
7193
  let target = filePath;
6376
- if (!existsSync7(target) || statSync2(target).isDirectory()) {
7194
+ if (!existsSync9(target) || statSync4(target).isDirectory()) {
6377
7195
  if (path.extname(rel) === "") {
6378
7196
  target = path.join(uiDist, "index.html");
6379
7197
  } else {
@@ -6390,7 +7208,7 @@ async function handleUiStatic(req, res, urlPath, uiDist) {
6390
7208
  }
6391
7209
 
6392
7210
  // src/admin/version.ts
6393
- var DAEMON_VERSION = true ? "0.1.8" : "0.0.0-dev";
7211
+ var DAEMON_VERSION = true ? "0.1.10" : "0.0.0-dev";
6394
7212
 
6395
7213
  // src/admin/AdminServer.ts
6396
7214
  var LOOPBACK_ADDR = "127.0.0.1";
@@ -6502,6 +7320,14 @@ var AdminServer = class {
6502
7320
  await handleAuditStatsQuery(req, res, this.deps.auditStatsReader);
6503
7321
  return;
6504
7322
  }
7323
+ if (path2 === "/admin/api/audit/body" && (req.method === "GET" || req.method === "HEAD")) {
7324
+ handleAuditBodyQuery(req, res, this.deps.auditBodyReader);
7325
+ return;
7326
+ }
7327
+ if (path2 === "/admin/api/audit/compact" && req.method === "POST") {
7328
+ handleAuditCompact(res, this.deps.auditCompactor);
7329
+ return;
7330
+ }
6505
7331
  if (path2 === "/admin/api/billing-status" && (req.method === "GET" || req.method === "HEAD")) {
6506
7332
  handleBillingStatus(res, this.deps.billingStatusReader);
6507
7333
  return;
@@ -6934,6 +7760,15 @@ function toLLMProvider(row) {
6934
7760
  api_base_url: row.baseUrl,
6935
7761
  api_key: resolvePreferredApiKey(row),
6936
7762
  models,
7763
+ modelConfigs: row.modelConfigs?.map((config) => ({
7764
+ id: config.id,
7765
+ name: config.name ?? config.id,
7766
+ enabled: config.enabled ?? true,
7767
+ vision: config.vision,
7768
+ reasoning: config.reasoning,
7769
+ thinkingLevels: config.thinkingLevels,
7770
+ thinkingTokenLimit: config.thinkingTokenLimit
7771
+ })),
6937
7772
  enabled: true,
6938
7773
  transformer,
6939
7774
  // app-parity-2 child 3: POPULATE the coding-plan endpoint onto the core
@@ -7105,7 +7940,7 @@ function safeStringify(value) {
7105
7940
  }
7106
7941
 
7107
7942
  // src/ports/JsonApiServerSettingsStore.ts
7108
- import { readFileSync as readFileSync8, writeFileSync as writeFileSync7 } from "fs";
7943
+ import { readFileSync as readFileSync10, writeFileSync as writeFileSync8 } from "fs";
7109
7944
  import { OUTBOUND_API_SERVER_CONFIG_KEY } from "@omnicross/core/outbound-api";
7110
7945
  var JsonApiServerSettingsStore = class {
7111
7946
  /**
@@ -7132,7 +7967,7 @@ var JsonApiServerSettingsStore = class {
7132
7967
  if (key !== OUTBOUND_API_SERVER_CONFIG_KEY) return;
7133
7968
  const file = this.readFile();
7134
7969
  file.server = this.encryptSecrets(value);
7135
- writeFileSync7(this.configPath, JSON.stringify(file, null, 2) + "\n", "utf8");
7970
+ writeFileSync8(this.configPath, JSON.stringify(file, null, 2) + "\n", "utf8");
7136
7971
  }
7137
7972
  /** Encrypt the proxy passwords + webhook + billing secrets before persisting (no-op without a box). */
7138
7973
  encryptSecrets(config) {
@@ -7155,7 +7990,7 @@ var JsonApiServerSettingsStore = class {
7155
7990
  /** Read the config.json, tolerating a missing/corrupt file (→ empty shape). */
7156
7991
  readFile() {
7157
7992
  try {
7158
- const raw = readFileSync8(this.configPath, "utf8");
7993
+ const raw = readFileSync10(this.configPath, "utf8");
7159
7994
  const parsed = JSON.parse(raw);
7160
7995
  if (parsed && typeof parsed === "object") return parsed;
7161
7996
  } catch {
@@ -7166,7 +8001,7 @@ var JsonApiServerSettingsStore = class {
7166
8001
 
7167
8002
  // src/ports/JsonlUsageEventStore.ts
7168
8003
  import { randomUUID as randomUUID4 } from "crypto";
7169
- import { appendFileSync, existsSync as existsSync8, readFileSync as readFileSync9 } from "fs";
8004
+ import { appendFileSync, existsSync as existsSync10, readFileSync as readFileSync11 } from "fs";
7170
8005
  var JsonlUsageEventStore = class {
7171
8006
  constructor(eventsPath, isPriced) {
7172
8007
  this.eventsPath = eventsPath;
@@ -7380,10 +8215,10 @@ var JsonlUsageEventStore = class {
7380
8215
  }
7381
8216
  /** Parse every line, skipping malformed/torn lines defensively. */
7382
8217
  readAllRows() {
7383
- if (!existsSync8(this.eventsPath)) return [];
8218
+ if (!existsSync10(this.eventsPath)) return [];
7384
8219
  let raw;
7385
8220
  try {
7386
- raw = readFileSync9(this.eventsPath, "utf8");
8221
+ raw = readFileSync11(this.eventsPath, "utf8");
7387
8222
  } catch {
7388
8223
  return [];
7389
8224
  }
@@ -7422,15 +8257,15 @@ function nextBoundary(ts, bucket) {
7422
8257
  return new Date(d.getFullYear(), d.getMonth() + 1, 1).getTime();
7423
8258
  }
7424
8259
  }
7425
- var pad2 = (n) => String(n).padStart(2, "0");
8260
+ var pad22 = (n) => String(n).padStart(2, "0");
7426
8261
  function bucketLabel(bucketStartTs, bucket) {
7427
8262
  const d = new Date(bucketStartTs);
7428
8263
  const y = d.getFullYear();
7429
- const mo = pad2(d.getMonth() + 1);
7430
- const day = pad2(d.getDate());
8264
+ const mo = pad22(d.getMonth() + 1);
8265
+ const day = pad22(d.getDate());
7431
8266
  switch (bucket) {
7432
8267
  case "hour":
7433
- return `${mo}-${day} ${pad2(d.getHours())}:00`;
8268
+ return `${mo}-${day} ${pad22(d.getHours())}:00`;
7434
8269
  case "day":
7435
8270
  return `${y}-${mo}-${day}`;
7436
8271
  case "month":
@@ -7486,7 +8321,7 @@ function median(values) {
7486
8321
  }
7487
8322
 
7488
8323
  // src/ports/JsonPricingStore.ts
7489
- import { existsSync as existsSync9, readFileSync as readFileSync10, renameSync as renameSync3, rmSync as rmSync3, writeFileSync as writeFileSync8 } from "fs";
8324
+ import { existsSync as existsSync11, readFileSync as readFileSync12, renameSync as renameSync4, rmSync as rmSync3, writeFileSync as writeFileSync9 } from "fs";
7490
8325
  import { randomUUID as randomUUID5 } from "crypto";
7491
8326
  var JsonPricingStore = class {
7492
8327
  constructor(pricingPath) {
@@ -7501,9 +8336,9 @@ var JsonPricingStore = class {
7501
8336
  * otherwise unusable pricing table after a crash or manual file edit.
7502
8337
  */
7503
8338
  hasUsableSnapshot() {
7504
- if (!existsSync9(this.pricingPath)) return false;
8339
+ if (!existsSync11(this.pricingPath)) return false;
7505
8340
  try {
7506
- const parsed = JSON.parse(readFileSync10(this.pricingPath, "utf8"));
8341
+ const parsed = JSON.parse(readFileSync12(this.pricingPath, "utf8"));
7507
8342
  return Array.isArray(parsed) && parsed.some(isUsablePricingRow);
7508
8343
  } catch {
7509
8344
  return false;
@@ -7616,9 +8451,9 @@ var JsonPricingStore = class {
7616
8451
  }
7617
8452
  /** Read the pricing rows, tolerating a missing/corrupt file (→ empty list). */
7618
8453
  readRows() {
7619
- if (!existsSync9(this.pricingPath)) return [];
8454
+ if (!existsSync11(this.pricingPath)) return [];
7620
8455
  try {
7621
- const parsed = JSON.parse(readFileSync10(this.pricingPath, "utf8"));
8456
+ const parsed = JSON.parse(readFileSync12(this.pricingPath, "utf8"));
7622
8457
  return Array.isArray(parsed) ? parsed : [];
7623
8458
  } catch {
7624
8459
  return [];
@@ -7627,7 +8462,7 @@ var JsonPricingStore = class {
7627
8462
  writeRows(rows) {
7628
8463
  const temporaryPath = `${this.pricingPath}.${process.pid}.${randomUUID5()}.tmp`;
7629
8464
  try {
7630
- writeFileSync8(temporaryPath, JSON.stringify(rows, null, 2) + "\n", {
8465
+ writeFileSync9(temporaryPath, JSON.stringify(rows, null, 2) + "\n", {
7631
8466
  encoding: "utf8",
7632
8467
  flag: "wx"
7633
8468
  });
@@ -7638,7 +8473,7 @@ var JsonPricingStore = class {
7638
8473
  }
7639
8474
  /** Isolated for deterministic failure testing; never removes the target. */
7640
8475
  replaceFile(temporaryPath) {
7641
- renameSync3(temporaryPath, this.pricingPath);
8476
+ renameSync4(temporaryPath, this.pricingPath);
7642
8477
  }
7643
8478
  };
7644
8479
  function isUsablePricingRow(value) {
@@ -7648,7 +8483,7 @@ function isUsablePricingRow(value) {
7648
8483
  }
7649
8484
 
7650
8485
  // src/pricing/PricingRefreshScheduler.ts
7651
- import { existsSync as existsSync10, readFileSync as readFileSync11, renameSync as renameSync4, writeFileSync as writeFileSync9 } from "fs";
8486
+ import { existsSync as existsSync12, readFileSync as readFileSync13, renameSync as renameSync5, writeFileSync as writeFileSync10 } from "fs";
7652
8487
  var EMPTY_STATE2 = {
7653
8488
  lastAttemptAt: null,
7654
8489
  lastSuccessAt: null,
@@ -7686,9 +8521,9 @@ var PricingRefreshScheduler = class {
7686
8521
  this.timer = null;
7687
8522
  }
7688
8523
  getState() {
7689
- if (!existsSync10(this.statePath)) return { ...EMPTY_STATE2, sources: [] };
8524
+ if (!existsSync12(this.statePath)) return { ...EMPTY_STATE2, sources: [] };
7690
8525
  try {
7691
- const value = JSON.parse(readFileSync11(this.statePath, "utf8"));
8526
+ const value = JSON.parse(readFileSync13(this.statePath, "utf8"));
7692
8527
  return {
7693
8528
  lastAttemptAt: finiteOrNull(value.lastAttemptAt),
7694
8529
  lastSuccessAt: finiteOrNull(value.lastSuccessAt),
@@ -7741,9 +8576,9 @@ var PricingRefreshScheduler = class {
7741
8576
  }
7742
8577
  writeState(state) {
7743
8578
  const temporaryPath = `${this.statePath}.tmp`;
7744
- writeFileSync9(temporaryPath, `${JSON.stringify(state, null, 2)}
8579
+ writeFileSync10(temporaryPath, `${JSON.stringify(state, null, 2)}
7745
8580
  `, "utf8");
7746
- renameSync4(temporaryPath, this.statePath);
8581
+ renameSync5(temporaryPath, this.statePath);
7747
8582
  }
7748
8583
  };
7749
8584
  function finiteOrNull(value) {
@@ -7751,7 +8586,7 @@ function finiteOrNull(value) {
7751
8586
  }
7752
8587
 
7753
8588
  // src/ports/JsonVoucherDb.ts
7754
- import { existsSync as existsSync11, readFileSync as readFileSync12, writeFileSync as writeFileSync10 } from "fs";
8589
+ import { existsSync as existsSync13, readFileSync as readFileSync14, writeFileSync as writeFileSync11 } from "fs";
7755
8590
  var JsonVoucherDb = class {
7756
8591
  constructor(vouchersPath) {
7757
8592
  this.vouchersPath = vouchersPath;
@@ -7829,21 +8664,21 @@ var JsonVoucherDb = class {
7829
8664
  }
7830
8665
  /** Read the voucher rows, tolerating a missing/corrupt file (→ empty list). */
7831
8666
  readRows() {
7832
- if (!existsSync11(this.vouchersPath)) return [];
8667
+ if (!existsSync13(this.vouchersPath)) return [];
7833
8668
  try {
7834
- const parsed = JSON.parse(readFileSync12(this.vouchersPath, "utf8"));
8669
+ const parsed = JSON.parse(readFileSync14(this.vouchersPath, "utf8"));
7835
8670
  return Array.isArray(parsed) ? parsed : [];
7836
8671
  } catch {
7837
8672
  return [];
7838
8673
  }
7839
8674
  }
7840
8675
  writeRows(rows) {
7841
- writeFileSync10(this.vouchersPath, JSON.stringify(rows, null, 2) + "\n", "utf8");
8676
+ writeFileSync11(this.vouchersPath, JSON.stringify(rows, null, 2) + "\n", "utf8");
7842
8677
  }
7843
8678
  };
7844
8679
 
7845
8680
  // src/ports/JsonSubscriptionCredentialStore.ts
7846
- import { existsSync as existsSync13, mkdirSync as mkdirSync4, readFileSync as readFileSync14, writeFileSync as writeFileSync11 } from "fs";
8681
+ import { existsSync as existsSync15, mkdirSync as mkdirSync4, readFileSync as readFileSync16, writeFileSync as writeFileSync12 } from "fs";
7847
8682
  import { dirname as dirname6 } from "path";
7848
8683
  import { getSharedAccountHealth as getSharedAccountHealth2 } from "@omnicross/core/pipeline/SubscriptionAccountHealth";
7849
8684
  import { getSharedAccountAllowanceScheduling as getSharedAccountAllowanceScheduling3 } from "@omnicross/core/pipeline/AccountAllowanceScheduling";
@@ -7897,11 +8732,11 @@ function findDuplicateCredentialIds(accounts) {
7897
8732
  }
7898
8733
 
7899
8734
  // src/ports/external-cli-credentials.ts
7900
- import { existsSync as existsSync12, readFileSync as readFileSync13 } from "fs";
8735
+ import { existsSync as existsSync14, readFileSync as readFileSync15 } from "fs";
7901
8736
  import { homedir as homedir3 } from "os";
7902
- import { join as join5 } from "path";
8737
+ import { join as join8 } from "path";
7903
8738
  function externalStorePath(provider, home = homedir3()) {
7904
- return provider === "claude" ? join5(home, ".claude", ".credentials.json") : join5(home, ".codex", "auth.json");
8739
+ return provider === "claude" ? join8(home, ".claude", ".credentials.json") : join8(home, ".codex", "auth.json");
7905
8740
  }
7906
8741
  function decodeJwtExpiryMs(token) {
7907
8742
  try {
@@ -7950,10 +8785,10 @@ function parseCodexTokensEnvelope(raw) {
7950
8785
  }
7951
8786
  function readExternalCliCredentials(provider, home = homedir3()) {
7952
8787
  const path2 = externalStorePath(provider, home);
7953
- if (!existsSync12(path2)) return null;
8788
+ if (!existsSync14(path2)) return null;
7954
8789
  let raw;
7955
8790
  try {
7956
- const parsed = JSON.parse(readFileSync13(path2, "utf8"));
8791
+ const parsed = JSON.parse(readFileSync15(path2, "utf8"));
7957
8792
  raw = parsed && typeof parsed === "object" && !Array.isArray(parsed) ? parsed : void 0;
7958
8793
  } catch {
7959
8794
  return null;
@@ -8526,7 +9361,7 @@ var JsonSubscriptionCredentialStore = class {
8526
9361
  persist(config) {
8527
9362
  mkdirSync4(dirname6(this.tokensPath), { recursive: true });
8528
9363
  const encrypted = encryptTokens(config, this.box);
8529
- writeFileSync11(this.tokensPath, JSON.stringify(encrypted, null, 2) + "\n", "utf8");
9364
+ writeFileSync12(this.tokensPath, JSON.stringify(encrypted, null, 2) + "\n", "utf8");
8530
9365
  }
8531
9366
  /**
8532
9367
  * Read + parse `tokens.json`, tolerating a missing/corrupt file, then DECRYPT
@@ -8542,10 +9377,10 @@ var JsonSubscriptionCredentialStore = class {
8542
9377
  * `config.ts loadConfig`, which decrypts outside its parse try.
8543
9378
  */
8544
9379
  readConfig() {
8545
- if (!existsSync13(this.tokensPath)) return { updatedAt: "" };
9380
+ if (!existsSync15(this.tokensPath)) return { updatedAt: "" };
8546
9381
  let parsed;
8547
9382
  try {
8548
- const raw = JSON.parse(readFileSync14(this.tokensPath, "utf8"));
9383
+ const raw = JSON.parse(readFileSync16(this.tokensPath, "utf8"));
8549
9384
  parsed = raw && typeof raw === "object" && !Array.isArray(raw) ? raw : null;
8550
9385
  } catch {
8551
9386
  parsed = null;
@@ -9065,39 +9900,21 @@ var AccountHealthSweeper = class {
9065
9900
  };
9066
9901
 
9067
9902
  // src/audit/AuditPruneSweeper.ts
9068
- import { existsSync as existsSync15, readdirSync as readdirSync2, unlinkSync as unlinkSync3 } from "fs";
9069
- import { join as join7 } from "path";
9070
-
9071
- // src/audit/auditFiles.ts
9072
- var AUDIT_FILE_RE = /^audit-(\d{4})-(\d{2})-(\d{2})\.jsonl$/;
9073
- var pad22 = (n) => String(n).padStart(2, "0");
9074
- function auditFileName(ts) {
9075
- const d = new Date(ts);
9076
- return `audit-${d.getFullYear()}-${pad22(d.getMonth() + 1)}-${pad22(d.getDate())}.jsonl`;
9077
- }
9078
- function auditFileDateMs(fileName) {
9079
- const m = AUDIT_FILE_RE.exec(fileName);
9080
- if (!m) return null;
9081
- const year = Number(m[1]);
9082
- const month = Number(m[2]);
9083
- const day = Number(m[3]);
9084
- const d = new Date(year, month - 1, day);
9085
- if (d.getFullYear() !== year || d.getMonth() !== month - 1 || d.getDate() !== day) {
9086
- return null;
9087
- }
9088
- return d.getTime();
9089
- }
9903
+ import { createReadStream as createReadStream2, createWriteStream as createWriteStream2, existsSync as existsSync17, readdirSync as readdirSync5, rmSync as rmSync4, unlinkSync as unlinkSync4 } from "fs";
9904
+ import { join as join10 } from "path";
9905
+ import { pipeline } from "stream/promises";
9906
+ import { createGzip } from "zlib";
9090
9907
 
9091
9908
  // src/audit/auditStats.ts
9092
9909
  import {
9093
9910
  createReadStream,
9094
- existsSync as existsSync14,
9095
- readFileSync as readFileSync15,
9096
- readdirSync,
9097
- statSync as statSync3,
9098
- writeFileSync as writeFileSync12
9911
+ existsSync as existsSync16,
9912
+ readFileSync as readFileSync17,
9913
+ readdirSync as readdirSync4,
9914
+ statSync as statSync5,
9915
+ writeFileSync as writeFileSync13
9099
9916
  } from "fs";
9100
- import { basename, dirname as dirname7, join as join6 } from "path";
9917
+ import { basename, dirname as dirname7, join as join9 } from "path";
9101
9918
  var SIDECAR_VERSION = 1;
9102
9919
  var META_PREFIX_BYTES = 64 * 1024;
9103
9920
  var READ_CHUNK_BYTES = 4 * 1024 * 1024;
@@ -9105,9 +9922,9 @@ function auditStatsFileName(auditFile) {
9105
9922
  return auditFile.replace(/\.jsonl$/, ".stats.json");
9106
9923
  }
9107
9924
  function readPersisted(path2) {
9108
- if (!existsSync14(path2)) return null;
9925
+ if (!existsSync16(path2)) return null;
9109
9926
  try {
9110
- const value = JSON.parse(readFileSync15(path2, "utf8"));
9927
+ const value = JSON.parse(readFileSync17(path2, "utf8"));
9111
9928
  if (value.version !== SIDECAR_VERSION || !Number.isSafeInteger(value.auditBytes) || (value.auditBytes ?? -1) < 0 || !Number.isSafeInteger(value.requestCount) || (value.requestCount ?? -1) < 0 || !Number.isSafeInteger(value.errorCount) || (value.errorCount ?? -1) < 0 || (value.errorCount ?? 0) > (value.requestCount ?? -1) || typeof value.complete !== "boolean" || value.minTs !== null && !Number.isFinite(value.minTs) || value.maxTs !== null && !Number.isFinite(value.maxTs)) {
9112
9929
  return null;
9113
9930
  }
@@ -9117,7 +9934,7 @@ function readPersisted(path2) {
9117
9934
  }
9118
9935
  }
9119
9936
  function updateAuditStatsAfterAppend(auditPath, auditBytesBefore, auditBytesAfter, record) {
9120
- const statsPath = join6(dirname7(auditPath), auditStatsFileName(basename(auditPath)));
9937
+ const statsPath = join9(dirname7(auditPath), auditStatsFileName(basename(auditPath)));
9121
9938
  const previous = auditBytesBefore === 0 ? {
9122
9939
  version: SIDECAR_VERSION,
9123
9940
  auditBytes: 0,
@@ -9137,13 +9954,13 @@ function updateAuditStatsAfterAppend(auditPath, auditBytesBefore, auditBytesAfte
9137
9954
  minTs: previous.minTs === null ? record.ts : Math.min(previous.minTs, record.ts),
9138
9955
  maxTs: previous.maxTs === null ? record.ts : Math.max(previous.maxTs, record.ts)
9139
9956
  };
9140
- writeFileSync12(statsPath, JSON.stringify(next), "utf8");
9957
+ writeFileSync13(statsPath, JSON.stringify(next), "utf8");
9141
9958
  }
9142
9959
  function queryCovers(stats, from, to) {
9143
9960
  return stats.requestCount === 0 || stats.minTs !== null && stats.maxTs !== null && from <= stats.minTs && to >= stats.maxTs;
9144
9961
  }
9145
- function fileOverlaps(file, from, to) {
9146
- const start = auditFileDateMs(file);
9962
+ function fileOverlaps(name, from, to) {
9963
+ const start = auditFileDateMs(name);
9147
9964
  if (start === null) return false;
9148
9965
  const date = new Date(start);
9149
9966
  const end = new Date(date.getFullYear(), date.getMonth(), date.getDate() + 1).getTime();
@@ -9248,21 +10065,27 @@ function mergePersistedStats(previous, appended) {
9248
10065
  };
9249
10066
  }
9250
10067
  async function readAuditStats(auditDir, query2 = {}) {
9251
- if (!existsSync14(auditDir)) return { requestCount: 0, errorCount: 0, complete: true };
10068
+ if (!existsSync16(auditDir)) return { requestCount: 0, errorCount: 0, complete: true };
9252
10069
  const from = typeof query2.from === "number" ? query2.from : -Infinity;
9253
10070
  const to = typeof query2.to === "number" ? query2.to : Infinity;
9254
- let files;
10071
+ let sources;
9255
10072
  try {
9256
- files = readdirSync(auditDir).filter((file) => AUDIT_FILE_RE.test(file) && fileOverlaps(file, from, to)).sort();
10073
+ sources = readdirSync4(auditDir).filter((name) => fileOverlaps(name, from, to)).sort().map(
10074
+ (name) => AUDIT_DAY_DIR_RE.test(name) ? {
10075
+ auditPath: join9(auditDir, name, AUDIT_META_FILE),
10076
+ statsPath: join9(auditDir, name, auditStatsFileName(AUDIT_META_FILE))
10077
+ } : {
10078
+ auditPath: join9(auditDir, name),
10079
+ statsPath: join9(auditDir, auditStatsFileName(name))
10080
+ }
10081
+ ).filter((source) => existsSync16(source.auditPath));
9257
10082
  } catch {
9258
10083
  return { requestCount: 0, errorCount: 0, complete: false };
9259
10084
  }
9260
10085
  const total = { requestCount: 0, errorCount: 0, complete: true };
9261
- for (const file of files) {
9262
- const auditPath = join6(auditDir, file);
10086
+ for (const { auditPath, statsPath } of sources) {
9263
10087
  try {
9264
- const auditBytes = statSync3(auditPath).size;
9265
- const statsPath = join6(auditDir, auditStatsFileName(file));
10088
+ const auditBytes = statSync5(auditPath).size;
9266
10089
  const persisted = readPersisted(statsPath);
9267
10090
  if (persisted && persisted.complete && persisted.auditBytes === auditBytes && queryCovers(persisted, from, to)) {
9268
10091
  total.requestCount += persisted.requestCount;
@@ -9281,7 +10104,7 @@ async function readAuditStats(auditDir, query2 = {}) {
9281
10104
  total.errorCount += scanned.filtered.errorCount + (resumable?.errorCount ?? 0);
9282
10105
  total.complete = total.complete && scanned.filtered.complete;
9283
10106
  const current = resumable ? mergePersistedStats(resumable, scanned.all) : scanned.all;
9284
- if (current.complete) writeFileSync12(statsPath, JSON.stringify(current), "utf8");
10107
+ if (current.complete) writeFileSync13(statsPath, JSON.stringify(current), "utf8");
9285
10108
  } catch {
9286
10109
  total.complete = false;
9287
10110
  }
@@ -9292,6 +10115,7 @@ async function readAuditStats(auditDir, query2 = {}) {
9292
10115
  // src/audit/AuditPruneSweeper.ts
9293
10116
  var DAY_MS = 24 * 60 * 6e4;
9294
10117
  var SWEEP_INTERVAL_MS2 = 60 * 6e4;
10118
+ var ARCHIVE_BATCH = 64;
9295
10119
  var AuditPruneSweeper = class {
9296
10120
  constructor(auditDir, logger, config, intervalMs = SWEEP_INTERVAL_MS2, now = Date.now) {
9297
10121
  this.auditDir = auditDir;
@@ -9307,6 +10131,7 @@ var AuditPruneSweeper = class {
9307
10131
  now;
9308
10132
  timer = null;
9309
10133
  sweeping = false;
10134
+ archiving = false;
9310
10135
  /** Whether pruning is active (audit enabled). */
9311
10136
  get enabled() {
9312
10137
  return this.config.enabled;
@@ -9316,13 +10141,13 @@ var AuditPruneSweeper = class {
9316
10141
  this.config = config;
9317
10142
  }
9318
10143
  /**
9319
- * Arm the prune interval AND run one prune immediately (boot cleanup). No-op
9320
- * when audit is disabled (zero regression). Idempotent.
10144
+ * Arm the interval AND run one pass immediately (boot cleanup). No-op when
10145
+ * audit is disabled (zero regression). Idempotent.
9321
10146
  */
9322
10147
  start() {
9323
10148
  if (this.timer || !this.config.enabled) return;
9324
- void this.sweep();
9325
- this.timer = setInterval(() => void this.sweep(), this.intervalMs);
10149
+ void this.runOnce();
10150
+ this.timer = setInterval(() => void this.runOnce(), this.intervalMs);
9326
10151
  this.timer.unref?.();
9327
10152
  }
9328
10153
  /** Clear the interval (daemon shutdown / test teardown). Idempotent. */
@@ -9332,31 +10157,43 @@ var AuditPruneSweeper = class {
9332
10157
  this.timer = null;
9333
10158
  }
9334
10159
  }
10160
+ /** Prune first, then archive — never spend CPU compressing a day about to go. */
10161
+ async runOnce() {
10162
+ await this.sweep();
10163
+ await this.archive();
10164
+ }
10165
+ /** The LOCAL-midnight epoch ms of the current day. */
10166
+ todayMidnight() {
10167
+ const today = new Date(this.now());
10168
+ return new Date(today.getFullYear(), today.getMonth(), today.getDate()).getTime();
10169
+ }
9335
10170
  /**
9336
- * One prune: unlink every audit date file strictly OLDER than the retention
9337
- * cutoff (`now - retentionDays` days, at local-midnight granularity). Exposed
9338
- * for tests; never throws. Returns the number of files removed.
10171
+ * One prune: remove every audit day strictly OLDER than the retention cutoff
10172
+ * (`now - retentionDays` days, at local-midnight granularity). Exposed for
10173
+ * tests; never throws. Returns the number of days removed.
9339
10174
  */
9340
10175
  async sweep() {
9341
10176
  if (!this.config.enabled || this.sweeping) return 0;
9342
10177
  this.sweeping = true;
9343
10178
  try {
9344
- if (!existsSync15(this.auditDir)) return 0;
9345
- const today = new Date(this.now());
9346
- const todayMidnight = new Date(today.getFullYear(), today.getMonth(), today.getDate()).getTime();
9347
- const cutoff = todayMidnight - (this.config.retentionDays - 1) * DAY_MS;
10179
+ if (!existsSync17(this.auditDir)) return 0;
10180
+ const cutoff = this.todayMidnight() - (this.config.retentionDays - 1) * DAY_MS;
9348
10181
  let removed = 0;
9349
- for (const file of readdirSync2(this.auditDir)) {
9350
- const dateMs = auditFileDateMs(file);
10182
+ for (const name of readdirSync5(this.auditDir)) {
10183
+ const dateMs = auditFileDateMs(name);
9351
10184
  if (dateMs === null || dateMs >= cutoff) continue;
9352
10185
  try {
9353
- unlinkSync3(join7(this.auditDir, file));
10186
+ if (isAuditDayDir(name)) {
10187
+ rmSync4(join10(this.auditDir, name), { recursive: true, force: true });
10188
+ } else {
10189
+ unlinkSync4(join10(this.auditDir, name));
10190
+ const statsPath = join10(this.auditDir, auditStatsFileName(name));
10191
+ if (existsSync17(statsPath)) unlinkSync4(statsPath);
10192
+ }
9354
10193
  removed += 1;
9355
- const statsPath = join7(this.auditDir, auditStatsFileName(file));
9356
- if (existsSync15(statsPath)) unlinkSync3(statsPath);
9357
10194
  } catch (error) {
9358
- this.logger.warn("[AuditPruneSweeper] failed to unlink expired audit file", {
9359
- file,
10195
+ this.logger.warn("[AuditPruneSweeper] failed to remove expired audit day", {
10196
+ name,
9360
10197
  error: error instanceof Error ? error.message : String(error)
9361
10198
  });
9362
10199
  }
@@ -9372,59 +10209,158 @@ var AuditPruneSweeper = class {
9372
10209
  this.sweeping = false;
9373
10210
  }
9374
10211
  }
10212
+ /**
10213
+ * Gzip the body shards of every CLOSED day (anything before today). Today is
10214
+ * deliberately left as plain text so it stays greppable while it is the day you
10215
+ * are debugging. Exposed for tests; never throws. Returns shards compressed.
10216
+ */
10217
+ async archive() {
10218
+ if (!this.config.enabled || this.archiving) return 0;
10219
+ this.archiving = true;
10220
+ try {
10221
+ if (!existsSync17(this.auditDir)) return 0;
10222
+ const today = this.todayMidnight();
10223
+ let compressed = 0;
10224
+ for (const name of readdirSync5(this.auditDir)) {
10225
+ if (compressed >= ARCHIVE_BATCH) break;
10226
+ const dateMs = auditFileDateMs(name);
10227
+ if (dateMs === null || dateMs >= today || !isAuditDayDir(name)) continue;
10228
+ const dayPath = join10(this.auditDir, name);
10229
+ try {
10230
+ const compaction = compactAuditDay(dayPath);
10231
+ if (compaction.shards > 0) {
10232
+ this.logger.debug("audit cross-session compaction complete", {
10233
+ day: name,
10234
+ shards: compaction.shards,
10235
+ anchors: compaction.anchors,
10236
+ savedBytes: compaction.savedBytes
10237
+ });
10238
+ }
10239
+ } catch (error) {
10240
+ this.logger.warn("[AuditPruneSweeper] cross-session compaction failed", {
10241
+ day: name,
10242
+ error: error instanceof Error ? error.message : String(error)
10243
+ });
10244
+ }
10245
+ compressed += await this.archiveDay(
10246
+ join10(dayPath, AUDIT_BODIES_DIR),
10247
+ ARCHIVE_BATCH - compressed
10248
+ );
10249
+ }
10250
+ if (compressed > 0) this.logger.debug("audit archive complete", { compressed });
10251
+ return compressed;
10252
+ } catch (error) {
10253
+ this.logger.warn("audit archive pass failed", {
10254
+ error: error instanceof Error ? error.message : String(error)
10255
+ });
10256
+ return 0;
10257
+ } finally {
10258
+ this.archiving = false;
10259
+ }
10260
+ }
10261
+ /** Gzip up to `budget` plain shards in one day's `bodies/` directory. */
10262
+ async archiveDay(bodiesPath, budget) {
10263
+ let shards;
10264
+ try {
10265
+ shards = readdirSync5(bodiesPath).filter((file) => file.endsWith(".jsonl"));
10266
+ } catch {
10267
+ return 0;
10268
+ }
10269
+ let compressed = 0;
10270
+ for (const shard of shards) {
10271
+ if (compressed >= budget) break;
10272
+ const source = join10(bodiesPath, shard);
10273
+ const target = `${source}.gz`;
10274
+ try {
10275
+ if (existsSync17(target)) {
10276
+ unlinkSync4(source);
10277
+ continue;
10278
+ }
10279
+ await pipeline(createReadStream2(source), createGzip(), createWriteStream2(target));
10280
+ unlinkSync4(source);
10281
+ compressed += 1;
10282
+ } catch (error) {
10283
+ try {
10284
+ if (existsSync17(target)) unlinkSync4(target);
10285
+ } catch {
10286
+ }
10287
+ this.logger.warn("[AuditPruneSweeper] failed to archive audit body shard", {
10288
+ shard,
10289
+ error: error instanceof Error ? error.message : String(error)
10290
+ });
10291
+ }
10292
+ }
10293
+ return compressed;
10294
+ }
9375
10295
  };
9376
10296
 
9377
10297
  // src/audit/auditReader.ts
9378
- import { existsSync as existsSync16, readdirSync as readdirSync3, readFileSync as readFileSync16 } from "fs";
9379
- import { join as join8 } from "path";
10298
+ import { existsSync as existsSync18, readdirSync as readdirSync6 } from "fs";
10299
+ import { join as join11 } from "path";
9380
10300
  var DEFAULT_LIMIT = 200;
9381
10301
  var MAX_LIMIT = 2e3;
9382
- function readAuditRecords(auditDir, query2 = {}) {
9383
- if (!existsSync16(auditDir)) return [];
9384
- let files;
10302
+ var OVERSCAN = 256;
10303
+ function daySources(auditDir) {
10304
+ let names;
9385
10305
  try {
9386
- files = readdirSync3(auditDir).filter((f) => AUDIT_FILE_RE.test(f));
10306
+ names = readdirSync6(auditDir);
9387
10307
  } catch {
9388
10308
  return [];
9389
10309
  }
10310
+ const sources = [];
10311
+ for (const name of names) {
10312
+ const dateMs = auditFileDateMs(name);
10313
+ if (dateMs === null) continue;
10314
+ if (AUDIT_DAY_DIR_RE.test(name)) {
10315
+ const path2 = join11(auditDir, name, AUDIT_META_FILE);
10316
+ if (existsSync18(path2)) sources.push({ path: path2, dateMs });
10317
+ } else if (AUDIT_FILE_RE.test(name)) {
10318
+ sources.push({ path: join11(auditDir, name), dateMs });
10319
+ }
10320
+ }
10321
+ return sources.sort((a, b) => b.dateMs - a.dateMs);
10322
+ }
10323
+ function isAuditRecord(value) {
10324
+ if (!value || typeof value !== "object" || Array.isArray(value)) return false;
10325
+ const r = value;
10326
+ return typeof r["id"] === "string" && typeof r["ts"] === "number" && typeof r["method"] === "string" && typeof r["path"] === "string" && typeof r["status"] === "number";
10327
+ }
10328
+ function toMetaRecord(record) {
10329
+ if (record.requestBody === void 0 && record.responseBody === void 0) return record;
10330
+ const { requestBody: _req, responseBody: _res, ...meta } = record;
10331
+ return { ...meta, hasBody: true };
10332
+ }
10333
+ function readAuditRecords(auditDir, query2 = {}) {
10334
+ if (!existsSync18(auditDir)) return [];
9390
10335
  const from = typeof query2.from === "number" ? query2.from : -Infinity;
9391
10336
  const to = typeof query2.to === "number" ? query2.to : Infinity;
9392
10337
  const limit = Math.min(MAX_LIMIT, Math.max(1, Math.trunc(query2.limit ?? DEFAULT_LIMIT)));
9393
10338
  const matched = [];
9394
- for (const file of files.sort().reverse()) {
9395
- let raw;
9396
- try {
9397
- raw = readFileSync16(join8(auditDir, file), "utf8");
9398
- } catch {
9399
- continue;
9400
- }
9401
- for (const line of raw.split("\n")) {
9402
- const trimmed = line.trim();
9403
- if (!trimmed) continue;
9404
- let rec;
10339
+ for (const source of daySources(auditDir)) {
10340
+ const before = matched.length;
10341
+ forEachLineFromTail(source.path, (line) => {
10342
+ let parsed;
9405
10343
  try {
9406
- rec = JSON.parse(trimmed);
10344
+ parsed = JSON.parse(line);
9407
10345
  } catch {
9408
- continue;
10346
+ return false;
9409
10347
  }
9410
- if (!isAuditRecord(rec)) continue;
9411
- if (query2.keyId !== void 0 && rec.keyId !== query2.keyId) continue;
9412
- if (rec.ts < from || rec.ts > to) continue;
9413
- matched.push(rec);
9414
- }
10348
+ if (!isAuditRecord(parsed)) return false;
10349
+ if (query2.keyId !== void 0 && parsed.keyId !== query2.keyId) return false;
10350
+ if (query2.sessionKey !== void 0 && parsed.sessionKey !== query2.sessionKey) return false;
10351
+ if (parsed.ts < from || parsed.ts > to) return false;
10352
+ matched.push(toMetaRecord(parsed));
10353
+ return matched.length - before >= limit + OVERSCAN;
10354
+ });
10355
+ if (matched.length >= limit) break;
9415
10356
  }
9416
10357
  matched.sort((a, b) => b.ts - a.ts);
9417
10358
  return matched.slice(0, limit);
9418
10359
  }
9419
- function isAuditRecord(value) {
9420
- if (!value || typeof value !== "object" || Array.isArray(value)) return false;
9421
- const r = value;
9422
- return typeof r["id"] === "string" && typeof r["ts"] === "number" && typeof r["method"] === "string" && typeof r["path"] === "string" && typeof r["status"] === "number";
9423
- }
9424
10360
 
9425
10361
  // src/audit/AuditWriter.ts
9426
- import { appendFileSync as appendFileSync2, existsSync as existsSync17, mkdirSync as mkdirSync5, statSync as statSync4 } from "fs";
9427
- import { join as join9 } from "path";
10362
+ import { appendFileSync as appendFileSync2, existsSync as existsSync19, mkdirSync as mkdirSync5, statSync as statSync6 } from "fs";
10363
+ import { join as join12 } from "path";
9428
10364
  var AuditWriter = class {
9429
10365
  constructor(auditDir, logger, defer = (fn) => setTimeout(fn, 0)) {
9430
10366
  this.auditDir = auditDir;
@@ -9434,10 +10370,13 @@ var AuditWriter = class {
9434
10370
  auditDir;
9435
10371
  logger;
9436
10372
  defer;
9437
- dirEnsured = false;
10373
+ /** Day directories already created this process (avoids an mkdir per record). */
10374
+ ensuredDirs = /* @__PURE__ */ new Set();
10375
+ /** Per-session encoding bases. Memory-only; a miss simply writes a full snapshot. */
10376
+ bases = new SessionBaseCache();
9438
10377
  /**
9439
- * Enqueue one record for append. Returns IMMEDIATELY (fire-and-forget); the fs
9440
- * write happens on the deferred tick. A failure is logged, never thrown.
10378
+ * Enqueue one record. Returns IMMEDIATELY (fire-and-forget); every fs write and
10379
+ * the delta encoding happen on the deferred tick. A failure is logged, never thrown.
9441
10380
  */
9442
10381
  record(record) {
9443
10382
  this.defer(() => {
@@ -9450,25 +10389,41 @@ var AuditWriter = class {
9450
10389
  }
9451
10390
  });
9452
10391
  }
10392
+ /** Drop all retained encoding bases (config reload / shutdown / test teardown). */
10393
+ reset() {
10394
+ this.bases.clear();
10395
+ this.ensuredDirs.clear();
10396
+ }
9453
10397
  /**
9454
- * Append synchronously — the awaitable form tests use to assert the line landed.
9455
- * Ensures the `audit/` directory exists on first write (lazy, like the usage
9456
- * store's lazy file creation).
10398
+ * Append synchronously — the awaitable form tests use to assert a line landed.
10399
+ * Writes the metadata line first (canonical), then the body shard.
9457
10400
  */
9458
10401
  appendNow(record) {
9459
- if (!this.dirEnsured) {
9460
- mkdirSync5(this.auditDir, { recursive: true });
9461
- this.dirEnsured = true;
9462
- }
9463
- const file = join9(this.auditDir, auditFileName(record.ts));
9464
- const line = JSON.stringify(record) + "\n";
9465
- const auditBytesBefore = existsSync17(file) ? statSync4(file).size : 0;
10402
+ const dayDir = auditDayDirName(record.ts);
10403
+ const dayPath = this.ensureDir(join12(this.auditDir, dayDir));
10404
+ this.appendMeta(dayPath, record);
10405
+ this.appendBody(dayPath, dayDir, record);
10406
+ }
10407
+ /** Create a directory once per process and remember it. */
10408
+ ensureDir(path2) {
10409
+ if (!this.ensuredDirs.has(path2)) {
10410
+ mkdirSync5(path2, { recursive: true });
10411
+ this.ensuredDirs.add(path2);
10412
+ }
10413
+ return path2;
10414
+ }
10415
+ /** Write the body-free metadata line + refresh the exact-count sidecar. */
10416
+ appendMeta(dayPath, record) {
10417
+ const { requestBody: _req, responseBody: _res, ...meta } = record;
10418
+ const file = join12(dayPath, AUDIT_META_FILE);
10419
+ const line = JSON.stringify(meta) + "\n";
10420
+ const bytesBefore = existsSync19(file) ? statSync6(file).size : 0;
9466
10421
  appendFileSync2(file, line, "utf8");
9467
10422
  try {
9468
10423
  updateAuditStatsAfterAppend(
9469
10424
  file,
9470
- auditBytesBefore,
9471
- auditBytesBefore + Buffer.byteLength(line, "utf8"),
10425
+ bytesBefore,
10426
+ bytesBefore + Buffer.byteLength(line, "utf8"),
9472
10427
  record
9473
10428
  );
9474
10429
  } catch (error) {
@@ -9477,12 +10432,39 @@ var AuditWriter = class {
9477
10432
  });
9478
10433
  }
9479
10434
  }
10435
+ /**
10436
+ * Write the delta-encoded body shard for one record. A no-op when nothing was
10437
+ * captured or when the session key is missing/unsafe — in which case the body
10438
+ * is dropped rather than written to an unvalidated path.
10439
+ */
10440
+ appendBody(dayPath, dayDir, record) {
10441
+ if (record.requestBody === void 0 && record.responseBody === void 0) return;
10442
+ const sessionKey = record.sessionKey;
10443
+ if (!isSafeSessionKey(sessionKey)) {
10444
+ this.logger.warn("[AuditWriter] dropping audit body with no usable session key", {
10445
+ id: record.id
10446
+ });
10447
+ return;
10448
+ }
10449
+ try {
10450
+ const line = encodeBodyEntry(record, sessionKey, dayDir, this.bases);
10451
+ if (line === null) return;
10452
+ const bodiesPath = this.ensureDir(join12(dayPath, AUDIT_BODIES_DIR));
10453
+ appendFileSync2(join12(bodiesPath, auditBodyFileName(sessionKey)), line + "\n", "utf8");
10454
+ } catch (error) {
10455
+ this.bases.forget(sessionKey);
10456
+ this.logger.warn("[AuditWriter] failed to append audit body shard", {
10457
+ id: record.id,
10458
+ error: error instanceof Error ? error.message : String(error)
10459
+ });
10460
+ }
10461
+ }
9480
10462
  };
9481
10463
 
9482
10464
  // src/billing/BillingPublisher.ts
9483
10465
  import { appendFileSync as appendFileSync3, mkdirSync as mkdirSync6 } from "fs";
9484
10466
  import { createHmac } from "crypto";
9485
- import { join as join10 } from "path";
10467
+ import { join as join13 } from "path";
9486
10468
  import { fetchUpstream as fetchUpstream5 } from "@omnicross/core/pipeline/upstreamFetch";
9487
10469
 
9488
10470
  // src/billing/billingFiles.ts
@@ -9553,7 +10535,7 @@ var BillingPublisher = class {
9553
10535
  */
9554
10536
  appendNow(event) {
9555
10537
  this.ensureDir();
9556
- const file = join10(this.billingDir, billingFileName(event.ts));
10538
+ const file = join13(this.billingDir, billingFileName(event.ts));
9557
10539
  appendFileSync3(file, JSON.stringify(event) + "\n", "utf8");
9558
10540
  }
9559
10541
  /**
@@ -9603,7 +10585,7 @@ var BillingPublisher = class {
9603
10585
  markDelivered(event) {
9604
10586
  try {
9605
10587
  this.ensureDir();
9606
- const file = join10(this.billingDir, deliveredFileName(event.ts));
10588
+ const file = join13(this.billingDir, deliveredFileName(event.ts));
9607
10589
  appendFileSync3(file, JSON.stringify({ id: event.id, deliveredAt: this.now() }) + "\n", "utf8");
9608
10590
  } catch (error) {
9609
10591
  this.logger.warn("[BillingPublisher] failed to append delivery marker", {
@@ -9619,14 +10601,14 @@ var BillingPublisher = class {
9619
10601
  };
9620
10602
 
9621
10603
  // src/billing/billingReader.ts
9622
- import { existsSync as existsSync18, readdirSync as readdirSync4, readFileSync as readFileSync17 } from "fs";
9623
- import { join as join11 } from "path";
10604
+ import { existsSync as existsSync20, readdirSync as readdirSync7, readFileSync as readFileSync18 } from "fs";
10605
+ import { join as join14 } from "path";
9624
10606
  function readBillingLedger(billingDir) {
9625
10607
  const view = { events: [], deliveredIds: /* @__PURE__ */ new Set() };
9626
- if (!existsSync18(billingDir)) return view;
10608
+ if (!existsSync20(billingDir)) return view;
9627
10609
  let files;
9628
10610
  try {
9629
- files = readdirSync4(billingDir);
10611
+ files = readdirSync7(billingDir);
9630
10612
  } catch {
9631
10613
  return view;
9632
10614
  }
@@ -9657,7 +10639,7 @@ function readBillingStatus(billingDir) {
9657
10639
  function parseLines(dir, file) {
9658
10640
  let raw;
9659
10641
  try {
9660
- raw = readFileSync17(join11(dir, file), "utf8");
10642
+ raw = readFileSync18(join14(dir, file), "utf8");
9661
10643
  } catch {
9662
10644
  return [];
9663
10645
  }
@@ -10161,8 +11143,10 @@ function buildDaemon(config, paths) {
10161
11143
  async (providerId, model) => await pricingEngine.getEntry(providerId, model) !== null
10162
11144
  );
10163
11145
  const keySpendTracker = new KeySpendTracker(usageEventStore);
11146
+ const usageThroughput = getSharedUsageThroughputTracker2();
10164
11147
  const usageRecorder = new UsageRecorder(usageEventStore, pricingEngine, logger, {
10165
- onRecord: (apiKeyId, costUsd, at) => keySpendTracker.add(apiKeyId, costUsd, at)
11148
+ onRecord: (apiKeyId, costUsd, at) => keySpendTracker.add(apiKeyId, costUsd, at),
11149
+ onEvent: (row, at) => usageThroughput.record(row, at)
10166
11150
  });
10167
11151
  const providerProxy = getProviderProxy({ llmConfig, apiKeyPool, usageRecorder });
10168
11152
  const routeLeaseManager = new RouteLeaseManager(
@@ -10311,6 +11295,11 @@ function buildDaemon(config, paths) {
10311
11295
  // NEVER unauth, NEVER on `/health`. Routed in `AdminServer` (not `adminApi.ts`).
10312
11296
  auditReader: (query2) => readAuditRecords(auditDir, query2),
10313
11297
  auditStatsReader: (query2) => readAuditStats(auditDir, query2),
11298
+ // audit-store-sharding: bodies live in per-session shards, so opening ONE
11299
+ // record's payload is a separate authed call that replays its delta chain.
11300
+ auditBodyReader: (query2) => readAuditBody(auditDir, query2),
11301
+ // audit-store-sharding D8: the manual counterpart to the daily pass.
11302
+ auditCompactor: () => compactAllClosedAuditDays(auditDir),
10314
11303
  // billing-event-stream: the AUTHED `GET /admin/api/billing-status` returns the
10315
11304
  // secret-free total/delivered/pending counts of the durable ledger.
10316
11305
  billingStatusReader: () => readBillingStatus(billingDir)
@@ -10369,7 +11358,7 @@ function buildDaemon(config, paths) {
10369
11358
  }
10370
11359
  function isTokensStoreReadable(tokensPath) {
10371
11360
  try {
10372
- if (!existsSync19(tokensPath)) return true;
11361
+ if (!existsSync21(tokensPath)) return true;
10373
11362
  accessSync(tokensPath, fsConstants.R_OK);
10374
11363
  return true;
10375
11364
  } catch {
@@ -10417,8 +11406,8 @@ function buildCliSpawnPlan(opts) {
10417
11406
  function resolveInPathDefault(candidate) {
10418
11407
  const segments = (process.env["PATH"] ?? "").split(delimiter2).filter(Boolean);
10419
11408
  for (const seg of segments) {
10420
- const full = join12(seg, candidate);
10421
- if (existsSync20(full)) return full;
11409
+ const full = join15(seg, candidate);
11410
+ if (existsSync22(full)) return full;
10422
11411
  }
10423
11412
  return null;
10424
11413
  }
@@ -10426,7 +11415,7 @@ async function runLaunch(argv, deps) {
10426
11415
  const sep = argv.indexOf("--");
10427
11416
  const own = sep === -1 ? argv : argv.slice(0, sep);
10428
11417
  const passthrough = sep === -1 ? [] : argv.slice(sep + 1);
10429
- const { values, positionals } = parseArgs4({
11418
+ const { values, positionals } = parseArgs5({
10430
11419
  args: own,
10431
11420
  options: {
10432
11421
  provider: { type: "string", short: "p" },
@@ -10596,12 +11585,12 @@ function spawnCliInherit(plan) {
10596
11585
  // src/commands/login.ts
10597
11586
  import { spawn as spawn3 } from "child_process";
10598
11587
  import { createInterface } from "readline";
10599
- import { parseArgs as parseArgs5 } from "util";
11588
+ import { parseArgs as parseArgs6 } from "util";
10600
11589
  import { fetchUpstream as fetchUpstream8, setUpstreamProxyResolver as setUpstreamProxyResolver2 } from "@omnicross/core/pipeline/upstreamFetch";
10601
11590
  import { claudeOAuth as claudeOAuth3, codexOAuth as codexOAuth3, geminiOAuth as geminiOAuth3 } from "@omnicross/subscriptions";
10602
11591
  var PROVIDERS2 = ["claude", "codex", "gemini"];
10603
11592
  async function runLogin(argv, deps) {
10604
- const { values, positionals } = parseArgs5({
11593
+ const { values, positionals } = parseArgs6({
10605
11594
  args: argv,
10606
11595
  options: {
10607
11596
  config: { type: "string", short: "c" },
@@ -10769,9 +11758,9 @@ function promptPaste(prompt) {
10769
11758
 
10770
11759
  // src/commands/providers.ts
10771
11760
  import { randomUUID as randomUUID7 } from "crypto";
10772
- import { parseArgs as parseArgs6 } from "util";
11761
+ import { parseArgs as parseArgs7 } from "util";
10773
11762
  async function runProviders(argv) {
10774
- const { values, positionals } = parseArgs6({
11763
+ const { values, positionals } = parseArgs7({
10775
11764
  args: argv,
10776
11765
  options: {
10777
11766
  config: { type: "string", short: "c" },
@@ -10918,10 +11907,10 @@ function providersRmKey(configPath, providerId, keyId) {
10918
11907
  }
10919
11908
 
10920
11909
  // src/commands/secrets.ts
10921
- import { existsSync as existsSync21, readFileSync as readFileSync18, writeFileSync as writeFileSync13 } from "fs";
10922
- import { parseArgs as parseArgs7 } from "util";
11910
+ import { existsSync as existsSync23, readFileSync as readFileSync19, writeFileSync as writeFileSync14 } from "fs";
11911
+ import { parseArgs as parseArgs8 } from "util";
10923
11912
  async function runSecrets(argv) {
10924
- const { values, positionals } = parseArgs7({
11913
+ const { values, positionals } = parseArgs8({
10925
11914
  args: argv,
10926
11915
  options: {
10927
11916
  config: { type: "string", short: "c" },
@@ -10991,12 +11980,12 @@ function secretsStatus(args) {
10991
11980
  reportField("admin.token", cfg.admin.token);
10992
11981
  }
10993
11982
  const tokensPath = defaultTokensPath(args.config);
10994
- if (existsSync21(tokensPath)) {
11983
+ if (existsSync23(tokensPath)) {
10995
11984
  console.info(`Secret status for ${tokensPath}:`);
10996
11985
  reportTokenFields(tokensPath);
10997
11986
  }
10998
11987
  const integrationsPath = defaultIntegrationsPath(args.config);
10999
- if (existsSync21(integrationsPath)) {
11988
+ if (existsSync23(integrationsPath)) {
11000
11989
  const state = readRawJson(integrationsPath);
11001
11990
  const key = state.gatewayKey;
11002
11991
  if (key && typeof key === "object" && !Array.isArray(key)) {
@@ -11050,8 +12039,8 @@ async function secretsRotate(args) {
11050
12039
  const integrationsPath = defaultIntegrationsPath(args.config);
11051
12040
  try {
11052
12041
  cfg = loadConfig(args.config);
11053
- if (existsSync21(tokensPath)) tokensPlain = decryptTokensFile(tokensPath, oldBox);
11054
- if (existsSync21(integrationsPath)) {
12042
+ if (existsSync23(tokensPath)) tokensPlain = decryptTokensFile(tokensPath, oldBox);
12043
+ if (existsSync23(integrationsPath)) {
11055
12044
  integrationsPlain = new IntegrationStateStore(integrationsPath, oldBox).load();
11056
12045
  }
11057
12046
  } finally {
@@ -11086,20 +12075,20 @@ function secretsDecrypt(args) {
11086
12075
  let tokensPlain = null;
11087
12076
  try {
11088
12077
  cfg = loadConfig(args.config);
11089
- if (existsSync21(tokensPath)) tokensPlain = decryptTokensFile(tokensPath, box);
12078
+ if (existsSync23(tokensPath)) tokensPlain = decryptTokensFile(tokensPath, box);
11090
12079
  } finally {
11091
12080
  setSecretBox(null);
11092
12081
  }
11093
12082
  saveConfig(args.config, cfg);
11094
12083
  if (tokensPlain) {
11095
- writeFileSync13(tokensPath, JSON.stringify(tokensPlain, null, 2) + "\n", "utf8");
12084
+ writeFileSync14(tokensPath, JSON.stringify(tokensPlain, null, 2) + "\n", "utf8");
11096
12085
  }
11097
12086
  console.info(`Decrypted secrets to plaintext in ${args.config}` + tokensSuffix(args.config));
11098
12087
  }
11099
12088
  function readRawConfig(path2) {
11100
12089
  let parsed;
11101
12090
  try {
11102
- parsed = JSON.parse(readFileSync18(path2, "utf8"));
12091
+ parsed = JSON.parse(readFileSync19(path2, "utf8"));
11103
12092
  } catch {
11104
12093
  throw new Error(`secrets: cannot read or parse '${path2}'`);
11105
12094
  }
@@ -11107,7 +12096,7 @@ function readRawConfig(path2) {
11107
12096
  }
11108
12097
  function readRawJson(path2) {
11109
12098
  try {
11110
- const parsed = JSON.parse(readFileSync18(path2, "utf8"));
12099
+ const parsed = JSON.parse(readFileSync19(path2, "utf8"));
11111
12100
  if (parsed && typeof parsed === "object" && !Array.isArray(parsed)) {
11112
12101
  return parsed;
11113
12102
  }
@@ -11117,13 +12106,13 @@ function readRawJson(path2) {
11117
12106
  }
11118
12107
  function encryptTokensFileInPlace(configPath, box) {
11119
12108
  const tokensPath = defaultTokensPath(configPath);
11120
- if (!existsSync21(tokensPath)) return;
12109
+ if (!existsSync23(tokensPath)) return;
11121
12110
  const plain = decryptTokensFile(tokensPath, box);
11122
12111
  writeTokensEncrypted(tokensPath, plain, box);
11123
12112
  }
11124
12113
  function rewriteIntegrationState(configPath, readBox, writeBox) {
11125
12114
  const path2 = defaultIntegrationsPath(configPath);
11126
- if (!existsSync21(path2)) return;
12115
+ if (!existsSync23(path2)) return;
11127
12116
  const state = new IntegrationStateStore(path2, readBox).load();
11128
12117
  new IntegrationStateStore(path2, writeBox).save(state);
11129
12118
  }
@@ -11136,7 +12125,7 @@ function writeTokensEncrypted(tokensPath, plain, box) {
11136
12125
  { updatedAt: "", ...plain },
11137
12126
  box
11138
12127
  );
11139
- writeFileSync13(tokensPath, JSON.stringify(encrypted, null, 2) + "\n", "utf8");
12128
+ writeFileSync14(tokensPath, JSON.stringify(encrypted, null, 2) + "\n", "utf8");
11140
12129
  }
11141
12130
  var TOKEN_FIELDS2 = {
11142
12131
  claude: ["accessToken", "refreshToken"],
@@ -11159,11 +12148,11 @@ function walkTokens(raw, fn) {
11159
12148
  return next;
11160
12149
  }
11161
12150
  function tokensSuffix(configPath) {
11162
- return existsSync21(defaultTokensPath(configPath)) ? " (+ tokens.json)" : "";
12151
+ return existsSync23(defaultTokensPath(configPath)) ? " (+ tokens.json)" : "";
11163
12152
  }
11164
12153
 
11165
12154
  // src/commands/start.ts
11166
- import { parseArgs as parseArgs8 } from "util";
12155
+ import { parseArgs as parseArgs9 } from "util";
11167
12156
  import { loadServerConfig as loadServerConfig3 } from "@omnicross/core/outbound-api";
11168
12157
  import { getSharedAccountHealth as getSharedAccountHealth5 } from "@omnicross/core/pipeline/SubscriptionAccountHealth";
11169
12158
  import { getSharedAccountAllowanceScheduling as getSharedAccountAllowanceScheduling6 } from "@omnicross/core/pipeline/AccountAllowanceScheduling";
@@ -11202,7 +12191,7 @@ async function seedIdentities(store, credentialStore) {
11202
12191
 
11203
12192
  // src/commands/start.ts
11204
12193
  async function runStart(argv) {
11205
- const { values } = parseArgs8({
12194
+ const { values } = parseArgs9({
11206
12195
  args: argv,
11207
12196
  options: {
11208
12197
  config: { type: "string", short: "c" },
@@ -11342,6 +12331,10 @@ Usage:
11342
12331
  omnicross secrets encrypt --config <p> Encrypt all at-rest secrets in place.
11343
12332
  omnicross secrets status --config <p> Report each secret field (no values shown).
11344
12333
  omnicross secrets rotate --config <p> --new-master-key-file <p> Re-seal under a new master key.
12334
+
12335
+ omnicross audit sessions --config <p> [--date YYYY-MM-DD] List captured body shards per session.
12336
+ omnicross audit show --config <p> --session <key> [--id <recordId>] Print reconstructed request/response bodies.
12337
+ omnicross audit compact --config <p> [--date YYYY-MM-DD] Run cross-session body compaction now.
11345
12338
  `;
11346
12339
  async function main() {
11347
12340
  const [, , subcommand, ...rest] = process.argv;
@@ -11373,6 +12366,9 @@ async function main() {
11373
12366
  case "secrets":
11374
12367
  await runSecrets(rest);
11375
12368
  return;
12369
+ case "audit":
12370
+ await runAudit(rest);
12371
+ return;
11376
12372
  case void 0:
11377
12373
  case "-h":
11378
12374
  case "--help":