kibi-cli 2.4.0 → 2.5.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 +6 -0
- package/dist/cli-json-command.d.ts.map +1 -1
- package/dist/cli-json-command.js +37 -9
- package/dist/cli-operation-loader.d.ts.map +1 -1
- package/dist/cli-operation-loader.js +7 -0
- package/dist/cli-operation-metadata.d.ts +12 -4
- package/dist/cli-operation-metadata.d.ts.map +1 -1
- package/dist/cli-operation-metadata.js +14 -4
- package/dist/cli-protocol.d.ts +14 -0
- package/dist/cli-protocol.d.ts.map +1 -1
- package/dist/cli-protocol.js +31 -2
- package/dist/cli-register-proof.d.ts.map +1 -1
- package/dist/cli-register-proof.js +13 -0
- package/dist/commands/check.d.ts.map +1 -1
- package/dist/commands/check.js +11 -2
- package/dist/commands/discovery-shared.d.ts.map +1 -1
- package/dist/commands/discovery-shared.js +8 -2
- package/dist/commands/engine.d.ts.map +1 -1
- package/dist/commands/engine.js +4 -2
- package/dist/commands/gc.d.ts.map +1 -1
- package/dist/commands/gc.js +7 -0
- package/dist/commands/init-helpers.d.ts.map +1 -1
- package/dist/commands/init-helpers.js +0 -1
- package/dist/commands/migrate.d.ts.map +1 -1
- package/dist/commands/migrate.js +281 -14
- package/dist/commands/proof-compact.d.ts +9 -0
- package/dist/commands/proof-compact.d.ts.map +1 -0
- package/dist/commands/proof-compact.js +58 -0
- package/dist/commands/prove.d.ts +38 -0
- package/dist/commands/prove.d.ts.map +1 -1
- package/dist/commands/prove.js +222 -47
- package/dist/commands/sync/persistence.d.ts.map +1 -1
- package/dist/commands/sync/persistence.js +61 -16
- package/dist/commands/sync.d.ts +8 -0
- package/dist/commands/sync.d.ts.map +1 -1
- package/dist/commands/sync.js +42 -16
- package/dist/diagnostics.js +1 -1
- package/dist/engine-limits.d.ts +74 -0
- package/dist/engine-limits.d.ts.map +1 -0
- package/dist/engine-limits.js +201 -0
- package/dist/engine.d.ts +10 -0
- package/dist/engine.d.ts.map +1 -1
- package/dist/engine.js +57 -9
- package/dist/extractors/manifest.d.ts +8 -0
- package/dist/extractors/manifest.d.ts.map +1 -1
- package/dist/extractors/manifest.js +34 -5
- package/dist/extractors/markdown.d.ts +8 -0
- package/dist/extractors/markdown.d.ts.map +1 -1
- package/dist/extractors/markdown.js +57 -0
- package/dist/extractors/relationships.d.ts.map +1 -1
- package/dist/extractors/relationships.js +2 -0
- package/dist/intent-search.d.ts +4 -1
- package/dist/intent-search.d.ts.map +1 -1
- package/dist/intent-search.js +186 -33
- package/dist/operations/bootstrap/candidate-helpers.d.ts.map +1 -1
- package/dist/operations/bootstrap/candidate-helpers.js +8 -1
- package/dist/operations/bootstrap/candidates.d.ts.map +1 -1
- package/dist/operations/bootstrap/candidates.js +54 -38
- package/dist/operations/bootstrap/generate.d.ts +2 -0
- package/dist/operations/bootstrap/generate.d.ts.map +1 -1
- package/dist/operations/bootstrap/generate.js +87 -33
- package/dist/operations/bootstrap/intent-claims.d.ts.map +1 -1
- package/dist/operations/bootstrap/intent-claims.js +12 -4
- package/dist/operations/bootstrap/markdown-candidates.d.ts +2 -0
- package/dist/operations/bootstrap/markdown-candidates.d.ts.map +1 -1
- package/dist/operations/bootstrap/markdown-candidates.js +32 -10
- package/dist/operations/bootstrap/presentation.d.ts.map +1 -1
- package/dist/operations/bootstrap/presentation.js +6 -2
- package/dist/operations/bootstrap/requirement-claims.d.ts +1 -0
- package/dist/operations/bootstrap/requirement-claims.d.ts.map +1 -1
- package/dist/operations/bootstrap/requirement-claims.js +13 -1
- package/dist/operations/bootstrap/validation.d.ts +4 -0
- package/dist/operations/bootstrap/validation.d.ts.map +1 -0
- package/dist/operations/bootstrap/validation.js +20 -0
- package/dist/operations/migration/inventory-rederive.d.ts +81 -0
- package/dist/operations/migration/inventory-rederive.d.ts.map +1 -0
- package/dist/operations/migration/inventory-rederive.js +484 -0
- package/dist/operations/migration/kb-sources.d.ts +53 -0
- package/dist/operations/migration/kb-sources.d.ts.map +1 -0
- package/dist/operations/migration/kb-sources.js +233 -0
- package/dist/operations/migration/origin-backfill.d.ts +39 -0
- package/dist/operations/migration/origin-backfill.d.ts.map +1 -0
- package/dist/operations/migration/origin-backfill.js +164 -0
- package/dist/operations/migration/polarity-values.d.ts +10 -0
- package/dist/operations/migration/polarity-values.d.ts.map +1 -0
- package/dist/operations/migration/polarity-values.js +60 -0
- package/dist/operations/migration/schema6.d.ts +59 -0
- package/dist/operations/migration/schema6.d.ts.map +1 -0
- package/dist/operations/migration/schema6.js +379 -0
- package/dist/operations/migration/source-paths.d.ts +131 -0
- package/dist/operations/migration/source-paths.d.ts.map +1 -0
- package/dist/operations/migration/source-paths.js +308 -0
- package/dist/operations/migration/superseded-closure.d.ts +54 -0
- package/dist/operations/migration/superseded-closure.d.ts.map +1 -0
- package/dist/operations/migration/superseded-closure.js +187 -0
- package/dist/operations/modeling/logic-modeling.d.ts.map +1 -1
- package/dist/operations/modeling/logic-modeling.js +3 -5
- package/dist/operations/modeling/model-requirement.d.ts.map +1 -1
- package/dist/operations/modeling/model-requirement.js +225 -67
- package/dist/operations/mutation/contradictions.d.ts +16 -0
- package/dist/operations/mutation/contradictions.d.ts.map +1 -1
- package/dist/operations/mutation/contradictions.js +32 -0
- package/dist/operations/mutation/delete.d.ts.map +1 -1
- package/dist/operations/mutation/delete.js +15 -7
- package/dist/operations/mutation/origin.d.ts +21 -0
- package/dist/operations/mutation/origin.d.ts.map +1 -0
- package/dist/operations/mutation/origin.js +78 -0
- package/dist/operations/mutation/plan-apply-journal.d.ts +182 -0
- package/dist/operations/mutation/plan-apply-journal.d.ts.map +1 -0
- package/dist/operations/mutation/plan-apply-journal.js +613 -0
- package/dist/operations/mutation/predicate-vocabulary-guard.d.ts +3 -1
- package/dist/operations/mutation/predicate-vocabulary-guard.d.ts.map +1 -1
- package/dist/operations/mutation/predicate-vocabulary-guard.js +13 -2
- package/dist/operations/mutation/relationships.d.ts +5 -5
- package/dist/operations/mutation/relationships.d.ts.map +1 -1
- package/dist/operations/mutation/relationships.js +31 -11
- package/dist/operations/mutation/serialization.d.ts.map +1 -1
- package/dist/operations/mutation/serialization.js +3 -1
- package/dist/operations/mutation/source-authoring.d.ts +6 -0
- package/dist/operations/mutation/source-authoring.d.ts.map +1 -1
- package/dist/operations/mutation/source-authoring.js +7 -1
- package/dist/operations/mutation/types.d.ts +14 -0
- package/dist/operations/mutation/types.d.ts.map +1 -1
- package/dist/operations/mutation/upsert.d.ts +30 -3
- package/dist/operations/mutation/upsert.d.ts.map +1 -1
- package/dist/operations/mutation/upsert.js +105 -35
- package/dist/operations/mutation/validate-upsert.d.ts +6 -0
- package/dist/operations/mutation/validate-upsert.d.ts.map +1 -1
- package/dist/operations/mutation/validate-upsert.js +34 -30
- package/dist/operations/planning/apply-plan.d.ts.map +1 -1
- package/dist/operations/planning/apply-plan.js +751 -144
- package/dist/operations/planning/compile-intent.d.ts +34 -1
- package/dist/operations/planning/compile-intent.d.ts.map +1 -1
- package/dist/operations/planning/compile-intent.js +314 -98
- package/dist/operations/proof/code-scope.d.ts +28 -0
- package/dist/operations/proof/code-scope.d.ts.map +1 -1
- package/dist/operations/proof/code-scope.js +72 -0
- package/dist/operations/proof/compact-receipts.d.ts +49 -0
- package/dist/operations/proof/compact-receipts.d.ts.map +1 -0
- package/dist/operations/proof/compact-receipts.js +160 -0
- package/dist/operations/proof/ingest-proof.d.ts +2 -0
- package/dist/operations/proof/ingest-proof.d.ts.map +1 -1
- package/dist/operations/proof/ingest-proof.js +44 -23
- package/dist/operations/proof/prune-receipts.d.ts.map +1 -1
- package/dist/operations/proof/prune-receipts.js +5 -9
- package/dist/operations/proof/receipt-compaction.d.ts +48 -0
- package/dist/operations/proof/receipt-compaction.d.ts.map +1 -0
- package/dist/operations/proof/receipt-compaction.js +121 -0
- package/dist/operations/semantic-advisor/analysis-receipt.d.ts.map +1 -1
- package/dist/operations/semantic-advisor/analysis-receipt.js +12 -1
- package/dist/operations/semantic-advisor/analyze-prose.d.ts +2 -1
- package/dist/operations/semantic-advisor/analyze-prose.d.ts.map +1 -1
- package/dist/operations/semantic-advisor/analyze-prose.js +51 -5
- package/dist/operations/semantic-advisor/clauses.d.ts +1 -0
- package/dist/operations/semantic-advisor/clauses.d.ts.map +1 -1
- package/dist/operations/semantic-advisor/clauses.js +11 -1
- package/dist/operations/semantic-advisor/conditional-rules.d.ts +33 -0
- package/dist/operations/semantic-advisor/conditional-rules.d.ts.map +1 -0
- package/dist/operations/semantic-advisor/conditional-rules.js +262 -0
- package/dist/operations/semantic-advisor/ingestion-boundary.d.ts +3 -1
- package/dist/operations/semantic-advisor/ingestion-boundary.d.ts.map +1 -1
- package/dist/operations/semantic-advisor/ingestion-boundary.js +14 -6
- package/dist/operations/semantic-advisor/plugin-orchestration.js +1 -1
- package/dist/prolog/codec.d.ts.map +1 -1
- package/dist/prolog/codec.js +2 -1
- package/dist/prolog.d.ts +9 -0
- package/dist/prolog.d.ts.map +1 -1
- package/dist/prolog.js +56 -10
- package/dist/proof/command-test-report.d.ts +74 -0
- package/dist/proof/command-test-report.d.ts.map +1 -0
- package/dist/proof/command-test-report.js +206 -0
- package/dist/public/branch-resolver.d.ts +1 -0
- package/dist/public/branch-resolver.d.ts.map +1 -1
- package/dist/public/branch-resolver.js +1 -0
- package/dist/public/entity-origin.d.ts +69 -0
- package/dist/public/entity-origin.d.ts.map +1 -0
- package/dist/public/entity-origin.js +142 -0
- package/dist/public/impact/full-kb-quality.d.ts.map +1 -1
- package/dist/public/impact/full-kb-quality.js +1 -0
- package/dist/public/impact/requirement-quality.js +1 -1
- package/dist/public/operations/catalog.d.ts +130 -19
- package/dist/public/operations/catalog.d.ts.map +1 -1
- package/dist/public/operations/catalog.js +3 -0
- package/dist/public/operations/check-executor.d.ts.map +1 -1
- package/dist/public/operations/check-executor.js +8 -0
- package/dist/public/operations/contracts.d.ts +0 -5
- package/dist/public/operations/contracts.d.ts.map +1 -1
- package/dist/public/operations/contracts.js +63 -14
- package/dist/public/operations/discovery-entities.d.ts +15 -0
- package/dist/public/operations/discovery-entities.d.ts.map +1 -1
- package/dist/public/operations/discovery-entities.js +59 -0
- package/dist/public/operations/discovery-executors.d.ts +6 -1
- package/dist/public/operations/discovery-executors.d.ts.map +1 -1
- package/dist/public/operations/discovery-executors.js +65 -6
- package/dist/public/operations/index.d.ts +1 -0
- package/dist/public/operations/index.d.ts.map +1 -1
- package/dist/public/operations/index.js +1 -0
- package/dist/public/operations/migration-plan.d.ts +5 -0
- package/dist/public/operations/migration-plan.d.ts.map +1 -1
- package/dist/public/operations/migration-plan.js +26 -1
- package/dist/public/operations/node-ports.d.ts.map +1 -1
- package/dist/public/operations/node-ports.js +24 -3
- package/dist/public/operations/origin-review.d.ts +51 -0
- package/dist/public/operations/origin-review.d.ts.map +1 -0
- package/dist/public/operations/origin-review.js +307 -0
- package/dist/public/operations/predicate-schema-conformance.js +1 -1
- package/dist/public/operations/repair-plan.d.ts.map +1 -1
- package/dist/public/operations/repair-plan.js +4 -0
- package/dist/public/operations/result-envelope.d.ts.map +1 -1
- package/dist/public/operations/result-envelope.js +17 -5
- package/dist/public/operations/runtime-types.d.ts +9 -0
- package/dist/public/operations/runtime-types.d.ts.map +1 -1
- package/dist/public/operations/schema6-check-actions.d.ts +127 -0
- package/dist/public/operations/schema6-check-actions.d.ts.map +1 -0
- package/dist/public/operations/schema6-check-actions.js +575 -0
- package/dist/public/operations/source-path-dangling.d.ts +17 -0
- package/dist/public/operations/source-path-dangling.d.ts.map +1 -0
- package/dist/public/operations/source-path-dangling.js +66 -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 +15 -1
- package/dist/public/operations/specs/check.d.ts +2 -2
- package/dist/public/operations/specs/check.js +1 -1
- package/dist/public/operations/specs/composite.d.ts +351 -0
- package/dist/public/operations/specs/composite.d.ts.map +1 -0
- package/dist/public/operations/specs/composite.js +96 -0
- package/dist/public/operations/specs/discovery.d.ts +8 -3
- package/dist/public/operations/specs/discovery.d.ts.map +1 -1
- package/dist/public/operations/specs/discovery.js +8 -3
- package/dist/public/operations/specs/modeling.d.ts +2 -2
- package/dist/public/operations/specs/modeling.js +2 -2
- package/dist/public/operations/specs/mutation-schemas.d.ts +73 -8
- package/dist/public/operations/specs/mutation-schemas.d.ts.map +1 -1
- package/dist/public/operations/specs/mutation-schemas.js +43 -7
- package/dist/public/operations/specs/mutation.d.ts +1 -1
- package/dist/public/operations/specs/mutation.js +1 -1
- package/dist/public/operations/specs/planning.d.ts +2 -2
- package/dist/public/operations/specs/planning.js +4 -4
- package/dist/public/operations/specs/reporting.d.ts.map +1 -1
- package/dist/public/operations/specs/reporting.js +13 -26
- package/dist/public/operations/specs/upsert.d.ts +79 -9
- package/dist/public/operations/specs/upsert.d.ts.map +1 -1
- package/dist/public/operations/specs/upsert.js +6 -1
- package/dist/public/operations/types.d.ts +1 -1
- package/dist/public/operations/types.d.ts.map +1 -1
- package/dist/public/proof-receipt.d.ts +1 -0
- package/dist/public/proof-receipt.d.ts.map +1 -1
- package/dist/public/schemas/entity.d.ts.map +1 -1
- package/dist/public/schemas/entity.js +52 -0
- package/dist/public/schemas/relationship.d.ts.map +1 -1
- package/dist/public/schemas/relationship.js +2 -0
- package/dist/public/skills/kibi-bootstrap/SKILL.md +6 -1
- package/dist/public/skills/kibi-bootstrap/resources/bootstrap.md +6 -0
- package/dist/public/skills/kibi-usage/SKILL.md +68 -18
- package/dist/public/skills/kibi-usage/resources/fact-lanes.md +5 -5
- package/dist/public/skills/kibi-usage/resources/kb-improvement.md +1 -1
- package/dist/public/skills/kibi-usage/resources/logic-ir.md +2 -2
- package/dist/public/skills/kibi-usage/resources/operation-access.md +25 -1
- package/dist/public/skills/kibi-usage/resources/ui-requirements.md +4 -4
- package/dist/public/skills/kibi-usage/resources/workflows.md +42 -25
- package/dist/public/telemetry-acceptance.d.ts +58 -2
- package/dist/public/telemetry-acceptance.d.ts.map +1 -1
- package/dist/public/telemetry-acceptance.js +136 -10
- package/dist/public/telemetry-remediation.d.ts.map +1 -1
- package/dist/public/telemetry-remediation.js +26 -10
- package/dist/relationships/shards.d.ts +13 -0
- package/dist/relationships/shards.d.ts.map +1 -1
- package/dist/relationships/shards.js +54 -28
- package/dist/runtime/cli-runtime.d.ts.map +1 -1
- package/dist/runtime/cli-runtime.js +44 -3
- package/dist/runtime/detached-snapshot.d.ts +38 -0
- package/dist/runtime/detached-snapshot.d.ts.map +1 -0
- package/dist/runtime/detached-snapshot.js +92 -0
- package/dist/schemas/entity.schema.json +122 -0
- package/dist/search-answer.d.ts +157 -0
- package/dist/search-answer.d.ts.map +1 -0
- package/dist/search-answer.js +846 -0
- package/dist/traceability/impact-knowledge.d.ts.map +1 -1
- package/dist/traceability/impact-knowledge.js +7 -0
- package/dist/traceability/symbol-extract.js +3 -3
- package/dist/traceability/temp-kb.d.ts.map +1 -1
- package/dist/traceability/temp-kb.js +12 -0
- package/dist/types/entities.d.ts +13 -0
- package/dist/types/entities.d.ts.map +1 -1
- package/dist/types/relationships.d.ts +1 -1
- package/dist/types/relationships.d.ts.map +1 -1
- package/dist/utils/branch-resolver.d.ts +37 -1
- package/dist/utils/branch-resolver.d.ts.map +1 -1
- package/dist/utils/branch-resolver.js +130 -3
- package/dist/utils/repo-relative-path.d.ts +18 -0
- package/dist/utils/repo-relative-path.d.ts.map +1 -0
- package/dist/utils/repo-relative-path.js +58 -0
- package/dist/utils/rule-registry.generated.d.ts +75 -3
- package/dist/utils/rule-registry.generated.d.ts.map +1 -1
- package/dist/utils/rule-registry.generated.js +89 -3
- package/dist/utils/schema-version.d.ts +1 -1
- package/dist/utils/schema-version.d.ts.map +1 -1
- package/dist/utils/schema-version.js +4 -3
- package/dist/utils/strict-modeling.d.ts +1 -1
- package/dist/utils/strict-modeling.d.ts.map +1 -1
- package/dist/utils/strict-modeling.js +23 -3
- package/package.json +3 -3
- package/schema/entities.pl +22 -0
- package/schema/relationships.pl +14 -0
- package/schema/validation.pl +45 -1
- package/src/public/branch-resolver.ts +1 -0
- package/src/public/entity-origin.ts +175 -0
- package/src/public/impact/full-kb-quality.ts +1 -0
- package/src/public/impact/requirement-quality.ts +1 -1
- package/src/public/operations/catalog.ts +3 -0
- package/src/public/operations/check-executor.ts +15 -0
- package/src/public/operations/contracts.ts +75 -15
- package/src/public/operations/discovery-entities.ts +74 -0
- package/src/public/operations/discovery-executors.ts +88 -10
- package/src/public/operations/index.ts +1 -0
- package/src/public/operations/migration-plan.ts +30 -1
- package/src/public/operations/node-ports.ts +24 -3
- package/src/public/operations/origin-review.ts +375 -0
- package/src/public/operations/predicate-schema-conformance.ts +1 -1
- package/src/public/operations/repair-plan.ts +4 -0
- package/src/public/operations/result-envelope.ts +18 -6
- package/src/public/operations/runtime-types.ts +9 -0
- package/src/public/operations/schema6-check-actions.ts +699 -0
- package/src/public/operations/source-path-dangling.ts +81 -0
- package/src/public/operations/specs/check-rules.generated.ts +15 -1
- package/src/public/operations/specs/check.ts +1 -1
- package/src/public/operations/specs/composite.ts +141 -0
- package/src/public/operations/specs/discovery.ts +9 -3
- package/src/public/operations/specs/modeling.ts +2 -2
- package/src/public/operations/specs/mutation-schemas.ts +49 -7
- package/src/public/operations/specs/mutation.ts +1 -1
- package/src/public/operations/specs/planning.ts +4 -4
- package/src/public/operations/specs/reporting.ts +13 -38
- package/src/public/operations/specs/upsert.ts +7 -1
- package/src/public/operations/types.ts +2 -0
- package/src/public/proof-receipt.ts +1 -0
- package/src/public/schemas/entity.ts +57 -0
- package/src/public/schemas/relationship.ts +2 -0
- package/src/public/skills/kibi-bootstrap/SKILL.md +6 -1
- package/src/public/skills/kibi-bootstrap/resources/bootstrap.md +6 -0
- package/src/public/skills/kibi-usage/SKILL.md +68 -18
- package/src/public/skills/kibi-usage/resources/fact-lanes.md +5 -5
- package/src/public/skills/kibi-usage/resources/kb-improvement.md +1 -1
- package/src/public/skills/kibi-usage/resources/logic-ir.md +2 -2
- package/src/public/skills/kibi-usage/resources/operation-access.md +25 -1
- package/src/public/skills/kibi-usage/resources/ui-requirements.md +4 -4
- package/src/public/skills/kibi-usage/resources/workflows.md +42 -25
- package/src/public/telemetry-acceptance-types.d.ts +4 -1
- package/src/public/telemetry-acceptance.ts +204 -10
- package/src/public/telemetry-remediation.ts +39 -10
- package/src/schemas/entity.schema.json +122 -0
- package/src/schemas/relationship.schema.json +2 -0
|
@@ -51,7 +51,14 @@ export function readShard(shardPath) {
|
|
|
51
51
|
if (!fs.existsSync(shardPath)) {
|
|
52
52
|
return [];
|
|
53
53
|
}
|
|
54
|
-
|
|
54
|
+
return parseShardText(fs.readFileSync(shardPath, "utf8"), shardPath);
|
|
55
|
+
}
|
|
56
|
+
/**
|
|
57
|
+
* Parses relationship shard text read from `shardPath`.
|
|
58
|
+
* Returns an empty array for blank text. Throws on parse errors.
|
|
59
|
+
*/
|
|
60
|
+
// implements REQ-kibi-operation-interface-parity
|
|
61
|
+
export function parseShardText(content, shardPath) {
|
|
55
62
|
if (!content.trim()) {
|
|
56
63
|
return [];
|
|
57
64
|
}
|
|
@@ -121,7 +128,10 @@ export function writeShard(shardPath, records) {
|
|
|
121
128
|
if (!fs.existsSync(dir)) {
|
|
122
129
|
fs.mkdirSync(dir, { recursive: true });
|
|
123
130
|
}
|
|
124
|
-
|
|
131
|
+
atomicWriteText(shardPath, renderShardRecords(records));
|
|
132
|
+
}
|
|
133
|
+
/** Canonical shard text for `records`: sorted and deduplicated. */
|
|
134
|
+
function renderShardRecords(records) {
|
|
125
135
|
const sorted = sortRecords(records);
|
|
126
136
|
const seen = new Set();
|
|
127
137
|
const unique = [];
|
|
@@ -132,8 +142,7 @@ export function writeShard(shardPath, records) {
|
|
|
132
142
|
seen.add(key);
|
|
133
143
|
unique.push(record);
|
|
134
144
|
}
|
|
135
|
-
|
|
136
|
-
atomicWriteText(shardPath, yamlContent);
|
|
145
|
+
return serializeToYAML(unique);
|
|
137
146
|
}
|
|
138
147
|
/**
|
|
139
148
|
* Publish one canonical shard replacement atomically. Relationship shards are
|
|
@@ -254,32 +263,49 @@ function sortRecords(records) {
|
|
|
254
263
|
*/
|
|
255
264
|
export function appendRelationship(kbRoot, relationship) {
|
|
256
265
|
const shardPath = computeShardPath(kbRoot, relationship.from);
|
|
257
|
-
const existing =
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
if (!exists) {
|
|
265
|
-
const newRecord = {
|
|
266
|
-
...relationship,
|
|
267
|
-
id: recordId,
|
|
268
|
-
};
|
|
269
|
-
if (fs.existsSync(shardPath)) {
|
|
270
|
-
const document = parseDocument(fs.readFileSync(shardPath, "utf8"));
|
|
271
|
-
const sequence = document.get("relationships", true);
|
|
272
|
-
if (!sequence || typeof sequence !== "object" || !("items" in sequence)) {
|
|
273
|
-
throw new Error(`Invalid shard file: missing 'relationships' array at ${shardPath}`);
|
|
274
|
-
}
|
|
275
|
-
sequence.items.push(newRecord);
|
|
276
|
-
atomicWriteText(shardPath, document.toString());
|
|
277
|
-
}
|
|
278
|
-
else {
|
|
279
|
-
writeShard(shardPath, [newRecord]);
|
|
266
|
+
const existing = fs.existsSync(shardPath)
|
|
267
|
+
? fs.readFileSync(shardPath, "utf8")
|
|
268
|
+
: null;
|
|
269
|
+
const next = renderShardWithRelationship(shardPath, existing, relationship);
|
|
270
|
+
if (next !== null) {
|
|
271
|
+
if (existing === null) {
|
|
272
|
+
fs.mkdirSync(path.dirname(shardPath), { recursive: true });
|
|
280
273
|
}
|
|
274
|
+
atomicWriteText(shardPath, next);
|
|
281
275
|
}
|
|
282
|
-
return {
|
|
276
|
+
return {
|
|
277
|
+
shardPath,
|
|
278
|
+
recordId: relationshipIdFor(relationship.type, relationship.from, relationship.to),
|
|
279
|
+
};
|
|
280
|
+
}
|
|
281
|
+
/**
|
|
282
|
+
* The shard text appendRelationship would publish for `relationship`, without
|
|
283
|
+
* writing it: `existing` is the current shard text, or null when the shard
|
|
284
|
+
* file does not exist. Returns null when the shard already records the
|
|
285
|
+
* relationship. Callers that must journal exact after-bytes before any write
|
|
286
|
+
* (atomic plan application) render a shard through this function.
|
|
287
|
+
*/
|
|
288
|
+
// implements REQ-kibi-operation-interface-parity, REQ-core-atomic-upsert-persistence
|
|
289
|
+
export function renderShardWithRelationship(shardPath, existing, relationship) {
|
|
290
|
+
const records = existing === null ? [] : parseShardText(existing, shardPath);
|
|
291
|
+
if (records.some((r) => r.type === relationship.type &&
|
|
292
|
+
r.from === relationship.from &&
|
|
293
|
+
r.to === relationship.to)) {
|
|
294
|
+
return null;
|
|
295
|
+
}
|
|
296
|
+
const newRecord = {
|
|
297
|
+
...relationship,
|
|
298
|
+
id: relationshipIdFor(relationship.type, relationship.from, relationship.to),
|
|
299
|
+
};
|
|
300
|
+
if (existing === null)
|
|
301
|
+
return renderShardRecords([newRecord]);
|
|
302
|
+
const document = parseDocument(existing);
|
|
303
|
+
const sequence = document.get("relationships", true);
|
|
304
|
+
if (!sequence || typeof sequence !== "object" || !("items" in sequence)) {
|
|
305
|
+
throw new Error(`Invalid shard file: missing 'relationships' array at ${shardPath}`);
|
|
306
|
+
}
|
|
307
|
+
sequence.items.push(newRecord);
|
|
308
|
+
return document.toString();
|
|
283
309
|
}
|
|
284
310
|
/**
|
|
285
311
|
* Lists all shard files in the relationships directory.
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"cli-runtime.d.ts","sourceRoot":"","sources":["../../src/runtime/cli-runtime.ts"],"names":[],"mappings":"AAeA,OAAO,KAAK,EAKV,gBAAgB,EAEhB,cAAc,EACf,MAAM,uCAAuC,CAAC;AAC/C,OAAO,
|
|
1
|
+
{"version":3,"file":"cli-runtime.d.ts","sourceRoot":"","sources":["../../src/runtime/cli-runtime.ts"],"names":[],"mappings":"AAeA,OAAO,KAAK,EAKV,gBAAgB,EAEhB,cAAc,EACf,MAAM,uCAAuC,CAAC;AAC/C,OAAO,EAEL,KAAK,qBAAqB,EAE3B,MAAM,6BAA6B,CAAC;AAOrC,wBAAgB,wBAAwB,CACtC,UAAU,EAAE,qBAAqB,GAChC,MAAM,CAOR;AA2GD,wBAAgB,gBAAgB,CAC9B,OAAO,GAAE,cAAmB,GAC3B,gBAAgB,CA4IlB"}
|
|
@@ -3,7 +3,8 @@ import { retryAttachAfterBreakingStaleLock } from "../prolog/store-lock.js";
|
|
|
3
3
|
import { EngineClient } from "../engine.js";
|
|
4
4
|
import { CapabilityRegistryCache, ensureCapabilityRegistry, } from "../plugins/registry.js";
|
|
5
5
|
import { nodeFilesystem, nodeGit, nodeNetwork, } from "../public/operations/node-ports.js";
|
|
6
|
-
import {
|
|
6
|
+
import { resolveReadBranchAttachment, } from "../utils/branch-resolver.js";
|
|
7
|
+
import { declaresWriteEffect, refreshDetachedSnapshot, resolveOperationAttachment, } from "./detached-snapshot.js";
|
|
7
8
|
export function attachmentFailureMessage(attachment) {
|
|
8
9
|
const isNonGitContext = attachment.code === "NOT_A_GIT_REPO" ||
|
|
9
10
|
attachment.code === "GIT_NOT_AVAILABLE";
|
|
@@ -65,6 +66,27 @@ function resolvePluginsOption(plugins) {
|
|
|
65
66
|
return plugins;
|
|
66
67
|
return async () => plugins;
|
|
67
68
|
}
|
|
69
|
+
/**
|
|
70
|
+
* The detached-HEAD snapshot attachment for a KB read that may run without
|
|
71
|
+
* Prolog (status), or undefined when the checkout resolves normally (that
|
|
72
|
+
* path keeps its lazy, non-mutating behavior). A failed snapshot compile is
|
|
73
|
+
* reported but not fatal, so status can still diagnose the snapshot store.
|
|
74
|
+
*/
|
|
75
|
+
// implements REQ-branch-store-recovery-v4
|
|
76
|
+
async function resolveDetachedReadAttachment(root) {
|
|
77
|
+
const attachment = resolveReadBranchAttachment(root);
|
|
78
|
+
if ("error" in attachment || attachment.readOnly === undefined) {
|
|
79
|
+
return undefined;
|
|
80
|
+
}
|
|
81
|
+
console.warn(`[KIBI] ${attachment.readOnly.notice}`);
|
|
82
|
+
try {
|
|
83
|
+
await refreshDetachedSnapshot(root, attachment);
|
|
84
|
+
}
|
|
85
|
+
catch (error) {
|
|
86
|
+
console.warn(`[KIBI] ${error instanceof Error ? error.message : String(error)}`);
|
|
87
|
+
}
|
|
88
|
+
return attachment;
|
|
89
|
+
}
|
|
68
90
|
// implements REQ-kibi-operation-interface-parity
|
|
69
91
|
export function createCliRuntime(options = {}) {
|
|
70
92
|
const ownedPrologs = new WeakMap();
|
|
@@ -102,10 +124,16 @@ export function createCliRuntime(options = {}) {
|
|
|
102
124
|
// That keeps pre-init and damaged-store diagnostics non-mutating.
|
|
103
125
|
let lazyProlog = merged.prolog;
|
|
104
126
|
const lazyContext = {};
|
|
127
|
+
// A KB read on a detached HEAD answers from the checkout's snapshot;
|
|
128
|
+
// resolve it up front so the operation reports which store it read.
|
|
129
|
+
const detachedAttachment = !declaresWriteEffect(spec.effects) && spec.effects.includes("kb-read")
|
|
130
|
+
? await resolveDetachedReadAttachment(root)
|
|
131
|
+
: undefined;
|
|
105
132
|
const ensureProlog = async () => {
|
|
106
133
|
if (lazyProlog !== undefined)
|
|
107
134
|
return bindSignal(lazyProlog, signal);
|
|
108
|
-
const attachment =
|
|
135
|
+
const attachment = detachedAttachment ??
|
|
136
|
+
(await resolveOperationAttachment(root, spec));
|
|
109
137
|
if ("error" in attachment) {
|
|
110
138
|
throw new Error(`Failed to resolve active branch: ${attachment.error}`);
|
|
111
139
|
}
|
|
@@ -125,16 +153,29 @@ export function createCliRuntime(options = {}) {
|
|
|
125
153
|
? { prolog: bindSignal(merged.prolog, signal) }
|
|
126
154
|
: {}),
|
|
127
155
|
...(lazyEngine ? { engine: lazyEngine } : {}),
|
|
156
|
+
...(detachedAttachment
|
|
157
|
+
? { branchAttachment: detachedAttachment }
|
|
158
|
+
: {}),
|
|
128
159
|
ensureProlog,
|
|
129
160
|
};
|
|
130
161
|
lazyContext.current = context;
|
|
131
162
|
return context;
|
|
132
163
|
}
|
|
133
|
-
|
|
164
|
+
let attachment;
|
|
165
|
+
try {
|
|
166
|
+
attachment = await resolveOperationAttachment(root, spec);
|
|
167
|
+
}
|
|
168
|
+
catch (error) {
|
|
169
|
+
await merged.prolog?.terminate?.();
|
|
170
|
+
throw error;
|
|
171
|
+
}
|
|
134
172
|
if ("error" in attachment) {
|
|
135
173
|
await merged.prolog?.terminate?.();
|
|
136
174
|
throw new Error(attachmentFailureMessage(attachment));
|
|
137
175
|
}
|
|
176
|
+
if (attachment.readOnly !== undefined) {
|
|
177
|
+
console.warn(`[KIBI] ${attachment.readOnly.notice}`);
|
|
178
|
+
}
|
|
138
179
|
if (attachment.migrationRequired) {
|
|
139
180
|
console.warn(`[KIBI] Legacy branch attachment: Git '${attachment.gitBranch}' is reading KB '${attachment.kbBranch}'. Migrate with 'kibi branch migrate --from ${attachment.kbBranch} --to ${attachment.gitBranch} --apply'; writes are blocked until then.`);
|
|
140
181
|
}
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
import type { OperationEffect } from "../public/operations/types.js";
|
|
2
|
+
import { type BranchAttachment, type BranchResolutionError } from "../utils/branch-resolver.js";
|
|
3
|
+
/** Envelope diagnostic code reported while a detached snapshot is attached. */
|
|
4
|
+
export declare const DETACHED_HEAD_READ_ONLY_CODE = "detached_head_read_only";
|
|
5
|
+
export type DetachedReadOnlyDiagnostic = {
|
|
6
|
+
readonly code: typeof DETACHED_HEAD_READ_ONLY_CODE;
|
|
7
|
+
readonly severity: "warning";
|
|
8
|
+
readonly message: string;
|
|
9
|
+
readonly detail: {
|
|
10
|
+
readonly head: string;
|
|
11
|
+
readonly branchesAtHead: readonly string[];
|
|
12
|
+
readonly kbBranch: string;
|
|
13
|
+
readonly storePath: string;
|
|
14
|
+
readonly writes: "refused";
|
|
15
|
+
};
|
|
16
|
+
};
|
|
17
|
+
/** True when an operation declares a KB or workspace write. */
|
|
18
|
+
export declare function declaresWriteEffect(effects: readonly OperationEffect[] | readonly string[]): boolean;
|
|
19
|
+
/**
|
|
20
|
+
* Compile (or incrementally refresh) the read-only snapshot of a detached
|
|
21
|
+
* checkout. The snapshot store is a cache of the checkout's tracked sources:
|
|
22
|
+
* refreshing it never touches a branch KB or an authored file.
|
|
23
|
+
*/
|
|
24
|
+
export declare function refreshDetachedSnapshot(workspaceRoot: string, attachment: BranchAttachment): Promise<void>;
|
|
25
|
+
/**
|
|
26
|
+
* Resolve the branch attachment an operation may use.
|
|
27
|
+
*
|
|
28
|
+
* Writes keep the exact-branch contract and receive an actionable refusal on
|
|
29
|
+
* a detached HEAD. Reads on a detached HEAD that no single branch points at
|
|
30
|
+
* attach a freshly compiled read-only snapshot of the checkout.
|
|
31
|
+
*/
|
|
32
|
+
export declare function resolveOperationAttachment(workspaceRoot: string, spec: {
|
|
33
|
+
readonly name: string;
|
|
34
|
+
readonly effects: readonly OperationEffect[];
|
|
35
|
+
}): Promise<BranchAttachment | BranchResolutionError>;
|
|
36
|
+
/** The envelope diagnostic for an operation answered from a snapshot. */
|
|
37
|
+
export declare function detachedReadOnlyDiagnostic(attachment: BranchAttachment | undefined): DetachedReadOnlyDiagnostic | undefined;
|
|
38
|
+
//# sourceMappingURL=detached-snapshot.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"detached-snapshot.d.ts","sourceRoot":"","sources":["../../src/runtime/detached-snapshot.ts"],"names":[],"mappings":"AAkBA,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,+BAA+B,CAAC;AACrE,OAAO,EACL,KAAK,gBAAgB,EACrB,KAAK,qBAAqB,EAI3B,MAAM,6BAA6B,CAAC;AAErC,+EAA+E;AAE/E,eAAO,MAAM,4BAA4B,4BAA4B,CAAC;AAGtE,MAAM,MAAM,0BAA0B,GAAG;IACvC,QAAQ,CAAC,IAAI,EAAE,OAAO,4BAA4B,CAAC;IACnD,QAAQ,CAAC,QAAQ,EAAE,SAAS,CAAC;IAC7B,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;IACzB,QAAQ,CAAC,MAAM,EAAE;QACf,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;QACtB,QAAQ,CAAC,cAAc,EAAE,SAAS,MAAM,EAAE,CAAC;QAC3C,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;QAC1B,QAAQ,CAAC,SAAS,EAAE,MAAM,CAAC;QAC3B,QAAQ,CAAC,MAAM,EAAE,SAAS,CAAC;KAC5B,CAAC;CACH,CAAC;AAEF,+DAA+D;AAE/D,wBAAgB,mBAAmB,CACjC,OAAO,EAAE,SAAS,eAAe,EAAE,GAAG,SAAS,MAAM,EAAE,GACtD,OAAO,CAIT;AAED;;;;GAIG;AAEH,wBAAsB,uBAAuB,CAC3C,aAAa,EAAE,MAAM,EACrB,UAAU,EAAE,gBAAgB,GAC3B,OAAO,CAAC,IAAI,CAAC,CAcf;AAED;;;;;;GAMG;AAEH,wBAAsB,0BAA0B,CAC9C,aAAa,EAAE,MAAM,EACrB,IAAI,EAAE;IAAE,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IAAC,QAAQ,CAAC,OAAO,EAAE,SAAS,eAAe,EAAE,CAAA;CAAE,GAC5E,OAAO,CAAC,gBAAgB,GAAG,qBAAqB,CAAC,CAoBnD;AAED,yEAAyE;AAEzE,wBAAgB,0BAA0B,CACxC,UAAU,EAAE,gBAAgB,GAAG,SAAS,GACvC,0BAA0B,GAAG,SAAS,CAexC"}
|
|
@@ -0,0 +1,92 @@
|
|
|
1
|
+
/*
|
|
2
|
+
Kibi — repo-local, per-branch, queryable long-term memory for software projects
|
|
3
|
+
Copyright (C) 2026 Piotr Franczyk
|
|
4
|
+
|
|
5
|
+
This program is free software: you can redistribute it and/or modify
|
|
6
|
+
it under the terms of the GNU Affero General Public License as published by
|
|
7
|
+
the Free Software Foundation, either version 3 of the License, or
|
|
8
|
+
(at your option) any later version.
|
|
9
|
+
|
|
10
|
+
This program is distributed in the hope that it will be useful,
|
|
11
|
+
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
12
|
+
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
13
|
+
GNU Affero General Public License for more details.
|
|
14
|
+
|
|
15
|
+
You should have received a copy of the GNU Affero General Public License
|
|
16
|
+
along with this program. If not, see <https://www.gnu.org/licenses/>.
|
|
17
|
+
*/
|
|
18
|
+
import { detachedHeadWriteRefusal, resolveBranchAttachment, resolveReadBranchAttachment, } from "../utils/branch-resolver.js";
|
|
19
|
+
/** Envelope diagnostic code reported while a detached snapshot is attached. */
|
|
20
|
+
// implements REQ-branch-store-recovery-v4
|
|
21
|
+
export const DETACHED_HEAD_READ_ONLY_CODE = "detached_head_read_only";
|
|
22
|
+
/** True when an operation declares a KB or workspace write. */
|
|
23
|
+
// implements REQ-branch-store-recovery-v4
|
|
24
|
+
export function declaresWriteEffect(effects) {
|
|
25
|
+
return effects.some((effect) => effect === "kb-write" || effect === "workspace-write");
|
|
26
|
+
}
|
|
27
|
+
/**
|
|
28
|
+
* Compile (or incrementally refresh) the read-only snapshot of a detached
|
|
29
|
+
* checkout. The snapshot store is a cache of the checkout's tracked sources:
|
|
30
|
+
* refreshing it never touches a branch KB or an authored file.
|
|
31
|
+
*/
|
|
32
|
+
// implements REQ-branch-store-recovery-v4
|
|
33
|
+
export async function refreshDetachedSnapshot(workspaceRoot, attachment) {
|
|
34
|
+
const { syncCommand } = await import("../commands/sync.js");
|
|
35
|
+
try {
|
|
36
|
+
await syncCommand({
|
|
37
|
+
workspaceRoot,
|
|
38
|
+
detachedSnapshot: attachment,
|
|
39
|
+
quiet: true,
|
|
40
|
+
});
|
|
41
|
+
}
|
|
42
|
+
catch (error) {
|
|
43
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
44
|
+
throw new Error(`Failed to compile the read-only snapshot for this detached HEAD: ${message}`);
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
/**
|
|
48
|
+
* Resolve the branch attachment an operation may use.
|
|
49
|
+
*
|
|
50
|
+
* Writes keep the exact-branch contract and receive an actionable refusal on
|
|
51
|
+
* a detached HEAD. Reads on a detached HEAD that no single branch points at
|
|
52
|
+
* attach a freshly compiled read-only snapshot of the checkout.
|
|
53
|
+
*/
|
|
54
|
+
// implements REQ-branch-store-recovery-v4
|
|
55
|
+
export async function resolveOperationAttachment(workspaceRoot, spec) {
|
|
56
|
+
if (declaresWriteEffect(spec.effects)) {
|
|
57
|
+
const attachment = resolveBranchAttachment(workspaceRoot);
|
|
58
|
+
if ("error" in attachment && attachment.code === "DETACHED_HEAD") {
|
|
59
|
+
return {
|
|
60
|
+
error: detachedHeadWriteRefusal(spec.name, workspaceRoot),
|
|
61
|
+
code: "DETACHED_HEAD",
|
|
62
|
+
};
|
|
63
|
+
}
|
|
64
|
+
return attachment;
|
|
65
|
+
}
|
|
66
|
+
const attachment = resolveReadBranchAttachment(workspaceRoot);
|
|
67
|
+
if (!("error" in attachment) &&
|
|
68
|
+
attachment.readOnly !== undefined &&
|
|
69
|
+
spec.effects.includes("kb-read")) {
|
|
70
|
+
await refreshDetachedSnapshot(workspaceRoot, attachment);
|
|
71
|
+
}
|
|
72
|
+
return attachment;
|
|
73
|
+
}
|
|
74
|
+
/** The envelope diagnostic for an operation answered from a snapshot. */
|
|
75
|
+
// implements REQ-branch-store-recovery-v4
|
|
76
|
+
export function detachedReadOnlyDiagnostic(attachment) {
|
|
77
|
+
const readOnly = attachment?.readOnly;
|
|
78
|
+
if (attachment === undefined || readOnly === undefined)
|
|
79
|
+
return undefined;
|
|
80
|
+
return {
|
|
81
|
+
code: DETACHED_HEAD_READ_ONLY_CODE,
|
|
82
|
+
severity: "warning",
|
|
83
|
+
message: readOnly.notice,
|
|
84
|
+
detail: {
|
|
85
|
+
head: readOnly.head,
|
|
86
|
+
branchesAtHead: readOnly.branchesAtHead,
|
|
87
|
+
kbBranch: attachment.kbBranch,
|
|
88
|
+
storePath: attachment.storePath,
|
|
89
|
+
writes: "refused",
|
|
90
|
+
},
|
|
91
|
+
};
|
|
92
|
+
}
|
|
@@ -478,6 +478,51 @@
|
|
|
478
478
|
"text_ref": {
|
|
479
479
|
"type": "string"
|
|
480
480
|
},
|
|
481
|
+
"origin": {
|
|
482
|
+
"type": "object",
|
|
483
|
+
"required": [
|
|
484
|
+
"kind"
|
|
485
|
+
],
|
|
486
|
+
"properties": {
|
|
487
|
+
"kind": {
|
|
488
|
+
"type": "string",
|
|
489
|
+
"enum": [
|
|
490
|
+
"human",
|
|
491
|
+
"agent",
|
|
492
|
+
"migration",
|
|
493
|
+
"import"
|
|
494
|
+
],
|
|
495
|
+
"description": "Who authored the entity: human, agent, migration (backfilled by kibi migrate) or import."
|
|
496
|
+
},
|
|
497
|
+
"ref": {
|
|
498
|
+
"type": "string",
|
|
499
|
+
"minLength": 1,
|
|
500
|
+
"pattern": "\\S",
|
|
501
|
+
"description": "Source reference for the authored content: URL, document path, ticket, commit or conversation id."
|
|
502
|
+
},
|
|
503
|
+
"approved_by": {
|
|
504
|
+
"type": "string",
|
|
505
|
+
"minLength": 1,
|
|
506
|
+
"pattern": "\\S",
|
|
507
|
+
"description": "The person who reviewed and approved this entity's content. Distinct from the requirement-level approved_by of an exception."
|
|
508
|
+
},
|
|
509
|
+
"recorded_at": {
|
|
510
|
+
"type": "string",
|
|
511
|
+
"pattern": "^\\d{4}-\\d{2}-\\d{2}(?:[T ]\\d{2}:\\d{2}(?::\\d{2}(?:\\.\\d+)?)?(?:Z|[+-]\\d{2}:?\\d{2})?)?$",
|
|
512
|
+
"description": "ISO-8601 time the provenance was recorded."
|
|
513
|
+
}
|
|
514
|
+
},
|
|
515
|
+
"additionalProperties": false
|
|
516
|
+
},
|
|
517
|
+
"expects": {
|
|
518
|
+
"type": "string",
|
|
519
|
+
"enum": [
|
|
520
|
+
"success",
|
|
521
|
+
"rejection",
|
|
522
|
+
"error"
|
|
523
|
+
],
|
|
524
|
+
"description": "Scenario-only. The scenario's intended outcome. A scenario that expects success and assumes (via `assumes` facts) a value a current requirement forbids fails the scenario-feasibility check."
|
|
525
|
+
},
|
|
481
526
|
"proof_exempt": {
|
|
482
527
|
"type": "boolean",
|
|
483
528
|
"description": "Requirement-only. Marks a current requirement as intentionally outside E2E-proof scope; requires proof_exempt_reason."
|
|
@@ -487,6 +532,33 @@
|
|
|
487
532
|
"minLength": 1,
|
|
488
533
|
"description": "Requirement-only. Required when proof_exempt is true; surfaces as the applicability reason in coverage rows."
|
|
489
534
|
},
|
|
535
|
+
"approved_by": {
|
|
536
|
+
"type": "string",
|
|
537
|
+
"minLength": 1,
|
|
538
|
+
"pattern": "\\S",
|
|
539
|
+
"description": "Requirement-only. The human who approved this exception requirement. An exception (a requirement that exempts another and is specified_by a scenario) makes that success scenario feasible only when approved_by is set."
|
|
540
|
+
},
|
|
541
|
+
"approval_ref": {
|
|
542
|
+
"type": "string",
|
|
543
|
+
"minLength": 1,
|
|
544
|
+
"description": "Requirement-only. Optional reference to the approval decision record (ticket, ADR or review link) for an exception requirement."
|
|
545
|
+
},
|
|
546
|
+
"rationale": {
|
|
547
|
+
"type": "string",
|
|
548
|
+
"minLength": 1,
|
|
549
|
+
"pattern": "\\S",
|
|
550
|
+
"description": "Requirement-only. Why the requirement exists, in one or two sentences from whoever stated the intent. Explanation only: it is not part of the checked meaning."
|
|
551
|
+
},
|
|
552
|
+
"exempts_claims": {
|
|
553
|
+
"type": "array",
|
|
554
|
+
"minItems": 1,
|
|
555
|
+
"uniqueItems": true,
|
|
556
|
+
"items": {
|
|
557
|
+
"type": "string",
|
|
558
|
+
"pattern": "^CLAIM-[A-F0-9]{16}$"
|
|
559
|
+
},
|
|
560
|
+
"description": "Requirement-only. Narrows an exception requirement to individual clauses: the claim keys (from logic_claims) of the requirement it exempts whose constraints it waives. Without it the exception waives the whole exempted requirement."
|
|
561
|
+
},
|
|
490
562
|
"semantic_text": {
|
|
491
563
|
"type": "string",
|
|
492
564
|
"description": "Requirement-only authored prose whose exact UTF-8 bytes anchor the semantic inventory without replacing text_ref evidence."
|
|
@@ -1155,6 +1227,15 @@
|
|
|
1155
1227
|
"type": "string"
|
|
1156
1228
|
}
|
|
1157
1229
|
},
|
|
1230
|
+
"key_arguments": {
|
|
1231
|
+
"type": "array",
|
|
1232
|
+
"minItems": 1,
|
|
1233
|
+
"uniqueItems": true,
|
|
1234
|
+
"items": {
|
|
1235
|
+
"type": "string",
|
|
1236
|
+
"minLength": 1
|
|
1237
|
+
}
|
|
1238
|
+
},
|
|
1158
1239
|
"aliases": {
|
|
1159
1240
|
"type": "array",
|
|
1160
1241
|
"items": {
|
|
@@ -1380,6 +1461,11 @@
|
|
|
1380
1461
|
"argument_descriptions"
|
|
1381
1462
|
]
|
|
1382
1463
|
},
|
|
1464
|
+
{
|
|
1465
|
+
"required": [
|
|
1466
|
+
"key_arguments"
|
|
1467
|
+
]
|
|
1468
|
+
},
|
|
1383
1469
|
{
|
|
1384
1470
|
"required": [
|
|
1385
1471
|
"aliases"
|
|
@@ -1546,11 +1632,47 @@
|
|
|
1546
1632
|
"required": [
|
|
1547
1633
|
"proof_exempt_reason"
|
|
1548
1634
|
]
|
|
1635
|
+
},
|
|
1636
|
+
{
|
|
1637
|
+
"required": [
|
|
1638
|
+
"approved_by"
|
|
1639
|
+
]
|
|
1640
|
+
},
|
|
1641
|
+
{
|
|
1642
|
+
"required": [
|
|
1643
|
+
"approval_ref"
|
|
1644
|
+
]
|
|
1645
|
+
},
|
|
1646
|
+
{
|
|
1647
|
+
"required": [
|
|
1648
|
+
"rationale"
|
|
1649
|
+
]
|
|
1650
|
+
},
|
|
1651
|
+
{
|
|
1652
|
+
"required": [
|
|
1653
|
+
"exempts_claims"
|
|
1654
|
+
]
|
|
1549
1655
|
}
|
|
1550
1656
|
]
|
|
1551
1657
|
}
|
|
1552
1658
|
}
|
|
1553
1659
|
},
|
|
1660
|
+
{
|
|
1661
|
+
"if": {
|
|
1662
|
+
"properties": {
|
|
1663
|
+
"type": {
|
|
1664
|
+
"const": "scenario"
|
|
1665
|
+
}
|
|
1666
|
+
}
|
|
1667
|
+
},
|
|
1668
|
+
"else": {
|
|
1669
|
+
"not": {
|
|
1670
|
+
"required": [
|
|
1671
|
+
"expects"
|
|
1672
|
+
]
|
|
1673
|
+
}
|
|
1674
|
+
}
|
|
1675
|
+
},
|
|
1554
1676
|
{
|
|
1555
1677
|
"if": {
|
|
1556
1678
|
"anyOf": [
|
|
@@ -0,0 +1,157 @@
|
|
|
1
|
+
import type { IntentSearchMatch } from "./intent-search.js";
|
|
2
|
+
import type { PrologPort } from "./public/operations/runtime-types.js";
|
|
3
|
+
/**
|
|
4
|
+
* The answer layer turns ranked matches into what an agent asking "what
|
|
5
|
+
* governs this?" needs: the current requirements that apply, why (ADRs, with
|
|
6
|
+
* an excerpt of their decision), what must stay true (linked facts), what
|
|
7
|
+
* verifies it (scenarios and tests), what the existing checks say about it
|
|
8
|
+
* (contradiction and scenario-feasibility witnesses, exceptions, and what is
|
|
9
|
+
* still unknown), and the KB snapshot the answer was computed from.
|
|
10
|
+
* Superseded or deprecated requirements are listed separately so they are
|
|
11
|
+
* never read as current policy, and observation facts are labelled as notes,
|
|
12
|
+
* not rules. Tests are collected through the canonical
|
|
13
|
+
* REQ -specified_by-> SCEN -verified_by-> TEST path as well as direct
|
|
14
|
+
* requirement links, and each says how it was reached. Graph links are
|
|
15
|
+
* discovery, not proof, and a verdict of `none` means no check named the
|
|
16
|
+
* requirement, not that it is proven.
|
|
17
|
+
*/
|
|
18
|
+
export type SearchAnswerEntity = Readonly<{
|
|
19
|
+
id: string;
|
|
20
|
+
title: string;
|
|
21
|
+
status?: string;
|
|
22
|
+
}>;
|
|
23
|
+
/**
|
|
24
|
+
* A test verifying a governing requirement. `via` is `"direct"` for a test
|
|
25
|
+
* linked to the requirement itself, or the id of the scenario it verifies.
|
|
26
|
+
*/
|
|
27
|
+
export type SearchAnswerTest = SearchAnswerEntity & Readonly<{
|
|
28
|
+
via: string;
|
|
29
|
+
}>;
|
|
30
|
+
/** An ADR with the opening of its decision (or rationale) section. */
|
|
31
|
+
export type SearchAnswerRationale = SearchAnswerEntity & Readonly<{
|
|
32
|
+
source?: string;
|
|
33
|
+
excerpt?: string;
|
|
34
|
+
}>;
|
|
35
|
+
/** A blocking finding of an existing check that names the requirement. */
|
|
36
|
+
export type SearchAnswerWitness = Readonly<{
|
|
37
|
+
check: "domain-contradictions" | "scenario-feasibility";
|
|
38
|
+
status: "contradiction" | "infeasible";
|
|
39
|
+
/** The other requirement in a contradiction, or the forbidding one. */
|
|
40
|
+
with?: string;
|
|
41
|
+
scenario?: string;
|
|
42
|
+
facts: readonly string[];
|
|
43
|
+
detail: string;
|
|
44
|
+
}>;
|
|
45
|
+
/**
|
|
46
|
+
* What the checks could not decide for the requirement: rule overlaps they
|
|
47
|
+
* could not classify, scenarios whose feasibility is unknown, propositions
|
|
48
|
+
* still ambiguous or ontology gaps, a missing clause ledger, or a verdict
|
|
49
|
+
* that could not be computed.
|
|
50
|
+
*/
|
|
51
|
+
export type SearchAnswerUnknown = Readonly<{
|
|
52
|
+
kind: "contradiction_unresolved" | "feasibility_unknown" | "unresolved_proposition" | "analysis_incomplete" | "verdict_unavailable";
|
|
53
|
+
detail: string;
|
|
54
|
+
entities: readonly string[];
|
|
55
|
+
}>;
|
|
56
|
+
export type SearchAnswerVerdict = Readonly<{
|
|
57
|
+
/**
|
|
58
|
+
* The worst finding: `contradiction` or `infeasible` when a blocking
|
|
59
|
+
* witness exists, `unknown` when only unknowns remain, `none` when no
|
|
60
|
+
* check named the requirement (absence of a witness is not proof).
|
|
61
|
+
*/
|
|
62
|
+
status: "contradiction" | "infeasible" | "unknown" | "none";
|
|
63
|
+
witnesses: readonly SearchAnswerWitness[];
|
|
64
|
+
}>;
|
|
65
|
+
/** A requirement that `exempts` the governing one. */
|
|
66
|
+
export type SearchAnswerException = SearchAnswerEntity & Readonly<{
|
|
67
|
+
approvedBy?: string;
|
|
68
|
+
}>;
|
|
69
|
+
export type SearchAnswerRequirement = SearchAnswerEntity & Readonly<{
|
|
70
|
+
score: number;
|
|
71
|
+
via: string;
|
|
72
|
+
facts: readonly (SearchAnswerEntity & {
|
|
73
|
+
factKind?: string;
|
|
74
|
+
})[];
|
|
75
|
+
scenarios: readonly SearchAnswerEntity[];
|
|
76
|
+
tests: readonly SearchAnswerTest[];
|
|
77
|
+
adrs: readonly SearchAnswerEntity[];
|
|
78
|
+
verdict: SearchAnswerVerdict;
|
|
79
|
+
exceptions: readonly SearchAnswerException[];
|
|
80
|
+
unknowns: readonly SearchAnswerUnknown[];
|
|
81
|
+
}>;
|
|
82
|
+
/** The KB the answer was computed from. */
|
|
83
|
+
export type SearchAnswerScope = Readonly<{
|
|
84
|
+
branch: string | null;
|
|
85
|
+
snapshotId: string;
|
|
86
|
+
syncedAt: string | null;
|
|
87
|
+
}>;
|
|
88
|
+
export type SearchAnswer = Readonly<{
|
|
89
|
+
version: "kibi.search-answer.v1";
|
|
90
|
+
governing: readonly SearchAnswerRequirement[];
|
|
91
|
+
rationale: readonly SearchAnswerRationale[];
|
|
92
|
+
notGoverning: readonly (SearchAnswerEntity & {
|
|
93
|
+
supersededBy?: string;
|
|
94
|
+
})[];
|
|
95
|
+
observations: readonly SearchAnswerEntity[];
|
|
96
|
+
scope: SearchAnswerScope;
|
|
97
|
+
truncated: boolean;
|
|
98
|
+
note: string;
|
|
99
|
+
}>;
|
|
100
|
+
export type SearchAnswerOptions = Readonly<{
|
|
101
|
+
/** Root that ADR sources resolve against; without it no excerpts. */
|
|
102
|
+
workspaceRoot?: string;
|
|
103
|
+
/** The Git branch identity of the attached KB. */
|
|
104
|
+
branch?: string | null;
|
|
105
|
+
}>;
|
|
106
|
+
export declare const SEARCH_ANSWER_LIMITS: {
|
|
107
|
+
readonly seeds: 10;
|
|
108
|
+
readonly governing: 5;
|
|
109
|
+
readonly perRequirement: 4;
|
|
110
|
+
readonly rationale: 3;
|
|
111
|
+
readonly notGoverning: 5;
|
|
112
|
+
readonly observations: 3;
|
|
113
|
+
/** Entity rows loaded per answer, the matched seeds included. */
|
|
114
|
+
readonly entityLoads: 70;
|
|
115
|
+
readonly maxBytes: 16384;
|
|
116
|
+
/** Title length (characters) kept when an answer must shrink to fit. */
|
|
117
|
+
readonly titleChars: 160;
|
|
118
|
+
/** Characters of an ADR decision kept as its excerpt. */
|
|
119
|
+
readonly excerptChars: 280;
|
|
120
|
+
/** Characters of a witness or unknown detail kept. */
|
|
121
|
+
readonly detailChars: 240;
|
|
122
|
+
};
|
|
123
|
+
/**
|
|
124
|
+
* The opening sentences of an ADR's Decision section (falling back to
|
|
125
|
+
* Rationale, then to the first prose paragraph), as plain text of at most
|
|
126
|
+
* `maxChars` characters.
|
|
127
|
+
*/
|
|
128
|
+
export declare function adrExcerpt(body: string, maxChars?: number): string | undefined;
|
|
129
|
+
type RawVerdict = Readonly<{
|
|
130
|
+
id?: unknown;
|
|
131
|
+
error?: unknown;
|
|
132
|
+
contradictions?: unknown;
|
|
133
|
+
scenarios?: unknown;
|
|
134
|
+
forbids?: unknown;
|
|
135
|
+
inventory?: unknown;
|
|
136
|
+
}>;
|
|
137
|
+
/** Project the Prolog verdict of one requirement onto the answer fields. */
|
|
138
|
+
export declare function projectVerdict(raw: RawVerdict | undefined, perRequirement?: number): {
|
|
139
|
+
verdict: SearchAnswerVerdict;
|
|
140
|
+
unknowns: SearchAnswerUnknown[];
|
|
141
|
+
truncated: boolean;
|
|
142
|
+
};
|
|
143
|
+
export declare function buildSearchAnswer(prolog: Pick<PrologPort, "query">, matches: readonly IntentSearchMatch[], options?: SearchAnswerOptions): Promise<SearchAnswer>;
|
|
144
|
+
/**
|
|
145
|
+
* Hold the whole answer under `maxBytes`, marking it truncated when anything
|
|
146
|
+
* is cut. In order: long titles, excerpts and details are clipped; ADR
|
|
147
|
+
* excerpts are dropped, last rationale entry first; the least relevant
|
|
148
|
+
* governing requirements are dropped;
|
|
149
|
+
* list items are dropped (notes and side lists before the remaining
|
|
150
|
+
* requirement's own lists, its verdict witnesses last); then the remaining
|
|
151
|
+
* requirement's title and `via` are clipped. A verdict keeps its status when
|
|
152
|
+
* its witnesses are dropped. If even that cannot fit, the requirement itself
|
|
153
|
+
* is dropped.
|
|
154
|
+
*/
|
|
155
|
+
export declare function fitSearchAnswer(answer: SearchAnswer, maxBytes?: number): SearchAnswer;
|
|
156
|
+
export {};
|
|
157
|
+
//# sourceMappingURL=search-answer.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"search-answer.d.ts","sourceRoot":"","sources":["../src/search-answer.ts"],"names":[],"mappings":"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"}
|