@suss/extractor 0.35.1 → 0.36.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/index.cjs +335 -91
- package/dist/index.d.cts +277 -29
- package/dist/index.d.ts +277 -29
- package/dist/index.js +294 -60
- package/package.json +2 -2
package/dist/index.cjs
CHANGED
|
@@ -48,6 +48,7 @@ __export(index_exports, {
|
|
|
48
48
|
assembleSummary: () => assembleSummary,
|
|
49
49
|
assessConfidence: () => assessConfidence,
|
|
50
50
|
buildUngatedExtractionReport: () => buildUngatedExtractionReport,
|
|
51
|
+
callSiteKey: () => callSiteKey,
|
|
51
52
|
chosenCacheRoot: () => chosenCacheRoot,
|
|
52
53
|
commonDirectoryOf: () => commonDirectoryOf,
|
|
53
54
|
composeWrappers: () => composeWrappers,
|
|
@@ -59,23 +60,28 @@ __export(index_exports, {
|
|
|
59
60
|
createCodeHasher: () => createCodeHasher,
|
|
60
61
|
createPackTallies: () => createPackTallies,
|
|
61
62
|
createTimer: () => createTimer,
|
|
63
|
+
describeMissingPath: () => describeMissingPath,
|
|
62
64
|
detectGaps: () => detectGaps,
|
|
63
65
|
effectToIR: () => effectToIR,
|
|
66
|
+
effectsFiringOn: () => effectsFiringOn,
|
|
64
67
|
emptyTally: () => emptyTally,
|
|
65
68
|
enumerateOrDegrade: () => enumerateOrDegrade,
|
|
66
69
|
enumerateStructuredPaths: () => enumerateStructuredPaths,
|
|
67
70
|
evaluatePackHealth: () => evaluatePackHealth,
|
|
68
71
|
extractionCacheDirFor: () => extractionCacheDirFor,
|
|
69
72
|
extractionConfigStamp: () => extractionConfigStamp,
|
|
73
|
+
firesOn: () => firesOn,
|
|
70
74
|
firstWrittenReading: () => firstWrittenReading,
|
|
71
75
|
formatPackHealth: () => formatPackHealth,
|
|
72
76
|
guardsHoldOn: () => guardsHoldOn,
|
|
73
77
|
helperPathsOnVariables: () => helperPathsOnVariables,
|
|
74
78
|
httpRouteDiscovery: () => httpRouteDiscovery,
|
|
75
79
|
isListedTestFile: () => isListedTestFile,
|
|
80
|
+
libraryEnvReadMarker: () => libraryEnvReadMarker,
|
|
76
81
|
liveRecordFor: () => liveRecordFor,
|
|
77
82
|
makeIgnoredDirectory: () => makeIgnoredDirectory,
|
|
78
83
|
makeTransitionId: () => makeTransitionId,
|
|
84
|
+
mapFolderFor: () => mapFolderFor,
|
|
79
85
|
mapReading: () => mapReading,
|
|
80
86
|
markReturnsAsExitCode: () => markReturnsAsExitCode,
|
|
81
87
|
matchesTestFileName: () => matchesTestFileName,
|
|
@@ -83,10 +89,13 @@ __export(index_exports, {
|
|
|
83
89
|
moduleInitStructure: () => moduleInitStructure,
|
|
84
90
|
moduleOfFile: () => moduleOfFile,
|
|
85
91
|
noopTimer: () => noopTimer,
|
|
92
|
+
numberRepeatedCallSites: () => numberRepeatedCallSites,
|
|
86
93
|
ownersWhereWritten: () => ownersWhereWritten,
|
|
87
94
|
packConfigCheck: () => packConfigCheck,
|
|
88
95
|
packGradients: () => packGradients,
|
|
96
|
+
packPathCheck: () => packPathCheck,
|
|
89
97
|
paramToInput: () => paramToInput,
|
|
98
|
+
placeTerminals: () => placeTerminals,
|
|
90
99
|
processCodeHasher: () => processCodeHasher,
|
|
91
100
|
projectFileStamp: () => projectFileStamp,
|
|
92
101
|
rawConditionToPredicate: () => rawConditionToPredicate,
|
|
@@ -104,6 +113,7 @@ __export(index_exports, {
|
|
|
104
113
|
stampMayMissAWrite: () => stampMayMissAWrite,
|
|
105
114
|
stampModuleImports: () => stampModuleImports,
|
|
106
115
|
stampModules: () => stampModules,
|
|
116
|
+
statementSites: () => statementSites,
|
|
107
117
|
storageSystemOption: () => storageSystemOption,
|
|
108
118
|
summaryCountsByPack: () => summaryCountsByPack,
|
|
109
119
|
tallyUnit: () => tallyUnit,
|
|
@@ -117,8 +127,8 @@ __export(index_exports, {
|
|
|
117
127
|
writtenReading: () => writtenReading
|
|
118
128
|
});
|
|
119
129
|
module.exports = __toCommonJS(index_exports);
|
|
120
|
-
var
|
|
121
|
-
var
|
|
130
|
+
var import_node_crypto8 = require("crypto");
|
|
131
|
+
var import_behavioral_ir10 = require("@suss/behavioral-ir");
|
|
122
132
|
|
|
123
133
|
// src/contractStatusGaps.ts
|
|
124
134
|
var import_behavioral_ir = require("@suss/behavioral-ir");
|
|
@@ -271,27 +281,66 @@ function mergeInputReads(derived, syntactic) {
|
|
|
271
281
|
return [...found.values()];
|
|
272
282
|
}
|
|
273
283
|
|
|
274
|
-
// src/
|
|
284
|
+
// src/callSiteGroup.ts
|
|
285
|
+
var import_node_crypto = require("crypto");
|
|
275
286
|
var import_behavioral_ir2 = require("@suss/behavioral-ir");
|
|
287
|
+
function callSiteKey(effect) {
|
|
288
|
+
const callee = calleeOf(effect);
|
|
289
|
+
const written = callee === void 0 ? effect : { ...effect, callee: (0, import_behavioral_ir2.normalizeCalleeText)(callee) };
|
|
290
|
+
const hash = (0, import_node_crypto.createHash)("sha1").update((0, import_behavioral_ir2.effectKey)(written)).digest("hex").slice(0, 7);
|
|
291
|
+
return callee === void 0 ? hash : `${(0, import_behavioral_ir2.normalizeCalleeText)(callee)}:${hash}`;
|
|
292
|
+
}
|
|
293
|
+
function calleeOf(effect) {
|
|
294
|
+
return effect.type === "interaction" || effect.type === "invocation" ? effect.callee : void 0;
|
|
295
|
+
}
|
|
296
|
+
function numberRepeatedCallSites(sites) {
|
|
297
|
+
const taken = /* @__PURE__ */ new Map();
|
|
298
|
+
return sites.map((entries) => {
|
|
299
|
+
const ids = /* @__PURE__ */ new Map();
|
|
300
|
+
for (const key of new Set(
|
|
301
|
+
entries.flatMap((entry) => groupIdOf(entry.effect))
|
|
302
|
+
)) {
|
|
303
|
+
const count = (taken.get(key) ?? 0) + 1;
|
|
304
|
+
taken.set(key, count);
|
|
305
|
+
ids.set(key, count === 1 ? key : `${key}#${count}`);
|
|
306
|
+
}
|
|
307
|
+
return entries.map((entry) => ({
|
|
308
|
+
...entry,
|
|
309
|
+
effect: withGroupId(entry.effect, ids)
|
|
310
|
+
}));
|
|
311
|
+
});
|
|
312
|
+
}
|
|
313
|
+
function groupIdOf(effect) {
|
|
314
|
+
return effect.type === "interaction" && effect.groupId !== void 0 ? [effect.groupId] : [];
|
|
315
|
+
}
|
|
316
|
+
function withGroupId(effect, ids) {
|
|
317
|
+
if (effect.type !== "interaction" || effect.groupId === void 0) {
|
|
318
|
+
return effect;
|
|
319
|
+
}
|
|
320
|
+
return { ...effect, groupId: ids.get(effect.groupId) ?? effect.groupId };
|
|
321
|
+
}
|
|
322
|
+
|
|
323
|
+
// src/composeWrappers.ts
|
|
324
|
+
var import_behavioral_ir3 = require("@suss/behavioral-ir");
|
|
276
325
|
function composeWrappers(summaries, options = {}) {
|
|
277
|
-
const chain = (0,
|
|
326
|
+
const chain = (0, import_behavioral_ir3.wrapperIndex)(summaries);
|
|
278
327
|
const keepGaps = options.gapHandling !== "silent";
|
|
279
328
|
return summaries.map((summary) => composeOne(summary, chain, keepGaps));
|
|
280
329
|
}
|
|
281
330
|
function composeOne(summary, chain, keepGaps) {
|
|
282
|
-
const recorded = (0,
|
|
331
|
+
const recorded = (0, import_behavioral_ir3.readWrapperMetadata)(summary);
|
|
283
332
|
const applied = recorded?.applied ?? [];
|
|
284
333
|
const covering = applied.filter(
|
|
285
334
|
(reference) => coversUnit(reference, summary)
|
|
286
335
|
);
|
|
287
336
|
const narrowed = covering.length === applied.length ? summary : {
|
|
288
337
|
...summary,
|
|
289
|
-
metadata: (0,
|
|
338
|
+
metadata: (0, import_behavioral_ir3.withWrapperMetadata)(summary.metadata, {
|
|
290
339
|
applied: covering
|
|
291
340
|
})
|
|
292
341
|
};
|
|
293
342
|
const wrappers = covering.flatMap((reference) => {
|
|
294
|
-
const found = (0,
|
|
343
|
+
const found = (0, import_behavioral_ir3.wrapperFor)(chain, reference);
|
|
295
344
|
return found === void 0 ? [] : [{ reference, summary: found }];
|
|
296
345
|
});
|
|
297
346
|
if (wrappers.length === 0) {
|
|
@@ -356,8 +405,8 @@ function settledUncaught(transitions, wrappers) {
|
|
|
356
405
|
function markedCaught(transition) {
|
|
357
406
|
return {
|
|
358
407
|
...transition,
|
|
359
|
-
metadata: (0,
|
|
360
|
-
...(0,
|
|
408
|
+
metadata: (0, import_behavioral_ir3.withWrapperMetadata)(transition.metadata, {
|
|
409
|
+
...(0, import_behavioral_ir3.readWrapperMetadata)(transition),
|
|
361
410
|
caught: true
|
|
362
411
|
})
|
|
363
412
|
};
|
|
@@ -470,9 +519,9 @@ function catchMatch(reference, thrown) {
|
|
|
470
519
|
return unread || reference.mayCatchAny === true ? "maybe" : "no";
|
|
471
520
|
}
|
|
472
521
|
function withContractStatusGaps(summary, composed, handled) {
|
|
473
|
-
const contract = (0,
|
|
522
|
+
const contract = (0, import_behavioral_ir3.readHttpMetadata)(summary)?.declaredContract;
|
|
474
523
|
const binding = summary.identity.boundaryBinding;
|
|
475
|
-
if (contract === void 0 || binding !== null && !(0,
|
|
524
|
+
if (contract === void 0 || binding !== null && !(0, import_behavioral_ir3.exchangesHttpResponses)(binding)) {
|
|
476
525
|
return summary.gaps;
|
|
477
526
|
}
|
|
478
527
|
const declared = {
|
|
@@ -497,12 +546,12 @@ function coversUnit(reference, summary) {
|
|
|
497
546
|
return true;
|
|
498
547
|
}
|
|
499
548
|
const binding = summary.identity.boundaryBinding;
|
|
500
|
-
return binding !== null && (0,
|
|
549
|
+
return binding !== null && (0, import_behavioral_ir3.withinScope)(binding, reference.scope);
|
|
501
550
|
}
|
|
502
551
|
function attribute(transitions, reference, catchUncertain = false) {
|
|
503
552
|
return transitions.map((transition) => ({
|
|
504
553
|
...transition,
|
|
505
|
-
metadata: (0,
|
|
554
|
+
metadata: (0, import_behavioral_ir3.withWrapperMetadata)(transition.metadata, {
|
|
506
555
|
from: reference,
|
|
507
556
|
...catchUncertain ? { catchUncertain } : {}
|
|
508
557
|
})
|
|
@@ -570,6 +619,22 @@ function modulesStamp(modules) {
|
|
|
570
619
|
// src/effectGuards.ts
|
|
571
620
|
var keyOf = (condition) => `${condition.polarity}:${condition.sourceText}`;
|
|
572
621
|
var opposite = (condition) => `${condition.polarity === "positive" ? "negative" : "positive"}:${condition.sourceText}`;
|
|
622
|
+
function firesOn(site, branch) {
|
|
623
|
+
const loop = branch.loopAround;
|
|
624
|
+
if (loop !== void 0 && site.line >= loop.start && site.line <= loop.end) {
|
|
625
|
+
return true;
|
|
626
|
+
}
|
|
627
|
+
if (!guardsHoldOn(site.preconditions, branch.conditions)) {
|
|
628
|
+
return false;
|
|
629
|
+
}
|
|
630
|
+
return runsBefore(
|
|
631
|
+
site.cleansUpFrom ?? site.line,
|
|
632
|
+
branch.terminal.location.end
|
|
633
|
+
);
|
|
634
|
+
}
|
|
635
|
+
function effectsFiringOn(placed, branch) {
|
|
636
|
+
return placed.filter((one) => firesOn(one.site, branch)).map((one) => one.effect);
|
|
637
|
+
}
|
|
573
638
|
function guardsHoldOn(preconditions, conditions) {
|
|
574
639
|
if (preconditions === void 0 || preconditions.length === 0) {
|
|
575
640
|
return true;
|
|
@@ -585,14 +650,14 @@ function runsBefore(effectLine, terminalEndLine) {
|
|
|
585
650
|
|
|
586
651
|
// src/exitCode.ts
|
|
587
652
|
var import_node_path2 = __toESM(require("path"), 1);
|
|
588
|
-
var
|
|
653
|
+
var import_behavioral_ir4 = require("@suss/behavioral-ir");
|
|
589
654
|
function markReturnsAsExitCode(summaries, returnsTheCode, workspaceRoot) {
|
|
590
655
|
for (const summary of summaries) {
|
|
591
656
|
const span = summary.location.span;
|
|
592
657
|
const file = workspaceRoot === void 0 ? summary.location.file : import_node_path2.default.resolve(workspaceRoot, summary.location.file);
|
|
593
658
|
markExitCodeFrom(
|
|
594
659
|
summary,
|
|
595
|
-
span !== void 0 && returnsTheCode.has((0,
|
|
660
|
+
span !== void 0 && returnsTheCode.has((0, import_behavioral_ir4.declarationKey)(file, span))
|
|
596
661
|
);
|
|
597
662
|
}
|
|
598
663
|
}
|
|
@@ -619,7 +684,7 @@ function markExitCodeFrom(summary, marked) {
|
|
|
619
684
|
}
|
|
620
685
|
|
|
621
686
|
// src/helperHandOff.ts
|
|
622
|
-
var
|
|
687
|
+
var import_behavioral_ir5 = require("@suss/behavioral-ir");
|
|
623
688
|
var MAX_HELPER_PATHS = 16;
|
|
624
689
|
function throughHelper(branch, at, helperBranches) {
|
|
625
690
|
return helperBranches.map((helper) => {
|
|
@@ -637,16 +702,21 @@ function throughHelper(branch, at, helperBranches) {
|
|
|
637
702
|
isDefault: branch.isDefault && helper.isDefault
|
|
638
703
|
};
|
|
639
704
|
}
|
|
705
|
+
const { loopAround, ...rest } = branch;
|
|
640
706
|
return {
|
|
641
|
-
...
|
|
707
|
+
...rest,
|
|
642
708
|
...reads,
|
|
643
709
|
conditions,
|
|
644
710
|
terminal: { ...helper.terminal, location: at },
|
|
645
711
|
location: at,
|
|
712
|
+
...loopAround !== void 0 && within(at, loopAround) ? { loopAround } : {},
|
|
646
713
|
isDefault: false
|
|
647
714
|
};
|
|
648
715
|
});
|
|
649
716
|
}
|
|
717
|
+
function within(inner, outer) {
|
|
718
|
+
return inner.start >= outer.start && inner.end <= outer.end;
|
|
719
|
+
}
|
|
650
720
|
function mergeReadShapes(a, b) {
|
|
651
721
|
if (a === null || b === null) {
|
|
652
722
|
return a ?? b;
|
|
@@ -664,12 +734,11 @@ function mergeReadShapes(a, b) {
|
|
|
664
734
|
function splitAtHandOffs(branch, sites, from = 0) {
|
|
665
735
|
for (let index = from; index < sites.length; index++) {
|
|
666
736
|
const site = sites[index];
|
|
667
|
-
|
|
668
|
-
if (!reached || !guardsHoldOn(site.preconditions, branch.conditions)) {
|
|
737
|
+
if (!firesOn(site, branch)) {
|
|
669
738
|
continue;
|
|
670
739
|
}
|
|
671
740
|
return throughHelper(branch, site.at, site.helper).flatMap(
|
|
672
|
-
(
|
|
741
|
+
(path11) => path11.terminal === branch.terminal ? splitAtHandOffs(path11, sites, index + 1) : [path11]
|
|
673
742
|
);
|
|
674
743
|
}
|
|
675
744
|
return [branch];
|
|
@@ -685,7 +754,7 @@ function helperPathsOnVariables(helperBranches, passed) {
|
|
|
685
754
|
const variables = new Set(passed.values());
|
|
686
755
|
const testsWhatItGot = renamed.some(
|
|
687
756
|
(branch) => branch.conditions.some(
|
|
688
|
-
(condition) => condition.structured !== null && (0,
|
|
757
|
+
(condition) => condition.structured !== null && (0, import_behavioral_ir5.predicateRefs)(condition.structured).some(
|
|
689
758
|
(ref) => variables.has(rootName(ref) ?? "")
|
|
690
759
|
)
|
|
691
760
|
)
|
|
@@ -707,7 +776,7 @@ function onCallerVariables(predicate, passed) {
|
|
|
707
776
|
}
|
|
708
777
|
return ref;
|
|
709
778
|
};
|
|
710
|
-
return (0,
|
|
779
|
+
return (0, import_behavioral_ir5.replacePredicateRefs)(predicate, rename);
|
|
711
780
|
}
|
|
712
781
|
function rootName(ref) {
|
|
713
782
|
if (ref.type === "derived") {
|
|
@@ -716,6 +785,34 @@ function rootName(ref) {
|
|
|
716
785
|
return ref.type === "dependency" ? ref.name : null;
|
|
717
786
|
}
|
|
718
787
|
|
|
788
|
+
// src/libraryEnvReads.ts
|
|
789
|
+
var import_behavioral_ir6 = require("@suss/behavioral-ir");
|
|
790
|
+
function libraryEnvReadMarker(recognition, declared, importer) {
|
|
791
|
+
return {
|
|
792
|
+
kind: "library",
|
|
793
|
+
location: { file: importer, range: { start: 0, end: 0 }, exportName: null },
|
|
794
|
+
identity: {
|
|
795
|
+
name: `${declared.module} env reads`,
|
|
796
|
+
exportPath: null,
|
|
797
|
+
boundaryBinding: (0, import_behavioral_ir6.functionCallBinding)({
|
|
798
|
+
transport: "in-process",
|
|
799
|
+
recognition
|
|
800
|
+
})
|
|
801
|
+
},
|
|
802
|
+
inputs: [],
|
|
803
|
+
transitions: [],
|
|
804
|
+
gaps: [],
|
|
805
|
+
confidence: { source: "declared", level: "high" },
|
|
806
|
+
metadata: {
|
|
807
|
+
libraryEnvReads: {
|
|
808
|
+
module: declared.module,
|
|
809
|
+
...declared.prefixes !== void 0 ? { prefixes: declared.prefixes } : {},
|
|
810
|
+
...declared.names !== void 0 ? { names: declared.names } : {}
|
|
811
|
+
}
|
|
812
|
+
}
|
|
813
|
+
};
|
|
814
|
+
}
|
|
815
|
+
|
|
719
816
|
// src/moduleImports.ts
|
|
720
817
|
function stampModuleImports(summaries, importsOf2) {
|
|
721
818
|
const byFile = /* @__PURE__ */ new Map();
|
|
@@ -969,7 +1066,7 @@ var configuredCallOption = import_zod.z.object({
|
|
|
969
1066
|
}).strict();
|
|
970
1067
|
|
|
971
1068
|
// src/paths/enumeratePaths.ts
|
|
972
|
-
var
|
|
1069
|
+
var import_behavioral_ir7 = require("@suss/behavioral-ir");
|
|
973
1070
|
var MAX_PATHS = 256;
|
|
974
1071
|
var UnmodeledFlow = class extends Error {
|
|
975
1072
|
};
|
|
@@ -1013,12 +1110,12 @@ var loopCompletedCond = (headerText, exit) => fixedCond(
|
|
|
1013
1110
|
exit === "throw" ? "earlyThrow" : "earlyReturn"
|
|
1014
1111
|
);
|
|
1015
1112
|
var catchEntryCond = () => fixedCond(
|
|
1016
|
-
{ sourceText:
|
|
1113
|
+
{ sourceText: import_behavioral_ir7.CATCH_ENTRY_TEXT, expression: null },
|
|
1017
1114
|
"positive",
|
|
1018
1115
|
"catchBlock"
|
|
1019
1116
|
);
|
|
1020
|
-
function classify(
|
|
1021
|
-
return
|
|
1117
|
+
function classify(path11, home, isAncestorOrSelf) {
|
|
1118
|
+
return path11.map((cond) => {
|
|
1022
1119
|
if (cond.branchStmt === null) {
|
|
1023
1120
|
return cond.info;
|
|
1024
1121
|
}
|
|
@@ -1090,9 +1187,9 @@ function limitOpenPaths(paths) {
|
|
|
1090
1187
|
);
|
|
1091
1188
|
}
|
|
1092
1189
|
}
|
|
1093
|
-
function recordTerminal(ctx, terminal, home,
|
|
1190
|
+
function recordTerminal(ctx, terminal, home, path11) {
|
|
1094
1191
|
chargeBudget(ctx.state);
|
|
1095
|
-
const info = classify(
|
|
1192
|
+
const info = classify(path11, home, ctx.isAncestorOrSelf);
|
|
1096
1193
|
const existing = ctx.state.byTerminal.get(terminal) ?? [];
|
|
1097
1194
|
existing.push(info);
|
|
1098
1195
|
ctx.state.byTerminal.set(terminal, existing);
|
|
@@ -1103,15 +1200,15 @@ function containsTerminal(ctx, stmt) {
|
|
|
1103
1200
|
}
|
|
1104
1201
|
return childrenOf(stmt).some((child) => containsTerminal(ctx, child));
|
|
1105
1202
|
}
|
|
1106
|
-
function stepIf(stmt,
|
|
1203
|
+
function stepIf(stmt, path11, ctx) {
|
|
1107
1204
|
const thenExit = exitKindOfList(stmt.thenBody);
|
|
1108
1205
|
const elseExit = stmt.elseBody === null ? null : exitKindOfList(stmt.elseBody);
|
|
1109
1206
|
const thenPath = [
|
|
1110
|
-
...
|
|
1207
|
+
...path11,
|
|
1111
1208
|
branchCond(stmt, stmt.condition, "positive", elseExit)
|
|
1112
1209
|
];
|
|
1113
1210
|
const elsePath = [
|
|
1114
|
-
...
|
|
1211
|
+
...path11,
|
|
1115
1212
|
branchCond(
|
|
1116
1213
|
stmt,
|
|
1117
1214
|
stmt.condition,
|
|
@@ -1128,7 +1225,7 @@ function stepIf(stmt, path10, ctx) {
|
|
|
1128
1225
|
}
|
|
1129
1226
|
return out;
|
|
1130
1227
|
}
|
|
1131
|
-
function stepSwitch(stmt,
|
|
1228
|
+
function stepSwitch(stmt, path11, ctx) {
|
|
1132
1229
|
const out = [];
|
|
1133
1230
|
const negations = [];
|
|
1134
1231
|
let defaultRanBody = false;
|
|
@@ -1138,7 +1235,7 @@ function stepSwitch(stmt, path10, ctx) {
|
|
|
1138
1235
|
if (hasStrayBreak(group.body)) {
|
|
1139
1236
|
throw new UnmodeledFlow("non-trailing break in switch clause");
|
|
1140
1237
|
}
|
|
1141
|
-
const groupPath = group.condition === null ? [...
|
|
1238
|
+
const groupPath = group.condition === null ? [...path11, ...negations] : [...path11, fixedCond(group.condition, "positive", "explicit")];
|
|
1142
1239
|
const conts = enumerate(ctx, group.body, groupPath);
|
|
1143
1240
|
if (conts.length > 0) {
|
|
1144
1241
|
if (!group.hasTrailingBreak && !fallthroughSafe) {
|
|
@@ -1155,24 +1252,24 @@ function stepSwitch(stmt, path10, ctx) {
|
|
|
1155
1252
|
}
|
|
1156
1253
|
}
|
|
1157
1254
|
if (!defaultRanBody) {
|
|
1158
|
-
out.push([...
|
|
1255
|
+
out.push([...path11, ...negations]);
|
|
1159
1256
|
}
|
|
1160
1257
|
return out;
|
|
1161
1258
|
}
|
|
1162
|
-
function stepLoop(stmt,
|
|
1259
|
+
function stepLoop(stmt, path11, ctx) {
|
|
1163
1260
|
const bodyExit = exitKindOfList(stmt.body);
|
|
1164
1261
|
if (containsTerminal(ctx, stmt)) {
|
|
1165
1262
|
enumerate(ctx, stmt.body, [
|
|
1166
|
-
...
|
|
1263
|
+
...path11,
|
|
1167
1264
|
loopIterationCond(stmt.condition.sourceText)
|
|
1168
1265
|
]);
|
|
1169
1266
|
}
|
|
1170
1267
|
if (bodyExit !== null) {
|
|
1171
|
-
return [[...
|
|
1268
|
+
return [[...path11, loopCompletedCond(stmt.condition.sourceText, bodyExit)]];
|
|
1172
1269
|
}
|
|
1173
|
-
return [
|
|
1270
|
+
return [path11];
|
|
1174
1271
|
}
|
|
1175
|
-
function stepTry(stmt,
|
|
1272
|
+
function stepTry(stmt, path11, ctx) {
|
|
1176
1273
|
if (stmt.finallyBody !== null) {
|
|
1177
1274
|
const finallyHasTerminal = stmt.finallyBody.some(
|
|
1178
1275
|
(s) => containsTerminal(ctx, s)
|
|
@@ -1182,22 +1279,22 @@ function stepTry(stmt, path10, ctx) {
|
|
|
1182
1279
|
}
|
|
1183
1280
|
}
|
|
1184
1281
|
const out = [];
|
|
1185
|
-
out.push(...enumerate(ctx, stmt.tryBody,
|
|
1282
|
+
out.push(...enumerate(ctx, stmt.tryBody, path11));
|
|
1186
1283
|
if (stmt.catchBody !== null) {
|
|
1187
|
-
const catchPath = [...
|
|
1284
|
+
const catchPath = [...path11, catchEntryCond()];
|
|
1188
1285
|
out.push(...enumerate(ctx, stmt.catchBody, catchPath));
|
|
1189
1286
|
}
|
|
1190
1287
|
return out;
|
|
1191
1288
|
}
|
|
1192
|
-
function stepExit(stmt,
|
|
1289
|
+
function stepExit(stmt, path11, ctx) {
|
|
1193
1290
|
const collector = ctx.state.callbackExits[ctx.state.callbackExits.length - 1];
|
|
1194
1291
|
if (collector !== void 0 && (stmt.exit === "return" || stmt.exit === "throw")) {
|
|
1195
|
-
collector.push(
|
|
1292
|
+
collector.push(path11);
|
|
1196
1293
|
}
|
|
1197
1294
|
return [];
|
|
1198
1295
|
}
|
|
1199
|
-
function stepOpaque(_stmt,
|
|
1200
|
-
return [
|
|
1296
|
+
function stepOpaque(_stmt, path11, _ctx) {
|
|
1297
|
+
return [path11];
|
|
1201
1298
|
}
|
|
1202
1299
|
var stepHandlers = {
|
|
1203
1300
|
if: stepIf,
|
|
@@ -1207,20 +1304,20 @@ var stepHandlers = {
|
|
|
1207
1304
|
exit: stepExit,
|
|
1208
1305
|
opaque: stepOpaque
|
|
1209
1306
|
};
|
|
1210
|
-
function stepCallback(ctx, body,
|
|
1307
|
+
function stepCallback(ctx, body, path11) {
|
|
1211
1308
|
const exits = [];
|
|
1212
1309
|
ctx.state.callbackExits.push(exits);
|
|
1213
1310
|
let fellThrough;
|
|
1214
1311
|
try {
|
|
1215
|
-
fellThrough = enumerate(ctx, body,
|
|
1312
|
+
fellThrough = enumerate(ctx, body, path11);
|
|
1216
1313
|
} finally {
|
|
1217
1314
|
ctx.state.callbackExits.pop();
|
|
1218
1315
|
}
|
|
1219
1316
|
const out = [...fellThrough, ...exits];
|
|
1220
|
-
return out.length === 0 ? [
|
|
1317
|
+
return out.length === 0 ? [path11] : out;
|
|
1221
1318
|
}
|
|
1222
|
-
function stepStatement(ctx, stmt,
|
|
1223
|
-
let paths = [
|
|
1319
|
+
function stepStatement(ctx, stmt, path11) {
|
|
1320
|
+
let paths = [path11];
|
|
1224
1321
|
for (const body of stmt.callbacks ?? []) {
|
|
1225
1322
|
paths = paths.flatMap((each) => stepCallback(ctx, body, each));
|
|
1226
1323
|
limitOpenPaths(paths);
|
|
@@ -1307,8 +1404,8 @@ function enumerate(ctx, stmts, prefix) {
|
|
|
1307
1404
|
let frontiers = [[...prefix]];
|
|
1308
1405
|
for (const stmt of stmts) {
|
|
1309
1406
|
const nextFrontiers = [];
|
|
1310
|
-
for (const
|
|
1311
|
-
nextFrontiers.push(...stepStatement(ctx, stmt,
|
|
1407
|
+
for (const path11 of mergeRejoined(frontiers, ctx.keepsArms)) {
|
|
1408
|
+
nextFrontiers.push(...stepStatement(ctx, stmt, path11));
|
|
1312
1409
|
}
|
|
1313
1410
|
frontiers = nextFrontiers;
|
|
1314
1411
|
limitOpenPaths(frontiers);
|
|
@@ -1332,6 +1429,39 @@ function buildParentMap(statements) {
|
|
|
1332
1429
|
}
|
|
1333
1430
|
return parentOf;
|
|
1334
1431
|
}
|
|
1432
|
+
function placeTerminals(input, parentOf = buildParentMap(input.statements)) {
|
|
1433
|
+
const placement = /* @__PURE__ */ new Map();
|
|
1434
|
+
for (const [home, terminals] of input.terminalsByStmt) {
|
|
1435
|
+
const placed = placementOf(home, parentOf);
|
|
1436
|
+
if (placed.loopAround === void 0 && placed.cleansUpFrom === void 0) {
|
|
1437
|
+
continue;
|
|
1438
|
+
}
|
|
1439
|
+
for (const terminal of terminals) {
|
|
1440
|
+
placement.set(terminal, placed);
|
|
1441
|
+
}
|
|
1442
|
+
}
|
|
1443
|
+
return placement;
|
|
1444
|
+
}
|
|
1445
|
+
function placementOf(home, parentOf) {
|
|
1446
|
+
let loopAround = home.kind === "loop" ? home.lines : void 0;
|
|
1447
|
+
let cleansUpFrom;
|
|
1448
|
+
let child = home;
|
|
1449
|
+
let parent = parentOf.get(home) ?? null;
|
|
1450
|
+
while (parent !== null) {
|
|
1451
|
+
if (parent.kind === "loop" && parent.lines !== void 0) {
|
|
1452
|
+
loopAround = parent.lines;
|
|
1453
|
+
}
|
|
1454
|
+
if (parent.kind === "try" && parent.lines !== void 0 && (parent.finallyBody ?? []).includes(child)) {
|
|
1455
|
+
cleansUpFrom = parent.lines.start;
|
|
1456
|
+
}
|
|
1457
|
+
child = parent;
|
|
1458
|
+
parent = parentOf.get(parent) ?? null;
|
|
1459
|
+
}
|
|
1460
|
+
return {
|
|
1461
|
+
...loopAround === void 0 ? {} : { loopAround: { start: loopAround.start, end: loopAround.end } },
|
|
1462
|
+
...cleansUpFrom === void 0 ? {} : { cleansUpFrom }
|
|
1463
|
+
};
|
|
1464
|
+
}
|
|
1335
1465
|
function enumerateStructuredPaths(input) {
|
|
1336
1466
|
const parentOf = buildParentMap(input.statements);
|
|
1337
1467
|
const isAncestorOrSelf = (a, b) => {
|
|
@@ -1357,11 +1487,15 @@ function enumerateStructuredPaths(input) {
|
|
|
1357
1487
|
isAncestorOrSelf
|
|
1358
1488
|
};
|
|
1359
1489
|
const continuations = withRejoined(enumerate(ctx, input.statements, []));
|
|
1360
|
-
for (const
|
|
1490
|
+
for (const path11 of continuations) {
|
|
1361
1491
|
chargeBudget(state);
|
|
1362
|
-
state.fallthrough.push(classify(
|
|
1492
|
+
state.fallthrough.push(classify(path11, null, isAncestorOrSelf));
|
|
1363
1493
|
}
|
|
1364
|
-
return {
|
|
1494
|
+
return {
|
|
1495
|
+
byTerminal: state.byTerminal,
|
|
1496
|
+
fallthrough: state.fallthrough,
|
|
1497
|
+
placement: placeTerminals(input, parentOf)
|
|
1498
|
+
};
|
|
1365
1499
|
}
|
|
1366
1500
|
function enumerateOrDegrade(input, terminals) {
|
|
1367
1501
|
try {
|
|
@@ -1381,9 +1515,28 @@ function enumerateOrDegrade(input, terminals) {
|
|
|
1381
1515
|
for (const terminal of terminals) {
|
|
1382
1516
|
byTerminal.set(terminal, [[marker]]);
|
|
1383
1517
|
}
|
|
1384
|
-
return {
|
|
1518
|
+
return {
|
|
1519
|
+
byTerminal,
|
|
1520
|
+
fallthrough: [[marker]],
|
|
1521
|
+
placement: placeTerminals(input),
|
|
1522
|
+
degraded: reason
|
|
1523
|
+
};
|
|
1385
1524
|
}
|
|
1386
1525
|
}
|
|
1526
|
+
function enumerateCallStatements(input, terminals) {
|
|
1527
|
+
const placement = placeTerminals(input);
|
|
1528
|
+
const enumerable = new Map(
|
|
1529
|
+
[...input.terminalsByStmt].filter(
|
|
1530
|
+
([, found]) => found.every(
|
|
1531
|
+
(terminal) => placement.get(terminal)?.cleansUpFrom === void 0
|
|
1532
|
+
)
|
|
1533
|
+
)
|
|
1534
|
+
);
|
|
1535
|
+
return {
|
|
1536
|
+
...enumerateOrDegrade({ ...input, terminalsByStmt: enumerable }, terminals),
|
|
1537
|
+
placement
|
|
1538
|
+
};
|
|
1539
|
+
}
|
|
1387
1540
|
function reasonToDegrade(error) {
|
|
1388
1541
|
if (error instanceof PathBudgetExceeded) {
|
|
1389
1542
|
return error.message === "" ? "path budget exceeded" : error.message;
|
|
@@ -1402,8 +1555,8 @@ function sharedGatingConditions(paths, readPredicate) {
|
|
|
1402
1555
|
return [];
|
|
1403
1556
|
}
|
|
1404
1557
|
const shared = new Set(first.map(keyOf2));
|
|
1405
|
-
for (const
|
|
1406
|
-
const here = new Set(
|
|
1558
|
+
for (const path11 of rest) {
|
|
1559
|
+
const here = new Set(path11.map(keyOf2));
|
|
1407
1560
|
for (const value of shared) {
|
|
1408
1561
|
if (!here.has(value)) {
|
|
1409
1562
|
shared.delete(value);
|
|
@@ -1521,6 +1674,43 @@ function walkDescendants(root, carried, childrenOf2, visitor) {
|
|
|
1521
1674
|
}
|
|
1522
1675
|
}
|
|
1523
1676
|
|
|
1677
|
+
// src/paths/statementSites.ts
|
|
1678
|
+
function statementSites(nodes, reading) {
|
|
1679
|
+
const statements = new IdMap();
|
|
1680
|
+
const statementOfNode = new IdMap();
|
|
1681
|
+
for (const node of nodes) {
|
|
1682
|
+
const written = reading.statementOf(node);
|
|
1683
|
+
if (written === null) {
|
|
1684
|
+
continue;
|
|
1685
|
+
}
|
|
1686
|
+
const statement = statements.get(written) ?? written;
|
|
1687
|
+
statements.set(statement, statement);
|
|
1688
|
+
statementOfNode.set(node, statement);
|
|
1689
|
+
}
|
|
1690
|
+
const terminals = [...statements].map(([statement]) => statement);
|
|
1691
|
+
const enumerated = enumerateCallStatements(
|
|
1692
|
+
reading.lower(terminals),
|
|
1693
|
+
terminals
|
|
1694
|
+
);
|
|
1695
|
+
const pathsTo = (node) => {
|
|
1696
|
+
const statement = statementOfNode.get(node);
|
|
1697
|
+
return statement === void 0 ? void 0 : enumerated.byTerminal.get(statement);
|
|
1698
|
+
};
|
|
1699
|
+
const siteOf = (node, preconditions) => {
|
|
1700
|
+
const statement = statementOfNode.get(node);
|
|
1701
|
+
return {
|
|
1702
|
+
line: reading.firstLine(statement ?? node),
|
|
1703
|
+
preconditions,
|
|
1704
|
+
cleansUpFrom: statement === void 0 ? void 0 : enumerated.placement.get(statement)?.cleansUpFrom
|
|
1705
|
+
};
|
|
1706
|
+
};
|
|
1707
|
+
return {
|
|
1708
|
+
pathsTo,
|
|
1709
|
+
siteOf,
|
|
1710
|
+
plainSiteOf: (node) => siteOf(node, sharedGatingConditions(pathsTo(node)))
|
|
1711
|
+
};
|
|
1712
|
+
}
|
|
1713
|
+
|
|
1524
1714
|
// src/projectRoot.ts
|
|
1525
1715
|
var import_node_path3 = __toESM(require("path"), 1);
|
|
1526
1716
|
function commonDirectoryOf(files) {
|
|
@@ -1669,13 +1859,13 @@ function quoted(text, key) {
|
|
|
1669
1859
|
}
|
|
1670
1860
|
|
|
1671
1861
|
// src/adapterStamp.ts
|
|
1672
|
-
var
|
|
1862
|
+
var import_node_crypto3 = require("crypto");
|
|
1673
1863
|
var import_node_fs3 = __toESM(require("fs"), 1);
|
|
1674
1864
|
var import_node_path5 = __toESM(require("path"), 1);
|
|
1675
1865
|
var import_node_url = require("url");
|
|
1676
1866
|
|
|
1677
1867
|
// src/codeHash.ts
|
|
1678
|
-
var
|
|
1868
|
+
var import_node_crypto2 = require("crypto");
|
|
1679
1869
|
var import_node_fs2 = __toESM(require("fs"), 1);
|
|
1680
1870
|
var import_node_module = require("module");
|
|
1681
1871
|
var import_node_path4 = __toESM(require("path"), 1);
|
|
@@ -1721,7 +1911,7 @@ function createCodeHasher() {
|
|
|
1721
1911
|
if (files.length === 0) {
|
|
1722
1912
|
return "";
|
|
1723
1913
|
}
|
|
1724
|
-
const hash = (0,
|
|
1914
|
+
const hash = (0, import_node_crypto2.createHash)("sha256");
|
|
1725
1915
|
for (const file of files) {
|
|
1726
1916
|
hash.update(read.get(file)?.digest ?? "");
|
|
1727
1917
|
}
|
|
@@ -1738,7 +1928,7 @@ function readCodeFile(file) {
|
|
|
1738
1928
|
return null;
|
|
1739
1929
|
}
|
|
1740
1930
|
return {
|
|
1741
|
-
digest: (0,
|
|
1931
|
+
digest: (0, import_node_crypto2.createHash)("sha256").update(text).digest("hex"),
|
|
1742
1932
|
imports: importsOf(file, text.toString("utf8"))
|
|
1743
1933
|
};
|
|
1744
1934
|
}
|
|
@@ -1896,7 +2086,7 @@ function computeContentHash(paths) {
|
|
|
1896
2086
|
if (paths.length === 0) {
|
|
1897
2087
|
return "";
|
|
1898
2088
|
}
|
|
1899
|
-
const hash = (0,
|
|
2089
|
+
const hash = (0, import_node_crypto3.createHash)("sha256");
|
|
1900
2090
|
for (const file of paths) {
|
|
1901
2091
|
try {
|
|
1902
2092
|
hash.update(import_node_fs3.default.readFileSync(file));
|
|
@@ -1910,7 +2100,7 @@ function projectFileStamp(paths) {
|
|
|
1910
2100
|
if (paths.length === 0) {
|
|
1911
2101
|
return "none";
|
|
1912
2102
|
}
|
|
1913
|
-
const hash = (0,
|
|
2103
|
+
const hash = (0, import_node_crypto3.createHash)("sha256");
|
|
1914
2104
|
for (const file of [...paths].sort()) {
|
|
1915
2105
|
hash.update(file);
|
|
1916
2106
|
hash.update("\0");
|
|
@@ -1945,13 +2135,13 @@ function runDigest(packsDigest, packs, files) {
|
|
|
1945
2135
|
}
|
|
1946
2136
|
|
|
1947
2137
|
// src/cache.ts
|
|
1948
|
-
var
|
|
2138
|
+
var import_node_crypto6 = require("crypto");
|
|
1949
2139
|
var import_promises2 = __toESM(require("fs/promises"), 1);
|
|
1950
2140
|
var import_node_path8 = __toESM(require("path"), 1);
|
|
1951
2141
|
var import_files3 = require("@suss/behavioral-ir/files");
|
|
1952
2142
|
|
|
1953
2143
|
// src/cacheIndex.ts
|
|
1954
|
-
var
|
|
2144
|
+
var import_behavioral_ir8 = require("@suss/behavioral-ir");
|
|
1955
2145
|
var import_files = require("@suss/behavioral-ir/files");
|
|
1956
2146
|
function entriesOf(units) {
|
|
1957
2147
|
const boundaries = [];
|
|
@@ -1968,7 +2158,7 @@ function entriesOf(units) {
|
|
|
1968
2158
|
if (own !== null) {
|
|
1969
2159
|
add(
|
|
1970
2160
|
keyOf3(own),
|
|
1971
|
-
|
|
2161
|
+
import_behavioral_ir8.BOUNDARY_ROLE[summary.kind] === "provider" ? "serves" : "calls"
|
|
1972
2162
|
);
|
|
1973
2163
|
}
|
|
1974
2164
|
const spellings = /* @__PURE__ */ new Set();
|
|
@@ -2046,14 +2236,14 @@ function writeStoreIndex(file, index) {
|
|
|
2046
2236
|
}
|
|
2047
2237
|
function keyOf3(binding) {
|
|
2048
2238
|
try {
|
|
2049
|
-
return (0,
|
|
2239
|
+
return (0, import_behavioral_ir8.displayLabel)(binding);
|
|
2050
2240
|
} catch {
|
|
2051
2241
|
return null;
|
|
2052
2242
|
}
|
|
2053
2243
|
}
|
|
2054
2244
|
|
|
2055
2245
|
// src/cacheShards.ts
|
|
2056
|
-
var
|
|
2246
|
+
var import_node_crypto4 = require("crypto");
|
|
2057
2247
|
var import_node_fs4 = __toESM(require("fs"), 1);
|
|
2058
2248
|
var import_node_path6 = __toESM(require("path"), 1);
|
|
2059
2249
|
var import_files2 = require("@suss/behavioral-ir/files");
|
|
@@ -2115,7 +2305,7 @@ function namesIn(dir) {
|
|
|
2115
2305
|
}
|
|
2116
2306
|
function writeOnce(root, value) {
|
|
2117
2307
|
const pieces = [...(0, import_files2.documentPieces)(value)];
|
|
2118
|
-
const hash = (0,
|
|
2308
|
+
const hash = (0, import_node_crypto4.createHash)("sha256");
|
|
2119
2309
|
for (const piece of pieces) {
|
|
2120
2310
|
hash.update(piece);
|
|
2121
2311
|
}
|
|
@@ -2219,7 +2409,7 @@ function copyOfJson(value) {
|
|
|
2219
2409
|
}
|
|
2220
2410
|
|
|
2221
2411
|
// src/cacheStamps.ts
|
|
2222
|
-
var
|
|
2412
|
+
var import_node_crypto5 = require("crypto");
|
|
2223
2413
|
var import_promises = __toESM(require("fs/promises"), 1);
|
|
2224
2414
|
var RECENT_CHANGE_MS = 2e3;
|
|
2225
2415
|
function stampMayMissAWrite(stat, statAt) {
|
|
@@ -2309,7 +2499,7 @@ function reusableHash(prior, stamp) {
|
|
|
2309
2499
|
async function hashFile(filePath) {
|
|
2310
2500
|
try {
|
|
2311
2501
|
const content = await import_promises.default.readFile(filePath);
|
|
2312
|
-
return (0,
|
|
2502
|
+
return (0, import_node_crypto5.createHash)("sha256").update(content).digest("hex").slice(0, 16);
|
|
2313
2503
|
} catch {
|
|
2314
2504
|
return null;
|
|
2315
2505
|
}
|
|
@@ -2765,7 +2955,7 @@ function entryDirFor(cacheDir, input) {
|
|
|
2765
2955
|
input.adapterPacksDigest,
|
|
2766
2956
|
input.configPath ?? ""
|
|
2767
2957
|
].join(" ");
|
|
2768
|
-
const name = (0,
|
|
2958
|
+
const name = (0, import_node_crypto6.createHash)("sha256").update(key).digest("hex").slice(0, 16);
|
|
2769
2959
|
return import_node_path8.default.join(cacheDir, `${ENTRY_PREFIX}${name}`);
|
|
2770
2960
|
}
|
|
2771
2961
|
function isEntryDir(name) {
|
|
@@ -2839,7 +3029,7 @@ async function readManifest2(manifestPath) {
|
|
|
2839
3029
|
}
|
|
2840
3030
|
|
|
2841
3031
|
// src/cacheLocation.ts
|
|
2842
|
-
var
|
|
3032
|
+
var import_node_crypto7 = require("crypto");
|
|
2843
3033
|
var import_node_fs6 = __toESM(require("fs"), 1);
|
|
2844
3034
|
var import_node_path9 = __toESM(require("path"), 1);
|
|
2845
3035
|
var CACHE_DIR_ENV = "SUSS_CACHE_DIR";
|
|
@@ -2858,7 +3048,7 @@ function realPathOrSelf(dir) {
|
|
|
2858
3048
|
}
|
|
2859
3049
|
}
|
|
2860
3050
|
function projectKey(projectDir) {
|
|
2861
|
-
return (0,
|
|
3051
|
+
return (0, import_node_crypto7.createHash)("sha256").update(realPathOrSelf(import_node_path9.default.resolve(projectDir))).digest("hex").slice(0, 16);
|
|
2862
3052
|
}
|
|
2863
3053
|
function extractionCacheDirFor(projectDir) {
|
|
2864
3054
|
const root = chosenCacheRoot();
|
|
@@ -2867,6 +3057,13 @@ function extractionCacheDirFor(projectDir) {
|
|
|
2867
3057
|
}
|
|
2868
3058
|
return import_node_path9.default.join(root, "cache", projectKey(projectDir));
|
|
2869
3059
|
}
|
|
3060
|
+
function mapFolderFor(projectDir) {
|
|
3061
|
+
const root = chosenCacheRoot();
|
|
3062
|
+
if (root === null) {
|
|
3063
|
+
return import_node_path9.default.join(projectDir, ".suss");
|
|
3064
|
+
}
|
|
3065
|
+
return import_node_path9.default.join(root, "map", projectKey(projectDir));
|
|
3066
|
+
}
|
|
2870
3067
|
function liveRecordFor(projectDir) {
|
|
2871
3068
|
const root = chosenCacheRoot();
|
|
2872
3069
|
if (root === null) {
|
|
@@ -2876,7 +3073,7 @@ function liveRecordFor(projectDir) {
|
|
|
2876
3073
|
}
|
|
2877
3074
|
|
|
2878
3075
|
// src/extractionReport.ts
|
|
2879
|
-
var
|
|
3076
|
+
var import_behavioral_ir9 = require("@suss/behavioral-ir");
|
|
2880
3077
|
var emptyTally = () => ({
|
|
2881
3078
|
candidateFiles: 0,
|
|
2882
3079
|
unitsDiscovered: 0,
|
|
@@ -2926,7 +3123,7 @@ function summaryCountsByPack(summaries) {
|
|
|
2926
3123
|
}
|
|
2927
3124
|
const entry = counts.get(recognition) ?? emptyCounts();
|
|
2928
3125
|
entry.bound += 1;
|
|
2929
|
-
if (
|
|
3126
|
+
if (import_behavioral_ir9.BOUNDARY_ROLE[summary.kind] === "provider") {
|
|
2930
3127
|
entry.providers += 1;
|
|
2931
3128
|
}
|
|
2932
3129
|
if (summary.transitions.length > 0) {
|
|
@@ -3015,6 +3212,7 @@ var KeptParses = class {
|
|
|
3015
3212
|
};
|
|
3016
3213
|
|
|
3017
3214
|
// src/packHealth.ts
|
|
3215
|
+
var import_node_path10 = __toESM(require("path"), 1);
|
|
3018
3216
|
function stagesOf(funnel) {
|
|
3019
3217
|
const stages = [];
|
|
3020
3218
|
const gateSaysSomething = funnel.gates.length > 0 && funnel.unresolvedGates.length === 0;
|
|
@@ -3162,6 +3360,30 @@ function packConfigCheck(needs) {
|
|
|
3162
3360
|
}))
|
|
3163
3361
|
};
|
|
3164
3362
|
}
|
|
3363
|
+
function describeMissingPath(missing) {
|
|
3364
|
+
const where = `${missing.option} is ${missing.value} in ${missing.configFile}`;
|
|
3365
|
+
if (import_node_path10.default.isAbsolute(missing.value)) {
|
|
3366
|
+
return {
|
|
3367
|
+
problem: `${where}, and nothing exists there.`,
|
|
3368
|
+
fix: `Set ${missing.option} to a path that exists.`
|
|
3369
|
+
};
|
|
3370
|
+
}
|
|
3371
|
+
return {
|
|
3372
|
+
problem: `${where}, and nothing exists at ${missing.resolved}. A relative path is read against the config file, not the project.`,
|
|
3373
|
+
fix: missing.inProject === void 0 ? `Set ${missing.option} to an absolute path, or move the config file into the project.` : `Set ${missing.option} to ${missing.inProject} in the config file, or move the config file into the project.`
|
|
3374
|
+
};
|
|
3375
|
+
}
|
|
3376
|
+
function packPathCheck(missing) {
|
|
3377
|
+
return {
|
|
3378
|
+
name: "every path a pack config gives exists",
|
|
3379
|
+
code: "no-path",
|
|
3380
|
+
audience: "run",
|
|
3381
|
+
violations: missing.map((one) => {
|
|
3382
|
+
const { problem, fix } = describeMissingPath(one);
|
|
3383
|
+
return { label: one.pack, detail: `${problem} ${fix}` };
|
|
3384
|
+
})
|
|
3385
|
+
};
|
|
3386
|
+
}
|
|
3165
3387
|
function evaluatePackHealth(report) {
|
|
3166
3388
|
const gradients = packGradients(report);
|
|
3167
3389
|
return [
|
|
@@ -3314,7 +3536,7 @@ function makeTransitionId(functionName, branch) {
|
|
|
3314
3536
|
const { terminal } = branch;
|
|
3315
3537
|
const statusKey = terminal.statusCode === null ? "none" : terminal.statusCode.type === "literal" ? String(terminal.statusCode.value) : `dyn:${terminal.statusCode.sourceText}`;
|
|
3316
3538
|
const conditionSig = branch.conditions.map((c) => `${c.polarity}:${c.sourceText}`).join(";");
|
|
3317
|
-
const conditionHash = (0,
|
|
3539
|
+
const conditionHash = (0, import_node_crypto8.createHash)("sha1").update(conditionSig).digest("hex").slice(0, 7);
|
|
3318
3540
|
return `${functionName}:${terminal.kind}:${statusKey}:${conditionHash}`;
|
|
3319
3541
|
}
|
|
3320
3542
|
function collapseReading(table, reading) {
|
|
@@ -3383,17 +3605,17 @@ function effectsOfBranch(branch) {
|
|
|
3383
3605
|
...branch.effects.map(effectToIR),
|
|
3384
3606
|
...branch.extraEffects ?? []
|
|
3385
3607
|
];
|
|
3386
|
-
return (0,
|
|
3608
|
+
return (0, import_behavioral_ir10.foldRepeatedEffects)(effects.map(withNormalizedCallee));
|
|
3387
3609
|
}
|
|
3388
3610
|
function provenanceOf(raw, effects) {
|
|
3389
3611
|
if (raw.length === 0) {
|
|
3390
3612
|
return [];
|
|
3391
3613
|
}
|
|
3392
|
-
const positionOf = new Map(effects.map((one, at) => [(0,
|
|
3614
|
+
const positionOf = new Map(effects.map((one, at) => [(0, import_behavioral_ir10.effectKey)(one), at]));
|
|
3393
3615
|
const bySlot = /* @__PURE__ */ new Map();
|
|
3394
3616
|
const said = /* @__PURE__ */ new Map();
|
|
3395
3617
|
for (const one of raw) {
|
|
3396
|
-
const effect = positionOf.get((0,
|
|
3618
|
+
const effect = positionOf.get((0, import_behavioral_ir10.effectKey)(withNormalizedCallee(one.effect)));
|
|
3397
3619
|
if (effect === void 0) {
|
|
3398
3620
|
continue;
|
|
3399
3621
|
}
|
|
@@ -3425,7 +3647,7 @@ function withNormalizedCallee(effect) {
|
|
|
3425
3647
|
if (effect.callee === void 0) {
|
|
3426
3648
|
return effect;
|
|
3427
3649
|
}
|
|
3428
|
-
return { ...effect, callee: (0,
|
|
3650
|
+
return { ...effect, callee: (0, import_behavioral_ir10.normalizeCalleeText)(effect.callee) };
|
|
3429
3651
|
}
|
|
3430
3652
|
function assembleSummary(raw, options = DEFAULT_OPTIONS) {
|
|
3431
3653
|
const transitions = raw.branches.map((rawBranch) => {
|
|
@@ -3490,28 +3712,31 @@ function buildMetadata(raw) {
|
|
|
3490
3712
|
let metadata = {};
|
|
3491
3713
|
const http = buildHttpMetadataValue(raw);
|
|
3492
3714
|
if (http !== null) {
|
|
3493
|
-
metadata = (0,
|
|
3715
|
+
metadata = (0, import_behavioral_ir10.withHttpMetadata)(metadata, http);
|
|
3494
3716
|
}
|
|
3495
3717
|
const graphql = buildGraphqlMetadataValue(raw);
|
|
3496
3718
|
if (graphql !== null) {
|
|
3497
|
-
metadata = (0,
|
|
3719
|
+
metadata = (0, import_behavioral_ir10.withGraphqlMetadata)(metadata, graphql);
|
|
3498
3720
|
}
|
|
3499
3721
|
if (raw.sourceDocumentLabel !== void 0) {
|
|
3500
|
-
metadata = (0,
|
|
3722
|
+
metadata = (0, import_behavioral_ir10.withSourceDocumentMetadata)(metadata, {
|
|
3501
3723
|
label: raw.sourceDocumentLabel
|
|
3502
3724
|
});
|
|
3503
3725
|
}
|
|
3504
3726
|
if (raw.mount !== void 0) {
|
|
3505
|
-
metadata = (0,
|
|
3727
|
+
metadata = (0, import_behavioral_ir10.withMountMetadata)(metadata, raw.mount);
|
|
3506
3728
|
}
|
|
3507
3729
|
if (raw.wrappers !== void 0 && raw.wrappers.length > 0) {
|
|
3508
|
-
metadata = (0,
|
|
3730
|
+
metadata = (0, import_behavioral_ir10.withWrapperMetadata)(metadata, { applied: raw.wrappers });
|
|
3509
3731
|
}
|
|
3510
3732
|
if (raw.requestSpelling !== void 0) {
|
|
3511
|
-
metadata = (0,
|
|
3733
|
+
metadata = (0, import_behavioral_ir10.withRequestSpellingMetadata)(metadata, raw.requestSpelling);
|
|
3512
3734
|
}
|
|
3513
3735
|
if (raw.test !== void 0) {
|
|
3514
|
-
metadata = (0,
|
|
3736
|
+
metadata = (0, import_behavioral_ir10.withTestMetadata)(metadata, raw.test);
|
|
3737
|
+
}
|
|
3738
|
+
if (raw.packMetadata !== void 0) {
|
|
3739
|
+
metadata = { ...metadata, ...raw.packMetadata };
|
|
3515
3740
|
}
|
|
3516
3741
|
return Object.keys(metadata).length > 0 ? metadata : null;
|
|
3517
3742
|
}
|
|
@@ -3564,13 +3789,19 @@ function buildGraphqlMetadataValue(raw) {
|
|
|
3564
3789
|
if (raw.graphqlUnresolvedDocument !== void 0) {
|
|
3565
3790
|
graphql.unresolvedDocument = raw.graphqlUnresolvedDocument;
|
|
3566
3791
|
}
|
|
3792
|
+
if (raw.graphqlClient !== void 0) {
|
|
3793
|
+
graphql.client = raw.graphqlClient;
|
|
3794
|
+
}
|
|
3795
|
+
if (raw.graphqlUnresolvedClient !== void 0) {
|
|
3796
|
+
graphql.unresolvedClient = raw.graphqlUnresolvedClient;
|
|
3797
|
+
}
|
|
3567
3798
|
return Object.keys(graphql).length > 0 ? graphql : null;
|
|
3568
3799
|
}
|
|
3569
3800
|
function answersWithHttpResponses(raw) {
|
|
3570
3801
|
if (raw.boundaryBinding === null || raw.boundaryBinding === void 0) {
|
|
3571
3802
|
return true;
|
|
3572
3803
|
}
|
|
3573
|
-
return (0,
|
|
3804
|
+
return (0, import_behavioral_ir10.exchangesHttpResponses)(raw.boundaryBinding);
|
|
3574
3805
|
}
|
|
3575
3806
|
function detectGaps(raw, transitions, options) {
|
|
3576
3807
|
if (options.gapHandling === "silent") {
|
|
@@ -3755,7 +3986,10 @@ var effectConverters = {
|
|
|
3755
3986
|
stateChange: (e) => ({ type: "stateChange", variable: e.variable })
|
|
3756
3987
|
};
|
|
3757
3988
|
function effectToIR(effect) {
|
|
3758
|
-
|
|
3989
|
+
const converted = effectConverters[effect.type](
|
|
3990
|
+
effect
|
|
3991
|
+
);
|
|
3992
|
+
return effect.location === void 0 ? converted : { ...converted, location: effect.location };
|
|
3759
3993
|
}
|
|
3760
3994
|
function paramToInput(param) {
|
|
3761
3995
|
return {
|
|
@@ -3787,6 +4021,7 @@ function paramToInput(param) {
|
|
|
3787
4021
|
assembleSummary,
|
|
3788
4022
|
assessConfidence,
|
|
3789
4023
|
buildUngatedExtractionReport,
|
|
4024
|
+
callSiteKey,
|
|
3790
4025
|
chosenCacheRoot,
|
|
3791
4026
|
commonDirectoryOf,
|
|
3792
4027
|
composeWrappers,
|
|
@@ -3798,23 +4033,28 @@ function paramToInput(param) {
|
|
|
3798
4033
|
createCodeHasher,
|
|
3799
4034
|
createPackTallies,
|
|
3800
4035
|
createTimer,
|
|
4036
|
+
describeMissingPath,
|
|
3801
4037
|
detectGaps,
|
|
3802
4038
|
effectToIR,
|
|
4039
|
+
effectsFiringOn,
|
|
3803
4040
|
emptyTally,
|
|
3804
4041
|
enumerateOrDegrade,
|
|
3805
4042
|
enumerateStructuredPaths,
|
|
3806
4043
|
evaluatePackHealth,
|
|
3807
4044
|
extractionCacheDirFor,
|
|
3808
4045
|
extractionConfigStamp,
|
|
4046
|
+
firesOn,
|
|
3809
4047
|
firstWrittenReading,
|
|
3810
4048
|
formatPackHealth,
|
|
3811
4049
|
guardsHoldOn,
|
|
3812
4050
|
helperPathsOnVariables,
|
|
3813
4051
|
httpRouteDiscovery,
|
|
3814
4052
|
isListedTestFile,
|
|
4053
|
+
libraryEnvReadMarker,
|
|
3815
4054
|
liveRecordFor,
|
|
3816
4055
|
makeIgnoredDirectory,
|
|
3817
4056
|
makeTransitionId,
|
|
4057
|
+
mapFolderFor,
|
|
3818
4058
|
mapReading,
|
|
3819
4059
|
markReturnsAsExitCode,
|
|
3820
4060
|
matchesTestFileName,
|
|
@@ -3822,10 +4062,13 @@ function paramToInput(param) {
|
|
|
3822
4062
|
moduleInitStructure,
|
|
3823
4063
|
moduleOfFile,
|
|
3824
4064
|
noopTimer,
|
|
4065
|
+
numberRepeatedCallSites,
|
|
3825
4066
|
ownersWhereWritten,
|
|
3826
4067
|
packConfigCheck,
|
|
3827
4068
|
packGradients,
|
|
4069
|
+
packPathCheck,
|
|
3828
4070
|
paramToInput,
|
|
4071
|
+
placeTerminals,
|
|
3829
4072
|
processCodeHasher,
|
|
3830
4073
|
projectFileStamp,
|
|
3831
4074
|
rawConditionToPredicate,
|
|
@@ -3843,6 +4086,7 @@ function paramToInput(param) {
|
|
|
3843
4086
|
stampMayMissAWrite,
|
|
3844
4087
|
stampModuleImports,
|
|
3845
4088
|
stampModules,
|
|
4089
|
+
statementSites,
|
|
3846
4090
|
storageSystemOption,
|
|
3847
4091
|
summaryCountsByPack,
|
|
3848
4092
|
tallyUnit,
|