@getrift/rift 0.1.0-beta.1 → 0.1.0-beta.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/README.md +154 -0
- package/dist/src/auth/keychain.d.ts +9 -0
- package/dist/src/auth/keychain.d.ts.map +1 -1
- package/dist/src/auth/keychain.js +37 -0
- package/dist/src/auth/keychain.js.map +1 -1
- package/dist/src/capture/recover-quarantine.d.ts +221 -0
- package/dist/src/capture/recover-quarantine.d.ts.map +1 -0
- package/dist/src/capture/recover-quarantine.js +453 -0
- package/dist/src/capture/recover-quarantine.js.map +1 -0
- package/dist/src/cli/commands/backfill.d.ts.map +1 -1
- package/dist/src/cli/commands/backfill.js +5 -2
- package/dist/src/cli/commands/backfill.js.map +1 -1
- package/dist/src/cli/commands/capture-recover.d.ts +12 -0
- package/dist/src/cli/commands/capture-recover.d.ts.map +1 -0
- package/dist/src/cli/commands/capture-recover.js +120 -0
- package/dist/src/cli/commands/capture-recover.js.map +1 -0
- package/dist/src/cli/commands/capture.d.ts.map +1 -1
- package/dist/src/cli/commands/capture.js +10 -4
- package/dist/src/cli/commands/capture.js.map +1 -1
- package/dist/src/cli/commands/feedback.d.ts.map +1 -1
- package/dist/src/cli/commands/feedback.js +6 -2
- package/dist/src/cli/commands/feedback.js.map +1 -1
- package/dist/src/cli/commands/mcp-install.js +5 -2
- package/dist/src/cli/commands/mcp-install.js.map +1 -1
- package/dist/src/cli/commands/onboard.d.ts +24 -0
- package/dist/src/cli/commands/onboard.d.ts.map +1 -1
- package/dist/src/cli/commands/onboard.js +119 -21
- package/dist/src/cli/commands/onboard.js.map +1 -1
- package/dist/src/cli/commands/rebuild.d.ts.map +1 -1
- package/dist/src/cli/commands/rebuild.js +6 -3
- package/dist/src/cli/commands/rebuild.js.map +1 -1
- package/dist/src/cli/commands/review.d.ts.map +1 -1
- package/dist/src/cli/commands/review.js +22 -7
- package/dist/src/cli/commands/review.js.map +1 -1
- package/dist/src/cli/commands/status.d.ts.map +1 -1
- package/dist/src/cli/commands/status.js +48 -2
- package/dist/src/cli/commands/status.js.map +1 -1
- package/dist/src/cli/commands/token-issue.d.ts.map +1 -1
- package/dist/src/cli/commands/token-issue.js +9 -1
- package/dist/src/cli/commands/token-issue.js.map +1 -1
- package/dist/src/cli/commands/triage.d.ts.map +1 -1
- package/dist/src/cli/commands/triage.js +7 -5
- package/dist/src/cli/commands/triage.js.map +1 -1
- package/dist/src/cli/commands/update.d.ts +26 -0
- package/dist/src/cli/commands/update.d.ts.map +1 -0
- package/dist/src/cli/commands/update.js +130 -0
- package/dist/src/cli/commands/update.js.map +1 -0
- package/dist/src/cli/default-config-path.d.ts +15 -0
- package/dist/src/cli/default-config-path.d.ts.map +1 -0
- package/dist/src/cli/default-config-path.js +27 -0
- package/dist/src/cli/default-config-path.js.map +1 -0
- package/dist/src/cli/http-client.d.ts +56 -1
- package/dist/src/cli/http-client.d.ts.map +1 -1
- package/dist/src/cli/http-client.js +140 -4
- package/dist/src/cli/http-client.js.map +1 -1
- package/dist/src/cli/index.d.ts.map +1 -1
- package/dist/src/cli/index.js +25 -6
- package/dist/src/cli/index.js.map +1 -1
- package/dist/src/cli/status/friend-header.d.ts.map +1 -1
- package/dist/src/cli/status/friend-header.js +117 -7
- package/dist/src/cli/status/friend-header.js.map +1 -1
- package/dist/src/ingestion/inbox-core/conversation-key.d.ts +2 -0
- package/dist/src/ingestion/inbox-core/conversation-key.d.ts.map +1 -0
- package/dist/src/ingestion/inbox-core/conversation-key.js +31 -0
- package/dist/src/ingestion/inbox-core/conversation-key.js.map +1 -0
- package/dist/src/ingestion/inbox-core/extensions.d.ts +3 -0
- package/dist/src/ingestion/inbox-core/extensions.d.ts.map +1 -0
- package/dist/src/ingestion/inbox-core/extensions.js +16 -0
- package/dist/src/ingestion/inbox-core/extensions.js.map +1 -0
- package/dist/src/ingestion/inbox-core/idempotency.d.ts +2 -0
- package/dist/src/ingestion/inbox-core/idempotency.d.ts.map +1 -0
- package/dist/src/ingestion/inbox-core/idempotency.js +22 -0
- package/dist/src/ingestion/inbox-core/idempotency.js.map +1 -0
- package/dist/src/ingestion/inbox-core/index.d.ts +19 -0
- package/dist/src/ingestion/inbox-core/index.d.ts.map +1 -0
- package/dist/src/ingestion/inbox-core/index.js +19 -0
- package/dist/src/ingestion/inbox-core/index.js.map +1 -0
- package/dist/src/ingestion/inbox-core/source-detection.d.ts +2 -0
- package/dist/src/ingestion/inbox-core/source-detection.d.ts.map +1 -0
- package/dist/src/ingestion/inbox-core/source-detection.js +23 -0
- package/dist/src/ingestion/inbox-core/source-detection.js.map +1 -0
- package/dist/src/ingestion/inbox-core/source-sniffer.d.ts +11 -0
- package/dist/src/ingestion/inbox-core/source-sniffer.d.ts.map +1 -0
- package/dist/src/ingestion/inbox-core/source-sniffer.js +69 -0
- package/dist/src/ingestion/inbox-core/source-sniffer.js.map +1 -0
- package/dist/src/ingestion/inbox-core/zip-sniffer.d.ts +70 -0
- package/dist/src/ingestion/inbox-core/zip-sniffer.d.ts.map +1 -0
- package/dist/src/ingestion/inbox-core/zip-sniffer.js +161 -0
- package/dist/src/ingestion/inbox-core/zip-sniffer.js.map +1 -0
- package/dist/src/ingestion/inbox-watcher.d.ts.map +1 -1
- package/dist/src/ingestion/inbox-watcher.js +34 -50
- package/dist/src/ingestion/inbox-watcher.js.map +1 -1
- package/dist/src/ingestion/indexer.d.ts +7 -0
- package/dist/src/ingestion/indexer.d.ts.map +1 -1
- package/dist/src/ingestion/indexer.js +36 -2
- package/dist/src/ingestion/indexer.js.map +1 -1
- package/dist/src/ingestion/metadata-extraction.d.ts +8 -5
- package/dist/src/ingestion/metadata-extraction.d.ts.map +1 -1
- package/dist/src/ingestion/metadata-extraction.js +24 -5
- package/dist/src/ingestion/metadata-extraction.js.map +1 -1
- package/dist/src/ingestion/skip-quarantine.d.ts +10 -0
- package/dist/src/ingestion/skip-quarantine.d.ts.map +1 -0
- package/dist/src/ingestion/skip-quarantine.js +35 -0
- package/dist/src/ingestion/skip-quarantine.js.map +1 -0
- package/dist/src/jobs/handlers/compact.d.ts.map +1 -1
- package/dist/src/jobs/handlers/compact.js +25 -4
- package/dist/src/jobs/handlers/compact.js.map +1 -1
- package/dist/src/jobs/handlers/ingest.d.ts.map +1 -1
- package/dist/src/jobs/handlers/ingest.js +49 -24
- package/dist/src/jobs/handlers/ingest.js.map +1 -1
- package/dist/src/jobs/handlers/reconcile.d.ts.map +1 -1
- package/dist/src/jobs/handlers/reconcile.js +30 -8
- package/dist/src/jobs/handlers/reconcile.js.map +1 -1
- package/dist/src/jobs/handlers/reindex.d.ts.map +1 -1
- package/dist/src/jobs/handlers/reindex.js +12 -2
- package/dist/src/jobs/handlers/reindex.js.map +1 -1
- package/dist/src/jobs/handlers/save.d.ts.map +1 -1
- package/dist/src/jobs/handlers/save.js +9 -2
- package/dist/src/jobs/handlers/save.js.map +1 -1
- package/dist/src/jobs/queue.d.ts +11 -0
- package/dist/src/jobs/queue.d.ts.map +1 -1
- package/dist/src/jobs/queue.js +18 -0
- package/dist/src/jobs/queue.js.map +1 -1
- package/dist/src/jobs/worker-entry.d.ts.map +1 -1
- package/dist/src/jobs/worker-entry.js +2 -0
- package/dist/src/jobs/worker-entry.js.map +1 -1
- package/dist/src/main.js +36 -4
- package/dist/src/main.js.map +1 -1
- package/dist/src/observability/embedding-events.d.ts +52 -0
- package/dist/src/observability/embedding-events.d.ts.map +1 -0
- package/dist/src/observability/embedding-events.js +149 -0
- package/dist/src/observability/embedding-events.js.map +1 -0
- package/dist/src/observability/index-events.d.ts +70 -0
- package/dist/src/observability/index-events.d.ts.map +1 -0
- package/dist/src/observability/index-events.js +148 -0
- package/dist/src/observability/index-events.js.map +1 -0
- package/dist/src/observability/tool-usage-stats.d.ts +7 -0
- package/dist/src/observability/tool-usage-stats.d.ts.map +1 -1
- package/dist/src/observability/tool-usage-stats.js +41 -5
- package/dist/src/observability/tool-usage-stats.js.map +1 -1
- package/dist/src/observability/tool-usage.d.ts +7 -7
- package/dist/src/observability/tool-usage.d.ts.map +1 -1
- package/dist/src/observability/tool-usage.js +78 -39
- package/dist/src/observability/tool-usage.js.map +1 -1
- package/dist/src/observability/version-check.d.ts +70 -0
- package/dist/src/observability/version-check.d.ts.map +1 -0
- package/dist/src/observability/version-check.js +197 -0
- package/dist/src/observability/version-check.js.map +1 -0
- package/dist/src/providers/ollama-embed.d.ts +2 -1
- package/dist/src/providers/ollama-embed.d.ts.map +1 -1
- package/dist/src/providers/ollama-embed.js +1 -0
- package/dist/src/providers/ollama-embed.js.map +1 -1
- package/dist/src/providers/openai-metadata-extraction.d.ts +3 -3
- package/dist/src/providers/openai-metadata-extraction.d.ts.map +1 -1
- package/dist/src/providers/openai-metadata-extraction.js +18 -3
- package/dist/src/providers/openai-metadata-extraction.js.map +1 -1
- package/dist/src/providers/stub.d.ts +2 -0
- package/dist/src/providers/stub.d.ts.map +1 -1
- package/dist/src/providers/stub.js +2 -0
- package/dist/src/providers/stub.js.map +1 -1
- package/dist/src/providers/types.d.ts +11 -0
- package/dist/src/providers/types.d.ts.map +1 -1
- package/dist/src/providers/voyage.d.ts +2 -1
- package/dist/src/providers/voyage.d.ts.map +1 -1
- package/dist/src/providers/voyage.js +1 -0
- package/dist/src/providers/voyage.js.map +1 -1
- package/dist/src/server/app.d.ts.map +1 -1
- package/dist/src/server/app.js +67 -1
- package/dist/src/server/app.js.map +1 -1
- package/dist/src/server/routes/friend-status.d.ts +202 -3
- package/dist/src/server/routes/friend-status.d.ts.map +1 -1
- package/dist/src/server/routes/friend-status.js +290 -7
- package/dist/src/server/routes/friend-status.js.map +1 -1
- package/dist/src/storage/rebuild.d.ts +14 -1
- package/dist/src/storage/rebuild.d.ts.map +1 -1
- package/dist/src/storage/rebuild.js +160 -34
- package/dist/src/storage/rebuild.js.map +1 -1
- package/package.json +1 -1
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
import type { EmbeddingPipeline } from "./embedding-events.js";
|
|
2
|
+
export type IndexOutcome = "success" | "error";
|
|
3
|
+
export interface IndexEvent {
|
|
4
|
+
ts: string;
|
|
5
|
+
/**
|
|
6
|
+
* Target LanceDB table. Free-form string (not `TableName`) so shadow
|
|
7
|
+
* writes can record their target without coupling to the live table
|
|
8
|
+
* name set.
|
|
9
|
+
*/
|
|
10
|
+
table: string;
|
|
11
|
+
pipeline: EmbeddingPipeline;
|
|
12
|
+
/**
|
|
13
|
+
* Free-form caller label (e.g. "structured_doc_upsert",
|
|
14
|
+
* "conversation_upsert", "digest_upsert"). Helps debug "which write
|
|
15
|
+
* path"; does not gate any status logic today.
|
|
16
|
+
*/
|
|
17
|
+
operation: string;
|
|
18
|
+
outcome: IndexOutcome;
|
|
19
|
+
/** Number of rows in this `table.add(...)` call (or rollback batch). */
|
|
20
|
+
row_count: number;
|
|
21
|
+
ms: number;
|
|
22
|
+
/**
|
|
23
|
+
* Lifecycle phase.
|
|
24
|
+
* - "live" (default when omitted) — the row is now searchable.
|
|
25
|
+
* Direct writes are always "live"; shadow rebuilds emit a single
|
|
26
|
+
* "live" event per table after `commitAllSwaps` succeeds.
|
|
27
|
+
* - "shadow" — the row was written to a pre-commit shadow table. If
|
|
28
|
+
* the subsequent swap fails the row is NOT searchable, so
|
|
29
|
+
* `computeIndexHealth` does NOT credit `last_update_at` from
|
|
30
|
+
* shadow successes. Shadow errors still surface as `last_error_at`
|
|
31
|
+
* because they represent real LanceDB write failures regardless of
|
|
32
|
+
* the eventual swap outcome.
|
|
33
|
+
*/
|
|
34
|
+
phase?: "live" | "shadow";
|
|
35
|
+
/** Compact error class. Present when outcome === "error". */
|
|
36
|
+
error_class?: string;
|
|
37
|
+
/** Truncated error message (≤ 512 chars). Present when outcome === "error". */
|
|
38
|
+
error_message?: string;
|
|
39
|
+
}
|
|
40
|
+
export interface IndexWriteContext {
|
|
41
|
+
table: string;
|
|
42
|
+
pipeline: EmbeddingPipeline;
|
|
43
|
+
operation: string;
|
|
44
|
+
row_count: number;
|
|
45
|
+
/** Defaults to "live". Set "shadow" for pre-commit shadow-table writes. */
|
|
46
|
+
phase?: "live" | "shadow";
|
|
47
|
+
}
|
|
48
|
+
export declare function indexEventsFilePath(dataDir: string): string;
|
|
49
|
+
/**
|
|
50
|
+
* Append a single event to the lane. Never throws — telemetry must not
|
|
51
|
+
* break indexing. On filesystem error, writes a single stderr line so
|
|
52
|
+
* the failure is at least visible to operators tailing logs.
|
|
53
|
+
*/
|
|
54
|
+
export declare function appendIndexEvent(dataDir: string, event: IndexEvent): void;
|
|
55
|
+
/**
|
|
56
|
+
* Run a LanceDB write and record one event. Re-throws errors so the
|
|
57
|
+
* caller's existing failure-handling path is unchanged; logging is a
|
|
58
|
+
* pure side effect.
|
|
59
|
+
*
|
|
60
|
+
* Use this only at write boundaries (`table.add(...)`). Do NOT use it
|
|
61
|
+
* for reads, queries, or deletes — keeping the lane write-only is what
|
|
62
|
+
* makes `last_update_at` meaningful.
|
|
63
|
+
*/
|
|
64
|
+
export declare function recordIndexWrite<T>(dataDir: string, ctx: IndexWriteContext, fn: () => Promise<T>): Promise<T>;
|
|
65
|
+
/**
|
|
66
|
+
* Tolerant reader. One bad JSON line is skipped; the rest are returned.
|
|
67
|
+
* Returns [] if the file is missing.
|
|
68
|
+
*/
|
|
69
|
+
export declare function readIndexEvents(dataDir: string): IndexEvent[];
|
|
70
|
+
//# sourceMappingURL=index-events.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index-events.d.ts","sourceRoot":"","sources":["../../../src/observability/index-events.ts"],"names":[],"mappings":"AAmBA,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,uBAAuB,CAAC;AAE/D,MAAM,MAAM,YAAY,GAAG,SAAS,GAAG,OAAO,CAAC;AAE/C,MAAM,WAAW,UAAU;IACzB,EAAE,EAAE,MAAM,CAAC;IACX;;;;OAIG;IACH,KAAK,EAAE,MAAM,CAAC;IACd,QAAQ,EAAE,iBAAiB,CAAC;IAC5B;;;;OAIG;IACH,SAAS,EAAE,MAAM,CAAC;IAClB,OAAO,EAAE,YAAY,CAAC;IACtB,wEAAwE;IACxE,SAAS,EAAE,MAAM,CAAC;IAClB,EAAE,EAAE,MAAM,CAAC;IACX;;;;;;;;;;;OAWG;IACH,KAAK,CAAC,EAAE,MAAM,GAAG,QAAQ,CAAC;IAC1B,6DAA6D;IAC7D,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,+EAA+E;IAC/E,aAAa,CAAC,EAAE,MAAM,CAAC;CACxB;AAID,MAAM,WAAW,iBAAiB;IAChC,KAAK,EAAE,MAAM,CAAC;IACd,QAAQ,EAAE,iBAAiB,CAAC;IAC5B,SAAS,EAAE,MAAM,CAAC;IAClB,SAAS,EAAE,MAAM,CAAC;IAClB,2EAA2E;IAC3E,KAAK,CAAC,EAAE,MAAM,GAAG,QAAQ,CAAC;CAC3B;AAED,wBAAgB,mBAAmB,CAAC,OAAO,EAAE,MAAM,GAAG,MAAM,CAE3D;AAED;;;;GAIG;AACH,wBAAgB,gBAAgB,CAC9B,OAAO,EAAE,MAAM,EACf,KAAK,EAAE,UAAU,GAChB,IAAI,CAUN;AAED;;;;;;;;GAQG;AACH,wBAAsB,gBAAgB,CAAC,CAAC,EACtC,OAAO,EAAE,MAAM,EACf,GAAG,EAAE,iBAAiB,EACtB,EAAE,EAAE,MAAM,OAAO,CAAC,CAAC,CAAC,GACnB,OAAO,CAAC,CAAC,CAAC,CAgCZ;AAmBD;;;GAGG;AACH,wBAAgB,eAAe,CAAC,OAAO,EAAE,MAAM,GAAG,UAAU,EAAE,CAoB7D"}
|
|
@@ -0,0 +1,148 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Index-events lane — append-only JSONL.
|
|
3
|
+
*
|
|
4
|
+
* One row per write boundary against LanceDB (`table.add(...)`). This
|
|
5
|
+
* complements `embedding-events.jsonl`: the embedding lane proves the
|
|
6
|
+
* vector was produced, this lane proves the row was actually persisted
|
|
7
|
+
* to LanceDB and is searchable. Without it, `/status/friend` cannot
|
|
8
|
+
* distinguish "embedded but not indexed yet" from "fully searchable".
|
|
9
|
+
*
|
|
10
|
+
* Provider-agnostic and table-agnostic: `table` and `pipeline` are
|
|
11
|
+
* payload fields. Reads / search queries are deliberately NOT wrapped —
|
|
12
|
+
* they're not write events and would muddy `index.last_update_at`.
|
|
13
|
+
*
|
|
14
|
+
* Failure mode: writes are best-effort and never throw — observability
|
|
15
|
+
* must not break indexing. The reader is tolerant of bad lines so one
|
|
16
|
+
* corrupt row doesn't blank the status dashboard.
|
|
17
|
+
*/
|
|
18
|
+
import fs from "node:fs";
|
|
19
|
+
import path from "node:path";
|
|
20
|
+
const MAX_ERROR_MESSAGE_LEN = 512;
|
|
21
|
+
export function indexEventsFilePath(dataDir) {
|
|
22
|
+
return path.join(dataDir, "observability", "index-events.jsonl");
|
|
23
|
+
}
|
|
24
|
+
/**
|
|
25
|
+
* Append a single event to the lane. Never throws — telemetry must not
|
|
26
|
+
* break indexing. On filesystem error, writes a single stderr line so
|
|
27
|
+
* the failure is at least visible to operators tailing logs.
|
|
28
|
+
*/
|
|
29
|
+
export function appendIndexEvent(dataDir, event) {
|
|
30
|
+
const filePath = indexEventsFilePath(dataDir);
|
|
31
|
+
try {
|
|
32
|
+
fs.mkdirSync(path.dirname(filePath), { recursive: true });
|
|
33
|
+
fs.appendFileSync(filePath, JSON.stringify(event) + "\n");
|
|
34
|
+
}
|
|
35
|
+
catch (err) {
|
|
36
|
+
process.stderr.write(`[index-events] write failed: ${err instanceof Error ? err.message : String(err)}\n`);
|
|
37
|
+
}
|
|
38
|
+
}
|
|
39
|
+
/**
|
|
40
|
+
* Run a LanceDB write and record one event. Re-throws errors so the
|
|
41
|
+
* caller's existing failure-handling path is unchanged; logging is a
|
|
42
|
+
* pure side effect.
|
|
43
|
+
*
|
|
44
|
+
* Use this only at write boundaries (`table.add(...)`). Do NOT use it
|
|
45
|
+
* for reads, queries, or deletes — keeping the lane write-only is what
|
|
46
|
+
* makes `last_update_at` meaningful.
|
|
47
|
+
*/
|
|
48
|
+
export async function recordIndexWrite(dataDir, ctx, fn) {
|
|
49
|
+
const start = Date.now();
|
|
50
|
+
const phase = ctx.phase ?? "live";
|
|
51
|
+
try {
|
|
52
|
+
const result = await fn();
|
|
53
|
+
appendIndexEvent(dataDir, {
|
|
54
|
+
ts: new Date().toISOString(),
|
|
55
|
+
table: ctx.table,
|
|
56
|
+
pipeline: ctx.pipeline,
|
|
57
|
+
operation: ctx.operation,
|
|
58
|
+
outcome: "success",
|
|
59
|
+
row_count: ctx.row_count,
|
|
60
|
+
ms: Date.now() - start,
|
|
61
|
+
phase,
|
|
62
|
+
});
|
|
63
|
+
return result;
|
|
64
|
+
}
|
|
65
|
+
catch (err) {
|
|
66
|
+
const message = err instanceof Error ? err.message : String(err);
|
|
67
|
+
appendIndexEvent(dataDir, {
|
|
68
|
+
ts: new Date().toISOString(),
|
|
69
|
+
table: ctx.table,
|
|
70
|
+
pipeline: ctx.pipeline,
|
|
71
|
+
operation: ctx.operation,
|
|
72
|
+
outcome: "error",
|
|
73
|
+
row_count: ctx.row_count,
|
|
74
|
+
ms: Date.now() - start,
|
|
75
|
+
phase,
|
|
76
|
+
error_class: classifyError(err),
|
|
77
|
+
error_message: message.slice(0, MAX_ERROR_MESSAGE_LEN),
|
|
78
|
+
});
|
|
79
|
+
throw err;
|
|
80
|
+
}
|
|
81
|
+
}
|
|
82
|
+
/**
|
|
83
|
+
* Best-effort classification for the `error_class` field. LanceDB
|
|
84
|
+
* surfaces schema mismatches, IO errors, and lock contention with
|
|
85
|
+
* different shapes — pick a coarse class so dashboards can group.
|
|
86
|
+
*/
|
|
87
|
+
function classifyError(err) {
|
|
88
|
+
const msg = err instanceof Error ? err.message : String(err);
|
|
89
|
+
const lower = msg.toLowerCase();
|
|
90
|
+
if (lower.includes("schema"))
|
|
91
|
+
return "schema_mismatch";
|
|
92
|
+
if (lower.includes("lock") || lower.includes("conflict"))
|
|
93
|
+
return "lock_conflict";
|
|
94
|
+
if (lower.includes("enoent") || lower.includes("eacces") || lower.includes("eio")) {
|
|
95
|
+
return "io";
|
|
96
|
+
}
|
|
97
|
+
if (err instanceof TypeError)
|
|
98
|
+
return "type";
|
|
99
|
+
return "unknown";
|
|
100
|
+
}
|
|
101
|
+
/**
|
|
102
|
+
* Tolerant reader. One bad JSON line is skipped; the rest are returned.
|
|
103
|
+
* Returns [] if the file is missing.
|
|
104
|
+
*/
|
|
105
|
+
export function readIndexEvents(dataDir) {
|
|
106
|
+
let raw;
|
|
107
|
+
try {
|
|
108
|
+
raw = fs.readFileSync(indexEventsFilePath(dataDir), "utf-8");
|
|
109
|
+
}
|
|
110
|
+
catch {
|
|
111
|
+
return [];
|
|
112
|
+
}
|
|
113
|
+
const out = [];
|
|
114
|
+
for (const line of raw.split("\n")) {
|
|
115
|
+
if (!line)
|
|
116
|
+
continue;
|
|
117
|
+
let parsed;
|
|
118
|
+
try {
|
|
119
|
+
parsed = JSON.parse(line);
|
|
120
|
+
}
|
|
121
|
+
catch {
|
|
122
|
+
continue;
|
|
123
|
+
}
|
|
124
|
+
if (!isIndexEvent(parsed))
|
|
125
|
+
continue;
|
|
126
|
+
out.push(parsed);
|
|
127
|
+
}
|
|
128
|
+
return out;
|
|
129
|
+
}
|
|
130
|
+
function isIndexEvent(value) {
|
|
131
|
+
if (value === null || typeof value !== "object")
|
|
132
|
+
return false;
|
|
133
|
+
const v = value;
|
|
134
|
+
if (!(typeof v["ts"] === "string" &&
|
|
135
|
+
typeof v["table"] === "string" &&
|
|
136
|
+
typeof v["pipeline"] === "string" &&
|
|
137
|
+
typeof v["operation"] === "string" &&
|
|
138
|
+
(v["outcome"] === "success" || v["outcome"] === "error") &&
|
|
139
|
+
typeof v["row_count"] === "number" &&
|
|
140
|
+
typeof v["ms"] === "number")) {
|
|
141
|
+
return false;
|
|
142
|
+
}
|
|
143
|
+
const phase = v["phase"];
|
|
144
|
+
if (phase !== undefined && phase !== "live" && phase !== "shadow")
|
|
145
|
+
return false;
|
|
146
|
+
return true;
|
|
147
|
+
}
|
|
148
|
+
//# sourceMappingURL=index-events.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index-events.js","sourceRoot":"","sources":["../../../src/observability/index-events.ts"],"names":[],"mappings":"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"}
|
|
@@ -10,6 +10,13 @@
|
|
|
10
10
|
import type { ToolUsageEntry } from "./tool-usage.js";
|
|
11
11
|
export interface UsageWindow {
|
|
12
12
|
calls: number;
|
|
13
|
+
/**
|
|
14
|
+
* Successful retrieval calls that returned at least one item and were not
|
|
15
|
+
* marked `degraded`. Captures rift_search, rift_conversations_search, and
|
|
16
|
+
* rift_context_pack — the tools whose job is to surface relevant context.
|
|
17
|
+
* Non-retrieval calls (rift_save, rift_status) are excluded.
|
|
18
|
+
*/
|
|
19
|
+
context_hits: number;
|
|
13
20
|
tokens_saved: number;
|
|
14
21
|
}
|
|
15
22
|
export interface UsageSummary {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"tool-usage-stats.d.ts","sourceRoot":"","sources":["../../../src/observability/tool-usage-stats.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AACH,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,iBAAiB,CAAC;AAyCtD,MAAM,WAAW,WAAW;IAC1B,KAAK,EAAE,MAAM,CAAC;IACd,YAAY,EAAE,MAAM,CAAC;CACtB;AAED,MAAM,WAAW,YAAY;IAC3B,KAAK,EAAE,WAAW,CAAC;IACnB,IAAI,EAAE,WAAW,CAAC;IAClB,KAAK,EAAE,WAAW,CAAC;IACnB,QAAQ,EAAE,WAAW,CAAC;IACtB,OAAO,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;CACjC;
|
|
1
|
+
{"version":3,"file":"tool-usage-stats.d.ts","sourceRoot":"","sources":["../../../src/observability/tool-usage-stats.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AACH,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,iBAAiB,CAAC;AAyCtD,MAAM,WAAW,WAAW;IAC1B,KAAK,EAAE,MAAM,CAAC;IACd;;;;;OAKG;IACH,YAAY,EAAE,MAAM,CAAC;IACrB,YAAY,EAAE,MAAM,CAAC;CACtB;AAED,MAAM,WAAW,YAAY;IAC3B,KAAK,EAAE,WAAW,CAAC;IACnB,IAAI,EAAE,WAAW,CAAC;IAClB,KAAK,EAAE,WAAW,CAAC;IACnB,QAAQ,EAAE,WAAW,CAAC;IACtB,OAAO,EAAE,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC;CACjC;AA0DD,wBAAgB,cAAc,CAC5B,OAAO,EAAE,cAAc,EAAE,EACzB,GAAG,GAAE,IAAiB,GACrB,YAAY,CAgDd"}
|
|
@@ -33,16 +33,48 @@ function canonicalToolName(tool) {
|
|
|
33
33
|
}
|
|
34
34
|
const DAY_MS = 24 * 60 * 60 * 1000;
|
|
35
35
|
function emptyWindow() {
|
|
36
|
-
return { calls: 0, tokens_saved: 0 };
|
|
36
|
+
return { calls: 0, context_hits: 0, tokens_saved: 0 };
|
|
37
37
|
}
|
|
38
38
|
function tokensSavedFor(tool) {
|
|
39
39
|
return TOKENS_SAVED_PER_TOOL[tool] ?? DEFAULT_TOKENS_SAVED;
|
|
40
40
|
}
|
|
41
|
-
|
|
42
|
-
|
|
41
|
+
/**
|
|
42
|
+
* Local-time start-of-day. The menu-bar "today" counter is a glanceable
|
|
43
|
+
* Mac-local metric, so the boundary follows the machine's wall clock — not
|
|
44
|
+
* UTC, which would reset mid-evening in Asia/early-morning in Europe.
|
|
45
|
+
*/
|
|
46
|
+
function startOfLocalDay(date) {
|
|
47
|
+
return new Date(date.getFullYear(), date.getMonth(), date.getDate()).getTime();
|
|
48
|
+
}
|
|
49
|
+
/**
|
|
50
|
+
* Local-time start of the following day. Built via the local-time Date
|
|
51
|
+
* constructor (not `startOfLocalDay + DAY_MS`) so DST-fallback days, which
|
|
52
|
+
* have 25 hours, still capture their final hour as "today".
|
|
53
|
+
*/
|
|
54
|
+
function startOfNextLocalDay(date) {
|
|
55
|
+
return new Date(date.getFullYear(), date.getMonth(), date.getDate() + 1).getTime();
|
|
56
|
+
}
|
|
57
|
+
/**
|
|
58
|
+
* Tools whose `result_count` counts toward `context_hits`. Belt-and-suspenders
|
|
59
|
+
* with the logger's own whitelist in [extractRetrievalSignal] — if a future
|
|
60
|
+
* code path ever writes `result_count` for a non-retrieval tool, this gate
|
|
61
|
+
* still keeps it out of the metric.
|
|
62
|
+
*/
|
|
63
|
+
const RETRIEVAL_TOOLS_FOR_HITS = new Set([
|
|
64
|
+
"rift_search",
|
|
65
|
+
"rift_conversations_search",
|
|
66
|
+
"rift_context_pack",
|
|
67
|
+
]);
|
|
68
|
+
function isContextHit(tool, entry) {
|
|
69
|
+
return (RETRIEVAL_TOOLS_FOR_HITS.has(tool) &&
|
|
70
|
+
entry.success === true &&
|
|
71
|
+
entry.degraded !== true &&
|
|
72
|
+
typeof entry.result_count === "number" &&
|
|
73
|
+
entry.result_count > 0);
|
|
43
74
|
}
|
|
44
75
|
export function aggregateUsage(entries, now = new Date()) {
|
|
45
|
-
const todayStartMs =
|
|
76
|
+
const todayStartMs = startOfLocalDay(now);
|
|
77
|
+
const todayEndMs = startOfNextLocalDay(now);
|
|
46
78
|
const nowMs = now.getTime();
|
|
47
79
|
const weekStartMs = nowMs - 7 * DAY_MS;
|
|
48
80
|
const monthStartMs = nowMs - 30 * DAY_MS;
|
|
@@ -53,29 +85,33 @@ export function aggregateUsage(entries, now = new Date()) {
|
|
|
53
85
|
all_time: emptyWindow(),
|
|
54
86
|
by_tool: {},
|
|
55
87
|
};
|
|
56
|
-
const todayEndMs = todayStartMs + DAY_MS;
|
|
57
88
|
for (const entry of entries) {
|
|
58
89
|
const ts = Date.parse(entry.timestamp);
|
|
59
90
|
if (Number.isNaN(ts))
|
|
60
91
|
continue;
|
|
61
92
|
const tool = canonicalToolName(entry.tool);
|
|
62
93
|
const tokens = entry.success ? tokensSavedFor(tool) : 0;
|
|
94
|
+
const hit = isContextHit(tool, entry) ? 1 : 0;
|
|
63
95
|
summary.all_time.calls += 1;
|
|
64
96
|
summary.all_time.tokens_saved += tokens;
|
|
97
|
+
summary.all_time.context_hits += hit;
|
|
65
98
|
summary.by_tool[tool] = (summary.by_tool[tool] ?? 0) + 1;
|
|
66
99
|
if (ts > nowMs)
|
|
67
100
|
continue;
|
|
68
101
|
if (ts >= monthStartMs) {
|
|
69
102
|
summary.month.calls += 1;
|
|
70
103
|
summary.month.tokens_saved += tokens;
|
|
104
|
+
summary.month.context_hits += hit;
|
|
71
105
|
}
|
|
72
106
|
if (ts >= weekStartMs) {
|
|
73
107
|
summary.week.calls += 1;
|
|
74
108
|
summary.week.tokens_saved += tokens;
|
|
109
|
+
summary.week.context_hits += hit;
|
|
75
110
|
}
|
|
76
111
|
if (ts >= todayStartMs && ts < todayEndMs) {
|
|
77
112
|
summary.today.calls += 1;
|
|
78
113
|
summary.today.tokens_saved += tokens;
|
|
114
|
+
summary.today.context_hits += hit;
|
|
79
115
|
}
|
|
80
116
|
}
|
|
81
117
|
return summary;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"tool-usage-stats.js","sourceRoot":"","sources":["../../../src/observability/tool-usage-stats.ts"],"names":[],"mappings":"AAWA;;;;;;;;GAQG;AACH,MAAM,qBAAqB,GAA2B;IACpD,iBAAiB,EAAE,MAAM;IACzB,yBAAyB,EAAE,KAAK;IAChC,WAAW,EAAE,KAAK;IAClB,SAAS,EAAE,KAAK;IAChB,WAAW,EAAE,KAAK;CACnB,CAAC;AAEF,MAAM,oBAAoB,GAAG,KAAK,CAAC;AAEnC;;;;;GAKG;AACH,MAAM,mBAAmB,GAA2B;IAClD,SAAS,EAAE,WAAW;IACtB,WAAW,EAAE,aAAa;IAC1B,yBAAyB,EAAE,2BAA2B;IACtD,iBAAiB,EAAE,mBAAmB;IACtC,WAAW,EAAE,aAAa;CAC3B,CAAC;AAEF,SAAS,iBAAiB,CAAC,IAAY;IACrC,OAAO,mBAAmB,CAAC,IAAI,CAAC,IAAI,IAAI,CAAC;AAC3C,CAAC;AAED,MAAM,MAAM,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,IAAI,CAAC;
|
|
1
|
+
{"version":3,"file":"tool-usage-stats.js","sourceRoot":"","sources":["../../../src/observability/tool-usage-stats.ts"],"names":[],"mappings":"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"}
|
|
@@ -11,12 +11,10 @@ export interface ToolUsageEntry {
|
|
|
11
11
|
}
|
|
12
12
|
export declare function sanitizeArgs(raw: Record<string, unknown>): Record<string, unknown>;
|
|
13
13
|
/**
|
|
14
|
-
* Try to extract result_count from
|
|
15
|
-
*
|
|
16
|
-
*
|
|
17
|
-
*
|
|
18
|
-
* and fall back to JSON-parsing the text channel for backwards compatibility
|
|
19
|
-
* with tools that still return JSON there.
|
|
14
|
+
* Try to extract `result_count` from a retrieval-tool response. For search
|
|
15
|
+
* tools this is `results.length`; for `rift_context_pack` it is the sum of
|
|
16
|
+
* all four bucket sizes (decisions + constraints + examples + rules).
|
|
17
|
+
* Returns `undefined` for non-retrieval tools.
|
|
20
18
|
*/
|
|
21
19
|
export declare function extractResultCount(tool: string, mcpResult: {
|
|
22
20
|
content: Array<{
|
|
@@ -26,7 +24,9 @@ export declare function extractResultCount(tool: string, mcpResult: {
|
|
|
26
24
|
structuredContent?: Record<string, unknown>;
|
|
27
25
|
}): number | undefined;
|
|
28
26
|
/**
|
|
29
|
-
* Try to extract degraded flag from
|
|
27
|
+
* Try to extract the `degraded` flag from a retrieval-tool response.
|
|
28
|
+
* Returns `undefined` for non-retrieval tools and for retrieval tools whose
|
|
29
|
+
* response did not carry the flag.
|
|
30
30
|
*/
|
|
31
31
|
export declare function extractDegraded(tool: string, mcpResult: {
|
|
32
32
|
content: Array<{
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"tool-usage.d.ts","sourceRoot":"","sources":["../../../src/observability/tool-usage.ts"],"names":[],"mappings":"AAwBA,MAAM,WAAW,cAAc;IAC7B,SAAS,EAAE,MAAM,CAAC;IAClB,IAAI,EAAE,eAAe,CAAC;IACtB,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IAC9B,UAAU,EAAE,MAAM,CAAC;IACnB,OAAO,EAAE,OAAO,CAAC;IACjB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB;AAID,wBAAgB,YAAY,CAC1B,GAAG,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAC3B,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAkBzB;
|
|
1
|
+
{"version":3,"file":"tool-usage.d.ts","sourceRoot":"","sources":["../../../src/observability/tool-usage.ts"],"names":[],"mappings":"AAwBA,MAAM,WAAW,cAAc;IAC7B,SAAS,EAAE,MAAM,CAAC;IAClB,IAAI,EAAE,eAAe,CAAC;IACtB,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IAC9B,UAAU,EAAE,MAAM,CAAC;IACnB,OAAO,EAAE,OAAO,CAAC;IACjB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB;AAID,wBAAgB,YAAY,CAC1B,GAAG,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAC3B,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAkBzB;AA8ED;;;;;GAKG;AACH,wBAAgB,kBAAkB,CAChC,IAAI,EAAE,MAAM,EACZ,SAAS,EAAE;IACT,OAAO,EAAE,KAAK,CAAC;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,IAAI,EAAE,MAAM,CAAA;KAAE,CAAC,CAAC;IAC/C,iBAAiB,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;CAC7C,GACA,MAAM,GAAG,SAAS,CAEpB;AAED;;;;GAIG;AACH,wBAAgB,eAAe,CAC7B,IAAI,EAAE,MAAM,EACZ,SAAS,EAAE;IACT,OAAO,EAAE,KAAK,CAAC;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,IAAI,EAAE,MAAM,CAAA;KAAE,CAAC,CAAC;IAC/C,iBAAiB,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;CAC7C,GACA,OAAO,GAAG,SAAS,CAErB;AAID,qBAAa,eAAe;IAC1B,OAAO,CAAC,QAAQ,CAAC,OAAO,CAAS;gBAErB,OAAO,EAAE,MAAM;IAK3B,2CAA2C;IAC3C,GAAG,CAAC,KAAK,EAAE,cAAc,GAAG,IAAI;IAWhC;;;OAGG;IACH,IAAI,CACF,CAAC,SAAS;QACR,OAAO,EAAE,KAAK,CAAC;YAAE,IAAI,EAAE,MAAM,CAAC;YAAC,IAAI,EAAE,MAAM,CAAA;SAAE,CAAC,CAAC;QAC/C,OAAO,CAAC,EAAE,OAAO,CAAC;QAClB,iBAAiB,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;KAC7C,EAED,IAAI,EAAE,MAAM,EACZ,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAC7B,OAAO,EAAE,MAAM,OAAO,CAAC,CAAC,CAAC,GACxB,OAAO,CAAC,CAAC,CAAC;IAwCb,sCAAsC;IACtC,OAAO,IAAI,cAAc,EAAE;IAa3B,IAAI,QAAQ,IAAI,MAAM,CAErB;CACF;AAED;;;;;;;GAOG;AACH,wBAAgB,4BAA4B,CAC1C,QAAQ,EAAE,MAAM,GACf,cAAc,EAAE,CA4BlB"}
|
|
@@ -40,53 +40,92 @@ export function sanitizeArgs(raw) {
|
|
|
40
40
|
}
|
|
41
41
|
// --- Result extraction ---
|
|
42
42
|
/**
|
|
43
|
-
*
|
|
44
|
-
*
|
|
45
|
-
*
|
|
46
|
-
*
|
|
47
|
-
* and fall back to JSON-parsing the text channel for backwards compatibility
|
|
48
|
-
* with tools that still return JSON there.
|
|
43
|
+
* Tools whose responses carry a retrieval-size signal we can count toward
|
|
44
|
+
* `context_hits`. Explicit whitelist (not a substring match on "search") so
|
|
45
|
+
* future non-retrieval tools that happen to return a `results` array don't
|
|
46
|
+
* pollute the metric.
|
|
49
47
|
*/
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
48
|
+
const RETRIEVAL_TOOLS = new Set([
|
|
49
|
+
"rift_search",
|
|
50
|
+
"rift_conversations_search",
|
|
51
|
+
"rift_context_pack",
|
|
52
|
+
]);
|
|
53
|
+
/**
|
|
54
|
+
* Per-tool extractor for `(result_count, degraded)` derived from the MCP
|
|
55
|
+
* response. Search tools expose `results: []`; context_pack exposes four
|
|
56
|
+
* named buckets we sum. Anything else returns `undefined` for both.
|
|
57
|
+
*/
|
|
58
|
+
function extractRetrievalSignal(tool, mcpResult) {
|
|
59
|
+
if (!RETRIEVAL_TOOLS.has(tool))
|
|
60
|
+
return {};
|
|
61
|
+
const sc = mcpResult.structuredContent;
|
|
62
|
+
const parseText = () => {
|
|
63
|
+
try {
|
|
64
|
+
const text = mcpResult.content[0]?.text;
|
|
65
|
+
if (!text)
|
|
66
|
+
return undefined;
|
|
67
|
+
const parsed = JSON.parse(text);
|
|
68
|
+
return typeof parsed === "object" && parsed !== null
|
|
69
|
+
? parsed
|
|
70
|
+
: undefined;
|
|
71
|
+
}
|
|
72
|
+
catch {
|
|
59
73
|
return undefined;
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
74
|
+
}
|
|
75
|
+
};
|
|
76
|
+
if (tool === "rift_context_pack") {
|
|
77
|
+
// context_pack always writes structuredContent (see tools/context-pack.ts).
|
|
78
|
+
// Skip the text-channel fallback — the text is human-readable markdown,
|
|
79
|
+
// not JSON, so attempting to parse it would always fail.
|
|
80
|
+
if (!sc)
|
|
81
|
+
return {};
|
|
82
|
+
const sum = (key) => {
|
|
83
|
+
const v = sc[key];
|
|
84
|
+
return Array.isArray(v) ? v.length : 0;
|
|
85
|
+
};
|
|
86
|
+
const count = sum("decisions") + sum("constraints") + sum("examples") + sum("rules");
|
|
87
|
+
const out = { count };
|
|
88
|
+
if (typeof sc["degraded"] === "boolean")
|
|
89
|
+
out.degraded = sc["degraded"];
|
|
90
|
+
return out;
|
|
63
91
|
}
|
|
64
|
-
|
|
65
|
-
|
|
92
|
+
// Search tools: prefer structuredContent, fall back to JSON-on-text for
|
|
93
|
+
// backwards compatibility with the pre-Slice-1 response shape.
|
|
94
|
+
const fromStructured = sc?.["results"];
|
|
95
|
+
if (Array.isArray(fromStructured)) {
|
|
96
|
+
const out = {
|
|
97
|
+
count: fromStructured.length,
|
|
98
|
+
};
|
|
99
|
+
if (typeof sc?.["degraded"] === "boolean")
|
|
100
|
+
out.degraded = sc["degraded"];
|
|
101
|
+
return out;
|
|
66
102
|
}
|
|
67
|
-
|
|
103
|
+
const parsed = parseText();
|
|
104
|
+
if (!parsed)
|
|
105
|
+
return {};
|
|
106
|
+
const out = {};
|
|
107
|
+
if (Array.isArray(parsed.results))
|
|
108
|
+
out.count = parsed.results.length;
|
|
109
|
+
if (typeof parsed.degraded === "boolean")
|
|
110
|
+
out.degraded = parsed.degraded;
|
|
111
|
+
return out;
|
|
112
|
+
}
|
|
113
|
+
/**
|
|
114
|
+
* Try to extract `result_count` from a retrieval-tool response. For search
|
|
115
|
+
* tools this is `results.length`; for `rift_context_pack` it is the sum of
|
|
116
|
+
* all four bucket sizes (decisions + constraints + examples + rules).
|
|
117
|
+
* Returns `undefined` for non-retrieval tools.
|
|
118
|
+
*/
|
|
119
|
+
export function extractResultCount(tool, mcpResult) {
|
|
120
|
+
return extractRetrievalSignal(tool, mcpResult).count;
|
|
68
121
|
}
|
|
69
122
|
/**
|
|
70
|
-
* Try to extract degraded flag from
|
|
123
|
+
* Try to extract the `degraded` flag from a retrieval-tool response.
|
|
124
|
+
* Returns `undefined` for non-retrieval tools and for retrieval tools whose
|
|
125
|
+
* response did not carry the flag.
|
|
71
126
|
*/
|
|
72
127
|
export function extractDegraded(tool, mcpResult) {
|
|
73
|
-
|
|
74
|
-
return undefined;
|
|
75
|
-
const fromStructured = mcpResult.structuredContent?.["degraded"];
|
|
76
|
-
if (typeof fromStructured === "boolean")
|
|
77
|
-
return fromStructured;
|
|
78
|
-
try {
|
|
79
|
-
const text = mcpResult.content[0]?.text;
|
|
80
|
-
if (!text)
|
|
81
|
-
return undefined;
|
|
82
|
-
const parsed = JSON.parse(text);
|
|
83
|
-
if (typeof parsed.degraded === "boolean")
|
|
84
|
-
return parsed.degraded;
|
|
85
|
-
}
|
|
86
|
-
catch {
|
|
87
|
-
// not parseable — fine
|
|
88
|
-
}
|
|
89
|
-
return undefined;
|
|
128
|
+
return extractRetrievalSignal(tool, mcpResult).degraded;
|
|
90
129
|
}
|
|
91
130
|
// --- Logger ---
|
|
92
131
|
export class ToolUsageLogger {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"tool-usage.js","sourceRoot":"","sources":["../../../src/observability/tool-usage.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AACH,OAAO,EAAE,MAAM,SAAS,CAAC;AACzB,OAAO,IAAI,MAAM,WAAW,CAAC;AAE7B,iBAAiB;AAEjB,MAAM,qBAAqB,GAAG,GAAG,CAAC;AAClC,MAAM,aAAa,GAAG,IAAI,GAAG,CAAC;IAC5B,OAAO;IACP,QAAQ;IACR,UAAU;IACV,eAAe;IACf,SAAS;IACT,QAAQ;CACT,CAAC,CAAC;AAgBH,uBAAuB;AAEvB,MAAM,UAAU,YAAY,CAC1B,GAA4B;IAE5B,MAAM,GAAG,GAA4B,EAAE,CAAC;IACxC,KAAK,MAAM,CAAC,GAAG,EAAE,KAAK,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,GAAG,CAAC,EAAE,CAAC;QAC/C,IAAI,aAAa,CAAC,GAAG,CAAC,GAAG,CAAC,WAAW,EAAE,CAAC,EAAE,CAAC;YACzC,GAAG,CAAC,GAAG,CAAC,GAAG,YAAY,CAAC;QAC1B,CAAC;aAAM,IAAI,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,CAAC,MAAM,GAAG,qBAAqB,EAAE,CAAC;YAC7E,GAAG,CAAC,GAAG,CAAC,GAAG,KAAK,CAAC,KAAK,CAAC,CAAC,EAAE,qBAAqB,CAAC,GAAG,iBAAiB,KAAK,CAAC,MAAM,GAAG,CAAC;QACtF,CAAC;aAAM,IAAI,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC,EAAE,CAAC;YAChC,GAAG,CAAC,GAAG,CAAC,GAAG,KAAK,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CACzB,OAAO,CAAC,KAAK,QAAQ,IAAI,CAAC,CAAC,MAAM,GAAG,qBAAqB;gBACvD,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC,CAAC,EAAE,qBAAqB,CAAC,GAAG,iBAAiB,CAAC,CAAC,MAAM,GAAG;gBAClE,CAAC,CAAC,CAAC,CACN,CAAC;QACJ,CAAC;aAAM,CAAC;YACN,GAAG,CAAC,GAAG,CAAC,GAAG,KAAK,CAAC;QACnB,CAAC;IACH,CAAC;IACD,OAAO,GAAG,CAAC;AACb,CAAC;AAED,4BAA4B;AAE5B
|
|
1
|
+
{"version":3,"file":"tool-usage.js","sourceRoot":"","sources":["../../../src/observability/tool-usage.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
export interface VersionCheckSnapshot {
|
|
2
|
+
/** Installed version (from getBuildInfo().version). */
|
|
3
|
+
installed: string;
|
|
4
|
+
/** Latest version on the `beta` dist-tag, or null when the probe failed. */
|
|
5
|
+
latest_beta: string | null;
|
|
6
|
+
/** ISO timestamp of the probe attempt (success or failure). */
|
|
7
|
+
checked_at: string;
|
|
8
|
+
/** Compact error class on failure, or null on success. */
|
|
9
|
+
error: string | null;
|
|
10
|
+
}
|
|
11
|
+
export declare function versionCheckPath(dataDir: string): string;
|
|
12
|
+
/**
|
|
13
|
+
* Write the snapshot atomically. Best-effort: a write failure logs to
|
|
14
|
+
* stderr but never throws — the update-check feature must not be able
|
|
15
|
+
* to break the daemon.
|
|
16
|
+
*/
|
|
17
|
+
export declare function writeVersionCheck(dataDir: string, snapshot: VersionCheckSnapshot): void;
|
|
18
|
+
/**
|
|
19
|
+
* Read the snapshot. Returns null when the file is missing or unparseable
|
|
20
|
+
* (a missing file is the steady-state on a fresh install before the first
|
|
21
|
+
* probe runs).
|
|
22
|
+
*/
|
|
23
|
+
export declare function readVersionCheck(dataDir: string): VersionCheckSnapshot | null;
|
|
24
|
+
/**
|
|
25
|
+
* Compare two `x.y.z-beta.N` versions. Returns:
|
|
26
|
+
* negative if a < b
|
|
27
|
+
* zero if a === b
|
|
28
|
+
* positive if a > b
|
|
29
|
+
*
|
|
30
|
+
* Anything we cannot parse is treated as equal — the status renderer
|
|
31
|
+
* uses this only to decide whether to *show* an update hint, so the
|
|
32
|
+
* conservative behavior on bad input is "don't nag."
|
|
33
|
+
*
|
|
34
|
+
* This is intentionally tiny and beta-aware rather than a full semver
|
|
35
|
+
* implementation. Our publish channel today is `x.y.z-beta.N` only.
|
|
36
|
+
*/
|
|
37
|
+
export declare function compareBetaVersions(a: string, b: string): number;
|
|
38
|
+
export declare const NPM_REGISTRY_URL = "https://registry.npmjs.org/@getrift/rift";
|
|
39
|
+
/**
|
|
40
|
+
* Hit the npm registry for the `beta` dist-tag. Metadata-only fetch —
|
|
41
|
+
* no auth, no headers beyond the default. Returns the resolved version
|
|
42
|
+
* or null on any failure (the caller writes the failure into the
|
|
43
|
+
* snapshot's `error` field).
|
|
44
|
+
*
|
|
45
|
+
* Test hook: `fetchFn` lets us mock the network without touching the
|
|
46
|
+
* global fetch.
|
|
47
|
+
*/
|
|
48
|
+
export declare function probeLatestBeta(opts?: {
|
|
49
|
+
fetchFn?: typeof fetch;
|
|
50
|
+
timeoutMs?: number;
|
|
51
|
+
}): Promise<{
|
|
52
|
+
ok: true;
|
|
53
|
+
latest_beta: string;
|
|
54
|
+
} | {
|
|
55
|
+
ok: false;
|
|
56
|
+
error: string;
|
|
57
|
+
}>;
|
|
58
|
+
/**
|
|
59
|
+
* Run one probe and persist the result. Pure orchestration: probe →
|
|
60
|
+
* write snapshot. On error, still writes a snapshot so the daemon's
|
|
61
|
+
* last attempt is observable.
|
|
62
|
+
*/
|
|
63
|
+
export declare function runVersionCheck(opts: {
|
|
64
|
+
dataDir: string;
|
|
65
|
+
installed: string;
|
|
66
|
+
fetchFn?: typeof fetch;
|
|
67
|
+
timeoutMs?: number;
|
|
68
|
+
now?: () => Date;
|
|
69
|
+
}): Promise<VersionCheckSnapshot>;
|
|
70
|
+
//# sourceMappingURL=version-check.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"version-check.d.ts","sourceRoot":"","sources":["../../../src/observability/version-check.ts"],"names":[],"mappings":"AAsBA,MAAM,WAAW,oBAAoB;IACnC,uDAAuD;IACvD,SAAS,EAAE,MAAM,CAAC;IAClB,4EAA4E;IAC5E,WAAW,EAAE,MAAM,GAAG,IAAI,CAAC;IAC3B,+DAA+D;IAC/D,UAAU,EAAE,MAAM,CAAC;IACnB,0DAA0D;IAC1D,KAAK,EAAE,MAAM,GAAG,IAAI,CAAC;CACtB;AAED,wBAAgB,gBAAgB,CAAC,OAAO,EAAE,MAAM,GAAG,MAAM,CAExD;AAED;;;;GAIG;AACH,wBAAgB,iBAAiB,CAC/B,OAAO,EAAE,MAAM,EACf,QAAQ,EAAE,oBAAoB,GAC7B,IAAI,CAYN;AAED;;;;GAIG;AACH,wBAAgB,gBAAgB,CAC9B,OAAO,EAAE,MAAM,GACd,oBAAoB,GAAG,IAAI,CAe7B;AAaD;;;;;;;;;;;;GAYG;AACH,wBAAgB,mBAAmB,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,EAAE,MAAM,GAAG,MAAM,CAahE;AAsBD,eAAO,MAAM,gBAAgB,6CACe,CAAC;AAE7C;;;;;;;;GAQG;AACH,wBAAsB,eAAe,CAAC,IAAI,GAAE;IAC1C,OAAO,CAAC,EAAE,OAAO,KAAK,CAAC;IACvB,SAAS,CAAC,EAAE,MAAM,CAAC;CACf,GAAG,OAAO,CACd;IAAE,EAAE,EAAE,IAAI,CAAC;IAAC,WAAW,EAAE,MAAM,CAAA;CAAE,GAAG;IAAE,EAAE,EAAE,KAAK,CAAC;IAAC,KAAK,EAAE,MAAM,CAAA;CAAE,CACjE,CA8BA;AAED;;;;GAIG;AACH,wBAAsB,eAAe,CAAC,IAAI,EAAE;IAC1C,OAAO,EAAE,MAAM,CAAC;IAChB,SAAS,EAAE,MAAM,CAAC;IAClB,OAAO,CAAC,EAAE,OAAO,KAAK,CAAC;IACvB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,GAAG,CAAC,EAAE,MAAM,IAAI,CAAC;CAClB,GAAG,OAAO,CAAC,oBAAoB,CAAC,CAwBhC"}
|