@geotechcli/core 0.4.50 → 0.4.52
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/ingest/document-evidence-packet.d.ts +157 -16
- package/dist/ingest/document-evidence-packet.d.ts.map +1 -1
- package/dist/ingest/document-evidence-packet.js +28 -2
- package/dist/ingest/document-evidence-packet.js.map +1 -1
- package/dist/ingest/geotech-document-benchmark.d.ts +1 -0
- package/dist/ingest/geotech-document-benchmark.d.ts.map +1 -1
- package/dist/ingest/geotech-document-benchmark.js +1 -0
- package/dist/ingest/geotech-document-benchmark.js.map +1 -1
- package/dist/ingest/geotech-document.d.ts +20 -0
- package/dist/ingest/geotech-document.d.ts.map +1 -1
- package/dist/ingest/geotech-document.js +278 -8
- package/dist/ingest/geotech-document.js.map +1 -1
- package/dist/meta/metadata.json +6 -2
- package/dist/report/html.d.ts.map +1 -1
- package/dist/report/html.js +389 -0
- package/dist/report/html.js.map +1 -1
- package/dist/report/ingest-dossier.d.ts +9 -0
- package/dist/report/ingest-dossier.d.ts.map +1 -1
- package/dist/report/ingest-dossier.js +336 -3
- package/dist/report/ingest-dossier.js.map +1 -1
- package/package.json +1 -1
|
@@ -1,3 +1,4 @@
|
|
|
1
|
+
import { buildGroundModelMap } from '../ground-model/index.js';
|
|
1
2
|
function uniqueStrings(values) {
|
|
2
3
|
return [...new Set(values.filter((value) => typeof value === 'string' && value.trim().length > 0))];
|
|
3
4
|
}
|
|
@@ -366,6 +367,15 @@ function toneFromParseStatus(parseStatus, confidence) {
|
|
|
366
367
|
}
|
|
367
368
|
return 'good';
|
|
368
369
|
}
|
|
370
|
+
function toneFromScore(score) {
|
|
371
|
+
if (score >= 80) {
|
|
372
|
+
return 'good';
|
|
373
|
+
}
|
|
374
|
+
if (score >= 60) {
|
|
375
|
+
return 'warning';
|
|
376
|
+
}
|
|
377
|
+
return 'danger';
|
|
378
|
+
}
|
|
369
379
|
function evidenceCacheStatusLabel(status) {
|
|
370
380
|
switch (status) {
|
|
371
381
|
case 'hit':
|
|
@@ -684,9 +694,17 @@ function buildGeotechMetrics(result) {
|
|
|
684
694
|
const statusCounts = countGeotechPageStatuses(result);
|
|
685
695
|
const cacheHits = result.pageAudits.filter((audit) => audit.evidenceCache?.status === 'hit').length;
|
|
686
696
|
const cacheStored = result.pageAudits.filter((audit) => audit.evidenceCache?.status === 'stored').length;
|
|
697
|
+
const breakdown = result.confidenceBreakdown;
|
|
687
698
|
return [
|
|
688
699
|
{ label: 'Pages processed', value: `${result.source.successfulPages}/${result.source.totalPages}`, tone: result.source.failedPages > 0 ? 'warning' : 'good' },
|
|
689
|
-
{
|
|
700
|
+
{
|
|
701
|
+
label: 'Review confidence',
|
|
702
|
+
value: `${result.confidence}%`,
|
|
703
|
+
detail: breakdown
|
|
704
|
+
? `pages avg ${breakdown.pageEvidenceConfidence}%, traceability ${breakdown.traceabilityScore}%, readiness ${breakdown.readinessScore}%`
|
|
705
|
+
: 'Workflow confidence for review triage.',
|
|
706
|
+
tone: toneFromParseStatus(result.parseStatus ?? 'parsed', result.confidence),
|
|
707
|
+
},
|
|
690
708
|
{ label: 'Page outcomes', value: `${statusCounts.parsed}/${result.pageAudits.length}`, detail: `${statusCounts.partial} partial, ${statusCounts.failed} failed`, tone: statusCounts.failed > 0 ? 'danger' : statusCounts.partial > 0 ? 'warning' : 'good' },
|
|
691
709
|
{ label: 'Materials', value: String(result.materials.length), detail: `${result.classifications.length} classifications`, tone: result.materials.length > 0 ? 'good' : 'warning' },
|
|
692
710
|
{ label: 'Parameters', value: String(result.parameters.length), detail: result.documentClass ?? 'No document class', tone: result.parameters.length > 0 ? 'good' : 'warning' },
|
|
@@ -694,6 +712,44 @@ function buildGeotechMetrics(result) {
|
|
|
694
712
|
{ label: 'Evidence cache', value: String(cacheHits), detail: `${cacheStored} stored this run`, tone: cacheHits > 0 ? 'good' : cacheStored > 0 ? 'accent' : 'neutral' },
|
|
695
713
|
];
|
|
696
714
|
}
|
|
715
|
+
function buildGeotechConfidenceItems(result) {
|
|
716
|
+
const breakdown = result.confidenceBreakdown;
|
|
717
|
+
if (!breakdown) {
|
|
718
|
+
return undefined;
|
|
719
|
+
}
|
|
720
|
+
return [
|
|
721
|
+
{
|
|
722
|
+
label: 'Workflow confidence',
|
|
723
|
+
value: `${breakdown.overall}%`,
|
|
724
|
+
detail: 'Legacy review-triage score; synthesis cannot raise it.',
|
|
725
|
+
tone: toneFromScore(breakdown.overall),
|
|
726
|
+
},
|
|
727
|
+
{
|
|
728
|
+
label: 'Page evidence',
|
|
729
|
+
value: `${breakdown.pageEvidenceConfidence}%`,
|
|
730
|
+
detail: `${result.pageAudits.length} audited page(s); extraction score ${breakdown.extractionConfidence}%.`,
|
|
731
|
+
tone: toneFromScore(breakdown.pageEvidenceConfidence),
|
|
732
|
+
},
|
|
733
|
+
{
|
|
734
|
+
label: 'Source traceability',
|
|
735
|
+
value: `${breakdown.traceabilityScore}%`,
|
|
736
|
+
detail: `${result.parameters.filter((parameter) => sourcePageText(parameter.context, parameter.sourcePages) !== '-').length}/${result.parameters.length} parameter(s) with source pages.`,
|
|
737
|
+
tone: toneFromScore(breakdown.traceabilityScore),
|
|
738
|
+
},
|
|
739
|
+
{
|
|
740
|
+
label: 'Review gates',
|
|
741
|
+
value: String(breakdown.reviewGates.length),
|
|
742
|
+
detail: breakdown.reviewGates.length > 0 ? breakdown.reviewGates.slice(0, 3).join(', ') : 'No retained confidence gates.',
|
|
743
|
+
tone: breakdown.reviewGates.length > 0 ? 'warning' : 'good',
|
|
744
|
+
},
|
|
745
|
+
{
|
|
746
|
+
label: 'Engineering completeness',
|
|
747
|
+
value: `${breakdown.engineeringCompleteness}%`,
|
|
748
|
+
detail: breakdown.missingCriticalData.length > 0 ? `Missing: ${breakdown.missingCriticalData.join(', ')}.` : 'Common critical data categories retained.',
|
|
749
|
+
tone: toneFromScore(breakdown.engineeringCompleteness),
|
|
750
|
+
},
|
|
751
|
+
];
|
|
752
|
+
}
|
|
697
753
|
function buildBoreholeMetrics(result) {
|
|
698
754
|
return [
|
|
699
755
|
{ label: 'Pages processed', value: `${result.source.successfulPages}/${result.source.totalPages}`, tone: result.source.failedPages > 0 ? 'warning' : 'good' },
|
|
@@ -733,7 +789,14 @@ function buildGeotechExecutiveItems(result, sourceLabel) {
|
|
|
733
789
|
detail: result.parseStatus,
|
|
734
790
|
tone: result.reviewRequired ? 'warning' : 'good',
|
|
735
791
|
},
|
|
736
|
-
{
|
|
792
|
+
{
|
|
793
|
+
label: 'Review confidence',
|
|
794
|
+
value: `${result.confidence}%`,
|
|
795
|
+
detail: result.confidenceBreakdown
|
|
796
|
+
? `Evidence ${result.confidenceBreakdown.pageEvidenceConfidence}%, readiness ${result.confidenceBreakdown.readinessScore}%.`
|
|
797
|
+
: undefined,
|
|
798
|
+
tone: toneFromParseStatus(result.parseStatus, result.confidence),
|
|
799
|
+
},
|
|
737
800
|
{ label: 'Boreholes detected', value: boreholeIds.length > 0 ? boreholeIds.join(', ') : 'Not explicitly detected', tone: boreholeIds.length > 0 ? 'good' : 'warning' },
|
|
738
801
|
{ label: 'Max depth', value: formatDepthMeters(maxDepth), tone: maxDepth != null ? 'good' : 'warning' },
|
|
739
802
|
{ label: 'Key engineering concern', value: inferKeyConcern(result), tone: 'warning' },
|
|
@@ -1157,6 +1220,273 @@ function buildGeotechBoreholeProfile(result) {
|
|
|
1157
1220
|
],
|
|
1158
1221
|
};
|
|
1159
1222
|
}
|
|
1223
|
+
function confidenceRatio(value) {
|
|
1224
|
+
if (typeof value !== 'number' || !Number.isFinite(value))
|
|
1225
|
+
return 0.5;
|
|
1226
|
+
const normalized = value > 1 ? value / 100 : value;
|
|
1227
|
+
return Math.round(Math.max(0, Math.min(1, normalized)) * 100) / 100;
|
|
1228
|
+
}
|
|
1229
|
+
function firstSourcePage(values) {
|
|
1230
|
+
return uniqueSortedPages(values.flatMap((pages) => pages ?? []))[0];
|
|
1231
|
+
}
|
|
1232
|
+
function evidenceMethodForPage(result, pageNumber) {
|
|
1233
|
+
const audit = pageNumber != null
|
|
1234
|
+
? result.pageAudits.find((candidate) => candidate.pageNumber === pageNumber)
|
|
1235
|
+
: undefined;
|
|
1236
|
+
if (!audit) {
|
|
1237
|
+
return 'manual';
|
|
1238
|
+
}
|
|
1239
|
+
switch (audit?.textHintSource) {
|
|
1240
|
+
case 'native-text':
|
|
1241
|
+
case 'pdfjs-text':
|
|
1242
|
+
return 'pdf-text';
|
|
1243
|
+
case 'none':
|
|
1244
|
+
return 'manual';
|
|
1245
|
+
default:
|
|
1246
|
+
return 'vision';
|
|
1247
|
+
}
|
|
1248
|
+
}
|
|
1249
|
+
function addReportEvidenceRef(state, input) {
|
|
1250
|
+
state.counter += 1;
|
|
1251
|
+
const id = `doc-ev-${String(state.counter).padStart(5, '0')}`;
|
|
1252
|
+
const hasAudit = input.pageNumber == null
|
|
1253
|
+
|| state.result.pageAudits.some((candidate) => candidate.pageNumber === input.pageNumber);
|
|
1254
|
+
const warnings = [
|
|
1255
|
+
...(input.warnings ?? []),
|
|
1256
|
+
...(!hasAudit ? [`Source page ${input.pageNumber} was not present in retained page audit; verify against the PDF.`] : []),
|
|
1257
|
+
];
|
|
1258
|
+
state.refs.push({
|
|
1259
|
+
id,
|
|
1260
|
+
sourceType: 'pdf-page',
|
|
1261
|
+
sourcePath: state.sourcePath,
|
|
1262
|
+
location: {
|
|
1263
|
+
filePath: state.sourcePath,
|
|
1264
|
+
...(input.pageNumber != null ? { pageNumber: input.pageNumber } : {}),
|
|
1265
|
+
},
|
|
1266
|
+
method: evidenceMethodForPage(state.result, input.pageNumber),
|
|
1267
|
+
confidence: confidenceRatio(state.result.confidence),
|
|
1268
|
+
rawValue: input.rawValue,
|
|
1269
|
+
normalizedValue: input.normalizedValue,
|
|
1270
|
+
...(input.unit ? { unit: input.unit } : {}),
|
|
1271
|
+
warnings,
|
|
1272
|
+
});
|
|
1273
|
+
return id;
|
|
1274
|
+
}
|
|
1275
|
+
function depthFromEvidenceText(...values) {
|
|
1276
|
+
for (const value of values) {
|
|
1277
|
+
const depth = readDepthMeters(value);
|
|
1278
|
+
if (depth != null && depth >= 0) {
|
|
1279
|
+
return depth;
|
|
1280
|
+
}
|
|
1281
|
+
}
|
|
1282
|
+
return undefined;
|
|
1283
|
+
}
|
|
1284
|
+
function numericParameterValue(parameter) {
|
|
1285
|
+
if (parameter.numericValue != null && Number.isFinite(parameter.numericValue)) {
|
|
1286
|
+
return parameter.numericValue;
|
|
1287
|
+
}
|
|
1288
|
+
const value = Number(String(parameter.valueText ?? '').replace(/,/g, '').trim());
|
|
1289
|
+
return Number.isFinite(value) ? value : undefined;
|
|
1290
|
+
}
|
|
1291
|
+
function parameterBoreholeId(parameter) {
|
|
1292
|
+
return inferBoreholeIdsFromText(parameter.material, parameter.context, parameter.name)[0];
|
|
1293
|
+
}
|
|
1294
|
+
function looksLikeBearingTableSptFalsePositive(parameter) {
|
|
1295
|
+
const normalizedName = parameter.name.toLowerCase().replace(/\s+/g, '');
|
|
1296
|
+
if (!/spt|nvalue|n-value|standardpenetration/.test(normalizedName)) {
|
|
1297
|
+
return false;
|
|
1298
|
+
}
|
|
1299
|
+
const retainedContext = [parameter.material, parameter.context].filter(Boolean).join(' ');
|
|
1300
|
+
return /\b(?:foundation|footing|allowable\s+bearing|bearing\s+pressure|net\s+bearing|dimension|size\s+of\s+footing)\b/i.test(retainedContext)
|
|
1301
|
+
&& !/\b(?:spt|standard\s+penetration|n[-\s]?value|blows?\b)\b/i.test(retainedContext);
|
|
1302
|
+
}
|
|
1303
|
+
function buildGroundModelFromGeotechReport(result, profile, sourceLabel) {
|
|
1304
|
+
const evidenceState = {
|
|
1305
|
+
refs: [],
|
|
1306
|
+
counter: 0,
|
|
1307
|
+
sourcePath: result.source.fileName ?? result.source.filePath ?? sourceLabel,
|
|
1308
|
+
result,
|
|
1309
|
+
};
|
|
1310
|
+
const boreholes = new Map();
|
|
1311
|
+
const strata = [];
|
|
1312
|
+
const groundwater = [];
|
|
1313
|
+
const parameters = [];
|
|
1314
|
+
const ensureBorehole = (id, evidenceIds = []) => {
|
|
1315
|
+
const normalizedId = normalizeBoreholeId(id);
|
|
1316
|
+
const existing = boreholes.get(normalizedId);
|
|
1317
|
+
if (existing) {
|
|
1318
|
+
existing.evidenceIds = uniqueStrings([...existing.evidenceIds, ...evidenceIds]);
|
|
1319
|
+
return existing;
|
|
1320
|
+
}
|
|
1321
|
+
const borehole = {
|
|
1322
|
+
id: normalizedId,
|
|
1323
|
+
sptTests: [],
|
|
1324
|
+
strata: [],
|
|
1325
|
+
groundwater: [],
|
|
1326
|
+
evidenceIds,
|
|
1327
|
+
confidence: confidenceRatio(result.confidence),
|
|
1328
|
+
warnings: [],
|
|
1329
|
+
};
|
|
1330
|
+
boreholes.set(normalizedId, borehole);
|
|
1331
|
+
return borehole;
|
|
1332
|
+
};
|
|
1333
|
+
for (const boreholeId of profile?.columns.map((column) => column.boreholeId) ?? inferGeotechBoreholeIds(result)) {
|
|
1334
|
+
ensureBorehole(boreholeId);
|
|
1335
|
+
}
|
|
1336
|
+
if (profile) {
|
|
1337
|
+
for (const column of profile.columns) {
|
|
1338
|
+
const borehole = ensureBorehole(column.boreholeId);
|
|
1339
|
+
for (const layer of column.layers) {
|
|
1340
|
+
const pageNumber = firstSourcePage([layer.sourcePages]);
|
|
1341
|
+
const warnings = layer.uncertain ? ['Layer boundary inferred or unverified.'] : [];
|
|
1342
|
+
const evidenceId = addReportEvidenceRef(evidenceState, {
|
|
1343
|
+
pageNumber,
|
|
1344
|
+
rawValue: layer.description,
|
|
1345
|
+
normalizedValue: `${layer.depthFrom}-${layer.depthTo}m ${layer.description}`,
|
|
1346
|
+
warnings,
|
|
1347
|
+
});
|
|
1348
|
+
const stratum = {
|
|
1349
|
+
boreholeId: borehole.id,
|
|
1350
|
+
topDepth: layer.depthFrom,
|
|
1351
|
+
bottomDepth: layer.depthTo,
|
|
1352
|
+
description: layer.description,
|
|
1353
|
+
evidenceIds: [evidenceId],
|
|
1354
|
+
confidence: confidenceRatio(result.confidence),
|
|
1355
|
+
warnings,
|
|
1356
|
+
};
|
|
1357
|
+
strata.push(stratum);
|
|
1358
|
+
borehole.strata.push(stratum);
|
|
1359
|
+
borehole.evidenceIds = uniqueStrings([...borehole.evidenceIds, evidenceId]);
|
|
1360
|
+
}
|
|
1361
|
+
// Groundwater is added from the source parameter rows below so page-level
|
|
1362
|
+
// evidence is preserved and duplicate profile-derived observations are avoided.
|
|
1363
|
+
}
|
|
1364
|
+
}
|
|
1365
|
+
for (const parameter of result.parameters) {
|
|
1366
|
+
const numericValue = numericParameterValue(parameter);
|
|
1367
|
+
const boreholeId = parameterBoreholeId(parameter);
|
|
1368
|
+
const depth = depthFromEvidenceText(parameter.context, parameter.material);
|
|
1369
|
+
const sourcePage = firstSourcePage([parameter.sourcePages]);
|
|
1370
|
+
const normalizedName = parameter.name.toLowerCase().replace(/\s+/g, '');
|
|
1371
|
+
if (numericValue != null && /spt|nvalue|n-value|standardpenetration/.test(normalizedName)) {
|
|
1372
|
+
if (!boreholeId || looksLikeBearingTableSptFalsePositive(parameter)) {
|
|
1373
|
+
continue;
|
|
1374
|
+
}
|
|
1375
|
+
const testDepth = depth ?? depthFromEvidenceText(parameter.valueText);
|
|
1376
|
+
if (testDepth != null && numericValue >= 0 && numericValue <= 100) {
|
|
1377
|
+
const evidenceId = addReportEvidenceRef(evidenceState, {
|
|
1378
|
+
pageNumber: sourcePage,
|
|
1379
|
+
rawValue: parameter.valueText,
|
|
1380
|
+
normalizedValue: numericValue,
|
|
1381
|
+
unit: parameter.unit,
|
|
1382
|
+
});
|
|
1383
|
+
ensureBorehole(boreholeId, [evidenceId]).sptTests.push({
|
|
1384
|
+
depth: testDepth,
|
|
1385
|
+
nValue: numericValue,
|
|
1386
|
+
...(parameter.unit ? { unit: parameter.unit } : {}),
|
|
1387
|
+
evidenceIds: [evidenceId],
|
|
1388
|
+
confidence: confidenceRatio(result.confidence),
|
|
1389
|
+
warnings: [],
|
|
1390
|
+
});
|
|
1391
|
+
}
|
|
1392
|
+
continue;
|
|
1393
|
+
}
|
|
1394
|
+
if (numericValue != null && /groundwater|ground\s*water|watertable|water\s*table|gwl/.test(normalizedName)) {
|
|
1395
|
+
const groundwaterDepth = depthFromEvidenceText(parameter.valueText, parameter.context, numericValue);
|
|
1396
|
+
if (groundwaterDepth != null) {
|
|
1397
|
+
const evidenceId = addReportEvidenceRef(evidenceState, {
|
|
1398
|
+
pageNumber: sourcePage,
|
|
1399
|
+
rawValue: parameter.valueText,
|
|
1400
|
+
normalizedValue: groundwaterDepth,
|
|
1401
|
+
unit: parameter.unit,
|
|
1402
|
+
});
|
|
1403
|
+
const observation = {
|
|
1404
|
+
...(boreholeId ? { boreholeId } : {}),
|
|
1405
|
+
depth: groundwaterDepth,
|
|
1406
|
+
evidenceIds: [evidenceId],
|
|
1407
|
+
confidence: confidenceRatio(result.confidence),
|
|
1408
|
+
warnings: [],
|
|
1409
|
+
};
|
|
1410
|
+
groundwater.push(observation);
|
|
1411
|
+
if (boreholeId) {
|
|
1412
|
+
ensureBorehole(boreholeId, [evidenceId]).groundwater.push(observation);
|
|
1413
|
+
}
|
|
1414
|
+
}
|
|
1415
|
+
continue;
|
|
1416
|
+
}
|
|
1417
|
+
if (numericValue == null || depth == null || /(?:^|[^a-z])depth|elevation|thickness/.test(normalizedName)) {
|
|
1418
|
+
continue;
|
|
1419
|
+
}
|
|
1420
|
+
const evidenceId = addReportEvidenceRef(evidenceState, {
|
|
1421
|
+
pageNumber: sourcePage,
|
|
1422
|
+
rawValue: parameter.valueText,
|
|
1423
|
+
normalizedValue: numericValue,
|
|
1424
|
+
unit: parameter.unit,
|
|
1425
|
+
});
|
|
1426
|
+
const visualParameter = {
|
|
1427
|
+
name: parameter.name,
|
|
1428
|
+
value: numericValue,
|
|
1429
|
+
...(parameter.unit ? { unit: parameter.unit } : {}),
|
|
1430
|
+
...(boreholeId ? { boreholeId } : {}),
|
|
1431
|
+
depth,
|
|
1432
|
+
evidenceIds: [evidenceId],
|
|
1433
|
+
confidence: confidenceRatio(result.confidence),
|
|
1434
|
+
warnings: [],
|
|
1435
|
+
};
|
|
1436
|
+
parameters.push(visualParameter);
|
|
1437
|
+
}
|
|
1438
|
+
const boreholeList = [...boreholes.values()].sort((left, right) => left.id.localeCompare(right.id, undefined, { numeric: true }));
|
|
1439
|
+
const sptTestCount = boreholeList.reduce((count, borehole) => count + borehole.sptTests.length, 0);
|
|
1440
|
+
if (strata.length === 0 && groundwater.length === 0 && parameters.length === 0 && sptTestCount === 0) {
|
|
1441
|
+
return undefined;
|
|
1442
|
+
}
|
|
1443
|
+
const labTests = parameters
|
|
1444
|
+
.filter((parameter) => parameter.depth != null)
|
|
1445
|
+
.map((parameter, index) => ({
|
|
1446
|
+
sampleId: `report-sample-${index + 1}`,
|
|
1447
|
+
...(parameter.boreholeId ? { boreholeId: parameter.boreholeId } : {}),
|
|
1448
|
+
depth: parameter.depth,
|
|
1449
|
+
parameters: [parameter],
|
|
1450
|
+
evidenceIds: parameter.evidenceIds,
|
|
1451
|
+
confidence: parameter.confidence,
|
|
1452
|
+
warnings: parameter.warnings,
|
|
1453
|
+
}));
|
|
1454
|
+
const model = {
|
|
1455
|
+
schemaVersion: 'ground-model.v1',
|
|
1456
|
+
generatedAt: result.generatedAt,
|
|
1457
|
+
project: {
|
|
1458
|
+
rootPath: result.source.filePath ?? result.source.fileName ?? sourceLabel,
|
|
1459
|
+
},
|
|
1460
|
+
coordinateSystem: {
|
|
1461
|
+
kind: 'unknown',
|
|
1462
|
+
warnings: ['PDF report evidence did not include plottable coordinate data.'],
|
|
1463
|
+
},
|
|
1464
|
+
boreholes: boreholeList,
|
|
1465
|
+
strata,
|
|
1466
|
+
groundwater,
|
|
1467
|
+
labTests,
|
|
1468
|
+
parameters,
|
|
1469
|
+
monitoringSeries: [],
|
|
1470
|
+
evidence: evidenceState.refs,
|
|
1471
|
+
rejectedObservations: [],
|
|
1472
|
+
warnings: ['GroundModel visual review was adapted from PDF report evidence; source-page verification is required before design use.'],
|
|
1473
|
+
stats: {
|
|
1474
|
+
boreholes: boreholeList.length,
|
|
1475
|
+
sptTests: sptTestCount,
|
|
1476
|
+
strata: strata.length,
|
|
1477
|
+
groundwaterObservations: groundwater.length,
|
|
1478
|
+
labTests: labTests.length,
|
|
1479
|
+
parameters: parameters.length,
|
|
1480
|
+
monitoringSeries: 0,
|
|
1481
|
+
evidenceRefs: evidenceState.refs.length,
|
|
1482
|
+
rejectedObservations: 0,
|
|
1483
|
+
},
|
|
1484
|
+
};
|
|
1485
|
+
return {
|
|
1486
|
+
...model,
|
|
1487
|
+
map: buildGroundModelMap(model),
|
|
1488
|
+
};
|
|
1489
|
+
}
|
|
1160
1490
|
function buildBoreholeProfile(result) {
|
|
1161
1491
|
if (result.boreholes.length === 0) {
|
|
1162
1492
|
return undefined;
|
|
@@ -1225,6 +1555,7 @@ export function buildIngestDossier(result, options) {
|
|
|
1225
1555
|
const cleanSummary = cleanNarrativeText(geotechResult.summary, 320);
|
|
1226
1556
|
const summary = cleanSummary
|
|
1227
1557
|
|| geotechOutcomeSummary(geotechResult);
|
|
1558
|
+
const boreholeProfile = buildGeotechBoreholeProfile(geotechResult);
|
|
1228
1559
|
return {
|
|
1229
1560
|
title,
|
|
1230
1561
|
subtitle: geotechResult.documentClass
|
|
@@ -1243,7 +1574,9 @@ export function buildIngestDossier(result, options) {
|
|
|
1243
1574
|
executiveItems: buildGeotechExecutiveItems(geotechResult, sourceLabel),
|
|
1244
1575
|
insightCards: buildGeotechInsightCards(geotechResult),
|
|
1245
1576
|
trustItems: buildGeotechTrustItems(geotechResult),
|
|
1246
|
-
|
|
1577
|
+
confidenceBreakdown: buildGeotechConfidenceItems(geotechResult),
|
|
1578
|
+
boreholeProfile,
|
|
1579
|
+
groundModel: buildGroundModelFromGeotechReport(geotechResult, boreholeProfile, sourceLabel),
|
|
1247
1580
|
storedReview,
|
|
1248
1581
|
approval,
|
|
1249
1582
|
footerNotes: buildFooterNotes(geotechResult),
|