@llm-dev-ops/agentics-cli 2.1.4 → 2.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/pipeline/auto-chain.d.ts +73 -0
- package/dist/pipeline/auto-chain.d.ts.map +1 -1
- package/dist/pipeline/auto-chain.js +525 -38
- package/dist/pipeline/auto-chain.js.map +1 -1
- package/dist/pipeline/phase2/phases/prompt-generator.d.ts.map +1 -1
- package/dist/pipeline/phase2/phases/prompt-generator.js +53 -6
- package/dist/pipeline/phase2/phases/prompt-generator.js.map +1 -1
- package/dist/pipeline/phase2/schemas.d.ts +10 -10
- package/dist/pipeline/phase4/phases/http-server-generator.d.ts +12 -0
- package/dist/pipeline/phase4/phases/http-server-generator.d.ts.map +1 -1
- package/dist/pipeline/phase4/phases/http-server-generator.js +92 -25
- package/dist/pipeline/phase4/phases/http-server-generator.js.map +1 -1
- package/dist/pipeline/phase5-build/phase5-build-coordinator.d.ts.map +1 -1
- package/dist/pipeline/phase5-build/phase5-build-coordinator.js +44 -0
- package/dist/pipeline/phase5-build/phase5-build-coordinator.js.map +1 -1
- package/dist/pipeline/phase5-build/phases/post-generation-validator.d.ts +75 -0
- package/dist/pipeline/phase5-build/phases/post-generation-validator.d.ts.map +1 -0
- package/dist/pipeline/phase5-build/phases/post-generation-validator.js +728 -0
- package/dist/pipeline/phase5-build/phases/post-generation-validator.js.map +1 -0
- package/dist/pipeline/phase5-build/types.d.ts +1 -1
- package/dist/pipeline/phase5-build/types.d.ts.map +1 -1
- package/dist/pipeline/types.d.ts +84 -0
- package/dist/pipeline/types.d.ts.map +1 -1
- package/dist/pipeline/types.js +43 -1
- package/dist/pipeline/types.js.map +1 -1
- package/dist/synthesis/consensus-svg.d.ts +19 -0
- package/dist/synthesis/consensus-svg.d.ts.map +1 -0
- package/dist/synthesis/consensus-svg.js +95 -0
- package/dist/synthesis/consensus-svg.js.map +1 -0
- package/dist/synthesis/consensus-tiers.d.ts +99 -0
- package/dist/synthesis/consensus-tiers.d.ts.map +1 -0
- package/dist/synthesis/consensus-tiers.js +285 -0
- package/dist/synthesis/consensus-tiers.js.map +1 -0
- package/dist/synthesis/domain-labor-classifier.d.ts +101 -0
- package/dist/synthesis/domain-labor-classifier.d.ts.map +1 -0
- package/dist/synthesis/domain-labor-classifier.js +312 -0
- package/dist/synthesis/domain-labor-classifier.js.map +1 -0
- package/dist/synthesis/domain-unit-registry.d.ts +59 -0
- package/dist/synthesis/domain-unit-registry.d.ts.map +1 -0
- package/dist/synthesis/domain-unit-registry.js +294 -0
- package/dist/synthesis/domain-unit-registry.js.map +1 -0
- package/dist/synthesis/financial-claim-extractor.d.ts +52 -0
- package/dist/synthesis/financial-claim-extractor.d.ts.map +1 -0
- package/dist/synthesis/financial-claim-extractor.js +351 -0
- package/dist/synthesis/financial-claim-extractor.js.map +1 -0
- package/dist/synthesis/financial-consistency-rules.d.ts +66 -0
- package/dist/synthesis/financial-consistency-rules.d.ts.map +1 -0
- package/dist/synthesis/financial-consistency-rules.js +432 -0
- package/dist/synthesis/financial-consistency-rules.js.map +1 -0
- package/dist/synthesis/financial-consistency-runner.d.ts +73 -0
- package/dist/synthesis/financial-consistency-runner.d.ts.map +1 -0
- package/dist/synthesis/financial-consistency-runner.js +131 -0
- package/dist/synthesis/financial-consistency-runner.js.map +1 -0
- package/dist/synthesis/forbidden-spin-phrases.d.ts +32 -0
- package/dist/synthesis/forbidden-spin-phrases.d.ts.map +1 -0
- package/dist/synthesis/forbidden-spin-phrases.js +84 -0
- package/dist/synthesis/forbidden-spin-phrases.js.map +1 -0
- package/dist/synthesis/phase-gate-thresholds.d.ts +30 -0
- package/dist/synthesis/phase-gate-thresholds.d.ts.map +1 -0
- package/dist/synthesis/phase-gate-thresholds.js +34 -0
- package/dist/synthesis/phase-gate-thresholds.js.map +1 -0
- package/dist/synthesis/prompts/index.d.ts.map +1 -1
- package/dist/synthesis/prompts/index.js +22 -0
- package/dist/synthesis/prompts/index.js.map +1 -1
- package/dist/synthesis/simulation-artifact-generator.d.ts.map +1 -1
- package/dist/synthesis/simulation-artifact-generator.js +89 -1
- package/dist/synthesis/simulation-artifact-generator.js.map +1 -1
- package/dist/synthesis/simulation-renderers.d.ts +105 -2
- package/dist/synthesis/simulation-renderers.d.ts.map +1 -1
- package/dist/synthesis/simulation-renderers.js +1056 -92
- package/dist/synthesis/simulation-renderers.js.map +1 -1
- package/dist/synthesis/unit-economics-loader.d.ts +71 -0
- package/dist/synthesis/unit-economics-loader.d.ts.map +1 -0
- package/dist/synthesis/unit-economics-loader.js +200 -0
- package/dist/synthesis/unit-economics-loader.js.map +1 -0
- package/package.json +1 -1
|
@@ -0,0 +1,294 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* ADR-PIPELINE-066: Domain Unit Registry
|
|
3
|
+
*
|
|
4
|
+
* Maps a detected sector to its domain unit (the thing savings actually scale
|
|
5
|
+
* with) and a savings-base formula. Replaces per-employee heuristics whenever
|
|
6
|
+
* a sector in this registry is detected.
|
|
7
|
+
*
|
|
8
|
+
* Pure functions — no I/O.
|
|
9
|
+
*/
|
|
10
|
+
/**
|
|
11
|
+
* The eight sectors called out in ADR-PIPELINE-066 §3.
|
|
12
|
+
* Order matters for classification — more specific patterns first.
|
|
13
|
+
*/
|
|
14
|
+
export const SECTOR_REGISTRY = [
|
|
15
|
+
{
|
|
16
|
+
sector: 'hospitality',
|
|
17
|
+
domainUnit: { label: 'occupied room night', abbrev: 'orn' },
|
|
18
|
+
scopeKeys: ['rooms', 'properties'],
|
|
19
|
+
savingsFormula: 'rooms × occupancy × $/occupied-room-night',
|
|
20
|
+
unitSavingsKey: 'usd_per_orn',
|
|
21
|
+
},
|
|
22
|
+
{
|
|
23
|
+
sector: 'commercial-real-estate',
|
|
24
|
+
domainUnit: { label: 'square foot-year', abbrev: 'sqft-yr' },
|
|
25
|
+
scopeKeys: ['sqft', 'properties'],
|
|
26
|
+
savingsFormula: 'sqft × $/sqft-year',
|
|
27
|
+
unitSavingsKey: 'usd_per_sqft_year',
|
|
28
|
+
},
|
|
29
|
+
{
|
|
30
|
+
sector: 'fleet',
|
|
31
|
+
domainUnit: { label: 'vehicle-mile', abbrev: 'vmi' },
|
|
32
|
+
scopeKeys: ['vehicles'],
|
|
33
|
+
savingsFormula: 'fleet × miles × $/mile',
|
|
34
|
+
unitSavingsKey: 'usd_per_vehicle_mile',
|
|
35
|
+
},
|
|
36
|
+
{
|
|
37
|
+
sector: 'retail',
|
|
38
|
+
domainUnit: { label: 'transaction', abbrev: 'txn' },
|
|
39
|
+
scopeKeys: ['properties', 'units'],
|
|
40
|
+
savingsFormula: 'daily transactions × 365 × $/transaction',
|
|
41
|
+
unitSavingsKey: 'usd_per_transaction',
|
|
42
|
+
},
|
|
43
|
+
{
|
|
44
|
+
sector: 'manufacturing',
|
|
45
|
+
domainUnit: { label: 'unit produced', abbrev: 'unit' },
|
|
46
|
+
scopeKeys: ['units'],
|
|
47
|
+
savingsFormula: 'throughput × $/unit',
|
|
48
|
+
unitSavingsKey: 'usd_per_unit_produced',
|
|
49
|
+
},
|
|
50
|
+
{
|
|
51
|
+
sector: 'healthcare',
|
|
52
|
+
domainUnit: { label: 'patient-day', abbrev: 'pday' },
|
|
53
|
+
scopeKeys: ['beds'],
|
|
54
|
+
savingsFormula: 'census × $/patient-day',
|
|
55
|
+
unitSavingsKey: 'usd_per_patient_day',
|
|
56
|
+
},
|
|
57
|
+
{
|
|
58
|
+
sector: 'data-center',
|
|
59
|
+
domainUnit: { label: 'kilowatt-hour', abbrev: 'kWh' },
|
|
60
|
+
scopeKeys: ['units'],
|
|
61
|
+
savingsFormula: 'load × 8760 × $/kWh',
|
|
62
|
+
unitSavingsKey: 'usd_per_kwh',
|
|
63
|
+
},
|
|
64
|
+
{
|
|
65
|
+
sector: 'call-center',
|
|
66
|
+
domainUnit: { label: 'contact minute', abbrev: 'cmin' },
|
|
67
|
+
scopeKeys: ['agents'],
|
|
68
|
+
savingsFormula: 'agents × minutes × $/contact-minute',
|
|
69
|
+
unitSavingsKey: 'usd_per_contact_minute',
|
|
70
|
+
},
|
|
71
|
+
];
|
|
72
|
+
const REGISTRY_BY_SECTOR = new Map(SECTOR_REGISTRY.map(e => [e.sector, e]));
|
|
73
|
+
export function getSectorEntry(sector) {
|
|
74
|
+
return REGISTRY_BY_SECTOR.get(sector) ?? null;
|
|
75
|
+
}
|
|
76
|
+
// Hard patterns: unambiguous sector indicators that lock the classification.
|
|
77
|
+
const HARD_RULES = [
|
|
78
|
+
{
|
|
79
|
+
sector: 'hospitality',
|
|
80
|
+
patterns: [
|
|
81
|
+
/\bhotel\b/i,
|
|
82
|
+
/\bhousekeep/i,
|
|
83
|
+
/\blodging\b/i,
|
|
84
|
+
/\bhospitality\b/i,
|
|
85
|
+
/\bresort\b/i,
|
|
86
|
+
/\broom\s*night/i,
|
|
87
|
+
/\boccupanc/i,
|
|
88
|
+
],
|
|
89
|
+
},
|
|
90
|
+
{
|
|
91
|
+
sector: 'commercial-real-estate',
|
|
92
|
+
patterns: [
|
|
93
|
+
/\bcommercial\s+real\s+estate\b/i,
|
|
94
|
+
/\boffice\s+portfolio\b/i,
|
|
95
|
+
/\bbuilding\s+portfolio\b/i,
|
|
96
|
+
/\bworkplace\s+(?:optim|utiliz)/i,
|
|
97
|
+
/\bsqft\b/i,
|
|
98
|
+
/\bsquare\s+f(?:oot|eet)\b/i,
|
|
99
|
+
/\bfacility\s+management\b/i,
|
|
100
|
+
],
|
|
101
|
+
},
|
|
102
|
+
{
|
|
103
|
+
sector: 'fleet',
|
|
104
|
+
patterns: [
|
|
105
|
+
/\bfleet\b/i,
|
|
106
|
+
/\b(?:truck|vehicle)\s+fleet\b/i,
|
|
107
|
+
/\bEV\s+transition\b/i,
|
|
108
|
+
/\bfleet\s+electrification\b/i,
|
|
109
|
+
/\btransportation\s+(?:cost|fuel)/i,
|
|
110
|
+
],
|
|
111
|
+
},
|
|
112
|
+
{
|
|
113
|
+
sector: 'retail',
|
|
114
|
+
patterns: [
|
|
115
|
+
/\bretail\s+chain\b/i,
|
|
116
|
+
/\bstores?\b/i,
|
|
117
|
+
/\bgrocery\b/i,
|
|
118
|
+
/\bpoint[-\s]?of[-\s]?sale\b/i,
|
|
119
|
+
/\bregister\s+throughput\b/i,
|
|
120
|
+
],
|
|
121
|
+
},
|
|
122
|
+
{
|
|
123
|
+
sector: 'manufacturing',
|
|
124
|
+
patterns: [
|
|
125
|
+
/\bmanufactur/i,
|
|
126
|
+
/\bfactory\b/i,
|
|
127
|
+
/\bproduction\s+line\b/i,
|
|
128
|
+
/\bassembly\s+line\b/i,
|
|
129
|
+
/\bOEE\b/i,
|
|
130
|
+
],
|
|
131
|
+
},
|
|
132
|
+
{
|
|
133
|
+
sector: 'healthcare',
|
|
134
|
+
patterns: [
|
|
135
|
+
/\bhospital\b/i,
|
|
136
|
+
/\bclinic\b/i,
|
|
137
|
+
/\bpatient\b/i,
|
|
138
|
+
/\bnurs(?:e|ing)\b/i,
|
|
139
|
+
/\bhealthcare\b/i,
|
|
140
|
+
/\bhealth\s*system\b/i,
|
|
141
|
+
],
|
|
142
|
+
},
|
|
143
|
+
{
|
|
144
|
+
sector: 'data-center',
|
|
145
|
+
patterns: [
|
|
146
|
+
/\bdata\s*center\b/i,
|
|
147
|
+
/\bdatacenter\b/i,
|
|
148
|
+
/\bPUE\b/i,
|
|
149
|
+
/\bserver\s+farm\b/i,
|
|
150
|
+
/\bcolocation\b/i,
|
|
151
|
+
],
|
|
152
|
+
},
|
|
153
|
+
{
|
|
154
|
+
sector: 'call-center',
|
|
155
|
+
patterns: [
|
|
156
|
+
/\bcall\s*center\b/i,
|
|
157
|
+
/\bcontact\s*center\b/i,
|
|
158
|
+
/\bBPO\b/i,
|
|
159
|
+
/\bagent\s+productivity\b/i,
|
|
160
|
+
/\bcustomer\s+service\s+center\b/i,
|
|
161
|
+
],
|
|
162
|
+
},
|
|
163
|
+
];
|
|
164
|
+
/**
|
|
165
|
+
* Classify a query into a sector from the registry, or 'unknown'.
|
|
166
|
+
* Prefers an explicit sector hint (from domain_analysis.sector) when provided.
|
|
167
|
+
*/
|
|
168
|
+
export function classifySector(query, sectorHint) {
|
|
169
|
+
if (sectorHint) {
|
|
170
|
+
const normalized = normalizeSectorHint(sectorHint);
|
|
171
|
+
if (normalized !== 'unknown')
|
|
172
|
+
return normalized;
|
|
173
|
+
}
|
|
174
|
+
for (const rule of HARD_RULES) {
|
|
175
|
+
if (rule.patterns.some(p => p.test(query)))
|
|
176
|
+
return rule.sector;
|
|
177
|
+
}
|
|
178
|
+
return 'unknown';
|
|
179
|
+
}
|
|
180
|
+
function normalizeSectorHint(hint) {
|
|
181
|
+
const h = hint.toLowerCase().trim();
|
|
182
|
+
if (/hospitality|hotel|lodging|resort/.test(h))
|
|
183
|
+
return 'hospitality';
|
|
184
|
+
if (/commercial[-\s]real[-\s]estate|cre\b|office|workplace|building/.test(h))
|
|
185
|
+
return 'commercial-real-estate';
|
|
186
|
+
if (/fleet|transportation|vehicle/.test(h))
|
|
187
|
+
return 'fleet';
|
|
188
|
+
if (/retail|store/.test(h))
|
|
189
|
+
return 'retail';
|
|
190
|
+
if (/manufactur|factory|production/.test(h))
|
|
191
|
+
return 'manufacturing';
|
|
192
|
+
if (/healthcare|hospital|clinic|patient/.test(h))
|
|
193
|
+
return 'healthcare';
|
|
194
|
+
if (/data[-\s]?center|datacenter/.test(h))
|
|
195
|
+
return 'data-center';
|
|
196
|
+
if (/call[-\s]?center|contact[-\s]?center|bpo/.test(h))
|
|
197
|
+
return 'call-center';
|
|
198
|
+
return 'unknown';
|
|
199
|
+
}
|
|
200
|
+
/** Extract employee count from free text. Used for context only. */
|
|
201
|
+
export function extractEmployeeCountFromText(query) {
|
|
202
|
+
const lower = query.toLowerCase();
|
|
203
|
+
let employees = 10000;
|
|
204
|
+
const empIdx = lower.indexOf('employees');
|
|
205
|
+
const staffIdx = lower.indexOf('staff');
|
|
206
|
+
const targetIdx = empIdx !== -1 ? empIdx : staffIdx;
|
|
207
|
+
if (targetIdx > 5) {
|
|
208
|
+
const before = query.substring(Math.max(0, targetIdx - 30), targetIdx).trim();
|
|
209
|
+
const words = before.split(/\s+/);
|
|
210
|
+
for (let i = words.length - 1; i >= 0; i--) {
|
|
211
|
+
const cleaned = (words[i] ?? '').replace(/,/g, '').replace(/approximately/i, '').trim();
|
|
212
|
+
const num = parseInt(cleaned, 10);
|
|
213
|
+
if (num > 100 && num < 10_000_000) {
|
|
214
|
+
employees = num;
|
|
215
|
+
break;
|
|
216
|
+
}
|
|
217
|
+
}
|
|
218
|
+
}
|
|
219
|
+
return employees;
|
|
220
|
+
}
|
|
221
|
+
const UNIT_PATTERNS = [
|
|
222
|
+
{ pattern: /(\d[\d,]*)\s*(?:hotels?|properties|resorts?)/i, sector: 'hospitality', unitLabel: 'rooms', unitAbbrev: 'rooms' },
|
|
223
|
+
{ pattern: /(\d[\d,]*)\s*(?:rooms?)\b/i, sector: 'hospitality', unitLabel: 'rooms', unitAbbrev: 'rooms' },
|
|
224
|
+
{ pattern: /(\d[\d,]*)\s*(?:buildings?|offices?|sites?)/i, sector: 'commercial-real-estate', unitLabel: 'sqft', unitAbbrev: 'sqft' },
|
|
225
|
+
{ pattern: /(\d[\d,]*)\s*(?:vehicles?|trucks?|vans?|cars?)/i, sector: 'fleet', unitLabel: 'vehicles', unitAbbrev: 'vehicles' },
|
|
226
|
+
{ pattern: /(\d[\d,]*)\s*(?:stores?|locations?|outlets?|branches?)/i, sector: 'retail', unitLabel: 'stores', unitAbbrev: 'stores' },
|
|
227
|
+
{ pattern: /(\d[\d,]*)\s*(?:plants?|factor(?:y|ies))/i, sector: 'manufacturing', unitLabel: 'plants', unitAbbrev: 'plants' },
|
|
228
|
+
{ pattern: /(\d[\d,]*)\s*(?:beds?|patients?)/i, sector: 'healthcare', unitLabel: 'beds', unitAbbrev: 'beds' },
|
|
229
|
+
{ pattern: /(\d[\d,]*)\s*(?:agents?)/i, sector: 'call-center', unitLabel: 'agents', unitAbbrev: 'agents' },
|
|
230
|
+
];
|
|
231
|
+
/**
|
|
232
|
+
* ADR-PIPELINE-066 §4: Replace `extractEmployeeCount` with a richer shape that
|
|
233
|
+
* carries the operational unit *and* its source. Savings math that used to
|
|
234
|
+
* multiply `employees * ratio` must now multiply `operationalUnits * ratio`
|
|
235
|
+
* whenever `source !== 'default'`.
|
|
236
|
+
*/
|
|
237
|
+
export function extractDomainScale(query, sectorHint) {
|
|
238
|
+
const employees = extractEmployeeCountFromText(query);
|
|
239
|
+
const sector = classifySector(query, sectorHint);
|
|
240
|
+
// Prefer an explicit unit count in the query over sector-based fallback.
|
|
241
|
+
for (const rule of UNIT_PATTERNS) {
|
|
242
|
+
const match = query.match(rule.pattern);
|
|
243
|
+
if (match?.[1]) {
|
|
244
|
+
const count = parseInt(match[1].replace(/,/g, ''), 10);
|
|
245
|
+
if (count > 0) {
|
|
246
|
+
return {
|
|
247
|
+
employees,
|
|
248
|
+
operationalUnits: count,
|
|
249
|
+
unitLabel: rule.unitLabel,
|
|
250
|
+
unitAbbrev: rule.unitAbbrev,
|
|
251
|
+
sector: sector === 'unknown' ? rule.sector : sector,
|
|
252
|
+
source: 'query-regex',
|
|
253
|
+
};
|
|
254
|
+
}
|
|
255
|
+
}
|
|
256
|
+
}
|
|
257
|
+
// Sector-based ratios when no explicit count was given. These are
|
|
258
|
+
// intentionally coarse — the goal is to produce a plausible operational
|
|
259
|
+
// unit count, NOT to compute savings. Savings come from unit-economics.json.
|
|
260
|
+
if (sector !== 'unknown') {
|
|
261
|
+
const entry = getSectorEntry(sector);
|
|
262
|
+
const primaryKey = entry?.scopeKeys[0] ?? 'units';
|
|
263
|
+
const ratios = {
|
|
264
|
+
rooms: 0.02, // ~1 room per 50 employees (hotel avg)
|
|
265
|
+
sqft: 200, // ~200 sqft per employee
|
|
266
|
+
vehicles: 0.05, // ~5% of workforce drives fleet
|
|
267
|
+
stores: 0.005, // ~1 store per 200 employees
|
|
268
|
+
plants: 0.001, // ~1 plant per 1000 employees
|
|
269
|
+
beds: 0.2, // ~1 bed per 5 staff
|
|
270
|
+
agents: 0.3, // ~30% of headcount
|
|
271
|
+
units: 0.1,
|
|
272
|
+
properties: 0.002,
|
|
273
|
+
};
|
|
274
|
+
const ratio = ratios[primaryKey] ?? 0.1;
|
|
275
|
+
const operationalUnits = Math.max(1, Math.round(employees * ratio));
|
|
276
|
+
return {
|
|
277
|
+
employees,
|
|
278
|
+
operationalUnits,
|
|
279
|
+
unitLabel: primaryKey,
|
|
280
|
+
unitAbbrev: primaryKey,
|
|
281
|
+
sector,
|
|
282
|
+
source: 'query-regex',
|
|
283
|
+
};
|
|
284
|
+
}
|
|
285
|
+
return {
|
|
286
|
+
employees,
|
|
287
|
+
operationalUnits: employees,
|
|
288
|
+
unitLabel: 'employees',
|
|
289
|
+
unitAbbrev: 'emp',
|
|
290
|
+
sector: 'unknown',
|
|
291
|
+
source: 'default',
|
|
292
|
+
};
|
|
293
|
+
}
|
|
294
|
+
//# sourceMappingURL=domain-unit-registry.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"domain-unit-registry.js","sourceRoot":"","sources":["../../src/synthesis/domain-unit-registry.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* ADR-PIPELINE-067: Financial Claim Extractor
|
|
3
|
+
*
|
|
4
|
+
* Parses rendered executive markdown and returns a structured list of
|
|
5
|
+
* FinancialClaim records. Used by the cross-document consistency runner to
|
|
6
|
+
* compare dollar figures, timelines, and scope labels across documents.
|
|
7
|
+
*
|
|
8
|
+
* Pure functions. Regex-based — no LLM calls.
|
|
9
|
+
*
|
|
10
|
+
* Renderers can short-circuit extraction by emitting an HTML comment tag
|
|
11
|
+
* immediately before the figure:
|
|
12
|
+
*
|
|
13
|
+
* <!-- fcv:kind=investment scope=pilot -->
|
|
14
|
+
* **Pilot investment:** $1.0M–$1.4M
|
|
15
|
+
*/
|
|
16
|
+
export type FinancialClaimDocument = 'executive-summary' | 'decision-memo' | 'roadmap' | 'business-case' | 'risk-register' | 'financial-analysis' | 'unknown';
|
|
17
|
+
export type FinancialClaimKind = 'investment' | 'savings' | 'timeline' | 'headcount' | 'roi' | 'npv';
|
|
18
|
+
export type FinancialClaimScope = 'pilot' | 'phase-1' | 'phase-2' | 'phase-3' | 'full-program' | 'unscoped';
|
|
19
|
+
export type FinancialClaimUnit = 'USD' | 'weeks' | 'months' | 'years' | 'count' | 'percent';
|
|
20
|
+
export interface FinancialClaim {
|
|
21
|
+
readonly document: FinancialClaimDocument;
|
|
22
|
+
readonly section: string;
|
|
23
|
+
readonly kind: FinancialClaimKind;
|
|
24
|
+
readonly scope: FinancialClaimScope;
|
|
25
|
+
readonly rangeLow?: number;
|
|
26
|
+
readonly rangeHigh?: number;
|
|
27
|
+
readonly pointValue?: number;
|
|
28
|
+
readonly unit: FinancialClaimUnit;
|
|
29
|
+
readonly rawText: string;
|
|
30
|
+
readonly line: number;
|
|
31
|
+
/** True when the claim was pulled from an explicit fcv: HTML comment tag. */
|
|
32
|
+
readonly tagged: boolean;
|
|
33
|
+
}
|
|
34
|
+
/**
|
|
35
|
+
* Parse a single currency token like "$1.2M", "$600K", "$1,200,000",
|
|
36
|
+
* "USD 1.2M", or "1.2 million dollars". Returns NaN when the input does not
|
|
37
|
+
* look like a currency amount.
|
|
38
|
+
*/
|
|
39
|
+
export declare function parseCurrency(token: string): number;
|
|
40
|
+
/**
|
|
41
|
+
* Extract FinancialClaim records from a markdown document. The document name
|
|
42
|
+
* is recorded on every claim and becomes the primary key for
|
|
43
|
+
* cross-document rule evaluation.
|
|
44
|
+
*
|
|
45
|
+
* Scoping heuristic:
|
|
46
|
+
* 1. If an HTML fcv: tag precedes the figure (same line or prior line),
|
|
47
|
+
* use its declared kind/scope verbatim.
|
|
48
|
+
* 2. Otherwise scan a ±60 char window around the figure for scope words
|
|
49
|
+
* ("pilot", "phase 1", "full program", ...).
|
|
50
|
+
*/
|
|
51
|
+
export declare function extractClaims(markdown: string, document: FinancialClaimDocument): FinancialClaim[];
|
|
52
|
+
//# sourceMappingURL=financial-claim-extractor.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"financial-claim-extractor.d.ts","sourceRoot":"","sources":["../../src/synthesis/financial-claim-extractor.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;GAcG;AAEH,MAAM,MAAM,sBAAsB,GAC9B,mBAAmB,GACnB,eAAe,GACf,SAAS,GACT,eAAe,GACf,eAAe,GACf,oBAAoB,GACpB,SAAS,CAAC;AAEd,MAAM,MAAM,kBAAkB,GAC1B,YAAY,GACZ,SAAS,GACT,UAAU,GACV,WAAW,GACX,KAAK,GACL,KAAK,CAAC;AAEV,MAAM,MAAM,mBAAmB,GAC3B,OAAO,GACP,SAAS,GACT,SAAS,GACT,SAAS,GACT,cAAc,GACd,UAAU,CAAC;AAEf,MAAM,MAAM,kBAAkB,GAAG,KAAK,GAAG,OAAO,GAAG,QAAQ,GAAG,OAAO,GAAG,OAAO,GAAG,SAAS,CAAC;AAE5F,MAAM,WAAW,cAAc;IAC7B,QAAQ,CAAC,QAAQ,EAAE,sBAAsB,CAAC;IAC1C,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;IACzB,QAAQ,CAAC,IAAI,EAAE,kBAAkB,CAAC;IAClC,QAAQ,CAAC,KAAK,EAAE,mBAAmB,CAAC;IACpC,QAAQ,CAAC,QAAQ,CAAC,EAAE,MAAM,CAAC;IAC3B,QAAQ,CAAC,SAAS,CAAC,EAAE,MAAM,CAAC;IAC5B,QAAQ,CAAC,UAAU,CAAC,EAAE,MAAM,CAAC;IAC7B,QAAQ,CAAC,IAAI,EAAE,kBAAkB,CAAC;IAClC,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;IACzB,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,6EAA6E;IAC7E,QAAQ,CAAC,MAAM,EAAE,OAAO,CAAC;CAC1B;AAYD;;;;GAIG;AACH,wBAAgB,aAAa,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,CAsCnD;AAgID;;;;;;;;;;GAUG;AACH,wBAAgB,aAAa,CAC3B,QAAQ,EAAE,MAAM,EAChB,QAAQ,EAAE,sBAAsB,GAC/B,cAAc,EAAE,CAmClB"}
|