@debriefer/core 2.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (98) hide show
  1. package/README.md +86 -0
  2. package/dist/__tests__/base-source.test.d.ts +2 -0
  3. package/dist/__tests__/base-source.test.d.ts.map +1 -0
  4. package/dist/__tests__/base-source.test.js +333 -0
  5. package/dist/__tests__/base-source.test.js.map +1 -0
  6. package/dist/__tests__/batch-runner.test.d.ts +2 -0
  7. package/dist/__tests__/batch-runner.test.d.ts.map +1 -0
  8. package/dist/__tests__/batch-runner.test.js +217 -0
  9. package/dist/__tests__/batch-runner.test.js.map +1 -0
  10. package/dist/__tests__/cache.test.d.ts +2 -0
  11. package/dist/__tests__/cache.test.d.ts.map +1 -0
  12. package/dist/__tests__/cache.test.js +127 -0
  13. package/dist/__tests__/cache.test.js.map +1 -0
  14. package/dist/__tests__/confidence.test.d.ts +2 -0
  15. package/dist/__tests__/confidence.test.d.ts.map +1 -0
  16. package/dist/__tests__/confidence.test.js +81 -0
  17. package/dist/__tests__/confidence.test.js.map +1 -0
  18. package/dist/__tests__/cost-tracker.test.d.ts +2 -0
  19. package/dist/__tests__/cost-tracker.test.d.ts.map +1 -0
  20. package/dist/__tests__/cost-tracker.test.js +149 -0
  21. package/dist/__tests__/cost-tracker.test.js.map +1 -0
  22. package/dist/__tests__/orchestrator.test.d.ts +2 -0
  23. package/dist/__tests__/orchestrator.test.d.ts.map +1 -0
  24. package/dist/__tests__/orchestrator.test.js +751 -0
  25. package/dist/__tests__/orchestrator.test.js.map +1 -0
  26. package/dist/__tests__/rate-limiter.test.d.ts +2 -0
  27. package/dist/__tests__/rate-limiter.test.d.ts.map +1 -0
  28. package/dist/__tests__/rate-limiter.test.js +83 -0
  29. package/dist/__tests__/rate-limiter.test.js.map +1 -0
  30. package/dist/__tests__/reliability.test.d.ts +2 -0
  31. package/dist/__tests__/reliability.test.d.ts.map +1 -0
  32. package/dist/__tests__/reliability.test.js +207 -0
  33. package/dist/__tests__/reliability.test.js.map +1 -0
  34. package/dist/__tests__/synthesizer.test.d.ts +2 -0
  35. package/dist/__tests__/synthesizer.test.d.ts.map +1 -0
  36. package/dist/__tests__/synthesizer.test.js +50 -0
  37. package/dist/__tests__/synthesizer.test.js.map +1 -0
  38. package/dist/__tests__/telemetry.test.d.ts +2 -0
  39. package/dist/__tests__/telemetry.test.d.ts.map +1 -0
  40. package/dist/__tests__/telemetry.test.js +81 -0
  41. package/dist/__tests__/telemetry.test.js.map +1 -0
  42. package/dist/__tests__/types.test.d.ts +2 -0
  43. package/dist/__tests__/types.test.d.ts.map +1 -0
  44. package/dist/__tests__/types.test.js +708 -0
  45. package/dist/__tests__/types.test.js.map +1 -0
  46. package/dist/base-source.d.ts +91 -0
  47. package/dist/base-source.d.ts.map +1 -0
  48. package/dist/base-source.js +144 -0
  49. package/dist/base-source.js.map +1 -0
  50. package/dist/batch-runner.d.ts +40 -0
  51. package/dist/batch-runner.d.ts.map +1 -0
  52. package/dist/batch-runner.js +65 -0
  53. package/dist/batch-runner.js.map +1 -0
  54. package/dist/cache/in-memory.d.ts +26 -0
  55. package/dist/cache/in-memory.d.ts.map +1 -0
  56. package/dist/cache/in-memory.js +51 -0
  57. package/dist/cache/in-memory.js.map +1 -0
  58. package/dist/confidence.d.ts +13 -0
  59. package/dist/confidence.d.ts.map +1 -0
  60. package/dist/confidence.js +29 -0
  61. package/dist/confidence.js.map +1 -0
  62. package/dist/cost-tracker.d.ts +37 -0
  63. package/dist/cost-tracker.d.ts.map +1 -0
  64. package/dist/cost-tracker.js +62 -0
  65. package/dist/cost-tracker.js.map +1 -0
  66. package/dist/index.d.ts +25 -0
  67. package/dist/index.d.ts.map +1 -0
  68. package/dist/index.js +28 -0
  69. package/dist/index.js.map +1 -0
  70. package/dist/orchestrator.d.ts +92 -0
  71. package/dist/orchestrator.d.ts.map +1 -0
  72. package/dist/orchestrator.js +373 -0
  73. package/dist/orchestrator.js.map +1 -0
  74. package/dist/rate-limiter.d.ts +31 -0
  75. package/dist/rate-limiter.d.ts.map +1 -0
  76. package/dist/rate-limiter.js +79 -0
  77. package/dist/rate-limiter.js.map +1 -0
  78. package/dist/reliability.d.ts +49 -0
  79. package/dist/reliability.d.ts.map +1 -0
  80. package/dist/reliability.js +67 -0
  81. package/dist/reliability.js.map +1 -0
  82. package/dist/synthesizer.d.ts +31 -0
  83. package/dist/synthesizer.d.ts.map +1 -0
  84. package/dist/synthesizer.js +47 -0
  85. package/dist/synthesizer.js.map +1 -0
  86. package/dist/telemetry/console.d.ts +7 -0
  87. package/dist/telemetry/console.d.ts.map +1 -0
  88. package/dist/telemetry/console.js +21 -0
  89. package/dist/telemetry/console.js.map +1 -0
  90. package/dist/telemetry/noop.d.ts +7 -0
  91. package/dist/telemetry/noop.d.ts.map +1 -0
  92. package/dist/telemetry/noop.js +12 -0
  93. package/dist/telemetry/noop.js.map +1 -0
  94. package/dist/types.d.ts +417 -0
  95. package/dist/types.d.ts.map +1 -0
  96. package/dist/types.js +102 -0
  97. package/dist/types.js.map +1 -0
  98. package/package.json +46 -0
@@ -0,0 +1,79 @@
1
+ /**
2
+ * Per-domain async rate limiter shared across all source instances.
3
+ *
4
+ * Uses an async queue per domain to prevent thundering herd — when multiple
5
+ * callers request the same domain simultaneously, they're serialized so each
6
+ * waits the correct delay after the previous one, rather than all sleeping
7
+ * the same amount and firing together.
8
+ *
9
+ * Example: Three sources all query en.wikipedia.org. Without rate limiting,
10
+ * they'd fire simultaneously and risk being blocked. The rate limiter
11
+ * serializes them with configurable delays between requests.
12
+ */
13
+ export class SourceRateLimiter {
14
+ domains = new Map();
15
+ getOrCreateDomain(domain) {
16
+ let state = this.domains.get(domain);
17
+ if (!state) {
18
+ state = {
19
+ lastRequestTime: 0,
20
+ queue: [],
21
+ processing: false,
22
+ totalRequests: 0,
23
+ totalWaitMs: 0,
24
+ };
25
+ this.domains.set(domain, state);
26
+ }
27
+ return state;
28
+ }
29
+ /**
30
+ * Acquire permission to make a request to the given domain.
31
+ * Blocks until minDelayMs has passed since the last request to this domain.
32
+ */
33
+ async acquire(domain, minDelayMs) {
34
+ const state = this.getOrCreateDomain(domain);
35
+ return new Promise((resolve) => {
36
+ state.queue.push({ minDelayMs, resolve });
37
+ this.processQueue(state);
38
+ });
39
+ }
40
+ async processQueue(state) {
41
+ if (state.processing || state.queue.length === 0)
42
+ return;
43
+ state.processing = true;
44
+ try {
45
+ while (state.queue.length > 0) {
46
+ const item = state.queue.shift();
47
+ const now = Date.now();
48
+ const timeSinceLast = now - state.lastRequestTime;
49
+ const waitTime = Math.max(0, item.minDelayMs - timeSinceLast);
50
+ if (waitTime > 0) {
51
+ state.totalWaitMs += waitTime;
52
+ await new Promise((r) => setTimeout(r, waitTime));
53
+ }
54
+ state.lastRequestTime = Date.now();
55
+ state.totalRequests++;
56
+ item.resolve();
57
+ }
58
+ }
59
+ finally {
60
+ state.processing = false;
61
+ }
62
+ }
63
+ /** Get rate limiting stats per domain */
64
+ getStats() {
65
+ const stats = new Map();
66
+ for (const [domain, state] of this.domains) {
67
+ stats.set(domain, {
68
+ totalRequests: state.totalRequests,
69
+ totalWaitMs: state.totalWaitMs,
70
+ });
71
+ }
72
+ return stats;
73
+ }
74
+ /** Reset all state (useful for testing) */
75
+ reset() {
76
+ this.domains.clear();
77
+ }
78
+ }
79
+ //# sourceMappingURL=rate-limiter.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"rate-limiter.js","sourceRoot":"","sources":["../src/rate-limiter.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;GAWG;AAkBH,MAAM,OAAO,iBAAiB;IACpB,OAAO,GAAG,IAAI,GAAG,EAAuB,CAAA;IAExC,iBAAiB,CAAC,MAAc;QACtC,IAAI,KAAK,GAAG,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,MAAM,CAAC,CAAA;QACpC,IAAI,CAAC,KAAK,EAAE,CAAC;YACX,KAAK,GAAG;gBACN,eAAe,EAAE,CAAC;gBAClB,KAAK,EAAE,EAAE;gBACT,UAAU,EAAE,KAAK;gBACjB,aAAa,EAAE,CAAC;gBAChB,WAAW,EAAE,CAAC;aACf,CAAA;YACD,IAAI,CAAC,OAAO,CAAC,GAAG,CAAC,MAAM,EAAE,KAAK,CAAC,CAAA;QACjC,CAAC;QACD,OAAO,KAAK,CAAA;IACd,CAAC;IAED;;;OAGG;IACH,KAAK,CAAC,OAAO,CAAC,MAAc,EAAE,UAAkB;QAC9C,MAAM,KAAK,GAAG,IAAI,CAAC,iBAAiB,CAAC,MAAM,CAAC,CAAA;QAE5C,OAAO,IAAI,OAAO,CAAO,CAAC,OAAO,EAAE,EAAE;YACnC,KAAK,CAAC,KAAK,CAAC,IAAI,CAAC,EAAE,UAAU,EAAE,OAAO,EAAE,CAAC,CAAA;YACzC,IAAI,CAAC,YAAY,CAAC,KAAK,CAAC,CAAA;QAC1B,CAAC,CAAC,CAAA;IACJ,CAAC;IAEO,KAAK,CAAC,YAAY,CAAC,KAAkB;QAC3C,IAAI,KAAK,CAAC,UAAU,IAAI,KAAK,CAAC,KAAK,CAAC,MAAM,KAAK,CAAC;YAAE,OAAM;QACxD,KAAK,CAAC,UAAU,GAAG,IAAI,CAAA;QAEvB,IAAI,CAAC;YACH,OAAO,KAAK,CAAC,KAAK,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;gBAC9B,MAAM,IAAI,GAAG,KAAK,CAAC,KAAK,CAAC,KAAK,EAAG,CAAA;gBACjC,MAAM,GAAG,GAAG,IAAI,CAAC,GAAG,EAAE,CAAA;gBACtB,MAAM,aAAa,GAAG,GAAG,GAAG,KAAK,CAAC,eAAe,CAAA;gBACjD,MAAM,QAAQ,GAAG,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,IAAI,CAAC,UAAU,GAAG,aAAa,CAAC,CAAA;gBAE7D,IAAI,QAAQ,GAAG,CAAC,EAAE,CAAC;oBACjB,KAAK,CAAC,WAAW,IAAI,QAAQ,CAAA;oBAC7B,MAAM,IAAI,OAAO,CAAO,CAAC,CAAC,EAAE,EAAE,CAAC,UAAU,CAAC,CAAC,EAAE,QAAQ,CAAC,CAAC,CAAA;gBACzD,CAAC;gBAED,KAAK,CAAC,eAAe,GAAG,IAAI,CAAC,GAAG,EAAE,CAAA;gBAClC,KAAK,CAAC,aAAa,EAAE,CAAA;gBACrB,IAAI,CAAC,OAAO,EAAE,CAAA;YAChB,CAAC;QACH,CAAC;gBAAS,CAAC;YACT,KAAK,CAAC,UAAU,GAAG,KAAK,CAAA;QAC1B,CAAC;IACH,CAAC;IAED,yCAAyC;IACzC,QAAQ;QACN,MAAM,KAAK,GAAG,IAAI,GAAG,EAA4B,CAAA;QACjD,KAAK,MAAM,CAAC,MAAM,EAAE,KAAK,CAAC,IAAI,IAAI,CAAC,OAAO,EAAE,CAAC;YAC3C,KAAK,CAAC,GAAG,CAAC,MAAM,EAAE;gBAChB,aAAa,EAAE,KAAK,CAAC,aAAa;gBAClC,WAAW,EAAE,KAAK,CAAC,WAAW;aAC/B,CAAC,CAAA;QACJ,CAAC;QACD,OAAO,KAAK,CAAA;IACd,CAAC;IAED,2CAA2C;IAC3C,KAAK;QACH,IAAI,CAAC,OAAO,CAAC,KAAK,EAAE,CAAA;IACtB,CAAC;CACF"}
@@ -0,0 +1,49 @@
1
+ /**
2
+ * Source reliability scoring based on Wikipedia's Reliable Sources Perennial list (RSP).
3
+ * https://en.wikipedia.org/wiki/Wikipedia:Reliable_sources/Perennial_sources
4
+ *
5
+ * RSP is a community-maintained assessment of source trustworthiness for encyclopedic use.
6
+ * We map their ratings to numeric scores (0.0-1.0).
7
+ *
8
+ * This is independent from content confidence:
9
+ * - Reliability = "how trustworthy is this publisher?" (Reuters vs TMZ)
10
+ * - Confidence = "does this specific page answer the question?" (Reuters weather article vs Reuters obituary)
11
+ */
12
+ export declare enum ReliabilityTier {
13
+ /** Wikidata, government databases: community-curated structured data */
14
+ STRUCTURED_DATA = "structured_data",
15
+ /** AP, NYT, BBC, Guardian, Reuters, WaPo: independent, fact-checking reputation */
16
+ TIER_1_NEWS = "tier_1_news",
17
+ /** Variety, Deadline, THR, BFI, Nature, Lancet: reliable within their domain */
18
+ TRADE_PRESS = "trade_press",
19
+ /** Trove, Europeana, Chronicling America: institutional archives */
20
+ ARCHIVAL = "archival",
21
+ /** Wikipedia: secondary compilation, varies by article */
22
+ SECONDARY_COMPILATION = "secondary",
23
+ /** Google, Bing, DDG, Brave, NewsAPI: depends on linked pages */
24
+ SEARCH_AGGREGATOR = "search_aggregator",
25
+ /** Internet Archive: mirrors of other sources */
26
+ ARCHIVE_MIRROR = "archive_mirror",
27
+ /** People Magazine: celebrity magazine, decent for announcements */
28
+ MARGINAL_EDITORIAL = "marginal_editorial",
29
+ /** Legacy.com, FamilySearch: mix of official and user-submitted */
30
+ MARGINAL_MIXED = "marginal_mixed",
31
+ /** Claude, GPT, Gemini: hallucination risk, no original reporting */
32
+ AI_MODEL = "ai_model",
33
+ /** TMZ: fast on announcements, weak on cause details */
34
+ UNRELIABLE_FAST = "unreliable_fast",
35
+ /** Find a Grave: user-generated, no editorial oversight */
36
+ UNRELIABLE_UGC = "unreliable_ugc"
37
+ }
38
+ /**
39
+ * Numeric reliability scores for each tier (0.0-1.0).
40
+ *
41
+ * Higher scores indicate more trustworthy publishers. These are based on
42
+ * Wikipedia's RSP community assessments mapped to our tier system.
43
+ */
44
+ export declare const RELIABILITY_SCORES: Record<ReliabilityTier, number>;
45
+ /** Get the numeric reliability score for a tier */
46
+ export declare function getReliabilityScore(tier: ReliabilityTier): number;
47
+ /** Check if a source meets a minimum reliability threshold */
48
+ export declare function meetsReliabilityThreshold(tier: ReliabilityTier, threshold: number): boolean;
49
+ //# sourceMappingURL=reliability.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"reliability.d.ts","sourceRoot":"","sources":["../src/reliability.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAEH,oBAAY,eAAe;IACzB,wEAAwE;IACxE,eAAe,oBAAoB;IACnC,mFAAmF;IACnF,WAAW,gBAAgB;IAC3B,gFAAgF;IAChF,WAAW,gBAAgB;IAC3B,oEAAoE;IACpE,QAAQ,aAAa;IACrB,0DAA0D;IAC1D,qBAAqB,cAAc;IACnC,iEAAiE;IACjE,iBAAiB,sBAAsB;IACvC,iDAAiD;IACjD,cAAc,mBAAmB;IACjC,oEAAoE;IACpE,kBAAkB,uBAAuB;IACzC,mEAAmE;IACnE,cAAc,mBAAmB;IACjC,qEAAqE;IACrE,QAAQ,aAAa;IACrB,wDAAwD;IACxD,eAAe,oBAAoB;IACnC,2DAA2D;IAC3D,cAAc,mBAAmB;CAClC;AAED;;;;;GAKG;AACH,eAAO,MAAM,kBAAkB,EAAE,MAAM,CAAC,eAAe,EAAE,MAAM,CAa9D,CAAA;AAED,mDAAmD;AACnD,wBAAgB,mBAAmB,CAAC,IAAI,EAAE,eAAe,GAAG,MAAM,CAEjE;AAED,8DAA8D;AAC9D,wBAAgB,yBAAyB,CAAC,IAAI,EAAE,eAAe,EAAE,SAAS,EAAE,MAAM,GAAG,OAAO,CAE3F"}
@@ -0,0 +1,67 @@
1
+ /**
2
+ * Source reliability scoring based on Wikipedia's Reliable Sources Perennial list (RSP).
3
+ * https://en.wikipedia.org/wiki/Wikipedia:Reliable_sources/Perennial_sources
4
+ *
5
+ * RSP is a community-maintained assessment of source trustworthiness for encyclopedic use.
6
+ * We map their ratings to numeric scores (0.0-1.0).
7
+ *
8
+ * This is independent from content confidence:
9
+ * - Reliability = "how trustworthy is this publisher?" (Reuters vs TMZ)
10
+ * - Confidence = "does this specific page answer the question?" (Reuters weather article vs Reuters obituary)
11
+ */
12
+ export var ReliabilityTier;
13
+ (function (ReliabilityTier) {
14
+ /** Wikidata, government databases: community-curated structured data */
15
+ ReliabilityTier["STRUCTURED_DATA"] = "structured_data";
16
+ /** AP, NYT, BBC, Guardian, Reuters, WaPo: independent, fact-checking reputation */
17
+ ReliabilityTier["TIER_1_NEWS"] = "tier_1_news";
18
+ /** Variety, Deadline, THR, BFI, Nature, Lancet: reliable within their domain */
19
+ ReliabilityTier["TRADE_PRESS"] = "trade_press";
20
+ /** Trove, Europeana, Chronicling America: institutional archives */
21
+ ReliabilityTier["ARCHIVAL"] = "archival";
22
+ /** Wikipedia: secondary compilation, varies by article */
23
+ ReliabilityTier["SECONDARY_COMPILATION"] = "secondary";
24
+ /** Google, Bing, DDG, Brave, NewsAPI: depends on linked pages */
25
+ ReliabilityTier["SEARCH_AGGREGATOR"] = "search_aggregator";
26
+ /** Internet Archive: mirrors of other sources */
27
+ ReliabilityTier["ARCHIVE_MIRROR"] = "archive_mirror";
28
+ /** People Magazine: celebrity magazine, decent for announcements */
29
+ ReliabilityTier["MARGINAL_EDITORIAL"] = "marginal_editorial";
30
+ /** Legacy.com, FamilySearch: mix of official and user-submitted */
31
+ ReliabilityTier["MARGINAL_MIXED"] = "marginal_mixed";
32
+ /** Claude, GPT, Gemini: hallucination risk, no original reporting */
33
+ ReliabilityTier["AI_MODEL"] = "ai_model";
34
+ /** TMZ: fast on announcements, weak on cause details */
35
+ ReliabilityTier["UNRELIABLE_FAST"] = "unreliable_fast";
36
+ /** Find a Grave: user-generated, no editorial oversight */
37
+ ReliabilityTier["UNRELIABLE_UGC"] = "unreliable_ugc";
38
+ })(ReliabilityTier || (ReliabilityTier = {}));
39
+ /**
40
+ * Numeric reliability scores for each tier (0.0-1.0).
41
+ *
42
+ * Higher scores indicate more trustworthy publishers. These are based on
43
+ * Wikipedia's RSP community assessments mapped to our tier system.
44
+ */
45
+ export const RELIABILITY_SCORES = {
46
+ [ReliabilityTier.STRUCTURED_DATA]: 1.0,
47
+ [ReliabilityTier.TIER_1_NEWS]: 0.95,
48
+ [ReliabilityTier.TRADE_PRESS]: 0.9,
49
+ [ReliabilityTier.ARCHIVAL]: 0.9,
50
+ [ReliabilityTier.SECONDARY_COMPILATION]: 0.85,
51
+ [ReliabilityTier.SEARCH_AGGREGATOR]: 0.7,
52
+ [ReliabilityTier.ARCHIVE_MIRROR]: 0.7,
53
+ [ReliabilityTier.MARGINAL_EDITORIAL]: 0.65,
54
+ [ReliabilityTier.MARGINAL_MIXED]: 0.6,
55
+ [ReliabilityTier.AI_MODEL]: 0.55,
56
+ [ReliabilityTier.UNRELIABLE_FAST]: 0.5,
57
+ [ReliabilityTier.UNRELIABLE_UGC]: 0.35,
58
+ };
59
+ /** Get the numeric reliability score for a tier */
60
+ export function getReliabilityScore(tier) {
61
+ return RELIABILITY_SCORES[tier];
62
+ }
63
+ /** Check if a source meets a minimum reliability threshold */
64
+ export function meetsReliabilityThreshold(tier, threshold) {
65
+ return RELIABILITY_SCORES[tier] >= threshold;
66
+ }
67
+ //# sourceMappingURL=reliability.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"reliability.js","sourceRoot":"","sources":["../src/reliability.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAEH,MAAM,CAAN,IAAY,eAyBX;AAzBD,WAAY,eAAe;IACzB,wEAAwE;IACxE,sDAAmC,CAAA;IACnC,mFAAmF;IACnF,8CAA2B,CAAA;IAC3B,gFAAgF;IAChF,8CAA2B,CAAA;IAC3B,oEAAoE;IACpE,wCAAqB,CAAA;IACrB,0DAA0D;IAC1D,sDAAmC,CAAA;IACnC,iEAAiE;IACjE,0DAAuC,CAAA;IACvC,iDAAiD;IACjD,oDAAiC,CAAA;IACjC,oEAAoE;IACpE,4DAAyC,CAAA;IACzC,mEAAmE;IACnE,oDAAiC,CAAA;IACjC,qEAAqE;IACrE,wCAAqB,CAAA;IACrB,wDAAwD;IACxD,sDAAmC,CAAA;IACnC,2DAA2D;IAC3D,oDAAiC,CAAA;AACnC,CAAC,EAzBW,eAAe,KAAf,eAAe,QAyB1B;AAED;;;;;GAKG;AACH,MAAM,CAAC,MAAM,kBAAkB,GAAoC;IACjE,CAAC,eAAe,CAAC,eAAe,CAAC,EAAE,GAAG;IACtC,CAAC,eAAe,CAAC,WAAW,CAAC,EAAE,IAAI;IACnC,CAAC,eAAe,CAAC,WAAW,CAAC,EAAE,GAAG;IAClC,CAAC,eAAe,CAAC,QAAQ,CAAC,EAAE,GAAG;IAC/B,CAAC,eAAe,CAAC,qBAAqB,CAAC,EAAE,IAAI;IAC7C,CAAC,eAAe,CAAC,iBAAiB,CAAC,EAAE,GAAG;IACxC,CAAC,eAAe,CAAC,cAAc,CAAC,EAAE,GAAG;IACrC,CAAC,eAAe,CAAC,kBAAkB,CAAC,EAAE,IAAI;IAC1C,CAAC,eAAe,CAAC,cAAc,CAAC,EAAE,GAAG;IACrC,CAAC,eAAe,CAAC,QAAQ,CAAC,EAAE,IAAI;IAChC,CAAC,eAAe,CAAC,eAAe,CAAC,EAAE,GAAG;IACtC,CAAC,eAAe,CAAC,cAAc,CAAC,EAAE,IAAI;CACvC,CAAA;AAED,mDAAmD;AACnD,MAAM,UAAU,mBAAmB,CAAC,IAAqB;IACvD,OAAO,kBAAkB,CAAC,IAAI,CAAC,CAAA;AACjC,CAAC;AAED,8DAA8D;AAC9D,MAAM,UAAU,yBAAyB,CAAC,IAAqB,EAAE,SAAiB;IAChF,OAAO,kBAAkB,CAAC,IAAI,CAAC,IAAI,SAAS,CAAA;AAC9C,CAAC"}
@@ -0,0 +1,31 @@
1
+ /**
2
+ * Synthesis utilities and NoopSynthesizer for the debriefer core.
3
+ *
4
+ * ClaudeSynthesizer has been moved to @debriefer/ai. This module retains
5
+ * NoopSynthesizer (pass-through) and the stripMarkdownCodeFences utility
6
+ * which has no AI dependency.
7
+ */
8
+ import type { ResearchSubject, ScoredFinding, SynthesisResult, Synthesizer } from "./types.js";
9
+ /**
10
+ * Strip markdown code fences from Claude's response.
11
+ *
12
+ * Claude sometimes wraps JSON responses in ```json ... ``` or ``` ... ```
13
+ * code fences despite being told to return raw JSON. This utility removes
14
+ * those wrappings to allow JSON.parse to succeed.
15
+ */
16
+ export declare function stripMarkdownCodeFences(text: string): string;
17
+ /**
18
+ * No-op synthesizer that returns findings as-is without AI processing.
19
+ *
20
+ * Useful for consumers who want raw gathered data without paying for
21
+ * AI synthesis, or for testing/debugging the source gathering pipeline.
22
+ *
23
+ * @typeParam TSubject - The research subject type
24
+ */
25
+ export declare class NoopSynthesizer<TSubject extends ResearchSubject> implements Synthesizer<TSubject, ScoredFinding[]> {
26
+ /**
27
+ * Returns the findings array unchanged with zero cost.
28
+ */
29
+ synthesize(_subject: TSubject, findings: ScoredFinding[]): Promise<SynthesisResult<ScoredFinding[]>>;
30
+ }
31
+ //# sourceMappingURL=synthesizer.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"synthesizer.d.ts","sourceRoot":"","sources":["../src/synthesizer.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAEH,OAAO,KAAK,EAAE,eAAe,EAAE,aAAa,EAAE,eAAe,EAAE,WAAW,EAAE,MAAM,YAAY,CAAA;AAE9F;;;;;;GAMG;AACH,wBAAgB,uBAAuB,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAS5D;AAED;;;;;;;GAOG;AACH,qBAAa,eAAe,CAAC,QAAQ,SAAS,eAAe,CAAE,YAAW,WAAW,CACnF,QAAQ,EACR,aAAa,EAAE,CAChB;IACC;;OAEG;IACG,UAAU,CACd,QAAQ,EAAE,QAAQ,EAClB,QAAQ,EAAE,aAAa,EAAE,GACxB,OAAO,CAAC,eAAe,CAAC,aAAa,EAAE,CAAC,CAAC;CAS7C"}
@@ -0,0 +1,47 @@
1
+ /**
2
+ * Synthesis utilities and NoopSynthesizer for the debriefer core.
3
+ *
4
+ * ClaudeSynthesizer has been moved to @debriefer/ai. This module retains
5
+ * NoopSynthesizer (pass-through) and the stripMarkdownCodeFences utility
6
+ * which has no AI dependency.
7
+ */
8
+ /**
9
+ * Strip markdown code fences from Claude's response.
10
+ *
11
+ * Claude sometimes wraps JSON responses in ```json ... ``` or ``` ... ```
12
+ * code fences despite being told to return raw JSON. This utility removes
13
+ * those wrappings to allow JSON.parse to succeed.
14
+ */
15
+ export function stripMarkdownCodeFences(text) {
16
+ const trimmed = text.trim();
17
+ if (trimmed.startsWith("```")) {
18
+ const lines = trimmed.split("\n");
19
+ // Remove first line (```json or ```) and last line (```)
20
+ const inner = lines.slice(1, lines.length - 1).join("\n");
21
+ return inner.trim();
22
+ }
23
+ return trimmed;
24
+ }
25
+ /**
26
+ * No-op synthesizer that returns findings as-is without AI processing.
27
+ *
28
+ * Useful for consumers who want raw gathered data without paying for
29
+ * AI synthesis, or for testing/debugging the source gathering pipeline.
30
+ *
31
+ * @typeParam TSubject - The research subject type
32
+ */
33
+ export class NoopSynthesizer {
34
+ /**
35
+ * Returns the findings array unchanged with zero cost.
36
+ */
37
+ async synthesize(_subject, findings) {
38
+ return {
39
+ data: findings,
40
+ costUsd: 0,
41
+ inputTokens: 0,
42
+ outputTokens: 0,
43
+ model: "none",
44
+ };
45
+ }
46
+ }
47
+ //# sourceMappingURL=synthesizer.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"synthesizer.js","sourceRoot":"","sources":["../src/synthesizer.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAIH;;;;;;GAMG;AACH,MAAM,UAAU,uBAAuB,CAAC,IAAY;IAClD,MAAM,OAAO,GAAG,IAAI,CAAC,IAAI,EAAE,CAAA;IAC3B,IAAI,OAAO,CAAC,UAAU,CAAC,KAAK,CAAC,EAAE,CAAC;QAC9B,MAAM,KAAK,GAAG,OAAO,CAAC,KAAK,CAAC,IAAI,CAAC,CAAA;QACjC,yDAAyD;QACzD,MAAM,KAAK,GAAG,KAAK,CAAC,KAAK,CAAC,CAAC,EAAE,KAAK,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAA;QACzD,OAAO,KAAK,CAAC,IAAI,EAAE,CAAA;IACrB,CAAC;IACD,OAAO,OAAO,CAAA;AAChB,CAAC;AAED;;;;;;;GAOG;AACH,MAAM,OAAO,eAAe;IAI1B;;OAEG;IACH,KAAK,CAAC,UAAU,CACd,QAAkB,EAClB,QAAyB;QAEzB,OAAO;YACL,IAAI,EAAE,QAAQ;YACd,OAAO,EAAE,CAAC;YACV,WAAW,EAAE,CAAC;YACd,YAAY,EAAE,CAAC;YACf,KAAK,EAAE,MAAM;SACd,CAAA;IACH,CAAC;CACF"}
@@ -0,0 +1,7 @@
1
+ import type { TelemetryProvider, TelemetrySpan } from "../types.js";
2
+ export declare class ConsoleTelemetry implements TelemetryProvider {
3
+ recordEvent(name: string, data: Record<string, unknown>): void;
4
+ startSpan(name: string): TelemetrySpan;
5
+ recordError(error: Error, context?: Record<string, unknown>): void;
6
+ }
7
+ //# sourceMappingURL=console.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"console.d.ts","sourceRoot":"","sources":["../../src/telemetry/console.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,iBAAiB,EAAE,aAAa,EAAE,MAAM,aAAa,CAAA;AAEnE,qBAAa,gBAAiB,YAAW,iBAAiB;IACxD,WAAW,CAAC,IAAI,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,IAAI;IAI9D,SAAS,CAAC,IAAI,EAAE,MAAM,GAAG,aAAa;IAatC,WAAW,CAAC,KAAK,EAAE,KAAK,EAAE,OAAO,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,IAAI;CAGnE"}
@@ -0,0 +1,21 @@
1
+ export class ConsoleTelemetry {
2
+ recordEvent(name, data) {
3
+ console.log(`[debriefer] ${name}`, data);
4
+ }
5
+ startSpan(name) {
6
+ const start = Date.now();
7
+ console.log(`[debriefer] span:start ${name}`);
8
+ return {
9
+ end() {
10
+ console.log(`[debriefer] span:end ${name} (${Date.now() - start}ms)`);
11
+ },
12
+ setAttributes(_attrs) {
13
+ // Console telemetry ignores attributes
14
+ },
15
+ };
16
+ }
17
+ recordError(error, context) {
18
+ console.error(`[debriefer] error: ${error.message}`, context);
19
+ }
20
+ }
21
+ //# sourceMappingURL=console.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"console.js","sourceRoot":"","sources":["../../src/telemetry/console.ts"],"names":[],"mappings":"AAGA,MAAM,OAAO,gBAAgB;IAC3B,WAAW,CAAC,IAAY,EAAE,IAA6B;QACrD,OAAO,CAAC,GAAG,CAAC,eAAe,IAAI,EAAE,EAAE,IAAI,CAAC,CAAA;IAC1C,CAAC;IAED,SAAS,CAAC,IAAY;QACpB,MAAM,KAAK,GAAG,IAAI,CAAC,GAAG,EAAE,CAAA;QACxB,OAAO,CAAC,GAAG,CAAC,0BAA0B,IAAI,EAAE,CAAC,CAAA;QAC7C,OAAO;YACL,GAAG;gBACD,OAAO,CAAC,GAAG,CAAC,wBAAwB,IAAI,KAAK,IAAI,CAAC,GAAG,EAAE,GAAG,KAAK,KAAK,CAAC,CAAA;YACvE,CAAC;YACD,aAAa,CAAC,MAAiD;gBAC7D,uCAAuC;YACzC,CAAC;SACF,CAAA;IACH,CAAC;IAED,WAAW,CAAC,KAAY,EAAE,OAAiC;QACzD,OAAO,CAAC,KAAK,CAAC,sBAAsB,KAAK,CAAC,OAAO,EAAE,EAAE,OAAO,CAAC,CAAA;IAC/D,CAAC;CACF"}
@@ -0,0 +1,7 @@
1
+ import type { TelemetryProvider, TelemetrySpan } from "../types.js";
2
+ export declare class NoopTelemetry implements TelemetryProvider {
3
+ recordEvent(_name: string, _data: Record<string, unknown>): void;
4
+ startSpan(_name: string): TelemetrySpan;
5
+ recordError(_error: Error, _context?: Record<string, unknown>): void;
6
+ }
7
+ //# sourceMappingURL=noop.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"noop.d.ts","sourceRoot":"","sources":["../../src/telemetry/noop.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,iBAAiB,EAAE,aAAa,EAAE,MAAM,aAAa,CAAA;AAOnE,qBAAa,aAAc,YAAW,iBAAiB;IACrD,WAAW,CAAC,KAAK,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,IAAI;IAChE,SAAS,CAAC,KAAK,EAAE,MAAM,GAAG,aAAa;IAGvC,WAAW,CAAC,MAAM,EAAE,KAAK,EAAE,QAAQ,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,GAAG,IAAI;CACrE"}
@@ -0,0 +1,12 @@
1
+ const NOOP_SPAN = {
2
+ end() { },
3
+ setAttributes(_attrs) { },
4
+ };
5
+ export class NoopTelemetry {
6
+ recordEvent(_name, _data) { }
7
+ startSpan(_name) {
8
+ return NOOP_SPAN;
9
+ }
10
+ recordError(_error, _context) { }
11
+ }
12
+ //# sourceMappingURL=noop.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"noop.js","sourceRoot":"","sources":["../../src/telemetry/noop.ts"],"names":[],"mappings":"AAEA,MAAM,SAAS,GAAkB;IAC/B,GAAG,KAAI,CAAC;IACR,aAAa,CAAC,MAAiD,IAAG,CAAC;CACpE,CAAA;AAED,MAAM,OAAO,aAAa;IACxB,WAAW,CAAC,KAAa,EAAE,KAA8B,IAAS,CAAC;IACnE,SAAS,CAAC,KAAa;QACrB,OAAO,SAAS,CAAA;IAClB,CAAC;IACD,WAAW,CAAC,MAAa,EAAE,QAAkC,IAAS,CAAC;CACxE"}