kibi-cli 2.36.0 → 2.39.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/cli-json-command.d.ts.map +1 -1
- package/dist/cli-json-command.js +4 -0
- package/dist/cli-operation-metadata.d.ts +1 -1
- package/dist/cli-operation-metadata.js +1 -1
- package/dist/cli-register-foundation.d.ts.map +1 -1
- package/dist/cli-register-foundation.js +2 -1
- package/dist/cli-register-maintenance.d.ts.map +1 -1
- package/dist/cli-register-maintenance.js +5 -0
- package/dist/cli-register-reporting.d.ts.map +1 -1
- package/dist/cli-register-reporting.js +1 -0
- package/dist/cli-validate.d.ts.map +1 -1
- package/dist/cli-validate.js +21 -2
- package/dist/cli.d.ts.map +1 -1
- package/dist/cli.js +19 -1
- package/dist/commands/aggregated-checks.d.ts.map +1 -1
- package/dist/commands/aggregated-checks.js +89 -16
- package/dist/commands/coverage.d.ts +1 -0
- package/dist/commands/coverage.d.ts.map +1 -1
- package/dist/commands/coverage.js +40 -0
- package/dist/commands/doctor.d.ts +5 -0
- package/dist/commands/doctor.d.ts.map +1 -1
- package/dist/commands/doctor.js +70 -35
- package/dist/commands/github-init.d.ts.map +1 -1
- package/dist/commands/github-init.js +4 -2
- package/dist/commands/hook-managers.d.ts +43 -0
- package/dist/commands/hook-managers.d.ts.map +1 -0
- package/dist/commands/hook-managers.js +426 -0
- package/dist/commands/init.d.ts +1 -0
- package/dist/commands/init.d.ts.map +1 -1
- package/dist/commands/init.js +40 -5
- package/dist/commands/migrate.d.ts.map +1 -1
- package/dist/commands/migrate.js +9 -3
- package/dist/commands/sync/persistence.d.ts.map +1 -1
- package/dist/commands/sync/persistence.js +49 -1
- package/dist/commands/telemetry.d.ts +7 -0
- package/dist/commands/telemetry.d.ts.map +1 -0
- package/dist/commands/telemetry.js +23 -0
- package/dist/decision-firmness.d.ts.map +1 -1
- package/dist/decision-firmness.js +11 -14
- package/dist/engine-limits.d.ts.map +1 -1
- package/dist/engine-limits.js +8 -10
- package/dist/entity-body-context.d.ts.map +1 -1
- package/dist/entity-body-context.js +39 -36
- package/dist/extractors/markdown.d.ts +6 -0
- package/dist/extractors/markdown.d.ts.map +1 -1
- package/dist/extractors/markdown.js +21 -0
- package/dist/extractors/symbol-coordinates.d.ts.map +1 -1
- package/dist/extractors/symbol-coordinates.js +23 -4
- package/dist/firm-decision-edit.d.ts.map +1 -1
- package/dist/firm-decision-edit.js +1 -3
- package/dist/intent-search.d.ts +5 -1
- package/dist/intent-search.d.ts.map +1 -1
- package/dist/intent-search.js +118 -33
- package/dist/logic/ir.d.ts.map +1 -1
- package/dist/logic/ir.js +82 -108
- package/dist/operations/bootstrap/discovery-evidence.d.ts.map +1 -1
- package/dist/operations/bootstrap/discovery-evidence.js +44 -2
- package/dist/operations/bootstrap/discovery.d.ts.map +1 -1
- package/dist/operations/bootstrap/discovery.js +1 -0
- package/dist/operations/bootstrap/guidance-actions.d.ts.map +1 -1
- package/dist/operations/bootstrap/guidance-actions.js +2 -1
- package/dist/operations/bootstrap/plugin-offers.d.ts +11 -2
- package/dist/operations/bootstrap/plugin-offers.d.ts.map +1 -1
- package/dist/operations/bootstrap/plugin-offers.js +48 -9
- package/dist/operations/proof/claim-bindings.d.ts.map +1 -1
- package/dist/operations/proof/claim-bindings.js +1 -0
- package/dist/operations/proof/code-certificates.d.ts +2 -0
- package/dist/operations/proof/code-certificates.d.ts.map +1 -1
- package/dist/operations/proof/code-certificates.js +34 -14
- package/dist/operations/proof/code-models.d.ts.map +1 -1
- package/dist/operations/proof/code-models.js +19 -5
- package/dist/operations/proof/code-runner.d.ts +16 -0
- package/dist/operations/proof/code-runner.d.ts.map +1 -1
- package/dist/operations/proof/code-runner.js +42 -6
- package/dist/operations/proof/explain.d.ts +63 -0
- package/dist/operations/proof/explain.d.ts.map +1 -1
- package/dist/operations/proof/explain.js +162 -0
- package/dist/operations/semantic-advisor/analyze-prose.d.ts +9 -1
- package/dist/operations/semantic-advisor/analyze-prose.d.ts.map +1 -1
- package/dist/operations/semantic-advisor/analyze-prose.js +21 -0
- package/dist/operations/semantic-advisor/case-preview.d.ts +24 -0
- package/dist/operations/semantic-advisor/case-preview.d.ts.map +1 -0
- package/dist/operations/semantic-advisor/case-preview.js +216 -0
- package/dist/operations/semantic-advisor/shared.d.ts.map +1 -1
- package/dist/operations/semantic-advisor/shared.js +3 -0
- package/dist/operations/semantic-advisor/types.d.ts +23 -0
- package/dist/operations/semantic-advisor/types.d.ts.map +1 -1
- package/dist/plugins/approved-source-analyzers.generated.d.ts +11 -8
- package/dist/plugins/approved-source-analyzers.generated.d.ts.map +1 -1
- package/dist/plugins/approved-source-analyzers.generated.js +11 -8
- package/dist/plugins/compose-search-hints.d.ts +29 -0
- package/dist/plugins/compose-search-hints.d.ts.map +1 -0
- package/dist/plugins/compose-search-hints.js +94 -0
- package/dist/plugins/external-allowlist.d.ts +7 -0
- package/dist/plugins/external-allowlist.d.ts.map +1 -1
- package/dist/plugins/external-allowlist.js +11 -0
- package/dist/plugins/registry.d.ts +8 -1
- package/dist/plugins/registry.d.ts.map +1 -1
- package/dist/plugins/registry.js +22 -3
- package/dist/plugins/source-classification.d.ts +2 -2
- package/dist/plugins/source-classification.d.ts.map +1 -1
- package/dist/plugins/source-classification.js +25 -1
- package/dist/prolog/codec.d.ts.map +1 -1
- package/dist/prolog/codec.js +10 -20
- package/dist/public/impact/coverage-depth-quality.d.ts.map +1 -1
- package/dist/public/impact/coverage-depth-quality.js +32 -16
- package/dist/public/impact/full-kb-quality.d.ts +6 -0
- package/dist/public/impact/full-kb-quality.d.ts.map +1 -1
- package/dist/public/impact/full-kb-quality.js +8 -3
- package/dist/public/impact/requirement-quality.d.ts.map +1 -1
- package/dist/public/impact/requirement-quality.js +56 -29
- package/dist/public/operations/catalog.d.ts +44 -4
- package/dist/public/operations/catalog.d.ts.map +1 -1
- package/dist/public/operations/check-executor.d.ts +6 -0
- package/dist/public/operations/check-executor.d.ts.map +1 -1
- package/dist/public/operations/check-executor.js +34 -2
- package/dist/public/operations/discovery-executors.d.ts +5 -1
- package/dist/public/operations/discovery-executors.d.ts.map +1 -1
- package/dist/public/operations/discovery-executors.js +65 -4
- package/dist/public/operations/evidence-floor.d.ts +8 -1
- package/dist/public/operations/evidence-floor.d.ts.map +1 -1
- package/dist/public/operations/evidence-floor.js +3 -4
- package/dist/public/operations/migration-plan.d.ts.map +1 -1
- package/dist/public/operations/migration-plan.js +41 -10
- package/dist/public/operations/node-ports.d.ts.map +1 -1
- package/dist/public/operations/node-ports.js +3 -1
- package/dist/public/operations/repair-plan.d.ts +46 -0
- package/dist/public/operations/repair-plan.d.ts.map +1 -1
- package/dist/public/operations/repair-plan.js +110 -1
- package/dist/public/operations/schema6-check-actions.js +1 -1
- package/dist/public/operations/source-analysis-cache.d.ts +22 -0
- package/dist/public/operations/source-analysis-cache.d.ts.map +1 -0
- package/dist/public/operations/source-analysis-cache.js +157 -0
- package/dist/public/operations/specs/check-rules.generated.d.ts +1 -1
- package/dist/public/operations/specs/check-rules.generated.d.ts.map +1 -1
- package/dist/public/operations/specs/check-rules.generated.js +2 -1
- package/dist/public/operations/specs/check.d.ts +1 -1
- package/dist/public/operations/specs/discovery.d.ts +7 -2
- package/dist/public/operations/specs/discovery.d.ts.map +1 -1
- package/dist/public/operations/specs/discovery.js +7 -2
- package/dist/public/operations/specs/mutation-schemas.d.ts +36 -1
- package/dist/public/operations/specs/mutation-schemas.d.ts.map +1 -1
- package/dist/public/operations/specs/mutation-schemas.js +30 -0
- package/dist/public/operations/specs/upsert.d.ts +36 -1
- package/dist/public/operations/specs/upsert.d.ts.map +1 -1
- package/dist/public/operations/symbol-granularity-check.d.ts +3 -1
- package/dist/public/operations/symbol-granularity-check.d.ts.map +1 -1
- package/dist/public/operations/symbol-granularity-check.js +21 -7
- package/dist/public/proof-protocol.d.ts +6 -1
- package/dist/public/proof-protocol.d.ts.map +1 -1
- package/dist/public/proof-protocol.js +12 -3
- package/dist/public/proof-sources.d.ts +2 -0
- package/dist/public/proof-sources.d.ts.map +1 -1
- package/dist/public/proof-sources.js +32 -6
- package/dist/public/schemas/entity.d.ts.map +1 -1
- package/dist/public/schemas/entity.js +59 -0
- package/dist/public/skills/kibi-bootstrap/SKILL.md +2 -2
- package/dist/public/skills/kibi-commit-review/SKILL.md +6 -2
- package/dist/public/skills/kibi-decisions/SKILL.md +7 -2
- package/dist/public/skills/kibi-decisions/resources/signoff-views.md +3 -1
- package/dist/public/skills/kibi-usage/SKILL.md +50 -3
- package/dist/public/skills/kibi-usage/resources/fact-lanes.md +34 -0
- package/dist/public/skills/kibi-usage/resources/proof.md +13 -5
- package/dist/public/skills/kibi-usage/resources/workflows.md +10 -0
- package/dist/relationships/shards.d.ts +2 -0
- package/dist/relationships/shards.d.ts.map +1 -1
- package/dist/relationships/shards.js +25 -1
- package/dist/schemas/entity.schema.json +98 -1
- package/dist/search-answer.d.ts +3 -2
- package/dist/search-answer.d.ts.map +1 -1
- package/dist/search-answer.js +57 -4
- package/dist/search-hints.d.ts +58 -0
- package/dist/search-hints.d.ts.map +1 -0
- package/dist/search-hints.js +187 -0
- package/dist/search-ranking.d.ts +7 -0
- package/dist/search-ranking.d.ts.map +1 -1
- package/dist/search-ranking.js +54 -56
- package/dist/search-token-cache.d.ts +30 -0
- package/dist/search-token-cache.d.ts.map +1 -0
- package/dist/search-token-cache.js +86 -0
- package/dist/traceability/impact-knowledge.d.ts.map +1 -1
- package/dist/traceability/impact-knowledge.js +2 -0
- package/dist/traceability/temp-kb.d.ts.map +1 -1
- package/dist/traceability/temp-kb.js +11 -1
- package/dist/types/entities.d.ts +12 -0
- package/dist/types/entities.d.ts.map +1 -1
- package/dist/usage-telemetry.d.ts +20 -0
- package/dist/usage-telemetry.d.ts.map +1 -0
- package/dist/usage-telemetry.js +93 -0
- package/dist/utils/branch-resolver.d.ts.map +1 -1
- package/dist/utils/branch-resolver.js +1 -0
- package/dist/utils/rule-registry.generated.d.ts +5 -0
- package/dist/utils/rule-registry.generated.d.ts.map +1 -1
- package/dist/utils/rule-registry.generated.js +6 -0
- package/package.json +5 -4
- package/schema/entities.pl +12 -0
- package/src/public/impact/coverage-depth-quality.ts +59 -21
- package/src/public/impact/full-kb-quality.ts +15 -1
- package/src/public/impact/requirement-quality.ts +95 -38
- package/src/public/operations/check-executor.ts +41 -1
- package/src/public/operations/discovery-executors.ts +92 -4
- package/src/public/operations/evidence-floor.ts +15 -3
- package/src/public/operations/migration-plan.ts +41 -9
- package/src/public/operations/node-ports.ts +3 -1
- package/src/public/operations/repair-plan.ts +152 -1
- package/src/public/operations/schema6-check-actions.ts +1 -1
- package/src/public/operations/source-analysis-cache.ts +196 -0
- package/src/public/operations/specs/check-rules.generated.ts +2 -1
- package/src/public/operations/specs/discovery.ts +8 -2
- package/src/public/operations/specs/mutation-schemas.ts +34 -0
- package/src/public/operations/symbol-granularity-check.ts +25 -5
- package/src/public/proof-protocol-types.d.ts +1 -1
- package/src/public/proof-protocol.ts +18 -4
- package/src/public/proof-sources.ts +37 -6
- package/src/public/schemas/entity.ts +65 -0
- package/src/public/skills/kibi-bootstrap/SKILL.md +2 -2
- package/src/public/skills/kibi-commit-review/SKILL.md +6 -2
- package/src/public/skills/kibi-decisions/SKILL.md +7 -2
- package/src/public/skills/kibi-decisions/resources/signoff-views.md +3 -1
- package/src/public/skills/kibi-usage/SKILL.md +50 -3
- package/src/public/skills/kibi-usage/resources/fact-lanes.md +34 -0
- package/src/public/skills/kibi-usage/resources/proof.md +13 -5
- package/src/public/skills/kibi-usage/resources/workflows.md +10 -0
- package/src/schemas/entity.schema.json +98 -1
|
@@ -45,6 +45,8 @@ export declare function compiledToSourcePath(workspaceRoot: string, relativePath
|
|
|
45
45
|
export declare function evaluateDomain(workspaceRoot: string, sourceFile: string, exportName: string, options?: Readonly<{
|
|
46
46
|
/** The TypeScript runners to try, in order (default all three). */
|
|
47
47
|
runners?: readonly ("bun" | "tsx" | "node")[];
|
|
48
|
+
/** Read this field of each member instead of the member itself. */
|
|
49
|
+
field?: string;
|
|
48
50
|
}>): {
|
|
49
51
|
ok: true;
|
|
50
52
|
count: number;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"code-certificates.d.ts","sourceRoot":"","sources":["../../../src/operations/proof/code-certificates.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"code-certificates.d.ts","sourceRoot":"","sources":["../../../src/operations/proof/code-certificates.ts"],"names":[],"mappings":"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"}
|
|
@@ -15,7 +15,6 @@
|
|
|
15
15
|
You should have received a copy of the GNU Affero General Public License
|
|
16
16
|
along with this program. If not, see <https://www.gnu.org/licenses/>.
|
|
17
17
|
*/
|
|
18
|
-
import { spawnSync } from "node:child_process";
|
|
19
18
|
import { createHash } from "node:crypto";
|
|
20
19
|
import { existsSync, readFileSync } from "node:fs";
|
|
21
20
|
import { createRequire } from "node:module";
|
|
@@ -25,7 +24,7 @@ import { runOperationJsonQuery, toPrologAtom, } from "../../public/operations/pr
|
|
|
25
24
|
import { canonicalCertificateJson, certificateDigest, } from "../../public/proof-certificates.js";
|
|
26
25
|
import { CODE_CERTIFICATE_VERSION, isCertificateProofKind, } from "../../public/proof-protocol.js";
|
|
27
26
|
import { describeSource, normalizeSourceSpec, readSource, } from "../../public/proof-sources.js";
|
|
28
|
-
import { runCodeEvaluator, TS_RESOLVE_HOOKS, } from "./code-runner.js";
|
|
27
|
+
import { runCodeEvaluator, spawnSyncThroughFiles, TS_RESOLVE_HOOKS, } from "./code-runner.js";
|
|
29
28
|
import { evaluateSourceCode } from "./source-code-readers.js";
|
|
30
29
|
import { machineCertificateProblem, patternCertificateProblem, ruleCertificateProblem, } from "./code-models.js";
|
|
31
30
|
function record(value) {
|
|
@@ -64,7 +63,9 @@ const IMPORT_SPECIFIER = /(?:\bfrom\s*|\bimport\s*\(\s*|\bimport\s+|\brequire\s*
|
|
|
64
63
|
*/
|
|
65
64
|
// implements REQ-kibi-code-proof-kinds
|
|
66
65
|
export function importsDomain(source, sourcePath, targetPath, identifier, workspaceRoot) {
|
|
67
|
-
|
|
66
|
+
// A dotted export (BRAND.name) is imported under its head.
|
|
67
|
+
const imported = identifier.split(".")[0] ?? "";
|
|
68
|
+
if (imported === "" || !new RegExp(`\\b${escapeRegExp(imported)}\\b`).test(source))
|
|
68
69
|
return false;
|
|
69
70
|
const target = stripExtension(path.normalize(targetPath));
|
|
70
71
|
if (/\.py$/i.test(sourcePath))
|
|
@@ -203,21 +204,30 @@ function escapeRegExp(value) {
|
|
|
203
204
|
return value.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
|
|
204
205
|
}
|
|
205
206
|
const DOMAIN_EVALUATOR = `
|
|
206
|
-
const [file, name] = process.argv.slice(-
|
|
207
|
+
const [file, name, projected] = process.argv.slice(-3);
|
|
207
208
|
const { pathToFileURL } = await import("node:url");
|
|
208
209
|
if (typeof globalThis.Bun === "undefined") {
|
|
209
210
|
const { register } = await import("node:module");
|
|
210
211
|
register?.("data:text/javascript," + encodeURIComponent(${JSON.stringify(TS_RESOLVE_HOOKS)}));
|
|
211
212
|
}
|
|
212
|
-
|
|
213
|
+
// A dotted name reads a field of the export (POLICY.eventLimit).
|
|
214
|
+
const [head, ...fields] = name.split(".");
|
|
215
|
+
let value = (await import(pathToFileURL(file).href))[head];
|
|
216
|
+
for (const field of fields) value = value !== null && typeof value === "object" ? value[field] : undefined;
|
|
213
217
|
let items = null;
|
|
214
218
|
if (Array.isArray(value)) items = value;
|
|
215
219
|
else if (value instanceof Set) items = [...value];
|
|
216
220
|
else if (value instanceof Map) items = [...value.keys()];
|
|
217
221
|
else if (value !== null && typeof value === "object") items = Object.keys(value);
|
|
222
|
+
// A field projects a list of records onto one field of each (catalog names).
|
|
223
|
+
if (projected !== "" && items !== null)
|
|
224
|
+
items = items.map((item) => (item !== null && typeof item === "object" ? item[projected] : undefined));
|
|
218
225
|
const primitive = (item) => ["string", "number", "boolean", "bigint"].includes(typeof item);
|
|
226
|
+
const unprojected = projected !== "" && items !== null && items.some((item) => item === undefined);
|
|
219
227
|
const scalar = typeof value === "number" || typeof value === "bigint" ? Number(value) : null;
|
|
220
|
-
console.log(JSON.stringify(
|
|
228
|
+
console.log(JSON.stringify(unprojected
|
|
229
|
+
? { error: \`a member of \${name} has no field \${projected}\` }
|
|
230
|
+
: scalar !== null
|
|
221
231
|
? { scalar }
|
|
222
232
|
: items === null
|
|
223
233
|
? { error: \`\${name} is not an array, set, map or object\` }
|
|
@@ -226,7 +236,7 @@ console.log(JSON.stringify(scalar !== null
|
|
|
226
236
|
// A Python domain: a list, tuple, set, frozenset, dict or Enum class.
|
|
227
237
|
const PYTHON_DOMAIN_EVALUATOR = `
|
|
228
238
|
import enum, importlib, json, os, sys
|
|
229
|
-
file, name = sys.argv[-2], sys.argv[-1]
|
|
239
|
+
file, name, projected = sys.argv[-3], sys.argv[-2], sys.argv[-1]
|
|
230
240
|
# Import the module under its package name, from the directory above its
|
|
231
241
|
# topmost package, so absolute and relative imports inside it resolve.
|
|
232
242
|
directory, module_name = os.path.split(os.path.splitext(file)[0])
|
|
@@ -236,7 +246,11 @@ while os.path.exists(os.path.join(directory, "__init__.py")):
|
|
|
236
246
|
parts.insert(0, package)
|
|
237
247
|
sys.path.insert(0, directory)
|
|
238
248
|
module = importlib.import_module(".".join(parts))
|
|
239
|
-
|
|
249
|
+
# A dotted name reads a field of the export (POLICY.event_limit).
|
|
250
|
+
head, *fields = name.split(".")
|
|
251
|
+
value = getattr(module, head, None)
|
|
252
|
+
for field in fields:
|
|
253
|
+
value = value.get(field) if isinstance(value, dict) else getattr(value, field, None)
|
|
240
254
|
if isinstance(value, type) and issubclass(value, enum.Enum):
|
|
241
255
|
items = [member.value for member in value]
|
|
242
256
|
elif isinstance(value, dict):
|
|
@@ -245,13 +259,18 @@ elif isinstance(value, (list, tuple, set, frozenset)):
|
|
|
245
259
|
items = list(value)
|
|
246
260
|
else:
|
|
247
261
|
items = None
|
|
262
|
+
# A field projects a list of records onto one field of each (catalog names).
|
|
263
|
+
if projected and items is not None:
|
|
264
|
+
items = [item.get(projected) if isinstance(item, dict) else getattr(item, projected, None) for item in items]
|
|
248
265
|
def primitive(item):
|
|
249
266
|
return isinstance(item, (str, int, float, bool))
|
|
250
267
|
def text(item):
|
|
251
268
|
if isinstance(item, bool):
|
|
252
269
|
return "true" if item else "false"
|
|
253
270
|
return str(item)
|
|
254
|
-
if
|
|
271
|
+
if projected and items is not None and any(item is None for item in items):
|
|
272
|
+
print(json.dumps({"error": f"a member of {name} has no field {projected}"}))
|
|
273
|
+
elif isinstance(value, (int, float)) and not isinstance(value, bool):
|
|
255
274
|
print(json.dumps({"scalar": value}))
|
|
256
275
|
elif items is None:
|
|
257
276
|
print(json.dumps({"error": f"{name} is not a list, tuple, set, dict or Enum"}))
|
|
@@ -293,7 +312,7 @@ export function evaluateScalar(workspaceRoot, sourceFile, exportName) {
|
|
|
293
312
|
}
|
|
294
313
|
function evaluateExport(workspaceRoot, sourceFile, exportName, options = {}) {
|
|
295
314
|
const absolute = path.resolve(workspaceRoot, sourceFile);
|
|
296
|
-
const run = runCodeEvaluator(workspaceRoot, sourceFile, { js: DOMAIN_EVALUATOR, python: PYTHON_DOMAIN_EVALUATOR }, [absolute, exportName], (parsed) => {
|
|
315
|
+
const run = runCodeEvaluator(workspaceRoot, sourceFile, { js: DOMAIN_EVALUATOR, python: PYTHON_DOMAIN_EVALUATOR }, [absolute, exportName, options.field ?? ""], (parsed) => {
|
|
297
316
|
const row = parsed;
|
|
298
317
|
return (row.error !== undefined ||
|
|
299
318
|
typeof row.scalar === "number" ||
|
|
@@ -668,9 +687,8 @@ export function rerunSmtQuery(solver, query) {
|
|
|
668
687
|
: null;
|
|
669
688
|
if (argv === null)
|
|
670
689
|
return { ok: false, reason: `solver ${solver} is not z3 or cvc5` };
|
|
671
|
-
const run =
|
|
690
|
+
const run = spawnSyncThroughFiles(solver, argv, {
|
|
672
691
|
input: query,
|
|
673
|
-
encoding: "utf8",
|
|
674
692
|
timeout: 60_000,
|
|
675
693
|
});
|
|
676
694
|
if (run.error)
|
|
@@ -678,7 +696,7 @@ export function rerunSmtQuery(solver, query) {
|
|
|
678
696
|
ok: false,
|
|
679
697
|
reason: `Kibi could not re-run ${solver} on the query: ${run.error.message}`,
|
|
680
698
|
};
|
|
681
|
-
const answer =
|
|
699
|
+
const answer = run.stdout.trim().split(/\s+/)[0] ?? "";
|
|
682
700
|
return answer === "unsat"
|
|
683
701
|
? { ok: true }
|
|
684
702
|
: {
|
|
@@ -711,7 +729,9 @@ async function workspaceProblem(context, contract, certificate) {
|
|
|
711
729
|
if (!importing)
|
|
712
730
|
return `the proof does not import ${exportName || domainId} from ${domain.sourceFile}, so its domain may be hand-listed${contract.domain_source?.export === undefined ? ` (Kibi reads the export named by the symbol's title; set domain_source.export when the export has another name)` : ""}`;
|
|
713
731
|
if (kind === "exhaustive") {
|
|
714
|
-
const evaluated = evaluateDomain(context.workspaceRoot, domain.sourceFile, exportName
|
|
732
|
+
const evaluated = evaluateDomain(context.workspaceRoot, domain.sourceFile, exportName, contract.domain_source?.field === undefined
|
|
733
|
+
? {}
|
|
734
|
+
: { field: contract.domain_source.field });
|
|
715
735
|
if (!evaluated.ok)
|
|
716
736
|
return evaluated.reason;
|
|
717
737
|
const members = record(certificate.domain)?.members;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"code-models.d.ts","sourceRoot":"","sources":["../../../src/operations/proof/code-models.ts"],"names":[],"mappings":"AA2BA,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,0CAA0C,CAAC;AACjF,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,gCAAgC,CAAC;AACpE,OAAO,EACL,KAAK,YAAY,EAKlB,MAAM,uBAAuB,CAAC;AAM/B,8DAA8D;AAC9D,eAAO,MAAM,cAAc,SAAU,CAAC;AAGtC,MAAM,MAAM,QAAQ,GAAG;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAA;CAAE,CAAC;AAExD,MAAM,MAAM,QAAQ,GAAG,QAAQ,CAAC;IAC9B,IAAI,EAAE,SAAS,MAAM,EAAE,CAAC;IACxB,KAAK,CAAC,EAAE,OAAO,CAAC;IAChB,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB,CAAC,CAAC;AAEH,2EAA2E;AAC3E,MAAM,MAAM,SAAS,GAAG,QAAQ,CAAC;IAC/B,OAAO,EAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,SAAS,MAAM,EAAE,CAAC,CAAC,CAAC;IACrD,UAAU,EAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,SAAS,QAAQ,EAAE,CAAC,CAAC,CAAC;CAC3D,CAAC,CAAC;AAEH,sDAAsD;AACtD,MAAM,MAAM,YAAY,GAAG,QAAQ,CAAC;IAClC,MAAM,EAAE,SAAS,MAAM,EAAE,CAAC;IAC1B,WAAW,EAAE,SAAS,CAAC,SAAS,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,EAAE,CAAC;IACpD,OAAO,CAAC,EAAE,SAAS,MAAM,EAAE,CAAC;CAC7B,CAAC,CAAC;AAEH,8CAA8C;AAC9C,MAAM,MAAM,YAAY,GACpB,QAAQ,CAAC;IAAE,IAAI,EAAE,QAAQ,CAAC;IAAC,MAAM,EAAE,MAAM,CAAC;IAAC,KAAK,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,IAAI,GAAG,QAAQ,CAAA;CAAE,CAAC,GACpF,QAAQ,CAAC;IAAE,IAAI,EAAE,QAAQ,CAAC;IAAC,KAAK,EAAE,MAAM,CAAA;CAAE,CAAC,CAAC;
|
|
1
|
+
{"version":3,"file":"code-models.d.ts","sourceRoot":"","sources":["../../../src/operations/proof/code-models.ts"],"names":[],"mappings":"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"}
|
|
@@ -42,8 +42,14 @@ if (typeof globalThis.Bun === "undefined") {
|
|
|
42
42
|
const modules = new Map();
|
|
43
43
|
async function load(ref) {
|
|
44
44
|
if (!modules.has(ref.file)) modules.set(ref.file, await import(pathToFileURL(ref.file).href));
|
|
45
|
-
|
|
46
|
-
|
|
45
|
+
// A dotted name reads a field of the export (BRAND.name).
|
|
46
|
+
const [head, ...fields] = ref.export.split(".");
|
|
47
|
+
let value = modules.get(ref.file)[head];
|
|
48
|
+
if (value === undefined) throw new Error(head + " is not exported from " + ref.file);
|
|
49
|
+
for (const field of fields) {
|
|
50
|
+
value = value !== null && typeof value === "object" ? value[field] : undefined;
|
|
51
|
+
if (value === undefined) throw new Error(ref.export + " has no field " + field + " in " + ref.file);
|
|
52
|
+
}
|
|
47
53
|
return value;
|
|
48
54
|
}
|
|
49
55
|
function items(value, name) {
|
|
@@ -179,9 +185,17 @@ def module_for(file):
|
|
|
179
185
|
return modules[file]
|
|
180
186
|
def load(ref):
|
|
181
187
|
module = module_for(ref["file"])
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
|
|
188
|
+
# A dotted name reads a field of the export (BRAND.name).
|
|
189
|
+
head, *fields = ref["export"].split(".")
|
|
190
|
+
if not hasattr(module, head):
|
|
191
|
+
raise ValueError(head + " is not defined in " + ref["file"])
|
|
192
|
+
value = getattr(module, head)
|
|
193
|
+
missing = object()
|
|
194
|
+
for field in fields:
|
|
195
|
+
value = value.get(field, missing) if isinstance(value, dict) else getattr(value, field, missing)
|
|
196
|
+
if value is missing:
|
|
197
|
+
raise ValueError(ref["export"] + " has no field " + field + " in " + ref["file"])
|
|
198
|
+
return value
|
|
185
199
|
def text(item):
|
|
186
200
|
if isinstance(item, enum.Enum):
|
|
187
201
|
return text(item.value)
|
|
@@ -15,6 +15,22 @@ export declare function workspaceBin(workspaceRoot: string, name: string): strin
|
|
|
15
15
|
* project's dependencies, so a project environment comes before it.
|
|
16
16
|
*/
|
|
17
17
|
export declare function pythonDomainInterpreters(workspaceRoot: string, sourceFile: string, env?: NodeJS.ProcessEnv): string[];
|
|
18
|
+
/**
|
|
19
|
+
* spawnSync with the child's stdin, stdout and stderr in temp files instead
|
|
20
|
+
* of pipes. Bun can miss the readiness event of a child's pipe, which leaves
|
|
21
|
+
* a synchronous spawn waiting until its timeout although the child has long
|
|
22
|
+
* exited; with no pipes the call only waits for the process to exit.
|
|
23
|
+
*/
|
|
24
|
+
export declare function spawnSyncThroughFiles(command: string, args: readonly string[], options: Readonly<{
|
|
25
|
+
cwd?: string;
|
|
26
|
+
input?: string;
|
|
27
|
+
timeout: number;
|
|
28
|
+
}>): {
|
|
29
|
+
error: Error | undefined;
|
|
30
|
+
status: number | null;
|
|
31
|
+
stdout: string;
|
|
32
|
+
stderr: string;
|
|
33
|
+
};
|
|
18
34
|
/**
|
|
19
35
|
* Run an evaluator script against the workspace code and return the JSON it
|
|
20
36
|
* prints last. A TypeScript or JavaScript file runs with bun when it is on
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"code-runner.d.ts","sourceRoot":"","sources":["../../../src/operations/proof/code-runner.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"code-runner.d.ts","sourceRoot":"","sources":["../../../src/operations/proof/code-runner.ts"],"names":[],"mappings":"AA+BA;;;;;;GAMG;AAKH,eAAO,MAAM,gBAAgB,8jBAgB5B,CAAC;AAEF,wBAAgB,YAAY,CAAC,aAAa,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAQ/E;AAED;;;;;;GAMG;AAEH,wBAAgB,wBAAwB,CACtC,aAAa,EAAE,MAAM,EACrB,UAAU,EAAE,MAAM,EAClB,GAAG,GAAE,MAAM,CAAC,UAAwB,GACnC,MAAM,EAAE,CAwBV;AAED;;;;;GAKG;AACH,wBAAgB,qBAAqB,CACnC,OAAO,EAAE,MAAM,EACf,IAAI,EAAE,SAAS,MAAM,EAAE,EACvB,OAAO,EAAE,QAAQ,CAAC;IAAE,GAAG,CAAC,EAAE,MAAM,CAAC;IAAC,KAAK,CAAC,EAAE,MAAM,CAAC;IAAC,OAAO,EAAE,MAAM,CAAA;CAAE,CAAC,GACnE;IAAE,KAAK,EAAE,KAAK,GAAG,SAAS,CAAC;IAAC,MAAM,EAAE,MAAM,GAAG,IAAI,CAAC;IAAC,MAAM,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAA;CAAE,CA2BrF;AAaD;;;;;;;GAOG;AAEH,wBAAgB,gBAAgB,CAC9B,aAAa,EAAE,MAAM,EACrB,UAAU,EAAE,MAAM,EAClB,OAAO,EAAE,QAAQ,CAAC;IAAE,EAAE,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAA;CAAE,CAAC,EACjD,IAAI,EAAE,SAAS,MAAM,EAAE,EACvB,MAAM,GAAE,CAAC,MAAM,EAAE,OAAO,KAAK,OAAoB,EACjD,OAAO,GAAE,QAAQ,CAAC;IAChB,OAAO,CAAC,EAAE,SAAS,CAAC,KAAK,GAAG,KAAK,GAAG,MAAM,CAAC,EAAE,CAAC;CAC/C,CAAM,GAEL;IAAE,EAAE,EAAE,IAAI,CAAC;IAAC,KAAK,EAAE,OAAO,CAAC;IAAC,MAAM,EAAE,OAAO,CAAA;CAAE,GAC7C;IAAE,EAAE,EAAE,KAAK,CAAC;IAAC,OAAO,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,OAAO,CAAA;CAAE,CAgDlD"}
|
|
@@ -16,7 +16,8 @@
|
|
|
16
16
|
along with this program. If not, see <https://www.gnu.org/licenses/>.
|
|
17
17
|
*/
|
|
18
18
|
import { spawnSync } from "node:child_process";
|
|
19
|
-
import { existsSync } from "node:fs";
|
|
19
|
+
import { closeSync, existsSync, mkdtempSync, openSync, readFileSync, rmSync, writeFileSync, } from "node:fs";
|
|
20
|
+
import os from "node:os";
|
|
20
21
|
import path from "node:path";
|
|
21
22
|
/**
|
|
22
23
|
* How Kibi runs a small evaluator script against the workspace's own code:
|
|
@@ -92,6 +93,43 @@ export function pythonDomainInterpreters(workspaceRoot, sourceFile, env = proces
|
|
|
92
93
|
add("python");
|
|
93
94
|
return interpreters;
|
|
94
95
|
}
|
|
96
|
+
/**
|
|
97
|
+
* spawnSync with the child's stdin, stdout and stderr in temp files instead
|
|
98
|
+
* of pipes. Bun can miss the readiness event of a child's pipe, which leaves
|
|
99
|
+
* a synchronous spawn waiting until its timeout although the child has long
|
|
100
|
+
* exited; with no pipes the call only waits for the process to exit.
|
|
101
|
+
*/
|
|
102
|
+
export function spawnSyncThroughFiles(command, args, options) {
|
|
103
|
+
const dir = mkdtempSync(path.join(os.tmpdir(), "kibi-spawn-"));
|
|
104
|
+
try {
|
|
105
|
+
const inPath = path.join(dir, "stdin");
|
|
106
|
+
const outPath = path.join(dir, "stdout");
|
|
107
|
+
const errPath = path.join(dir, "stderr");
|
|
108
|
+
writeFileSync(inPath, options.input ?? "");
|
|
109
|
+
const fds = [openSync(inPath, "r"), openSync(outPath, "w"), openSync(errPath, "w")];
|
|
110
|
+
let run;
|
|
111
|
+
try {
|
|
112
|
+
run = spawnSync(command, [...args], {
|
|
113
|
+
cwd: options.cwd,
|
|
114
|
+
stdio: fds,
|
|
115
|
+
timeout: options.timeout,
|
|
116
|
+
});
|
|
117
|
+
}
|
|
118
|
+
finally {
|
|
119
|
+
for (const fd of fds)
|
|
120
|
+
closeSync(fd);
|
|
121
|
+
}
|
|
122
|
+
return {
|
|
123
|
+
error: run.error,
|
|
124
|
+
status: run.status,
|
|
125
|
+
stdout: readFileSync(outPath, "utf8"),
|
|
126
|
+
stderr: readFileSync(errPath, "utf8"),
|
|
127
|
+
};
|
|
128
|
+
}
|
|
129
|
+
finally {
|
|
130
|
+
rmSync(dir, { recursive: true, force: true });
|
|
131
|
+
}
|
|
132
|
+
}
|
|
95
133
|
/** The line of a runner's stderr that names the failure. */
|
|
96
134
|
function failureLine(stderr, python) {
|
|
97
135
|
const lines = stderr
|
|
@@ -141,15 +179,13 @@ export function runCodeEvaluator(workspaceRoot, sourceFile, scripts, args, accep
|
|
|
141
179
|
});
|
|
142
180
|
let failure = "";
|
|
143
181
|
for (const [command, argv] of runners) {
|
|
144
|
-
const run =
|
|
182
|
+
const run = spawnSyncThroughFiles(command, [...argv, ...args], {
|
|
145
183
|
cwd: workspaceRoot,
|
|
146
|
-
encoding: "utf8",
|
|
147
184
|
timeout: 60_000,
|
|
148
|
-
maxBuffer: 64 * 1024 * 1024,
|
|
149
185
|
});
|
|
150
186
|
if (run.error)
|
|
151
187
|
continue;
|
|
152
|
-
const line =
|
|
188
|
+
const line = run.stdout.trim().split("\n").pop() ?? "";
|
|
153
189
|
try {
|
|
154
190
|
const parsed = JSON.parse(line);
|
|
155
191
|
if (accept(parsed))
|
|
@@ -158,7 +194,7 @@ export function runCodeEvaluator(workspaceRoot, sourceFile, scripts, args, accep
|
|
|
158
194
|
catch {
|
|
159
195
|
// Fall through to the next runner.
|
|
160
196
|
}
|
|
161
|
-
failure = failureLine(run.stderr
|
|
197
|
+
failure = failureLine(run.stderr, python);
|
|
162
198
|
}
|
|
163
199
|
return { ok: false, failure, python };
|
|
164
200
|
}
|
|
@@ -72,10 +72,73 @@ export type RequirementProofExplainView = {
|
|
|
72
72
|
id: string;
|
|
73
73
|
tests: readonly string[];
|
|
74
74
|
}[];
|
|
75
|
+
/** Whether a scenario exercises the requirement's failure side. */
|
|
76
|
+
readonly negativePath?: NegativePathExplain;
|
|
77
|
+
/** Quantified claims grounded only on booleans or ground predicates. */
|
|
78
|
+
readonly dimension?: DimensionExplain;
|
|
79
|
+
/** Edge cases derived from the typed claims and the scenarios covering them. */
|
|
80
|
+
readonly cases?: CasesExplain;
|
|
75
81
|
readonly tests: readonly ProofExplainTestBlock[];
|
|
76
82
|
readonly productionSymbols: readonly ProofExplainSymbolBlock[];
|
|
77
83
|
readonly structuralSymbols: readonly ProofExplainSymbolBlock[];
|
|
78
84
|
};
|
|
85
|
+
export type NegativePathExplain = {
|
|
86
|
+
readonly status: string;
|
|
87
|
+
readonly negativeScenarios: readonly string[];
|
|
88
|
+
readonly claims: readonly string[];
|
|
89
|
+
readonly suggestedNegatives: readonly {
|
|
90
|
+
readonly claimKey: string;
|
|
91
|
+
readonly factId: string;
|
|
92
|
+
readonly assumption: Readonly<Record<string, unknown>>;
|
|
93
|
+
}[];
|
|
94
|
+
/** An approved waiver carries approvedBy; a reason alone awaits approval. */
|
|
95
|
+
readonly waiver?: {
|
|
96
|
+
readonly reason: string;
|
|
97
|
+
readonly approvedBy?: string;
|
|
98
|
+
};
|
|
99
|
+
};
|
|
100
|
+
export type DimensionClaimExplain = {
|
|
101
|
+
readonly claimKey: string;
|
|
102
|
+
readonly claimText: string;
|
|
103
|
+
readonly quantifier: string;
|
|
104
|
+
readonly factIds: readonly string[];
|
|
105
|
+
/** Typed groundings that would represent the quantifier, likeliest first. */
|
|
106
|
+
readonly rewrites: readonly string[];
|
|
107
|
+
/** An approved waiver carries approvedBy; a reason alone awaits approval. */
|
|
108
|
+
readonly waiver?: {
|
|
109
|
+
readonly reason: string;
|
|
110
|
+
readonly approvedBy?: string;
|
|
111
|
+
};
|
|
112
|
+
};
|
|
113
|
+
export type DimensionExplain = {
|
|
114
|
+
readonly status: string;
|
|
115
|
+
readonly claims: readonly DimensionClaimExplain[];
|
|
116
|
+
readonly waivedClaims: readonly DimensionClaimExplain[];
|
|
117
|
+
};
|
|
118
|
+
export type CaseExplain = {
|
|
119
|
+
readonly caseId: string;
|
|
120
|
+
readonly claimKey: string;
|
|
121
|
+
readonly factId: string;
|
|
122
|
+
readonly generator: string;
|
|
123
|
+
readonly constraint: string;
|
|
124
|
+
/** success, rejection or unspecified */
|
|
125
|
+
readonly predicted: string;
|
|
126
|
+
/** covered, uncovered, unspecified or waived */
|
|
127
|
+
readonly coverage: string;
|
|
128
|
+
readonly scenarios: readonly string[];
|
|
129
|
+
/** The assumes fact a scenario would state to land in the case. */
|
|
130
|
+
readonly assumption: Readonly<Record<string, unknown>>;
|
|
131
|
+
readonly waiver?: {
|
|
132
|
+
readonly reason: string;
|
|
133
|
+
readonly approvedBy?: string;
|
|
134
|
+
};
|
|
135
|
+
};
|
|
136
|
+
export type CasesExplain = {
|
|
137
|
+
readonly status: string;
|
|
138
|
+
readonly cases: readonly CaseExplain[];
|
|
139
|
+
readonly summary: Readonly<Record<string, number>>;
|
|
140
|
+
readonly limitReached: boolean;
|
|
141
|
+
};
|
|
79
142
|
export type SymbolProofExplainView = {
|
|
80
143
|
readonly kind: "symbol";
|
|
81
144
|
readonly id: string;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"explain.d.ts","sourceRoot":"","sources":["../../../src/operations/proof/explain.ts"],"names":[],"mappings":"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
|
|
1
|
+
{"version":3,"file":"explain.d.ts","sourceRoot":"","sources":["../../../src/operations/proof/explain.ts"],"names":[],"mappings":"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"}
|
|
@@ -150,11 +150,170 @@ export function projectRequirementExplain(proof) {
|
|
|
150
150
|
: {}),
|
|
151
151
|
...claimFields(proof),
|
|
152
152
|
scenarios,
|
|
153
|
+
...negativePathField(stages.negativePath),
|
|
154
|
+
...dimensionField(stages.dimension),
|
|
155
|
+
...casesField(stages.cases),
|
|
153
156
|
tests,
|
|
154
157
|
productionSymbols: explanations.filter((item) => !structuralIds.has(item.symbolId)),
|
|
155
158
|
structuralSymbols: explanations.filter((item) => structuralIds.has(item.symbolId)),
|
|
156
159
|
};
|
|
157
160
|
}
|
|
161
|
+
// implements REQ-kibi-happy-path-gap
|
|
162
|
+
function negativePathField(stage) {
|
|
163
|
+
if (stage === undefined)
|
|
164
|
+
return {};
|
|
165
|
+
const record = asRecord(stage);
|
|
166
|
+
const suggestions = Array.isArray(record.suggestedNegatives)
|
|
167
|
+
? record.suggestedNegatives.map((item) => {
|
|
168
|
+
const entry = asRecord(item);
|
|
169
|
+
return {
|
|
170
|
+
claimKey: asString(entry.claimKey),
|
|
171
|
+
factId: asString(entry.factId),
|
|
172
|
+
assumption: asRecord(entry.assumption),
|
|
173
|
+
};
|
|
174
|
+
})
|
|
175
|
+
: [];
|
|
176
|
+
return {
|
|
177
|
+
negativePath: {
|
|
178
|
+
status: asString(record.status),
|
|
179
|
+
negativeScenarios: asStringArray(record.negativeScenarios),
|
|
180
|
+
claims: asStringArray(record.claims),
|
|
181
|
+
suggestedNegatives: suggestions,
|
|
182
|
+
...waiverField(record.waiver),
|
|
183
|
+
},
|
|
184
|
+
};
|
|
185
|
+
}
|
|
186
|
+
function waiverField(raw) {
|
|
187
|
+
const waiver = asRecord(raw);
|
|
188
|
+
const reason = asString(waiver.reason);
|
|
189
|
+
const approvedBy = asString(waiver.approvedBy);
|
|
190
|
+
return reason === ""
|
|
191
|
+
? {}
|
|
192
|
+
: { waiver: { reason, ...(approvedBy === "" ? {} : { approvedBy }) } };
|
|
193
|
+
}
|
|
194
|
+
// implements REQ-kibi-dimension-gap
|
|
195
|
+
function dimensionField(stage) {
|
|
196
|
+
if (stage === undefined)
|
|
197
|
+
return {};
|
|
198
|
+
const record = asRecord(stage);
|
|
199
|
+
const claims = (raw) => Array.isArray(raw)
|
|
200
|
+
? raw.map((item) => {
|
|
201
|
+
const entry = asRecord(item);
|
|
202
|
+
return {
|
|
203
|
+
claimKey: asString(entry.claimKey),
|
|
204
|
+
claimText: asString(entry.claimText),
|
|
205
|
+
quantifier: asString(entry.quantifier),
|
|
206
|
+
factIds: asStringArray(entry.factIds),
|
|
207
|
+
rewrites: asStringArray(entry.rewrites),
|
|
208
|
+
...waiverField(entry.waiver),
|
|
209
|
+
};
|
|
210
|
+
})
|
|
211
|
+
: [];
|
|
212
|
+
return {
|
|
213
|
+
dimension: {
|
|
214
|
+
status: asString(record.status),
|
|
215
|
+
claims: claims(record.claims),
|
|
216
|
+
waivedClaims: claims(record.waivedClaims),
|
|
217
|
+
},
|
|
218
|
+
};
|
|
219
|
+
}
|
|
220
|
+
// implements REQ-kibi-case-coverage
|
|
221
|
+
function casesField(stage) {
|
|
222
|
+
if (stage === undefined)
|
|
223
|
+
return {};
|
|
224
|
+
const record = asRecord(stage);
|
|
225
|
+
const cases = Array.isArray(record.cases)
|
|
226
|
+
? record.cases.map((item) => {
|
|
227
|
+
const entry = asRecord(item);
|
|
228
|
+
return {
|
|
229
|
+
caseId: asString(entry.caseId),
|
|
230
|
+
claimKey: asString(entry.claimKey),
|
|
231
|
+
factId: asString(entry.factId),
|
|
232
|
+
generator: asString(entry.generator),
|
|
233
|
+
constraint: asString(entry.constraint),
|
|
234
|
+
predicted: asString(entry.predicted),
|
|
235
|
+
coverage: asString(entry.coverage),
|
|
236
|
+
scenarios: asStringArray(entry.scenarios),
|
|
237
|
+
assumption: asRecord(entry.assumption),
|
|
238
|
+
...waiverField(entry.waiver),
|
|
239
|
+
};
|
|
240
|
+
})
|
|
241
|
+
: [];
|
|
242
|
+
const summary = asRecord(record.summary);
|
|
243
|
+
return {
|
|
244
|
+
cases: {
|
|
245
|
+
status: asString(record.status),
|
|
246
|
+
cases,
|
|
247
|
+
summary: Object.fromEntries(Object.entries(summary).filter((entry) => typeof entry[1] === "number")),
|
|
248
|
+
limitReached: record.limitReached === true,
|
|
249
|
+
},
|
|
250
|
+
};
|
|
251
|
+
}
|
|
252
|
+
function renderCases(view) {
|
|
253
|
+
const cases = view.cases;
|
|
254
|
+
if (cases === undefined || cases.cases.length === 0)
|
|
255
|
+
return [];
|
|
256
|
+
const summary = cases.summary;
|
|
257
|
+
const lines = [
|
|
258
|
+
"",
|
|
259
|
+
`Edge cases: ${cases.status} (${summary.covered ?? 0} covered, ${summary.uncovered ?? 0} uncovered, ${summary.unspecified ?? 0} unspecified, ${summary.waived ?? 0} waived)`,
|
|
260
|
+
];
|
|
261
|
+
for (const row of cases.cases) {
|
|
262
|
+
const where = row.coverage === "covered" ? ` by ${row.scenarios.join(", ")}` : "";
|
|
263
|
+
lines.push(` ${row.caseId} ${row.factId} ${row.constraint} -> ${row.predicted}: ${row.coverage}${where}`);
|
|
264
|
+
if (row.coverage === "uncovered" && row.predicted === "rejection")
|
|
265
|
+
lines.push(` add a scenario that assumes ${JSON.stringify(row.assumption)} and expects rejection`);
|
|
266
|
+
if (row.waiver !== undefined && row.waiver.approvedBy === undefined)
|
|
267
|
+
lines.push(` waiver awaiting approval (set case_waiver_approved_by to the person who accepts it, in this pull request): ${row.waiver.reason}`);
|
|
268
|
+
}
|
|
269
|
+
if (cases.limitReached)
|
|
270
|
+
lines.push(" (some facts have more cases than the per-fact limit of 12)");
|
|
271
|
+
return lines;
|
|
272
|
+
}
|
|
273
|
+
const DIMENSION_REWRITES = {
|
|
274
|
+
bound: "an integer property with the bound (lte, gte or eq)",
|
|
275
|
+
rule: "a rule over a variable (every X with P must Q)",
|
|
276
|
+
count: "an integer count of what varies",
|
|
277
|
+
set: "a set fact over the members",
|
|
278
|
+
};
|
|
279
|
+
function renderDimension(view) {
|
|
280
|
+
const dimension = view.dimension;
|
|
281
|
+
if (dimension === undefined || dimension.status === "not_required")
|
|
282
|
+
return [];
|
|
283
|
+
const lines = ["", `Quantified claims: ${dimension.status}`];
|
|
284
|
+
for (const claim of dimension.claims) {
|
|
285
|
+
lines.push(` ${claim.claimKey} (${claim.factIds.join(", ")}): "${claim.quantifier.replaceAll("_", " ")}" is grounded on a boolean: ${claim.claimText}`);
|
|
286
|
+
const rewrites = claim.rewrites
|
|
287
|
+
.map((rewrite) => DIMENSION_REWRITES[rewrite] ?? rewrite)
|
|
288
|
+
.join("; or ");
|
|
289
|
+
if (rewrites !== "")
|
|
290
|
+
lines.push(` ground it on ${rewrites}`);
|
|
291
|
+
if (claim.waiver !== undefined)
|
|
292
|
+
lines.push(` waiver awaiting approval (set dimension_waiver_approved_by to the person who accepts it, in this pull request): ${claim.waiver.reason}`);
|
|
293
|
+
}
|
|
294
|
+
for (const claim of dimension.waivedClaims) {
|
|
295
|
+
lines.push(` ${claim.claimKey} waived by ${claim.waiver?.approvedBy ?? ""}: ${claim.waiver?.reason ?? ""}`);
|
|
296
|
+
}
|
|
297
|
+
return lines;
|
|
298
|
+
}
|
|
299
|
+
function renderNegativePath(view) {
|
|
300
|
+
const negative = view.negativePath;
|
|
301
|
+
if (negative === undefined || negative.status === "not_required")
|
|
302
|
+
return [];
|
|
303
|
+
const lines = ["", `Failure side: ${negative.status}`];
|
|
304
|
+
if (negative.waiver !== undefined) {
|
|
305
|
+
lines.push(negative.waiver.approvedBy === undefined
|
|
306
|
+
? ` waiver awaiting approval (set failure_side_waiver_approved_by to the person who accepts it, in this pull request): ${negative.waiver.reason}`
|
|
307
|
+
: ` waived by ${negative.waiver.approvedBy}: ${negative.waiver.reason}`);
|
|
308
|
+
}
|
|
309
|
+
for (const scenarioId of negative.negativeScenarios) {
|
|
310
|
+
lines.push(` ${scenarioId} expects rejection or error`);
|
|
311
|
+
}
|
|
312
|
+
for (const suggestion of negative.suggestedNegatives) {
|
|
313
|
+
lines.push(` ${suggestion.claimKey} (${suggestion.factId}): assume ${JSON.stringify(suggestion.assumption)} and expect rejection`);
|
|
314
|
+
}
|
|
315
|
+
return lines;
|
|
316
|
+
}
|
|
158
317
|
function claimFields(proof) {
|
|
159
318
|
const summary = asRecord(proof.claimSummary);
|
|
160
319
|
const count = (key) => typeof summary[key] === "number" ? summary[key] : 0;
|
|
@@ -267,6 +426,9 @@ function renderRequirementExplain(view) {
|
|
|
267
426
|
for (const scenario of view.scenarios) {
|
|
268
427
|
lines.push(` ${scenario.id} -> ${scenario.tests.join(", ") || "(no tests)"}`);
|
|
269
428
|
}
|
|
429
|
+
lines.push(...renderNegativePath(view));
|
|
430
|
+
lines.push(...renderDimension(view));
|
|
431
|
+
lines.push(...renderCases(view));
|
|
270
432
|
lines.push("");
|
|
271
433
|
for (const test of view.tests) {
|
|
272
434
|
lines.push(`TEST ${test.testId}`);
|
|
@@ -1,8 +1,16 @@
|
|
|
1
1
|
import { propositionRole } from "./proposition-role.js";
|
|
2
|
-
import type { SemanticAdvisorAnalysisResult, SemanticAdvisorInput } from "./types.js";
|
|
2
|
+
import type { SemanticAdvisorAnalysisResult, SemanticAdvisorInput, SemanticPropositionDimension } from "./types.js";
|
|
3
3
|
export declare const SEMANTIC_ADVISOR_VERSION = "semantic-advisor-v2";
|
|
4
4
|
export { semanticClaimKey } from "./clauses.js";
|
|
5
5
|
export declare function stringLogicClaims(value: unknown): string[];
|
|
6
6
|
export { propositionRole };
|
|
7
|
+
/**
|
|
8
|
+
* The first quantifier over a collection or cardinality bound in a clause,
|
|
9
|
+
* and the typed groundings that represent it. The proof ladder's
|
|
10
|
+
* dimension_unrepresented gap uses the same words (requirement_proof.pl,
|
|
11
|
+
* claim_quantifier/2): only, any and some mostly scope a condition, so they
|
|
12
|
+
* are left out.
|
|
13
|
+
*/
|
|
14
|
+
export declare function claimDimension(text: string): SemanticPropositionDimension | undefined;
|
|
7
15
|
export declare function analyzeSemanticAdvisorInput(input: SemanticAdvisorInput): SemanticAdvisorAnalysisResult;
|
|
8
16
|
//# sourceMappingURL=analyze-prose.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"analyze-prose.d.ts","sourceRoot":"","sources":["../../../src/operations/semantic-advisor/analyze-prose.ts"],"names":[],"mappings":"AAuBA,OAAO,EAAE,eAAe,EAAE,MAAM,uBAAuB,CAAC;AAiBxD,OAAO,KAAK,EACV,6BAA6B,EAC7B,oBAAoB,
|
|
1
|
+
{"version":3,"file":"analyze-prose.d.ts","sourceRoot":"","sources":["../../../src/operations/semantic-advisor/analyze-prose.ts"],"names":[],"mappings":"AAuBA,OAAO,EAAE,eAAe,EAAE,MAAM,uBAAuB,CAAC;AAiBxD,OAAO,KAAK,EACV,6BAA6B,EAC7B,oBAAoB,EAKpB,4BAA4B,EAO7B,MAAM,YAAY,CAAC;AAEpB,eAAO,MAAM,wBAAwB,wBAAwB,CAAC;AAC9D,OAAO,EAAE,gBAAgB,EAAE,MAAM,cAAc,CAAC;AAEhD,wBAAgB,iBAAiB,CAAC,KAAK,EAAE,OAAO,GAAG,MAAM,EAAE,CAI1D;AA6gBD,OAAO,EAAE,eAAe,EAAE,CAAC;AAwT3B;;;;;;GAMG;AACH,wBAAgB,cAAc,CAC5B,IAAI,EAAE,MAAM,GACX,4BAA4B,GAAG,SAAS,CAY1C;AAsED,wBAAgB,2BAA2B,CACzC,KAAK,EAAE,oBAAoB,GAC1B,6BAA6B,CAgE/B"}
|