@remnic/core 9.3.624 → 9.3.625
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/access-cli.js +18 -16
- package/dist/access-cli.js.map +1 -1
- package/dist/access-http.d.ts +12 -5
- package/dist/access-http.js +10 -9
- package/dist/access-mcp.d.ts +5 -5
- package/dist/access-mcp.js +8 -8
- package/dist/access-schema.d.ts +5 -5
- package/dist/{access-service-CBNEKjzN.d.ts → access-service-C_sfOHsX.d.ts} +26 -3
- package/dist/access-service.d.ts +5 -5
- package/dist/access-service.js +7 -7
- package/dist/action-confidence.d.ts +1 -1
- package/dist/active-memory-bridge.d.ts +1 -1
- package/dist/active-recall.d.ts +1 -1
- package/dist/active-recall.js +2 -1
- package/dist/active-recall.js.map +1 -1
- package/dist/behavior-learner.d.ts +1 -1
- package/dist/behavior-signals.d.ts +1 -1
- package/dist/bootstrap.d.ts +4 -4
- package/dist/briefing.d.ts +1 -1
- package/dist/briefing.js +3 -3
- package/dist/buffer-surprise-report.d.ts +1 -1
- package/dist/buffer.d.ts +1 -1
- package/dist/calibration.d.ts +1 -1
- package/dist/causal-behavior.d.ts +1 -1
- package/dist/causal-consolidation.d.ts +1 -1
- package/dist/causal-consolidation.js +4 -4
- package/dist/{chunk-7TPH6UZL.js → chunk-2RHI3FGV.js} +540 -17
- package/dist/chunk-2RHI3FGV.js.map +1 -0
- package/dist/{chunk-GYTVOLNX.js → chunk-3MNBW7R7.js} +2 -2
- package/dist/{chunk-QFQQFX2H.js → chunk-3R2UZV3U.js} +2 -2
- package/dist/{chunk-O4UNM6OR.js → chunk-532VCWYW.js} +2 -2
- package/dist/{chunk-2UFQYU5F.js → chunk-57QXN2CS.js} +2 -2
- package/dist/chunk-7WV3F5DQ.js +22 -0
- package/dist/chunk-7WV3F5DQ.js.map +1 -0
- package/dist/{chunk-RKW6QR7W.js → chunk-AZ4RI3QD.js} +1461 -78
- package/dist/chunk-AZ4RI3QD.js.map +1 -0
- package/dist/{chunk-KQFQ3IS5.js → chunk-F3FY3D3S.js} +43 -7
- package/dist/chunk-F3FY3D3S.js.map +1 -0
- package/dist/{chunk-4R4KTDIE.js → chunk-FPNQF475.js} +1 -1
- package/dist/chunk-FPNQF475.js.map +1 -0
- package/dist/{chunk-UGEBPVNI.js → chunk-GE7Q7KXP.js} +2 -2
- package/dist/{chunk-GLWW3EJQ.js → chunk-KB4MFBF5.js} +3 -3
- package/dist/{chunk-5GOMXHLC.js → chunk-KKTXCFD7.js} +255 -1
- package/dist/chunk-KKTXCFD7.js.map +1 -0
- package/dist/{chunk-FH3PPO42.js → chunk-KVFYTRMV.js} +2 -2
- package/dist/{chunk-BNW5NJJH.js → chunk-LQYTQCXM.js} +2 -2
- package/dist/{chunk-AYHXQR53.js → chunk-MVQN73GT.js} +2 -2
- package/dist/{chunk-ZZPIJPPD.js → chunk-N5RGXWLQ.js} +2 -2
- package/dist/chunk-NDAH7BJ5.js +213 -0
- package/dist/chunk-NDAH7BJ5.js.map +1 -0
- package/dist/{chunk-R3OQGYOU.js → chunk-P2D2MM47.js} +2 -2
- package/dist/{chunk-PSUB67YB.js → chunk-PW6GURU3.js} +2 -2
- package/dist/{chunk-W3BKVM64.js → chunk-QDV6VAD4.js} +2 -2
- package/dist/{chunk-3QSU4NFF.js → chunk-QHXW3LZV.js} +3 -3
- package/dist/{chunk-I6UCUHLK.js → chunk-SHV5Y2WU.js} +182 -3
- package/dist/chunk-SHV5Y2WU.js.map +1 -0
- package/dist/{chunk-OZXVGYGZ.js → chunk-STDAAGH7.js} +2 -2
- package/dist/{chunk-FMGWXIES.js → chunk-TZDSNIRO.js} +5 -5
- package/dist/{chunk-2L54V4ZO.js → chunk-UELS6WWF.js} +2 -2
- package/dist/{chunk-PJGB7XRR.js → chunk-UGHUNQ74.js} +502 -134
- package/dist/chunk-UGHUNQ74.js.map +1 -0
- package/dist/{chunk-FG76RDVI.js → chunk-Y3TMFC6I.js} +136 -4
- package/dist/chunk-Y3TMFC6I.js.map +1 -0
- package/dist/{chunk-BPSGLMQ4.js → chunk-YQNADJCT.js} +2 -2
- package/dist/{cli-Cw729yLf.d.ts → cli-EZv6YE6_.d.ts} +3 -3
- package/dist/cli.d.ts +6 -6
- package/dist/cli.js +23 -21
- package/dist/compounding/engine.d.ts +1 -1
- package/dist/compounding/engine.js +3 -3
- package/dist/compounding/preference-consolidator.d.ts +1 -1
- package/dist/compression-optimizer.d.ts +1 -1
- package/dist/config.d.ts +1 -1
- package/dist/config.js +2 -1
- package/dist/connectors/codex-materialize-runner.d.ts +1 -1
- package/dist/connectors/codex-materialize-runner.js +3 -3
- package/dist/connectors/codex-materialize.d.ts +1 -1
- package/dist/connectors/index.d.ts +1 -1
- package/dist/connectors/index.js +3 -3
- package/dist/consolidation-provenance-check.d.ts +1 -1
- package/dist/consolidation-undo.d.ts +1 -1
- package/dist/contradiction/index.d.ts +2 -2
- package/dist/conversation-index/backend.d.ts +1 -1
- package/dist/conversation-index/chunker.d.ts +1 -1
- package/dist/conversation-index/faiss-adapter.d.ts +1 -1
- package/dist/conversation-index/indexer.d.ts +1 -1
- package/dist/conversation-index/search.d.ts +1 -1
- package/dist/day-summary.d.ts +1 -1
- package/dist/delinearize.d.ts +1 -1
- package/dist/direct-answer-wiring.d.ts +1 -1
- package/dist/direct-answer.d.ts +1 -1
- package/dist/embedding-fallback.d.ts +1 -1
- package/dist/enrichment/index.d.ts +1 -1
- package/dist/entity-retrieval.d.ts +1 -1
- package/dist/entity-retrieval.js +3 -3
- package/dist/entity-schema.d.ts +1 -1
- package/dist/explicit-capture.d.ts +4 -4
- package/dist/extraction-judge-telemetry.d.ts +1 -1
- package/dist/extraction-judge-training.d.ts +1 -1
- package/dist/extraction-judge.d.ts +1 -1
- package/dist/extraction.d.ts +1 -1
- package/dist/fallback-llm.d.ts +1 -1
- package/dist/identity-continuity.d.ts +1 -1
- package/dist/importance.d.ts +1 -1
- package/dist/index.d.ts +307 -9
- package/dist/index.js +155 -29
- package/dist/index.js.map +1 -1
- package/dist/intent.d.ts +1 -1
- package/dist/lcm/engine.d.ts +1 -1
- package/dist/lcm/index.d.ts +1 -1
- package/dist/lcm/tools.d.ts +1 -1
- package/dist/lifecycle.d.ts +1 -1
- package/dist/live-connectors-runner.d.ts +1 -1
- package/dist/local-llm.d.ts +1 -1
- package/dist/maintenance/memory-governance.d.ts +1 -1
- package/dist/maintenance/memory-governance.js +3 -3
- package/dist/maintenance/rebuild-memory-lifecycle-ledger.js +3 -3
- package/dist/maintenance/rebuild-memory-projection.js +4 -4
- package/dist/mcp-memory-inspector-app.d.ts +5 -5
- package/dist/memory-action-policy.d.ts +1 -1
- package/dist/memory-cache.d.ts +1 -1
- package/dist/memory-lifecycle-ledger-utils.d.ts +1 -1
- package/dist/memory-projection-store.d.ts +1 -1
- package/dist/memory-provenance.d.ts +1 -1
- package/dist/memory-worth-outcomes.d.ts +1 -1
- package/dist/models-json.d.ts +1 -1
- package/dist/namespaces/migrate.d.ts +1 -1
- package/dist/namespaces/migrate.js +4 -4
- package/dist/namespaces/principal.d.ts +1 -1
- package/dist/namespaces/search.d.ts +1 -1
- package/dist/namespaces/storage.d.ts +1 -1
- package/dist/namespaces/storage.js +3 -3
- package/dist/native-knowledge.d.ts +1 -1
- package/dist/operator-toolkit.d.ts +1 -1
- package/dist/operator-toolkit.js +8 -7
- package/dist/{orchestrator-CqWOjfgl.d.ts → orchestrator-CEycaY3M.d.ts} +361 -4
- package/dist/orchestrator.d.ts +4 -4
- package/dist/orchestrator.js +13 -11
- package/dist/patterns-cli.d.ts +1 -1
- package/dist/policy-runtime.d.ts +1 -1
- package/dist/qmd-recall-cache.d.ts +1 -1
- package/dist/qmd.d.ts +1 -1
- package/dist/recall-disclosure-escalation.d.ts +1 -1
- package/dist/recall-explain-renderer.d.ts +1 -1
- package/dist/recall-explain-renderer.js +3 -3
- package/dist/recall-planner-llm.d.ts +1 -1
- package/dist/recall-state.d.ts +1 -1
- package/dist/recall-tag-filter.d.ts +1 -1
- package/dist/recall-xray-cli.d.ts +1 -1
- package/dist/recall-xray-cli.js +4 -4
- package/dist/recall-xray-renderer.d.ts +1 -1
- package/dist/recall-xray-renderer.js +3 -3
- package/dist/recall-xray.d.ts +1 -1
- package/dist/recall-xray.js +2 -2
- package/dist/resolve-auth-token.d.ts +1 -1
- package/dist/resume-bundles.js +3 -2
- package/dist/retrieval-agents.d.ts +1 -1
- package/dist/retrieval-tiers.d.ts +1 -1
- package/dist/routing/engine.d.ts +1 -1
- package/dist/routing/store.d.ts +1 -1
- package/dist/schemas.d.ts +10 -10
- package/dist/search/embed-helper.d.ts +1 -1
- package/dist/search/factory.d.ts +1 -1
- package/dist/search/index.d.ts +1 -1
- package/dist/search/lancedb-backend.d.ts +1 -1
- package/dist/search/meilisearch-backend.d.ts +1 -1
- package/dist/search/noop-backend.d.ts +1 -1
- package/dist/search/orama-backend.d.ts +1 -1
- package/dist/search/port.d.ts +1 -1
- package/dist/search/remote-backend.d.ts +1 -1
- package/dist/{semantic-SLAa_prH.d.ts → semantic-DJR8_DMQ.d.ts} +1 -1
- package/dist/{semantic-consolidation-4HkHWgeI.d.ts → semantic-consolidation-FbhPeJjB.d.ts} +1 -1
- package/dist/semantic-consolidation.d.ts +2 -2
- package/dist/semantic-consolidation.js +4 -4
- package/dist/semantic-rule-promotion.js +3 -3
- package/dist/semantic-rule-verifier.d.ts +1 -1
- package/dist/semantic-rule-verifier.js +3 -3
- package/dist/session-observer-bands.d.ts +1 -1
- package/dist/session-observer-state.d.ts +1 -1
- package/dist/shared-context/manager.d.ts +5 -5
- package/dist/signal.d.ts +1 -1
- package/dist/storage.d.ts +19 -1
- package/dist/storage.js +2 -2
- package/dist/summarizer.d.ts +1 -1
- package/dist/summary-snapshot.d.ts +1 -1
- package/dist/temporal-supersession.d.ts +1 -1
- package/dist/temporal-validity.d.ts +1 -1
- package/dist/threading.d.ts +1 -1
- package/dist/tier-migration.d.ts +1 -1
- package/dist/tier-routing.d.ts +1 -1
- package/dist/topics.d.ts +1 -1
- package/dist/transcript.d.ts +1 -1
- package/dist/types-D5VRAI04.d.ts +3134 -0
- package/dist/types.d.ts +3 -2862
- package/dist/types.js +1 -1
- package/dist/utility-runtime.d.ts +1 -1
- package/dist/verified-recall.js +3 -3
- package/package.json +1 -1
- package/src/access-http.ts +167 -0
- package/src/access-mcp.ts +198 -0
- package/src/access-service.ts +65 -0
- package/src/cli.ts +187 -0
- package/src/config.ts +7 -0
- package/src/index.ts +7 -0
- package/src/orchestrator.ts +42 -0
- package/src/storage.ts +106 -0
- package/src/types.ts +5 -0
- package/src/wearables/cleanup.test.ts +134 -0
- package/src/wearables/cleanup.ts +188 -0
- package/src/wearables/cli.test.ts +170 -0
- package/src/wearables/cli.ts +441 -0
- package/src/wearables/config.test.ts +143 -0
- package/src/wearables/config.ts +332 -0
- package/src/wearables/corrections.test.ts +118 -0
- package/src/wearables/corrections.ts +211 -0
- package/src/wearables/day-store.test.ts +143 -0
- package/src/wearables/day-store.ts +238 -0
- package/src/wearables/errors.test.ts +32 -0
- package/src/wearables/errors.ts +29 -0
- package/src/wearables/index.ts +114 -0
- package/src/wearables/memory-gen.test.ts +342 -0
- package/src/wearables/memory-gen.ts +413 -0
- package/src/wearables/pipeline.test.ts +608 -0
- package/src/wearables/pipeline.ts +519 -0
- package/src/wearables/redaction.test.ts +94 -0
- package/src/wearables/redaction.ts +156 -0
- package/src/wearables/registry.test.ts +62 -0
- package/src/wearables/registry.ts +133 -0
- package/src/wearables/service.test.ts +425 -0
- package/src/wearables/service.ts +691 -0
- package/src/wearables/speakers.test.ts +110 -0
- package/src/wearables/speakers.ts +174 -0
- package/src/wearables/storage-io.test.ts +105 -0
- package/src/wearables/sync-state.test.ts +134 -0
- package/src/wearables/sync-state.ts +186 -0
- package/src/wearables/types.ts +285 -0
- package/dist/chunk-4R4KTDIE.js.map +0 -1
- package/dist/chunk-5GOMXHLC.js.map +0 -1
- package/dist/chunk-7TPH6UZL.js.map +0 -1
- package/dist/chunk-FG76RDVI.js.map +0 -1
- package/dist/chunk-I6UCUHLK.js.map +0 -1
- package/dist/chunk-KQFQ3IS5.js.map +0 -1
- package/dist/chunk-PJGB7XRR.js.map +0 -1
- package/dist/chunk-RKW6QR7W.js.map +0 -1
- /package/dist/{chunk-GYTVOLNX.js.map → chunk-3MNBW7R7.js.map} +0 -0
- /package/dist/{chunk-QFQQFX2H.js.map → chunk-3R2UZV3U.js.map} +0 -0
- /package/dist/{chunk-O4UNM6OR.js.map → chunk-532VCWYW.js.map} +0 -0
- /package/dist/{chunk-2UFQYU5F.js.map → chunk-57QXN2CS.js.map} +0 -0
- /package/dist/{chunk-UGEBPVNI.js.map → chunk-GE7Q7KXP.js.map} +0 -0
- /package/dist/{chunk-GLWW3EJQ.js.map → chunk-KB4MFBF5.js.map} +0 -0
- /package/dist/{chunk-FH3PPO42.js.map → chunk-KVFYTRMV.js.map} +0 -0
- /package/dist/{chunk-BNW5NJJH.js.map → chunk-LQYTQCXM.js.map} +0 -0
- /package/dist/{chunk-AYHXQR53.js.map → chunk-MVQN73GT.js.map} +0 -0
- /package/dist/{chunk-ZZPIJPPD.js.map → chunk-N5RGXWLQ.js.map} +0 -0
- /package/dist/{chunk-R3OQGYOU.js.map → chunk-P2D2MM47.js.map} +0 -0
- /package/dist/{chunk-PSUB67YB.js.map → chunk-PW6GURU3.js.map} +0 -0
- /package/dist/{chunk-W3BKVM64.js.map → chunk-QDV6VAD4.js.map} +0 -0
- /package/dist/{chunk-3QSU4NFF.js.map → chunk-QHXW3LZV.js.map} +0 -0
- /package/dist/{chunk-OZXVGYGZ.js.map → chunk-STDAAGH7.js.map} +0 -0
- /package/dist/{chunk-FMGWXIES.js.map → chunk-TZDSNIRO.js.map} +0 -0
- /package/dist/{chunk-2L54V4ZO.js.map → chunk-UELS6WWF.js.map} +0 -0
- /package/dist/{chunk-BPSGLMQ4.js.map → chunk-YQNADJCT.js.map} +0 -0
|
@@ -11,7 +11,7 @@ import {
|
|
|
11
11
|
} from "./chunk-LMDRGRJ2.js";
|
|
12
12
|
import {
|
|
13
13
|
parseConfig
|
|
14
|
-
} from "./chunk-
|
|
14
|
+
} from "./chunk-KKTXCFD7.js";
|
|
15
15
|
import {
|
|
16
16
|
resolveObjectiveStateStoreDir,
|
|
17
17
|
validateObjectiveStateSnapshot
|
|
@@ -268,4 +268,4 @@ export {
|
|
|
268
268
|
recordResumeBundle,
|
|
269
269
|
getResumeBundleStatus
|
|
270
270
|
};
|
|
271
|
-
//# sourceMappingURL=chunk-
|
|
271
|
+
//# sourceMappingURL=chunk-KVFYTRMV.js.map
|
|
@@ -4,7 +4,7 @@ import {
|
|
|
4
4
|
import {
|
|
5
5
|
compareEntityTimestamps,
|
|
6
6
|
normalizeEntityName
|
|
7
|
-
} from "./chunk-
|
|
7
|
+
} from "./chunk-UGHUNQ74.js";
|
|
8
8
|
import {
|
|
9
9
|
sanitizeMemoryContent
|
|
10
10
|
} from "./chunk-FVQJYWH7.js";
|
|
@@ -677,4 +677,4 @@ export {
|
|
|
677
677
|
entityIndexVersion,
|
|
678
678
|
entityRecentTranscriptLookbackHours
|
|
679
679
|
};
|
|
680
|
-
//# sourceMappingURL=chunk-
|
|
680
|
+
//# sourceMappingURL=chunk-LQYTQCXM.js.map
|
|
@@ -4,7 +4,7 @@ import {
|
|
|
4
4
|
import {
|
|
5
5
|
ALL_CATEGORY_DIRS,
|
|
6
6
|
NamespaceStorageRouter
|
|
7
|
-
} from "./chunk-
|
|
7
|
+
} from "./chunk-QDV6VAD4.js";
|
|
8
8
|
import {
|
|
9
9
|
namespaceIdentityFromToken,
|
|
10
10
|
namespaceIdentityToken
|
|
@@ -202,4 +202,4 @@ export {
|
|
|
202
202
|
verifyNamespaces,
|
|
203
203
|
runNamespaceMigration
|
|
204
204
|
};
|
|
205
|
-
//# sourceMappingURL=chunk-
|
|
205
|
+
//# sourceMappingURL=chunk-MVQN73GT.js.map
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import {
|
|
2
2
|
StorageManager
|
|
3
|
-
} from "./chunk-
|
|
3
|
+
} from "./chunk-UGHUNQ74.js";
|
|
4
4
|
|
|
5
5
|
// src/semantic-rule-promotion.ts
|
|
6
6
|
import { createHash, randomUUID } from "crypto";
|
|
@@ -529,4 +529,4 @@ export {
|
|
|
529
529
|
setSemanticRulePromotionTestHooks,
|
|
530
530
|
promoteSemanticRuleFromMemory
|
|
531
531
|
};
|
|
532
|
-
//# sourceMappingURL=chunk-
|
|
532
|
+
//# sourceMappingURL=chunk-N5RGXWLQ.js.map
|
|
@@ -0,0 +1,213 @@
|
|
|
1
|
+
// src/wearables/corrections.ts
|
|
2
|
+
import { promises as fsPromises } from "fs";
|
|
3
|
+
import * as path from "path";
|
|
4
|
+
var MAX_PATTERN_LENGTH = 256;
|
|
5
|
+
function escapeRegExp(value) {
|
|
6
|
+
return value.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
|
|
7
|
+
}
|
|
8
|
+
function compileCorrectionRule(rule, label) {
|
|
9
|
+
if (typeof rule.match !== "string" || rule.match.length === 0) {
|
|
10
|
+
throw new Error(`${label}: match must be a non-empty string`);
|
|
11
|
+
}
|
|
12
|
+
if (rule.match.length > MAX_PATTERN_LENGTH) {
|
|
13
|
+
throw new Error(
|
|
14
|
+
`${label}: match exceeds ${MAX_PATTERN_LENGTH} characters \u2014 correction patterns must stay short`
|
|
15
|
+
);
|
|
16
|
+
}
|
|
17
|
+
if (typeof rule.replace !== "string") {
|
|
18
|
+
throw new Error(`${label}: replace must be a string`);
|
|
19
|
+
}
|
|
20
|
+
const flags = rule.caseInsensitive === false ? "g" : "gi";
|
|
21
|
+
let pattern;
|
|
22
|
+
if (rule.regex === true) {
|
|
23
|
+
try {
|
|
24
|
+
pattern = new RegExp(rule.match, flags);
|
|
25
|
+
} catch (err) {
|
|
26
|
+
throw new Error(
|
|
27
|
+
`${label}: match is not a valid regular expression: ${err instanceof Error ? err.message : String(err)}`
|
|
28
|
+
);
|
|
29
|
+
}
|
|
30
|
+
} else {
|
|
31
|
+
const escaped = escapeRegExp(rule.match);
|
|
32
|
+
const leading = /^[\p{L}\p{N}_]/u.test(rule.match) ? "\\b" : "";
|
|
33
|
+
const trailing = /[\p{L}\p{N}_]$/u.test(rule.match) ? "\\b" : "";
|
|
34
|
+
pattern = new RegExp(`${leading}${escaped}${trailing}`, flags);
|
|
35
|
+
}
|
|
36
|
+
if (pattern.test("")) {
|
|
37
|
+
throw new Error(
|
|
38
|
+
`${label}: pattern matches the empty string and would corrupt every transcript`
|
|
39
|
+
);
|
|
40
|
+
}
|
|
41
|
+
pattern.lastIndex = 0;
|
|
42
|
+
return { rule, pattern };
|
|
43
|
+
}
|
|
44
|
+
function compileCorrectionRules(rules, labelPrefix) {
|
|
45
|
+
return rules.map(
|
|
46
|
+
(rule, index) => compileCorrectionRule(rule, `${labelPrefix}[${index}]`)
|
|
47
|
+
);
|
|
48
|
+
}
|
|
49
|
+
function applyCorrections(text, rules, sourceId) {
|
|
50
|
+
let applied = 0;
|
|
51
|
+
let result = text;
|
|
52
|
+
for (const { rule, pattern } of rules) {
|
|
53
|
+
if (Array.isArray(rule.sources) && rule.sources.length > 0 && !rule.sources.includes(sourceId)) {
|
|
54
|
+
continue;
|
|
55
|
+
}
|
|
56
|
+
pattern.lastIndex = 0;
|
|
57
|
+
result = result.replace(pattern, () => {
|
|
58
|
+
applied += 1;
|
|
59
|
+
return rule.replace;
|
|
60
|
+
});
|
|
61
|
+
}
|
|
62
|
+
return { text: result, applied };
|
|
63
|
+
}
|
|
64
|
+
function correctionsFilePath(memoryDir) {
|
|
65
|
+
return path.join(memoryDir, "state", "wearables", "corrections.json");
|
|
66
|
+
}
|
|
67
|
+
async function loadCorrectionsFile(memoryDir) {
|
|
68
|
+
const filePath = correctionsFilePath(memoryDir);
|
|
69
|
+
let raw;
|
|
70
|
+
try {
|
|
71
|
+
raw = await fsPromises.readFile(filePath, "utf-8");
|
|
72
|
+
} catch (err) {
|
|
73
|
+
if (err.code === "ENOENT") return [];
|
|
74
|
+
throw err;
|
|
75
|
+
}
|
|
76
|
+
let parsed;
|
|
77
|
+
try {
|
|
78
|
+
parsed = JSON.parse(raw);
|
|
79
|
+
} catch (err) {
|
|
80
|
+
throw new Error(
|
|
81
|
+
`wearables corrections file is not valid JSON (state/wearables/corrections.json): ${err instanceof Error ? err.message : String(err)}`
|
|
82
|
+
);
|
|
83
|
+
}
|
|
84
|
+
if (typeof parsed !== "object" || parsed === null || Array.isArray(parsed) || !Array.isArray(parsed.rules)) {
|
|
85
|
+
throw new Error(
|
|
86
|
+
'wearables corrections file has an unexpected shape (state/wearables/corrections.json); expected {"version":1,"rules":[...]}'
|
|
87
|
+
);
|
|
88
|
+
}
|
|
89
|
+
const rules = parsed.rules;
|
|
90
|
+
compileCorrectionRules(rules, "state corrections");
|
|
91
|
+
return rules;
|
|
92
|
+
}
|
|
93
|
+
async function saveCorrectionsFile(memoryDir, rules) {
|
|
94
|
+
compileCorrectionRules(rules, "state corrections");
|
|
95
|
+
const filePath = correctionsFilePath(memoryDir);
|
|
96
|
+
await fsPromises.mkdir(path.dirname(filePath), { recursive: true });
|
|
97
|
+
const payload = { version: 1, rules };
|
|
98
|
+
const tmpPath = `${filePath}.tmp-${process.pid}-${Date.now().toString(36)}`;
|
|
99
|
+
await fsPromises.writeFile(
|
|
100
|
+
tmpPath,
|
|
101
|
+
`${JSON.stringify(payload, null, 2)}
|
|
102
|
+
`,
|
|
103
|
+
"utf-8"
|
|
104
|
+
);
|
|
105
|
+
try {
|
|
106
|
+
await fsPromises.rename(tmpPath, filePath);
|
|
107
|
+
} catch (err) {
|
|
108
|
+
await fsPromises.unlink(tmpPath).catch(() => void 0);
|
|
109
|
+
throw err;
|
|
110
|
+
}
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
// src/wearables/redaction.ts
|
|
114
|
+
var REDACTION_PLACEHOLDER = "[redacted]";
|
|
115
|
+
var BUILT_IN_PATTERNS = [
|
|
116
|
+
/\b\d{3}-\d{2}-\d{4}\b/g,
|
|
117
|
+
// Starts and ENDS on a digit so a trailing separator is never
|
|
118
|
+
// consumed (replacing it would glue the placeholder to the next word).
|
|
119
|
+
/\b\d(?:[ -]?\d){12,18}\b/g
|
|
120
|
+
];
|
|
121
|
+
var CARD_MIN_DIGITS = 13;
|
|
122
|
+
function redactText(text, userPatterns) {
|
|
123
|
+
let redactions = 0;
|
|
124
|
+
let result = text;
|
|
125
|
+
result = result.replace(BUILT_IN_PATTERNS[0], () => {
|
|
126
|
+
redactions += 1;
|
|
127
|
+
return REDACTION_PLACEHOLDER;
|
|
128
|
+
});
|
|
129
|
+
result = result.replace(BUILT_IN_PATTERNS[1], (match) => {
|
|
130
|
+
const digits = match.replace(/\D/g, "");
|
|
131
|
+
if (digits.length < CARD_MIN_DIGITS || digits.length > 19) {
|
|
132
|
+
return match;
|
|
133
|
+
}
|
|
134
|
+
redactions += 1;
|
|
135
|
+
return REDACTION_PLACEHOLDER;
|
|
136
|
+
});
|
|
137
|
+
for (const pattern of userPatterns) {
|
|
138
|
+
result = result.replace(pattern, () => {
|
|
139
|
+
redactions += 1;
|
|
140
|
+
return REDACTION_PLACEHOLDER;
|
|
141
|
+
});
|
|
142
|
+
}
|
|
143
|
+
return { text: result, redactions };
|
|
144
|
+
}
|
|
145
|
+
function compileRedactionPatterns(patterns) {
|
|
146
|
+
return patterns.map((pattern, index) => {
|
|
147
|
+
if (typeof pattern !== "string" || pattern.trim().length === 0) {
|
|
148
|
+
throw new Error(
|
|
149
|
+
`wearables.redactionPatterns[${index}] must be a non-empty string`
|
|
150
|
+
);
|
|
151
|
+
}
|
|
152
|
+
if (pattern.length > 256) {
|
|
153
|
+
throw new Error(
|
|
154
|
+
`wearables.redactionPatterns[${index}] exceeds 256 characters \u2014 redaction patterns must stay short`
|
|
155
|
+
);
|
|
156
|
+
}
|
|
157
|
+
try {
|
|
158
|
+
return new RegExp(pattern, "gi");
|
|
159
|
+
} catch (err) {
|
|
160
|
+
throw new Error(
|
|
161
|
+
`wearables.redactionPatterns[${index}] is not a valid regular expression: ${err instanceof Error ? err.message : String(err)}`
|
|
162
|
+
);
|
|
163
|
+
}
|
|
164
|
+
});
|
|
165
|
+
}
|
|
166
|
+
var OFF_THE_RECORD = /\boff\s+the\s+record\b/i;
|
|
167
|
+
var BACK_ON_THE_RECORD = /\b(?:back\s+)?on\s+the\s+record\b/i;
|
|
168
|
+
function applyOffTheRecord(conversation) {
|
|
169
|
+
let offRecord = false;
|
|
170
|
+
let droppedSegments = 0;
|
|
171
|
+
const segments = [];
|
|
172
|
+
for (const segment of conversation.segments) {
|
|
173
|
+
if (!offRecord && OFF_THE_RECORD.test(segment.text)) {
|
|
174
|
+
offRecord = true;
|
|
175
|
+
segments.push({
|
|
176
|
+
...segment,
|
|
177
|
+
text: "[off the record \u2014 segment elided]"
|
|
178
|
+
});
|
|
179
|
+
continue;
|
|
180
|
+
}
|
|
181
|
+
if (offRecord) {
|
|
182
|
+
if (BACK_ON_THE_RECORD.test(segment.text)) {
|
|
183
|
+
offRecord = false;
|
|
184
|
+
segments.push({
|
|
185
|
+
...segment,
|
|
186
|
+
text: "[back on the record]"
|
|
187
|
+
});
|
|
188
|
+
} else {
|
|
189
|
+
droppedSegments += 1;
|
|
190
|
+
}
|
|
191
|
+
continue;
|
|
192
|
+
}
|
|
193
|
+
segments.push(segment);
|
|
194
|
+
}
|
|
195
|
+
return {
|
|
196
|
+
conversation: { ...conversation, segments },
|
|
197
|
+
droppedSegments
|
|
198
|
+
};
|
|
199
|
+
}
|
|
200
|
+
|
|
201
|
+
export {
|
|
202
|
+
compileCorrectionRule,
|
|
203
|
+
compileCorrectionRules,
|
|
204
|
+
applyCorrections,
|
|
205
|
+
correctionsFilePath,
|
|
206
|
+
loadCorrectionsFile,
|
|
207
|
+
saveCorrectionsFile,
|
|
208
|
+
REDACTION_PLACEHOLDER,
|
|
209
|
+
redactText,
|
|
210
|
+
compileRedactionPatterns,
|
|
211
|
+
applyOffTheRecord
|
|
212
|
+
};
|
|
213
|
+
//# sourceMappingURL=chunk-NDAH7BJ5.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"sources":["../src/wearables/corrections.ts","../src/wearables/redaction.ts"],"sourcesContent":["/**\n * Wearable transcript corrections — user-specific replacement rules.\n *\n * ASR engines consistently mishear the same proper nouns for the same\n * person (\"remnick\" for \"Remnic\", a colleague's name, product jargon).\n * Rules come from two places, merged at sync time:\n *\n * 1. `wearables.corrections` in plugin config (declarative, versioned\n * with the operator's config).\n * 2. A CLI-managed rules file at `state/wearables/corrections.json`\n * (added interactively via `remnic wearables corrections add`).\n *\n * Literal rules are regex-escaped before compilation and replacements\n * are applied via a function (never a replacement string) so `$` in\n * either side can't corrupt output.\n */\n\nimport { promises as fsPromises } from \"node:fs\";\nimport * as path from \"node:path\";\n\nimport type { WearableCorrectionRule } from \"./types.js\";\n\nexport interface CompiledCorrectionRule {\n rule: WearableCorrectionRule;\n pattern: RegExp;\n}\n\nexport interface CorrectionApplication {\n text: string;\n applied: number;\n}\n\n/** Hard cap on rule pattern length (bounds hostile/pathological regexes). */\nconst MAX_PATTERN_LENGTH = 256;\n\nfunction escapeRegExp(value: string): string {\n return value.replace(/[.*+?^${}()|[\\]\\\\]/g, \"\\\\$&\");\n}\n\n/**\n * Validate and compile a correction rule. Throws a descriptive error on\n * invalid input (empty match, regex that doesn't compile, regex that\n * matches the empty string) — callers surface this at config parse or\n * CLI time rather than skipping the rule silently.\n */\nexport function compileCorrectionRule(\n rule: WearableCorrectionRule,\n label: string,\n): CompiledCorrectionRule {\n if (typeof rule.match !== \"string\" || rule.match.length === 0) {\n throw new Error(`${label}: match must be a non-empty string`);\n }\n if (rule.match.length > MAX_PATTERN_LENGTH) {\n throw new Error(\n `${label}: match exceeds ${MAX_PATTERN_LENGTH} characters — correction patterns must stay short`,\n );\n }\n if (typeof rule.replace !== \"string\") {\n throw new Error(`${label}: replace must be a string`);\n }\n const flags = rule.caseInsensitive === false ? \"g\" : \"gi\";\n let pattern: RegExp;\n if (rule.regex === true) {\n try {\n // Operator-supplied regexes are the documented feature here\n // (rules live in the operator's own config / state file, never in\n // request input); the length cap above bounds pathological\n // patterns. CodeQL js/regex-injection is dismissed by design for\n // this site.\n pattern = new RegExp(rule.match, flags);\n } catch (err) {\n throw new Error(\n `${label}: match is not a valid regular expression: ${\n err instanceof Error ? err.message : String(err)\n }`,\n );\n }\n } else {\n // Literal rules match on word boundaries when both edges of the\n // match are word characters, so \"remnick\" doesn't fire inside\n // \"remnickson\" unless the user opts into regex mode.\n const escaped = escapeRegExp(rule.match);\n const leading = /^[\\p{L}\\p{N}_]/u.test(rule.match) ? \"\\\\b\" : \"\";\n const trailing = /[\\p{L}\\p{N}_]$/u.test(rule.match) ? \"\\\\b\" : \"\";\n pattern = new RegExp(`${leading}${escaped}${trailing}`, flags);\n }\n if (pattern.test(\"\")) {\n throw new Error(\n `${label}: pattern matches the empty string and would corrupt every transcript`,\n );\n }\n pattern.lastIndex = 0;\n return { rule, pattern };\n}\n\n/** Compile a rule list, labeling errors with their index. */\nexport function compileCorrectionRules(\n rules: WearableCorrectionRule[],\n labelPrefix: string,\n): CompiledCorrectionRule[] {\n return rules.map((rule, index) =>\n compileCorrectionRule(rule, `${labelPrefix}[${index}]`),\n );\n}\n\n/** Apply every applicable rule to a piece of transcript text. */\nexport function applyCorrections(\n text: string,\n rules: CompiledCorrectionRule[],\n sourceId: string,\n): CorrectionApplication {\n let applied = 0;\n let result = text;\n for (const { rule, pattern } of rules) {\n if (\n Array.isArray(rule.sources) &&\n rule.sources.length > 0 &&\n !rule.sources.includes(sourceId)\n ) {\n continue;\n }\n pattern.lastIndex = 0;\n result = result.replace(pattern, () => {\n applied += 1;\n // Replacement via function: `$` in rule.replace stays literal.\n return rule.replace;\n });\n }\n return { text: result, applied };\n}\n\n// ---------------------------------------------------------------------------\n// CLI-managed rules file\n// ---------------------------------------------------------------------------\n\ninterface CorrectionsFileShape {\n version: 1;\n rules: WearableCorrectionRule[];\n}\n\nexport function correctionsFilePath(memoryDir: string): string {\n return path.join(memoryDir, \"state\", \"wearables\", \"corrections.json\");\n}\n\n/**\n * Load CLI-managed correction rules. A missing file means no rules; a\n * malformed file throws (operators should know their corrections are\n * not being applied rather than silently losing them).\n */\nexport async function loadCorrectionsFile(\n memoryDir: string,\n): Promise<WearableCorrectionRule[]> {\n const filePath = correctionsFilePath(memoryDir);\n let raw: string;\n try {\n raw = await fsPromises.readFile(filePath, \"utf-8\");\n } catch (err) {\n if ((err as NodeJS.ErrnoException).code === \"ENOENT\") return [];\n throw err;\n }\n let parsed: unknown;\n try {\n parsed = JSON.parse(raw);\n } catch (err) {\n throw new Error(\n `wearables corrections file is not valid JSON (state/wearables/corrections.json): ${\n err instanceof Error ? err.message : String(err)\n }`,\n );\n }\n if (\n typeof parsed !== \"object\" ||\n parsed === null ||\n Array.isArray(parsed) ||\n !Array.isArray((parsed as CorrectionsFileShape).rules)\n ) {\n throw new Error(\n 'wearables corrections file has an unexpected shape (state/wearables/corrections.json); expected {\"version\":1,\"rules\":[...]}',\n );\n }\n const rules = (parsed as CorrectionsFileShape).rules;\n // Validate every persisted rule up front so a hand-edited bad rule\n // fails at load with its index, not mid-sync.\n compileCorrectionRules(rules, \"state corrections\");\n return rules;\n}\n\n/** Persist CLI-managed rules atomically (temp file + rename). */\nexport async function saveCorrectionsFile(\n memoryDir: string,\n rules: WearableCorrectionRule[],\n): Promise<void> {\n compileCorrectionRules(rules, \"state corrections\");\n const filePath = correctionsFilePath(memoryDir);\n await fsPromises.mkdir(path.dirname(filePath), { recursive: true });\n const payload: CorrectionsFileShape = { version: 1, rules };\n const tmpPath = `${filePath}.tmp-${process.pid}-${Date.now().toString(36)}`;\n await fsPromises.writeFile(\n tmpPath,\n `${JSON.stringify(payload, null, 2)}\\n`,\n \"utf-8\",\n );\n try {\n await fsPromises.rename(tmpPath, filePath);\n } catch (err) {\n // Clean up the temp file on rename failure; the original (if any)\n // is untouched.\n await fsPromises.unlink(tmpPath).catch(() => undefined);\n throw err;\n }\n}\n","/**\n * Wearable transcript redaction — privacy guard applied before any\n * transcript text is persisted or fed to extraction.\n *\n * Always-on recorders capture things nobody intended to store: card\n * numbers read aloud, SSNs dictated to a pharmacy line. Built-in\n * patterns cover the unambiguous, high-sensitivity cases; users can add\n * their own regexes via `wearables.redactionPatterns` (validated at\n * config parse — invalid patterns are rejected loudly, never ignored).\n *\n * All built-in patterns are simple linear scans (no nested quantifiers)\n * to stay safely outside polynomial-ReDoS territory.\n */\n\nimport type { WearableConversation } from \"./types.js\";\n\nexport const REDACTION_PLACEHOLDER = \"[redacted]\";\n\n/**\n * Built-in patterns. Conservative by design — false positives erase\n * real transcript content, so each pattern targets formats that are\n * near-certain PII:\n * - US SSN with separators (123-45-6789). Bare 9-digit runs are NOT\n * matched (too many false positives: ids, tracking numbers).\n * - Payment-card-like runs: 13–19 digits in groups separated by\n * spaces/dashes (4111 1111 1111 1111) or contiguous 15–16 digits.\n */\nconst BUILT_IN_PATTERNS: RegExp[] = [\n /\\b\\d{3}-\\d{2}-\\d{4}\\b/g,\n // Starts and ENDS on a digit so a trailing separator is never\n // consumed (replacing it would glue the placeholder to the next word).\n /\\b\\d(?:[ -]?\\d){12,18}\\b/g,\n];\n\n/** Minimum digit count before a digit-run is treated as a card number. */\nconst CARD_MIN_DIGITS = 13;\n\nexport interface RedactionResult {\n text: string;\n redactions: number;\n}\n\nexport function redactText(\n text: string,\n userPatterns: RegExp[],\n): RedactionResult {\n let redactions = 0;\n let result = text;\n\n // SSN pattern first (more specific than the digit-run pattern).\n result = result.replace(BUILT_IN_PATTERNS[0], () => {\n redactions += 1;\n return REDACTION_PLACEHOLDER;\n });\n\n // Digit-run pattern with a post-match digit-count check so short\n // grouped numbers (\"call 555 0125 today\") survive.\n result = result.replace(BUILT_IN_PATTERNS[1], (match) => {\n const digits = match.replace(/\\D/g, \"\");\n if (digits.length < CARD_MIN_DIGITS || digits.length > 19) {\n return match;\n }\n redactions += 1;\n return REDACTION_PLACEHOLDER;\n });\n\n for (const pattern of userPatterns) {\n result = result.replace(pattern, () => {\n redactions += 1;\n return REDACTION_PLACEHOLDER;\n });\n }\n\n return { text: result, redactions };\n}\n\n/**\n * Compile user-supplied redaction patterns. Throws with a descriptive\n * message on the first invalid pattern — config parsing surfaces this\n * to the operator instead of silently skipping the rule.\n */\nexport function compileRedactionPatterns(patterns: string[]): RegExp[] {\n return patterns.map((pattern, index) => {\n if (typeof pattern !== \"string\" || pattern.trim().length === 0) {\n throw new Error(\n `wearables.redactionPatterns[${index}] must be a non-empty string`,\n );\n }\n if (pattern.length > 256) {\n throw new Error(\n `wearables.redactionPatterns[${index}] exceeds 256 characters — redaction patterns must stay short`,\n );\n }\n try {\n // Operator-supplied regexes from the operator's own config —\n // length-capped above; never request input.\n return new RegExp(pattern, \"gi\");\n } catch (err) {\n throw new Error(\n `wearables.redactionPatterns[${index}] is not a valid regular expression: ${\n err instanceof Error ? err.message : String(err)\n }`,\n );\n }\n });\n}\n\nconst OFF_THE_RECORD = /\\boff\\s+the\\s+record\\b/i;\nconst BACK_ON_THE_RECORD = /\\b(?:back\\s+)?on\\s+the\\s+record\\b/i;\n\nexport interface OffTheRecordResult {\n conversation: WearableConversation;\n droppedSegments: number;\n}\n\n/**\n * Drop segments between a spoken \"off the record\" marker and the next\n * \"(back) on the record\" marker (or conversation end). The marker\n * segments themselves are kept, with the off-record span replaced by a\n * visible placeholder so the transcript shows that content was elided\n * by request rather than lost.\n */\nexport function applyOffTheRecord(\n conversation: WearableConversation,\n): OffTheRecordResult {\n let offRecord = false;\n let droppedSegments = 0;\n const segments = [];\n for (const segment of conversation.segments) {\n if (!offRecord && OFF_THE_RECORD.test(segment.text)) {\n offRecord = true;\n segments.push({\n ...segment,\n text: \"[off the record — segment elided]\",\n });\n continue;\n }\n if (offRecord) {\n if (BACK_ON_THE_RECORD.test(segment.text)) {\n offRecord = false;\n segments.push({\n ...segment,\n text: \"[back on the record]\",\n });\n } else {\n droppedSegments += 1;\n }\n continue;\n }\n segments.push(segment);\n }\n return {\n conversation: { ...conversation, segments },\n droppedSegments,\n };\n}\n"],"mappings":";AAiBA,SAAS,YAAY,kBAAkB;AACvC,YAAY,UAAU;AAetB,IAAM,qBAAqB;AAE3B,SAAS,aAAa,OAAuB;AAC3C,SAAO,MAAM,QAAQ,uBAAuB,MAAM;AACpD;AAQO,SAAS,sBACd,MACA,OACwB;AACxB,MAAI,OAAO,KAAK,UAAU,YAAY,KAAK,MAAM,WAAW,GAAG;AAC7D,UAAM,IAAI,MAAM,GAAG,KAAK,oCAAoC;AAAA,EAC9D;AACA,MAAI,KAAK,MAAM,SAAS,oBAAoB;AAC1C,UAAM,IAAI;AAAA,MACR,GAAG,KAAK,mBAAmB,kBAAkB;AAAA,IAC/C;AAAA,EACF;AACA,MAAI,OAAO,KAAK,YAAY,UAAU;AACpC,UAAM,IAAI,MAAM,GAAG,KAAK,4BAA4B;AAAA,EACtD;AACA,QAAM,QAAQ,KAAK,oBAAoB,QAAQ,MAAM;AACrD,MAAI;AACJ,MAAI,KAAK,UAAU,MAAM;AACvB,QAAI;AAMF,gBAAU,IAAI,OAAO,KAAK,OAAO,KAAK;AAAA,IACxC,SAAS,KAAK;AACZ,YAAM,IAAI;AAAA,QACR,GAAG,KAAK,8CACN,eAAe,QAAQ,IAAI,UAAU,OAAO,GAAG,CACjD;AAAA,MACF;AAAA,IACF;AAAA,EACF,OAAO;AAIL,UAAM,UAAU,aAAa,KAAK,KAAK;AACvC,UAAM,UAAU,kBAAkB,KAAK,KAAK,KAAK,IAAI,QAAQ;AAC7D,UAAM,WAAW,kBAAkB,KAAK,KAAK,KAAK,IAAI,QAAQ;AAC9D,cAAU,IAAI,OAAO,GAAG,OAAO,GAAG,OAAO,GAAG,QAAQ,IAAI,KAAK;AAAA,EAC/D;AACA,MAAI,QAAQ,KAAK,EAAE,GAAG;AACpB,UAAM,IAAI;AAAA,MACR,GAAG,KAAK;AAAA,IACV;AAAA,EACF;AACA,UAAQ,YAAY;AACpB,SAAO,EAAE,MAAM,QAAQ;AACzB;AAGO,SAAS,uBACd,OACA,aAC0B;AAC1B,SAAO,MAAM;AAAA,IAAI,CAAC,MAAM,UACtB,sBAAsB,MAAM,GAAG,WAAW,IAAI,KAAK,GAAG;AAAA,EACxD;AACF;AAGO,SAAS,iBACd,MACA,OACA,UACuB;AACvB,MAAI,UAAU;AACd,MAAI,SAAS;AACb,aAAW,EAAE,MAAM,QAAQ,KAAK,OAAO;AACrC,QACE,MAAM,QAAQ,KAAK,OAAO,KAC1B,KAAK,QAAQ,SAAS,KACtB,CAAC,KAAK,QAAQ,SAAS,QAAQ,GAC/B;AACA;AAAA,IACF;AACA,YAAQ,YAAY;AACpB,aAAS,OAAO,QAAQ,SAAS,MAAM;AACrC,iBAAW;AAEX,aAAO,KAAK;AAAA,IACd,CAAC;AAAA,EACH;AACA,SAAO,EAAE,MAAM,QAAQ,QAAQ;AACjC;AAWO,SAAS,oBAAoB,WAA2B;AAC7D,SAAY,UAAK,WAAW,SAAS,aAAa,kBAAkB;AACtE;AAOA,eAAsB,oBACpB,WACmC;AACnC,QAAM,WAAW,oBAAoB,SAAS;AAC9C,MAAI;AACJ,MAAI;AACF,UAAM,MAAM,WAAW,SAAS,UAAU,OAAO;AAAA,EACnD,SAAS,KAAK;AACZ,QAAK,IAA8B,SAAS,SAAU,QAAO,CAAC;AAC9D,UAAM;AAAA,EACR;AACA,MAAI;AACJ,MAAI;AACF,aAAS,KAAK,MAAM,GAAG;AAAA,EACzB,SAAS,KAAK;AACZ,UAAM,IAAI;AAAA,MACR,oFACE,eAAe,QAAQ,IAAI,UAAU,OAAO,GAAG,CACjD;AAAA,IACF;AAAA,EACF;AACA,MACE,OAAO,WAAW,YAClB,WAAW,QACX,MAAM,QAAQ,MAAM,KACpB,CAAC,MAAM,QAAS,OAAgC,KAAK,GACrD;AACA,UAAM,IAAI;AAAA,MACR;AAAA,IACF;AAAA,EACF;AACA,QAAM,QAAS,OAAgC;AAG/C,yBAAuB,OAAO,mBAAmB;AACjD,SAAO;AACT;AAGA,eAAsB,oBACpB,WACA,OACe;AACf,yBAAuB,OAAO,mBAAmB;AACjD,QAAM,WAAW,oBAAoB,SAAS;AAC9C,QAAM,WAAW,MAAW,aAAQ,QAAQ,GAAG,EAAE,WAAW,KAAK,CAAC;AAClE,QAAM,UAAgC,EAAE,SAAS,GAAG,MAAM;AAC1D,QAAM,UAAU,GAAG,QAAQ,QAAQ,QAAQ,GAAG,IAAI,KAAK,IAAI,EAAE,SAAS,EAAE,CAAC;AACzE,QAAM,WAAW;AAAA,IACf;AAAA,IACA,GAAG,KAAK,UAAU,SAAS,MAAM,CAAC,CAAC;AAAA;AAAA,IACnC;AAAA,EACF;AACA,MAAI;AACF,UAAM,WAAW,OAAO,SAAS,QAAQ;AAAA,EAC3C,SAAS,KAAK;AAGZ,UAAM,WAAW,OAAO,OAAO,EAAE,MAAM,MAAM,MAAS;AACtD,UAAM;AAAA,EACR;AACF;;;AClMO,IAAM,wBAAwB;AAWrC,IAAM,oBAA8B;AAAA,EAClC;AAAA;AAAA;AAAA,EAGA;AACF;AAGA,IAAM,kBAAkB;AAOjB,SAAS,WACd,MACA,cACiB;AACjB,MAAI,aAAa;AACjB,MAAI,SAAS;AAGb,WAAS,OAAO,QAAQ,kBAAkB,CAAC,GAAG,MAAM;AAClD,kBAAc;AACd,WAAO;AAAA,EACT,CAAC;AAID,WAAS,OAAO,QAAQ,kBAAkB,CAAC,GAAG,CAAC,UAAU;AACvD,UAAM,SAAS,MAAM,QAAQ,OAAO,EAAE;AACtC,QAAI,OAAO,SAAS,mBAAmB,OAAO,SAAS,IAAI;AACzD,aAAO;AAAA,IACT;AACA,kBAAc;AACd,WAAO;AAAA,EACT,CAAC;AAED,aAAW,WAAW,cAAc;AAClC,aAAS,OAAO,QAAQ,SAAS,MAAM;AACrC,oBAAc;AACd,aAAO;AAAA,IACT,CAAC;AAAA,EACH;AAEA,SAAO,EAAE,MAAM,QAAQ,WAAW;AACpC;AAOO,SAAS,yBAAyB,UAA8B;AACrE,SAAO,SAAS,IAAI,CAAC,SAAS,UAAU;AACtC,QAAI,OAAO,YAAY,YAAY,QAAQ,KAAK,EAAE,WAAW,GAAG;AAC9D,YAAM,IAAI;AAAA,QACR,+BAA+B,KAAK;AAAA,MACtC;AAAA,IACF;AACA,QAAI,QAAQ,SAAS,KAAK;AACxB,YAAM,IAAI;AAAA,QACR,+BAA+B,KAAK;AAAA,MACtC;AAAA,IACF;AACA,QAAI;AAGF,aAAO,IAAI,OAAO,SAAS,IAAI;AAAA,IACjC,SAAS,KAAK;AACZ,YAAM,IAAI;AAAA,QACR,+BAA+B,KAAK,wCAClC,eAAe,QAAQ,IAAI,UAAU,OAAO,GAAG,CACjD;AAAA,MACF;AAAA,IACF;AAAA,EACF,CAAC;AACH;AAEA,IAAM,iBAAiB;AACvB,IAAM,qBAAqB;AAcpB,SAAS,kBACd,cACoB;AACpB,MAAI,YAAY;AAChB,MAAI,kBAAkB;AACtB,QAAM,WAAW,CAAC;AAClB,aAAW,WAAW,aAAa,UAAU;AAC3C,QAAI,CAAC,aAAa,eAAe,KAAK,QAAQ,IAAI,GAAG;AACnD,kBAAY;AACZ,eAAS,KAAK;AAAA,QACZ,GAAG;AAAA,QACH,MAAM;AAAA,MACR,CAAC;AACD;AAAA,IACF;AACA,QAAI,WAAW;AACb,UAAI,mBAAmB,KAAK,QAAQ,IAAI,GAAG;AACzC,oBAAY;AACZ,iBAAS,KAAK;AAAA,UACZ,GAAG;AAAA,UACH,MAAM;AAAA,QACR,CAAC;AAAA,MACH,OAAO;AACL,2BAAmB;AAAA,MACrB;AACA;AAAA,IACF;AACA,aAAS,KAAK,OAAO;AAAA,EACvB;AACA,SAAO;AAAA,IACL,cAAc,EAAE,GAAG,cAAc,SAAS;AAAA,IAC1C;AAAA,EACF;AACF;","names":[]}
|
|
@@ -3,7 +3,7 @@ import {
|
|
|
3
3
|
} from "./chunk-HQ6NIBL6.js";
|
|
4
4
|
import {
|
|
5
5
|
StorageManager
|
|
6
|
-
} from "./chunk-
|
|
6
|
+
} from "./chunk-UGHUNQ74.js";
|
|
7
7
|
import {
|
|
8
8
|
getCachedEpisodeMap,
|
|
9
9
|
setCachedEpisodeMap
|
|
@@ -105,4 +105,4 @@ async function searchVerifiedEpisodes(options) {
|
|
|
105
105
|
export {
|
|
106
106
|
searchVerifiedEpisodes
|
|
107
107
|
};
|
|
108
|
-
//# sourceMappingURL=chunk-
|
|
108
|
+
//# sourceMappingURL=chunk-P2D2MM47.js.map
|
|
@@ -3,7 +3,7 @@ import {
|
|
|
3
3
|
} from "./chunk-SOBJ6NEY.js";
|
|
4
4
|
import {
|
|
5
5
|
summarizeDisclosureTokens
|
|
6
|
-
} from "./chunk-
|
|
6
|
+
} from "./chunk-YQNADJCT.js";
|
|
7
7
|
import {
|
|
8
8
|
summarizeRetrievedMemoryProvenance
|
|
9
9
|
} from "./chunk-AC5LO7IU.js";
|
|
@@ -567,4 +567,4 @@ export {
|
|
|
567
567
|
renderRecallExplain,
|
|
568
568
|
parseRecallExplainFormat
|
|
569
569
|
};
|
|
570
|
-
//# sourceMappingURL=chunk-
|
|
570
|
+
//# sourceMappingURL=chunk-PW6GURU3.js.map
|
|
@@ -4,7 +4,7 @@ import {
|
|
|
4
4
|
} from "./chunk-ZFXCQPNO.js";
|
|
5
5
|
import {
|
|
6
6
|
StorageManager
|
|
7
|
-
} from "./chunk-
|
|
7
|
+
} from "./chunk-UGHUNQ74.js";
|
|
8
8
|
import {
|
|
9
9
|
isSafeRouteNamespace
|
|
10
10
|
} from "./chunk-U3PN77QT.js";
|
|
@@ -161,4 +161,4 @@ export {
|
|
|
161
161
|
getCategoryDir,
|
|
162
162
|
NamespaceStorageRouter
|
|
163
163
|
};
|
|
164
|
-
//# sourceMappingURL=chunk-
|
|
164
|
+
//# sourceMappingURL=chunk-QDV6VAD4.js.map
|
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
import {
|
|
2
2
|
parseXrayFormat
|
|
3
|
-
} from "./chunk-
|
|
3
|
+
} from "./chunk-PW6GURU3.js";
|
|
4
4
|
import {
|
|
5
5
|
RECALL_DISCLOSURE_LEVELS,
|
|
6
6
|
isRecallDisclosure
|
|
7
|
-
} from "./chunk-
|
|
7
|
+
} from "./chunk-FPNQF475.js";
|
|
8
8
|
|
|
9
9
|
// src/recall-xray-cli.ts
|
|
10
10
|
function parseXrayDisclosureFlag(value) {
|
|
@@ -50,4 +50,4 @@ export {
|
|
|
50
50
|
parseXrayBudgetFlag,
|
|
51
51
|
parseXrayCliOptions
|
|
52
52
|
};
|
|
53
|
-
//# sourceMappingURL=chunk-
|
|
53
|
+
//# sourceMappingURL=chunk-QHXW3LZV.js.map
|
|
@@ -11,13 +11,13 @@ import {
|
|
|
11
11
|
} from "./chunk-D24OXEPB.js";
|
|
12
12
|
import {
|
|
13
13
|
EngramAccessInputError
|
|
14
|
-
} from "./chunk-
|
|
14
|
+
} from "./chunk-F3FY3D3S.js";
|
|
15
15
|
import {
|
|
16
16
|
projectTagProjectId
|
|
17
17
|
} from "./chunk-EDQVAMQI.js";
|
|
18
18
|
import {
|
|
19
19
|
validateBriefingFormat
|
|
20
|
-
} from "./chunk-
|
|
20
|
+
} from "./chunk-STDAAGH7.js";
|
|
21
21
|
import {
|
|
22
22
|
expandTildePath
|
|
23
23
|
} from "./chunk-EYIEWJNI.js";
|
|
@@ -136,6 +136,24 @@ function parseMcpRequest(schemaName, args) {
|
|
|
136
136
|
details.length > 0 ? `${validation.error.error}: ${details}` : validation.error.error
|
|
137
137
|
);
|
|
138
138
|
}
|
|
139
|
+
function optionalNonEmptyString(value, label) {
|
|
140
|
+
if (value === void 0 || value === null || value === "") return void 0;
|
|
141
|
+
if (typeof value !== "string") {
|
|
142
|
+
throw new Error(`${label} expects a string; got ${JSON.stringify(value)}`);
|
|
143
|
+
}
|
|
144
|
+
return value;
|
|
145
|
+
}
|
|
146
|
+
function optionalPositiveInteger(value, label) {
|
|
147
|
+
if (value === void 0 || value === null || value === "") return void 0;
|
|
148
|
+
if (typeof value !== "number" && typeof value !== "string") {
|
|
149
|
+
throw new Error(`${label} expects a positive integer; got ${JSON.stringify(value)}`);
|
|
150
|
+
}
|
|
151
|
+
const parsed = typeof value === "number" ? value : Number(value);
|
|
152
|
+
if (!Number.isFinite(parsed) || parsed <= 0 || !Number.isInteger(parsed)) {
|
|
153
|
+
throw new Error(`${label} expects a positive integer; got ${JSON.stringify(value)}`);
|
|
154
|
+
}
|
|
155
|
+
return parsed;
|
|
156
|
+
}
|
|
139
157
|
function getObjectProperties(value) {
|
|
140
158
|
return value && typeof value === "object" && !Array.isArray(value) ? value : void 0;
|
|
141
159
|
}
|
|
@@ -324,6 +342,119 @@ var EngramMcpServer = class {
|
|
|
324
342
|
additionalProperties: false
|
|
325
343
|
}
|
|
326
344
|
},
|
|
345
|
+
{
|
|
346
|
+
name: "engram.wearables_status",
|
|
347
|
+
description: "Status of wearable transcript sources (Limitless / Bee / Omi): configured sources, connector availability, last sync, stored transcript days.",
|
|
348
|
+
inputSchema: {
|
|
349
|
+
type: "object",
|
|
350
|
+
properties: {},
|
|
351
|
+
additionalProperties: false
|
|
352
|
+
}
|
|
353
|
+
},
|
|
354
|
+
{
|
|
355
|
+
name: "engram.wearables_sync",
|
|
356
|
+
description: "Pull, clean, and store wearable transcripts for one source or all enabled sources; optionally creates trust-gated memories per the source's memoryMode.",
|
|
357
|
+
inputSchema: {
|
|
358
|
+
type: "object",
|
|
359
|
+
properties: {
|
|
360
|
+
source: {
|
|
361
|
+
type: "string",
|
|
362
|
+
description: "Source id (e.g. limitless, bee, omi). Omit to sync every enabled source."
|
|
363
|
+
},
|
|
364
|
+
date: {
|
|
365
|
+
type: "string",
|
|
366
|
+
description: "Sync exactly this day (YYYY-MM-DD). Overrides days."
|
|
367
|
+
},
|
|
368
|
+
days: {
|
|
369
|
+
type: "integer",
|
|
370
|
+
minimum: 1,
|
|
371
|
+
maximum: 90,
|
|
372
|
+
description: "Lookback window in days ending today (default 2)."
|
|
373
|
+
},
|
|
374
|
+
forceMemories: {
|
|
375
|
+
type: "boolean",
|
|
376
|
+
description: "Re-run memory extraction even for unchanged days."
|
|
377
|
+
}
|
|
378
|
+
},
|
|
379
|
+
additionalProperties: false
|
|
380
|
+
}
|
|
381
|
+
},
|
|
382
|
+
{
|
|
383
|
+
name: "engram.transcript_day",
|
|
384
|
+
description: "Return the full stored wearable transcript(s) for a day, across all sources or one source, with cross-source overlap hints.",
|
|
385
|
+
inputSchema: {
|
|
386
|
+
type: "object",
|
|
387
|
+
properties: {
|
|
388
|
+
date: {
|
|
389
|
+
type: "string",
|
|
390
|
+
description: "Day to read (YYYY-MM-DD). Required."
|
|
391
|
+
},
|
|
392
|
+
source: {
|
|
393
|
+
type: "string",
|
|
394
|
+
description: "Optional source id to scope to (e.g. limitless)."
|
|
395
|
+
}
|
|
396
|
+
},
|
|
397
|
+
required: ["date"],
|
|
398
|
+
additionalProperties: false
|
|
399
|
+
}
|
|
400
|
+
},
|
|
401
|
+
{
|
|
402
|
+
name: "engram.transcript_search",
|
|
403
|
+
description: "Search stored wearable transcripts. Results carry source + date so callers can pull the full day via engram.transcript_day.",
|
|
404
|
+
inputSchema: {
|
|
405
|
+
type: "object",
|
|
406
|
+
properties: {
|
|
407
|
+
query: {
|
|
408
|
+
type: "string",
|
|
409
|
+
description: "Search query. Required; non-empty."
|
|
410
|
+
},
|
|
411
|
+
source: {
|
|
412
|
+
type: "string",
|
|
413
|
+
description: "Optional source id filter."
|
|
414
|
+
},
|
|
415
|
+
from: {
|
|
416
|
+
type: "string",
|
|
417
|
+
description: "Optional inclusive start date (YYYY-MM-DD)."
|
|
418
|
+
},
|
|
419
|
+
to: {
|
|
420
|
+
type: "string",
|
|
421
|
+
description: "Optional inclusive end date (YYYY-MM-DD)."
|
|
422
|
+
},
|
|
423
|
+
limit: {
|
|
424
|
+
type: "integer",
|
|
425
|
+
minimum: 1,
|
|
426
|
+
maximum: 50,
|
|
427
|
+
description: "Maximum results (default 10)."
|
|
428
|
+
}
|
|
429
|
+
},
|
|
430
|
+
required: ["query"],
|
|
431
|
+
additionalProperties: false
|
|
432
|
+
}
|
|
433
|
+
},
|
|
434
|
+
{
|
|
435
|
+
name: "engram.transcript_memories",
|
|
436
|
+
description: "List memories created from wearable transcripts, filterable by source and/or day. Includes pending_review candidates awaiting approval.",
|
|
437
|
+
inputSchema: {
|
|
438
|
+
type: "object",
|
|
439
|
+
properties: {
|
|
440
|
+
source: {
|
|
441
|
+
type: "string",
|
|
442
|
+
description: "Optional source id filter (e.g. limitless)."
|
|
443
|
+
},
|
|
444
|
+
date: {
|
|
445
|
+
type: "string",
|
|
446
|
+
description: "Optional transcript day filter (YYYY-MM-DD)."
|
|
447
|
+
},
|
|
448
|
+
limit: {
|
|
449
|
+
type: "integer",
|
|
450
|
+
minimum: 1,
|
|
451
|
+
maximum: 200,
|
|
452
|
+
description: "Maximum results (default 50)."
|
|
453
|
+
}
|
|
454
|
+
},
|
|
455
|
+
additionalProperties: false
|
|
456
|
+
}
|
|
457
|
+
},
|
|
327
458
|
{
|
|
328
459
|
name: "engram.action_confidence",
|
|
329
460
|
description: "Advisory ask/draft/act/refuse/escalate decision helper for interruption budgeting. Read-only; never mutates memory.",
|
|
@@ -2101,6 +2232,54 @@ ${body}`;
|
|
|
2101
2232
|
...disclosure !== void 0 ? { disclosure } : {}
|
|
2102
2233
|
});
|
|
2103
2234
|
}
|
|
2235
|
+
case "engram.wearables_status":
|
|
2236
|
+
return this.service.wearablesStatus();
|
|
2237
|
+
case "engram.wearables_sync": {
|
|
2238
|
+
const source = optionalNonEmptyString(args.source, "engram.wearables_sync: source");
|
|
2239
|
+
const date = optionalNonEmptyString(args.date, "engram.wearables_sync: date");
|
|
2240
|
+
const days = optionalPositiveInteger(args.days, "engram.wearables_sync: days");
|
|
2241
|
+
let forceMemories;
|
|
2242
|
+
if (args.forceMemories !== void 0 && args.forceMemories !== null) {
|
|
2243
|
+
if (typeof args.forceMemories !== "boolean") {
|
|
2244
|
+
throw new Error(
|
|
2245
|
+
`engram.wearables_sync: forceMemories expects a boolean; got ${JSON.stringify(args.forceMemories)}`
|
|
2246
|
+
);
|
|
2247
|
+
}
|
|
2248
|
+
forceMemories = args.forceMemories;
|
|
2249
|
+
}
|
|
2250
|
+
return this.service.wearablesSync({ source, date, days, forceMemories });
|
|
2251
|
+
}
|
|
2252
|
+
case "engram.transcript_day": {
|
|
2253
|
+
const date = typeof args.date === "string" ? args.date : "";
|
|
2254
|
+
if (date.trim().length === 0) {
|
|
2255
|
+
throw new Error(
|
|
2256
|
+
"engram.transcript_day: date is required and must be YYYY-MM-DD"
|
|
2257
|
+
);
|
|
2258
|
+
}
|
|
2259
|
+
const source = optionalNonEmptyString(args.source, "engram.transcript_day: source");
|
|
2260
|
+
return this.service.wearablesTranscriptDay({ date, source });
|
|
2261
|
+
}
|
|
2262
|
+
case "engram.transcript_search": {
|
|
2263
|
+
const query = typeof args.query === "string" ? args.query : "";
|
|
2264
|
+
if (query.trim().length === 0) {
|
|
2265
|
+
throw new Error(
|
|
2266
|
+
"engram.transcript_search: query is required and must be non-empty"
|
|
2267
|
+
);
|
|
2268
|
+
}
|
|
2269
|
+
return this.service.wearablesTranscriptSearch({
|
|
2270
|
+
query,
|
|
2271
|
+
source: optionalNonEmptyString(args.source, "engram.transcript_search: source"),
|
|
2272
|
+
from: optionalNonEmptyString(args.from, "engram.transcript_search: from"),
|
|
2273
|
+
to: optionalNonEmptyString(args.to, "engram.transcript_search: to"),
|
|
2274
|
+
limit: optionalPositiveInteger(args.limit, "engram.transcript_search: limit")
|
|
2275
|
+
});
|
|
2276
|
+
}
|
|
2277
|
+
case "engram.transcript_memories":
|
|
2278
|
+
return this.service.wearablesTranscriptMemories({
|
|
2279
|
+
source: optionalNonEmptyString(args.source, "engram.transcript_memories: source"),
|
|
2280
|
+
date: optionalNonEmptyString(args.date, "engram.transcript_memories: date"),
|
|
2281
|
+
limit: optionalPositiveInteger(args.limit, "engram.transcript_memories: limit")
|
|
2282
|
+
});
|
|
2104
2283
|
case "engram.action_confidence": {
|
|
2105
2284
|
const body = parseMcpRequest("actionConfidence", args);
|
|
2106
2285
|
return this.service.actionConfidence(body);
|
|
@@ -2903,4 +3082,4 @@ ${body}`;
|
|
|
2903
3082
|
export {
|
|
2904
3083
|
EngramMcpServer
|
|
2905
3084
|
};
|
|
2906
|
-
//# sourceMappingURL=chunk-
|
|
3085
|
+
//# sourceMappingURL=chunk-SHV5Y2WU.js.map
|