kibi-cli 2.18.0 → 2.20.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.
Files changed (106) hide show
  1. package/dist/cli-operation-metadata.d.ts +2 -2
  2. package/dist/cli-operation-metadata.js +2 -2
  3. package/dist/cli-register-maintenance.js +1 -1
  4. package/dist/commands/doctor.js +11 -5
  5. package/dist/commands/engine.d.ts +2 -1
  6. package/dist/commands/engine.d.ts.map +1 -1
  7. package/dist/commands/engine.js +6 -1
  8. package/dist/commands/sync/manifest.d.ts +10 -0
  9. package/dist/commands/sync/manifest.d.ts.map +1 -1
  10. package/dist/commands/sync/manifest.js +27 -0
  11. package/dist/commands/sync/untracked-targets.d.ts +17 -0
  12. package/dist/commands/sync/untracked-targets.d.ts.map +1 -1
  13. package/dist/commands/sync/untracked-targets.js +43 -1
  14. package/dist/commands/sync.d.ts.map +1 -1
  15. package/dist/commands/sync.js +51 -2
  16. package/dist/engine.d.ts.map +1 -1
  17. package/dist/engine.js +33 -22
  18. package/dist/intent-search.d.ts +7 -0
  19. package/dist/intent-search.d.ts.map +1 -1
  20. package/dist/intent-search.js +66 -4
  21. package/dist/operations/modeling/predicate-applicability.d.ts.map +1 -1
  22. package/dist/operations/modeling/predicate-applicability.js +10 -4
  23. package/dist/operations/modeling/predicate-applyplan.d.ts.map +1 -1
  24. package/dist/operations/modeling/predicate-applyplan.js +16 -5
  25. package/dist/operations/modeling/predicate-catalog-4.d.ts.map +1 -1
  26. package/dist/operations/modeling/predicate-catalog-4.js +3 -0
  27. package/dist/operations/modeling/predicate-inference-1.d.ts.map +1 -1
  28. package/dist/operations/modeling/predicate-inference-1.js +34 -7
  29. package/dist/operations/modeling/predicate-score-3.js +1 -1
  30. package/dist/operations/modeling/predicate-types.d.ts +6 -0
  31. package/dist/operations/modeling/predicate-types.d.ts.map +1 -1
  32. package/dist/operations/modeling/suggest-predicates.d.ts.map +1 -1
  33. package/dist/operations/modeling/suggest-predicates.js +111 -0
  34. package/dist/operations/mutation/source-authoring.d.ts.map +1 -1
  35. package/dist/operations/mutation/source-authoring.js +5 -12
  36. package/dist/operations/mutation/types.d.ts +26 -0
  37. package/dist/operations/mutation/types.d.ts.map +1 -1
  38. package/dist/operations/mutation/upsert.d.ts.map +1 -1
  39. package/dist/operations/mutation/upsert.js +8 -2
  40. package/dist/operations/mutation/validate-upsert.d.ts.map +1 -1
  41. package/dist/operations/mutation/validate-upsert.js +116 -4
  42. package/dist/operations/mutation/warnings.d.ts +10 -0
  43. package/dist/operations/mutation/warnings.d.ts.map +1 -1
  44. package/dist/operations/mutation/warnings.js +26 -0
  45. package/dist/operations/mutation/what-if.d.ts +25 -0
  46. package/dist/operations/mutation/what-if.d.ts.map +1 -0
  47. package/dist/operations/mutation/what-if.js +59 -0
  48. package/dist/operations/planning/compile-intent.d.ts +15 -20
  49. package/dist/operations/planning/compile-intent.d.ts.map +1 -1
  50. package/dist/operations/planning/compile-intent.js +64 -53
  51. package/dist/operations/semantic-advisor/clauses.d.ts.map +1 -1
  52. package/dist/operations/semantic-advisor/clauses.js +8 -7
  53. package/dist/prolog/janitor.d.ts +26 -2
  54. package/dist/prolog/janitor.d.ts.map +1 -1
  55. package/dist/prolog/janitor.js +55 -3
  56. package/dist/prolog/store-lock.d.ts +47 -3
  57. package/dist/prolog/store-lock.d.ts.map +1 -1
  58. package/dist/prolog/store-lock.js +148 -11
  59. package/dist/proof/inspect.d.ts +1 -1
  60. package/dist/proof/inspect.d.ts.map +1 -1
  61. package/dist/proof/inspect.js +9 -2
  62. package/dist/public/operations/catalog.d.ts +97 -4
  63. package/dist/public/operations/catalog.d.ts.map +1 -1
  64. package/dist/public/operations/check-executor.d.ts +2 -2
  65. package/dist/public/operations/check-executor.d.ts.map +1 -1
  66. package/dist/public/operations/check-executor.js +35 -0
  67. package/dist/public/operations/check-format-shared.d.ts +16 -0
  68. package/dist/public/operations/check-format-shared.d.ts.map +1 -1
  69. package/dist/public/operations/check-format-shared.js +19 -0
  70. package/dist/public/operations/contracts.d.ts.map +1 -1
  71. package/dist/public/operations/contracts.js +11 -4
  72. package/dist/public/operations/discovery-executors.d.ts +39 -0
  73. package/dist/public/operations/discovery-executors.d.ts.map +1 -1
  74. package/dist/public/operations/discovery-executors.js +368 -3
  75. package/dist/public/operations/specs/composite.d.ts +1 -1
  76. package/dist/public/operations/specs/composite.js +1 -1
  77. package/dist/public/operations/specs/discovery.d.ts +52 -3
  78. package/dist/public/operations/specs/discovery.d.ts.map +1 -1
  79. package/dist/public/operations/specs/discovery.js +58 -3
  80. package/dist/public/operations/specs/upsert.d.ts +44 -0
  81. package/dist/public/operations/specs/upsert.d.ts.map +1 -1
  82. package/dist/public/operations/specs/upsert.js +14 -0
  83. package/dist/public/skills/kibi-usage/SKILL.md +44 -1
  84. package/dist/public/skills/kibi-usage/resources/fact-lanes.md +4 -2
  85. package/dist/runtime/cli-runtime.d.ts.map +1 -1
  86. package/dist/runtime/cli-runtime.js +7 -2
  87. package/dist/search-answer.d.ts +25 -3
  88. package/dist/search-answer.d.ts.map +1 -1
  89. package/dist/search-answer.js +96 -8
  90. package/dist/utils/branch-store.d.ts.map +1 -1
  91. package/dist/utils/branch-store.js +4 -2
  92. package/dist/utils/content-freshness.d.ts.map +1 -1
  93. package/dist/utils/content-freshness.js +12 -2
  94. package/dist/utils/symbol-manifest-layout.d.ts +9 -0
  95. package/dist/utils/symbol-manifest-layout.d.ts.map +1 -0
  96. package/dist/utils/symbol-manifest-layout.js +18 -0
  97. package/package.json +3 -3
  98. package/src/public/operations/check-executor.ts +44 -1
  99. package/src/public/operations/check-format-shared.ts +35 -1
  100. package/src/public/operations/contracts.ts +15 -4
  101. package/src/public/operations/discovery-executors.ts +484 -2
  102. package/src/public/operations/specs/composite.ts +1 -1
  103. package/src/public/operations/specs/discovery.ts +70 -3
  104. package/src/public/operations/specs/upsert.ts +15 -0
  105. package/src/public/skills/kibi-usage/SKILL.md +44 -1
  106. package/src/public/skills/kibi-usage/resources/fact-lanes.md +4 -2
@@ -23,7 +23,7 @@ export declare const CLI_OPERATION_METADATA: readonly [{
23
23
  }, {
24
24
  readonly name: "kb_query";
25
25
  readonly cliName: "query";
26
- readonly description: "Read entities from the KB with filters. Use for discovery and lookup before edits. Do not use for writes. No mutation side effects. Tags filter by metadata tags only, not entity IDs.";
26
+ readonly description: "Read entities from the KB with exact filters, or ask typed fact questions. Use for lookup by id, type, tags or sourceFile, and for precise questions about modeled facts: predicate facts by name with named arguments (predicate + where), property facts of a subject (subjectKey + propertyKey), or the catalog of facts of one kind (factKind; 'predicate_schema' lists the predicates you can ask about with their argument names and constants). Typed answers return matching fact rows plus factQuery: the schema used, distinct counts, values that do exist when nothing matched, warnings about the question and the next call to make. Read-only. Tags filter by metadata tags only, not entity IDs.";
27
27
  }, {
28
28
  readonly name: "kb_search";
29
29
  readonly cliName: "search";
@@ -59,7 +59,7 @@ export declare const CLI_OPERATION_METADATA: readonly [{
59
59
  }, {
60
60
  readonly name: "kb_model";
61
61
  readonly cliName: "model";
62
- readonly description: "Turn requirement prose into checkable structure without writing the KB. mode:analyze returns the semantic advisor receipt: the clause ledger, what is grounded, what is ambiguous and suggested modeling (pass clauses for compound prose and optional typed kibi.logic.v1 interpretations). mode:requirement converts one claim (subjectKey, propertyKey, operator, value, or typed logic) into a strict-lane write set and applyPlan. mode:predicates ranks ontology predicate schemas and returns an applicable predicate-fact plan only for reviewed bindings, otherwise an ontology-gap observation. Apply returned plans with kb_upsert.";
62
+ readonly description: "Turn requirement prose into checkable structure without writing the KB. mode:analyze returns the semantic advisor receipt: the clause ledger, what is grounded, what is ambiguous and suggested modeling (pass clauses for compound prose and optional typed kibi.logic.v1 interpretations). mode:requirement converts one claim (subjectKey, propertyKey, operator, value, or typed logic) into a strict-lane write set and applyPlan. mode:predicates ranks ontology predicate schemas and returns an applicable predicate-fact plan only for reviewed bindings, otherwise an ontology-gap observation. With requirementId, mode:predicates also returns a hash-bound plan (fact write plus requires_predicate link) for kb_apply_plan, whose contradictionAnalysis is the what-if over the current KB; other returned plans apply with kb_upsert, and kb_upsert dryRun with plannedFacts previews a requirement before its facts exist.";
63
63
  }, {
64
64
  readonly name: "kb_plan_bootstrap";
65
65
  readonly cliName: "plan-bootstrap";
@@ -25,7 +25,7 @@ export const CLI_OPERATION_METADATA = [
25
25
  {
26
26
  name: "kb_query",
27
27
  cliName: "query",
28
- description: "Read entities from the KB with filters. Use for discovery and lookup before edits. Do not use for writes. No mutation side effects. Tags filter by metadata tags only, not entity IDs.",
28
+ description: "Read entities from the KB with exact filters, or ask typed fact questions. Use for lookup by id, type, tags or sourceFile, and for precise questions about modeled facts: predicate facts by name with named arguments (predicate + where), property facts of a subject (subjectKey + propertyKey), or the catalog of facts of one kind (factKind; 'predicate_schema' lists the predicates you can ask about with their argument names and constants). Typed answers return matching fact rows plus factQuery: the schema used, distinct counts, values that do exist when nothing matched, warnings about the question and the next call to make. Read-only. Tags filter by metadata tags only, not entity IDs.",
29
29
  },
30
30
  {
31
31
  name: "kb_search",
@@ -70,7 +70,7 @@ export const CLI_OPERATION_METADATA = [
70
70
  {
71
71
  name: "kb_model",
72
72
  cliName: "model",
73
- description: "Turn requirement prose into checkable structure without writing the KB. mode:analyze returns the semantic advisor receipt: the clause ledger, what is grounded, what is ambiguous and suggested modeling (pass clauses for compound prose and optional typed kibi.logic.v1 interpretations). mode:requirement converts one claim (subjectKey, propertyKey, operator, value, or typed logic) into a strict-lane write set and applyPlan. mode:predicates ranks ontology predicate schemas and returns an applicable predicate-fact plan only for reviewed bindings, otherwise an ontology-gap observation. Apply returned plans with kb_upsert.",
73
+ description: "Turn requirement prose into checkable structure without writing the KB. mode:analyze returns the semantic advisor receipt: the clause ledger, what is grounded, what is ambiguous and suggested modeling (pass clauses for compound prose and optional typed kibi.logic.v1 interpretations). mode:requirement converts one claim (subjectKey, propertyKey, operator, value, or typed logic) into a strict-lane write set and applyPlan. mode:predicates ranks ontology predicate schemas and returns an applicable predicate-fact plan only for reviewed bindings, otherwise an ontology-gap observation. With requirementId, mode:predicates also returns a hash-bound plan (fact write plus requires_predicate link) for kb_apply_plan, whose contradictionAnalysis is the what-if over the current KB; other returned plans apply with kb_upsert, and kb_upsert dryRun with plannedFacts previews a requirement before its facts exist.",
74
74
  },
75
75
  {
76
76
  name: "kb_plan_bootstrap",
@@ -14,7 +14,7 @@ export function registerMaintenanceCommands(program) {
14
14
  .action(async () => (await import("./commands/engine.js")).engineStopCommand());
15
15
  engine
16
16
  .command("janitor")
17
- .description("Classify and clean stale engine daemons and branch-store locks (crashed engines, removed worktrees)")
17
+ .description("Classify and clean stale engine daemons, branch-store locks and expired lock-takeover records (crashed engines, removed worktrees)")
18
18
  .option("--all", "Also sweep runtime-directory daemon sockets from other workspaces", false)
19
19
  .option("--apply", "Execute cleanups (default: report only)", false)
20
20
  .option("--format <format>", "Output format: json|table", "table")
@@ -694,14 +694,19 @@ function checkBranchStore() {
694
694
  const compilation = branchStoreCompilation(store);
695
695
  // implements REQ-core-journaled-engine-persistence
696
696
  const takeover = storeLockTakeoverReason(store.path);
697
+ // A takeover is reported whether or not the store holds a compilation yet.
698
+ const withTakeover = (message) => takeover
699
+ ? `${message}${message.endsWith(".") ? "" : "."} ${String(takeover.detail)}`
700
+ : message;
701
+ const takeoverDetails = takeover ? { lockTakeover: takeover } : {};
697
702
  if (compilation.compiled) {
698
703
  return {
699
704
  passed: true,
700
- message: `Compiled for ${branch}${compilation.generation ? ` (${compilation.generation})` : ""}${takeover ? `. ${String(takeover.detail)}` : ""}`,
705
+ message: withTakeover(`Compiled for ${branch}${compilation.generation ? ` (${compilation.generation})` : ""}`),
701
706
  details: {
702
707
  ...details,
703
708
  generation: compilation.generation,
704
- ...(takeover ? { lockTakeover: takeover } : {}),
709
+ ...takeoverDetails,
705
710
  },
706
711
  };
707
712
  }
@@ -709,18 +714,19 @@ function checkBranchStore() {
709
714
  if (reason === null) {
710
715
  return {
711
716
  passed: true,
712
- message: `Not compiled yet for ${branch}; .kb/ holds no authored sources`,
713
- details,
717
+ message: withTakeover(`Not compiled yet for ${branch}; .kb/ holds no authored sources`),
718
+ details: { ...details, ...takeoverDetails },
714
719
  };
715
720
  }
716
721
  return {
717
722
  passed: false,
718
- message: String(reason.detail),
723
+ message: withTakeover(String(reason.detail)),
719
724
  remediation: "Run: kibi sync",
720
725
  details: {
721
726
  ...details,
722
727
  generation: compilation.generation,
723
728
  authoredSources: reason.authoredSources,
729
+ ...takeoverDetails,
724
730
  },
725
731
  };
726
732
  }
@@ -9,7 +9,8 @@ export interface EngineJanitorOptions {
9
9
  /**
10
10
  * Classify and (optionally) clean stale engine daemons and branch-store
11
11
  * locks: crashed engines leave ownership journals behind, worktree removals
12
- * strand live daemons, dead daemons leave sockets. Report-only by default;
12
+ * strand live daemons, dead daemons leave sockets, and stale-lock takeover
13
+ * records outlive the window kb_status reports them for. Report-only by default;
13
14
  `--apply` executes the clean actions.
14
15
  */
15
16
  export declare function engineJanitorCommand(options: EngineJanitorOptions): Promise<void>;
@@ -1 +1 @@
1
- {"version":3,"file":"engine.d.ts","sourceRoot":"","sources":["../../src/commands/engine.ts"],"names":[],"mappings":"AAuCA,wBAAsB,mBAAmB,IAAI,OAAO,CAAC,IAAI,CAAC,CA4BzD;AAED,wBAAsB,iBAAiB,IAAI,OAAO,CAAC,IAAI,CAAC,CAWvD;AAED,wBAAsB,oBAAoB,IAAI,OAAO,CAAC,IAAI,CAAC,CAE1D;AAED,MAAM,WAAW,oBAAoB;IACnC,QAAQ,CAAC,GAAG,CAAC,EAAE,OAAO,CAAC;IACvB,QAAQ,CAAC,KAAK,CAAC,EAAE,OAAO,CAAC;IACzB,QAAQ,CAAC,MAAM,CAAC,EAAE,MAAM,CAAC;CAC1B;AAED;;;;;GAKG;AAEH,wBAAsB,oBAAoB,CACxC,OAAO,EAAE,oBAAoB,GAC5B,OAAO,CAAC,IAAI,CAAC,CA2Cf;AAED,wBAAsB,qBAAqB,IAAI,OAAO,CAAC,IAAI,CAAC,CAkB3D;AAED,wBAAsB,oBAAoB,CAAC,OAAO,EAAE;IAClD,MAAM,EAAE,MAAM,CAAC;CAChB,GAAG,OAAO,CAAC,IAAI,CAAC,CAWhB"}
1
+ {"version":3,"file":"engine.d.ts","sourceRoot":"","sources":["../../src/commands/engine.ts"],"names":[],"mappings":"AAuCA,wBAAsB,mBAAmB,IAAI,OAAO,CAAC,IAAI,CAAC,CA4BzD;AAED,wBAAsB,iBAAiB,IAAI,OAAO,CAAC,IAAI,CAAC,CAWvD;AAED,wBAAsB,oBAAoB,IAAI,OAAO,CAAC,IAAI,CAAC,CAE1D;AAED,MAAM,WAAW,oBAAoB;IACnC,QAAQ,CAAC,GAAG,CAAC,EAAE,OAAO,CAAC;IACvB,QAAQ,CAAC,KAAK,CAAC,EAAE,OAAO,CAAC;IACzB,QAAQ,CAAC,MAAM,CAAC,EAAE,MAAM,CAAC;CAC1B;AAED;;;;;;GAMG;AAEH,wBAAsB,oBAAoB,CACxC,OAAO,EAAE,oBAAoB,GAC5B,OAAO,CAAC,IAAI,CAAC,CAiDf;AAED,wBAAsB,qBAAqB,IAAI,OAAO,CAAC,IAAI,CAAC,CAkB3D;AAED,wBAAsB,oBAAoB,CAAC,OAAO,EAAE;IAClD,MAAM,EAAE,MAAM,CAAC;CAChB,GAAG,OAAO,CAAC,IAAI,CAAC,CAWhB"}
@@ -74,7 +74,8 @@ export async function storageStatusCommand() {
74
74
  /**
75
75
  * Classify and (optionally) clean stale engine daemons and branch-store
76
76
  * locks: crashed engines leave ownership journals behind, worktree removals
77
- * strand live daemons, dead daemons leave sockets. Report-only by default;
77
+ * strand live daemons, dead daemons leave sockets, and stale-lock takeover
78
+ * records outlive the window kb_status reports them for. Report-only by default;
78
79
  `--apply` executes the clean actions.
79
80
  */
80
81
  // implements REQ-core-journaled-engine-persistence
@@ -98,6 +99,10 @@ export async function engineJanitorCommand(options) {
98
99
  return;
99
100
  }
100
101
  for (const finding of findings) {
102
+ if (finding.kind === "takeover-record") {
103
+ console.log(`[${finding.action}] takeover record ${finding.recordPath} at=${finding.at} (past the kb_status notice window)`);
104
+ continue;
105
+ }
101
106
  const holder = "pid" in finding && finding.pid !== undefined
102
107
  ? ` pid=${finding.pid}`
103
108
  : "";
@@ -33,6 +33,16 @@ export declare function refreshManifestCoordinates(manifestPath: string, workspa
33
33
  refreshSymbolCoordinates?: boolean;
34
34
  quiet?: boolean;
35
35
  }): Promise<void>;
36
+ /**
37
+ * Rewrite a symbol manifest whose `symbols` sequence is in YAML flow layout
38
+ * (`symbols: [ { id: … }, … ]`) as block YAML, keeping comments and entry
39
+ * order. kibi-cli before 2.18.0 appended to the `symbols: []` that
40
+ * `kibi init` writes and kept every symbol on that one line; the hook
41
+ * scanners of older adapters cannot read it and diffs of it are unreviewable,
42
+ * so plain `kibi sync` normalises it once. Returns the number of symbols
43
+ * when the file was rewritten, otherwise null.
44
+ */
45
+ export declare function normalizeManifestLayout(manifestPath: string, deps?: Partial<ManifestDeps>): number | null;
36
46
  export declare function hasAllGeneratedCoordinates(entry: ManifestSymbolEntry): boolean;
37
47
  export declare function isEligibleForCoordinateRefresh(sourceFile: string | undefined, workspaceRoot: string, deps?: Partial<ManifestDeps>): boolean;
38
48
  //# sourceMappingURL=manifest.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"manifest.d.ts","sourceRoot":"","sources":["../../../src/commands/sync/manifest.ts"],"names":[],"mappings":"AAkBA,OAAO,EACL,UAAU,EACV,YAAY,EACZ,UAAU,EACV,UAAU,EACV,aAAa,EACd,MAAM,SAAS,CAAC;AAEjB,OAAO,EAAE,IAAI,IAAI,QAAQ,EAAE,IAAI,IAAI,SAAS,EAAE,MAAM,SAAS,CAAC;AAC9D,OAAO,EAML,uBAAuB,EACxB,MAAM,wCAAwC,CAAC;AAChD,OAAO,EACL,KAAK,mBAAmB,EACxB,uBAAuB,EACxB,MAAM,yCAAyC,CAAC;AACjD,OAAO,EACL,0BAA0B,EAG3B,MAAM,oCAAoC,CAAC;AAC5C,OAAO,EAAE,2BAA2B,EAAE,MAAM,+BAA+B,CAAC;AAE5E,UAAU,YAAY;IACpB,QAAQ,EAAE,OAAO,QAAQ,CAAC;IAC1B,uBAAuB,EAAE,OAAO,uBAAuB,CAAC;IACxD,UAAU,EAAE,OAAO,UAAU,CAAC;IAC9B,SAAS,EAAE,OAAO,SAAS,CAAC;IAC5B,YAAY,EAAE,OAAO,YAAY,CAAC;IAClC,UAAU,EAAE,OAAO,UAAU,CAAC;IAC9B,UAAU,EAAE,OAAO,UAAU,CAAC;IAC9B,aAAa,EAAE,OAAO,aAAa,CAAC;IACpC,uBAAuB,EAAE,OAAO,uBAAuB,CAAC;IACxD,2BAA2B,EAAE,OAAO,2BAA2B,CAAC;CACjE;AAkBD,eAAO,MAAM,8BAA8B,QAc1C,CAAC;AAaF;;;;;;;;;GASG;AACH,OAAO,EAAE,0BAA0B,EAAE,CAAC;AAEtC,wBAAgB,yBAAyB,CAAC,KAAK,EAAE,mBAAmB,GAAG,OAAO,CAG7E;AAoHD,wBAAsB,0BAA0B,CAE9C,YAAY,EAAE,MAAM,EACpB,aAAa,EAAE,MAAM,EACrB,IAAI,CAAC,EAAE,OAAO,CAAC,YAAY,CAAC,GAAG;IAC7B,wBAAwB,CAAC,EAAE,OAAO,CAAC;IACnC,KAAK,CAAC,EAAE,OAAO,CAAC;CACjB,GACA,OAAO,CAAC,IAAI,CAAC,CA0Mf;AAED,wBAAgB,0BAA0B,CAExC,KAAK,EAAE,mBAAmB,GACzB,OAAO,CAOT;AAED,wBAAgB,8BAA8B,CAE5C,UAAU,EAAE,MAAM,GAAG,SAAS,EAC9B,aAAa,EAAE,MAAM,EACrB,IAAI,CAAC,EAAE,OAAO,CAAC,YAAY,CAAC,GAC3B,OAAO,CAUT"}
1
+ {"version":3,"file":"manifest.d.ts","sourceRoot":"","sources":["../../../src/commands/sync/manifest.ts"],"names":[],"mappings":"AAkBA,OAAO,EACL,UAAU,EACV,YAAY,EACZ,UAAU,EACV,UAAU,EACV,aAAa,EACd,MAAM,SAAS,CAAC;AAEjB,OAAO,EAAE,IAAI,IAAI,QAAQ,EAAE,IAAI,IAAI,SAAS,EAAE,MAAM,SAAS,CAAC;AAE9D,OAAO,EAML,uBAAuB,EACxB,MAAM,wCAAwC,CAAC;AAChD,OAAO,EACL,KAAK,mBAAmB,EACxB,uBAAuB,EACxB,MAAM,yCAAyC,CAAC;AACjD,OAAO,EACL,0BAA0B,EAG3B,MAAM,oCAAoC,CAAC;AAC5C,OAAO,EAAE,2BAA2B,EAAE,MAAM,+BAA+B,CAAC;AAG5E,UAAU,YAAY;IACpB,QAAQ,EAAE,OAAO,QAAQ,CAAC;IAC1B,uBAAuB,EAAE,OAAO,uBAAuB,CAAC;IACxD,UAAU,EAAE,OAAO,UAAU,CAAC;IAC9B,SAAS,EAAE,OAAO,SAAS,CAAC;IAC5B,YAAY,EAAE,OAAO,YAAY,CAAC;IAClC,UAAU,EAAE,OAAO,UAAU,CAAC;IAC9B,UAAU,EAAE,OAAO,UAAU,CAAC;IAC9B,aAAa,EAAE,OAAO,aAAa,CAAC;IACpC,uBAAuB,EAAE,OAAO,uBAAuB,CAAC;IACxD,2BAA2B,EAAE,OAAO,2BAA2B,CAAC;CACjE;AAkBD,eAAO,MAAM,8BAA8B,QAc1C,CAAC;AAaF;;;;;;;;;GASG;AACH,OAAO,EAAE,0BAA0B,EAAE,CAAC;AAEtC,wBAAgB,yBAAyB,CAAC,KAAK,EAAE,mBAAmB,GAAG,OAAO,CAG7E;AAoHD,wBAAsB,0BAA0B,CAE9C,YAAY,EAAE,MAAM,EACpB,aAAa,EAAE,MAAM,EACrB,IAAI,CAAC,EAAE,OAAO,CAAC,YAAY,CAAC,GAAG;IAC7B,wBAAwB,CAAC,EAAE,OAAO,CAAC;IACnC,KAAK,CAAC,EAAE,OAAO,CAAC;CACjB,GACA,OAAO,CAAC,IAAI,CAAC,CA0Mf;AAED;;;;;;;;GAQG;AAEH,wBAAgB,uBAAuB,CACrC,YAAY,EAAE,MAAM,EACpB,IAAI,CAAC,EAAE,OAAO,CAAC,YAAY,CAAC,GAC3B,MAAM,GAAG,IAAI,CAWf;AAED,wBAAgB,0BAA0B,CAExC,KAAK,EAAE,mBAAmB,GACzB,OAAO,CAOT;AAED,wBAAgB,8BAA8B,CAE5C,UAAU,EAAE,MAAM,GAAG,SAAS,EAC9B,aAAa,EAAE,MAAM,EACrB,IAAI,CAAC,EAAE,OAAO,CAAC,YAAY,CAAC,GAC3B,OAAO,CAUT"}
@@ -18,10 +18,12 @@
18
18
  import { existsSync, readFileSync, renameSync, unlinkSync, writeFileSync, } from "node:fs";
19
19
  import * as path from "node:path";
20
20
  import { dump as dumpYAML, load as parseYAML } from "js-yaml";
21
+ import { isSeq, parseDocument } from "yaml";
21
22
  import { coarseCoordinateSpan, coordinateIdentityHash, coordinateSourceHash, parseCoordinateArtifact, writeCoordinateArtifact, } from "../../extractors/symbol-coordinates.js";
22
23
  import { enrichSymbolCoordinates, } from "../../extractors/symbols-coordinator.js";
23
24
  import { COARSE_GRANULARITY_REASONS, COARSE_GRANULARITY_REASONS_PARENTHESIZED, isCoarseGranularityReason, } from "../../public/symbol-granularity.js";
24
25
  import { resolveSymbolsManifestPaths } from "../../utils/manifest-paths.js";
26
+ import { blockifySymbolManifest } from "../../utils/symbol-manifest-layout.js";
25
27
  function resolveDeps(overrides) {
26
28
  return {
27
29
  dumpYAML,
@@ -307,6 +309,31 @@ manifestPath, workspaceRoot, deps) {
307
309
  }
308
310
  }
309
311
  }
312
+ /**
313
+ * Rewrite a symbol manifest whose `symbols` sequence is in YAML flow layout
314
+ * (`symbols: [ { id: … }, … ]`) as block YAML, keeping comments and entry
315
+ * order. kibi-cli before 2.18.0 appended to the `symbols: []` that
316
+ * `kibi init` writes and kept every symbol on that one line; the hook
317
+ * scanners of older adapters cannot read it and diffs of it are unreviewable,
318
+ * so plain `kibi sync` normalises it once. Returns the number of symbols
319
+ * when the file was rewritten, otherwise null.
320
+ */
321
+ // implements REQ-kibi-hooks-flow-manifest
322
+ export function normalizeManifestLayout(manifestPath, deps) {
323
+ const resolved = resolveDeps(deps);
324
+ const rawContent = String(resolved.readFileSync(manifestPath, "utf8"));
325
+ const doc = parseDocument(rawContent);
326
+ const symbols = doc.get("symbols", true);
327
+ if (!isSeq(symbols) || symbols.items.length === 0)
328
+ return null;
329
+ if (!blockifySymbolManifest(doc))
330
+ return null;
331
+ const nextContent = doc.toString({ lineWidth: 0 });
332
+ if (nextContent === rawContent)
333
+ return null;
334
+ publishAtomically(manifestPath, nextContent, resolved);
335
+ return symbols.items.length;
336
+ }
310
337
  export function hasAllGeneratedCoordinates(
311
338
  // implements REQ-003
312
339
  entry) {
@@ -20,5 +20,22 @@ interface UntrackedTargetsDeps {
20
20
  * the diagnostic can never break a sync run.
21
21
  */
22
22
  export declare function findUntrackedDocumentMatches(workspaceRoot: string, missingIds: readonly string[], deps?: Partial<UntrackedTargetsDeps>): Map<string, string>;
23
+ /**
24
+ * Give an upsert-only symbol manifest the pending-source receipt kb_upsert
25
+ * writes since it learned to (`writeSourceForUpsert`).
26
+ *
27
+ * Older Kibi appended symbols to the untracked `.kb/symbols.yaml` that
28
+ * `kibi init` creates without a receipt. The upsert wrote those symbols into
29
+ * the store directly, but sync never saw the manifest, so the store recorded
30
+ * no content hash for it and every source its symbols reference stayed
31
+ * "newer" after a clone or checkout, however many times sync ran.
32
+ *
33
+ * The manifest is adopted only when Git does not track it, no receipt covers
34
+ * it, and at least one symbol it declares is already in the compiled store
35
+ * (`isStored`): Kibi wrote it. A hand-written untracked manifest whose
36
+ * symbols the store never saw keeps the tracked-only boundary and sync's
37
+ * "stage this file" note. Returns whether a receipt was written.
38
+ */
39
+ export declare function adoptUpsertOnlySymbolManifest(workspaceRoot: string, isStored: (ids: readonly string[]) => Promise<boolean>): Promise<boolean>;
23
40
  export {};
24
41
  //# sourceMappingURL=untracked-targets.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"untracked-targets.d.ts","sourceRoot":"","sources":["../../../src/commands/sync/untracked-targets.ts"],"names":[],"mappings":"AAyBA,UAAU,oBAAoB;IAC5B,YAAY,EAAE,CACZ,IAAI,EAAE,MAAM,EACZ,IAAI,EAAE,SAAS,MAAM,EAAE,EACvB,OAAO,EAAE;QAAE,QAAQ,EAAE,MAAM,CAAC;QAAC,SAAS,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE,MAAM,CAAA;KAAE,KAC5D,MAAM,CAAC;IACZ,UAAU,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,OAAO,CAAC;IACtC,YAAY,EAAE,CAAC,IAAI,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,KAAK,MAAM,CAAC;CAC1D;AAQD;;;;;;;;;;;GAWG;AAEH,wBAAgB,4BAA4B,CAC1C,aAAa,EAAE,MAAM,EACrB,UAAU,EAAE,SAAS,MAAM,EAAE,EAC7B,IAAI,GAAE,OAAO,CAAC,oBAAoB,CAAM,GACvC,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,CAsDrB"}
1
+ {"version":3,"file":"untracked-targets.d.ts","sourceRoot":"","sources":["../../../src/commands/sync/untracked-targets.ts"],"names":[],"mappings":"AA6BA,UAAU,oBAAoB;IAC5B,YAAY,EAAE,CACZ,IAAI,EAAE,MAAM,EACZ,IAAI,EAAE,SAAS,MAAM,EAAE,EACvB,OAAO,EAAE;QAAE,QAAQ,EAAE,MAAM,CAAC;QAAC,SAAS,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE,MAAM,CAAA;KAAE,KAC5D,MAAM,CAAC;IACZ,UAAU,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,OAAO,CAAC;IACtC,YAAY,EAAE,CAAC,IAAI,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,KAAK,MAAM,CAAC;CAC1D;AAQD;;;;;;;;;;;GAWG;AAEH,wBAAgB,4BAA4B,CAC1C,aAAa,EAAE,MAAM,EACrB,UAAU,EAAE,SAAS,MAAM,EAAE,EAC7B,IAAI,GAAE,OAAO,CAAC,oBAAoB,CAAM,GACvC,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,CAsDrB;AAED;;;;;;;;;;;;;;;GAeG;AAEH,wBAAsB,6BAA6B,CACjD,aAAa,EAAE,MAAM,EACrB,QAAQ,EAAE,CAAC,GAAG,EAAE,SAAS,MAAM,EAAE,KAAK,OAAO,CAAC,OAAO,CAAC,GACrD,OAAO,CAAC,OAAO,CAAC,CAqBlB"}
@@ -20,7 +20,8 @@ import { createHash } from "node:crypto";
20
20
  import { existsSync, readFileSync } from "node:fs";
21
21
  import * as path from "node:path";
22
22
  import { load as parseYAML } from "js-yaml";
23
- import { isSymbolsManifestPath } from "../../utils/kb-paths.js";
23
+ import { isUntrackedByGit, writePendingSourceReceipt, } from "../../operations/mutation/source-authoring.js";
24
+ import { KB_PATHS, isSymbolsManifestPath } from "../../utils/kb-paths.js";
24
25
  const defaultDeps = {
25
26
  execFileSync: (file, args, options) => execFileSync(file, args, options),
26
27
  existsSync,
@@ -96,6 +97,47 @@ export function findUntrackedDocumentMatches(workspaceRoot, missingIds, deps = {
96
97
  }
97
98
  return matches;
98
99
  }
100
+ /**
101
+ * Give an upsert-only symbol manifest the pending-source receipt kb_upsert
102
+ * writes since it learned to (`writeSourceForUpsert`).
103
+ *
104
+ * Older Kibi appended symbols to the untracked `.kb/symbols.yaml` that
105
+ * `kibi init` creates without a receipt. The upsert wrote those symbols into
106
+ * the store directly, but sync never saw the manifest, so the store recorded
107
+ * no content hash for it and every source its symbols reference stayed
108
+ * "newer" after a clone or checkout, however many times sync ran.
109
+ *
110
+ * The manifest is adopted only when Git does not track it, no receipt covers
111
+ * it, and at least one symbol it declares is already in the compiled store
112
+ * (`isStored`): Kibi wrote it. A hand-written untracked manifest whose
113
+ * symbols the store never saw keeps the tracked-only boundary and sync's
114
+ * "stage this file" note. Returns whether a receipt was written.
115
+ */
116
+ // implements REQ-cli-status-pre-first-sync, REQ-core-persistence
117
+ export async function adoptUpsertOnlySymbolManifest(workspaceRoot, isStored) {
118
+ const relative = KB_PATHS.symbolsManifest;
119
+ const absolute = path.resolve(workspaceRoot, relative);
120
+ if (!existsSync(absolute))
121
+ return false;
122
+ if (existsSync(pendingReceiptFor(workspaceRoot, relative)))
123
+ return false;
124
+ let bytes;
125
+ try {
126
+ bytes = readFileSync(absolute);
127
+ }
128
+ catch {
129
+ return false;
130
+ }
131
+ const ids = manifestIds(bytes.toString("utf8"));
132
+ if (ids.length === 0)
133
+ return false;
134
+ if (!isUntrackedByGit(workspaceRoot, relative))
135
+ return false;
136
+ if (!(await isStored(ids)))
137
+ return false;
138
+ writePendingSourceReceipt(workspaceRoot, relative, createHash("sha256").update(bytes).digest("hex"));
139
+ return true;
140
+ }
99
141
  /** Where kb_upsert records the pending-source receipt of `relative`. */
100
142
  function pendingReceiptFor(workspaceRoot, relative) {
101
143
  return path.join(workspaceRoot, ".kb", "recovery", "pending-sources", `${createHash("sha256").update(relative).digest("hex")}.json`);
@@ -1 +1 @@
1
- {"version":3,"file":"sync.d.ts","sourceRoot":"","sources":["../../src/commands/sync.ts"],"names":[],"mappings":"AA6BA,OAAO,KAAK,EAAE,UAAU,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AA6BjE,OAAO,EAEL,yBAAyB,EAE1B,MAAM,gDAAgD,CAAC;AAGxD,OAAO,EAAE,aAAa,EAAE,MAAM,cAAc,CAAC;AAC7C,OAAO,EACL,KAAK,gBAAgB,EAGtB,MAAM,6BAA6B,CAAC;AAyBrC,OAAO,KAAK,EAAE,4BAA4B,EAAE,MAAM,qBAAqB,CAAC;AA4BxE,qBAAa,SAAU,SAAQ,KAAK;gBACtB,OAAO,EAAE,MAAM;CAI5B;AAmCD,wBAAgB,wBAAwB,CACtC,aAAa,EAAE,MAAM,EACrB,gBAAgB,EAAE,MAAM,EACxB,4BAA4B,UAAQ,EACpC,4BAA4B,GAAE,4BAA4B,EAAO,GAChE,MAAM,EAAE,CAuGV;AAqDD,MAAM,WAAW,UAAW,SAAQ,WAAW;IAC7C,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB;AAED,UAAU,yBAAyB;IACjC,aAAa,EAAE,MAAM,CAAC;IACtB,QAAQ,EAAE,MAAM,CAAC;IACjB,OAAO,EAAE,OAAO,CAAC;IACjB,WAAW,EAAE,MAAM,CAAC;IACpB,YAAY,EAAE,OAAO,CAAC;CACvB;AAED,UAAU,kBAAkB;IAC1B,WAAW,CAAC,EAAE,CAAC,OAAO,EAAE,yBAAyB,KAAK,OAAO,CAAC,IAAI,CAAC,GAAG,IAAI,CAAC;IAC3E,UAAU,CAAC,EAAE,CACX,OAAO,EAAE,yBAAyB,GAAG;QAAE,UAAU,EAAE,OAAO,CAAA;KAAE,KACzD,OAAO,CAAC,IAAI,CAAC,GAAG,IAAI,CAAC;IAC1B,YAAY,CAAC,EAAE,CAAC,OAAO,EAAE;QAAE,OAAO,EAAE,MAAM,CAAA;KAAE,KAAK,aAAa,CAAC;IAC/D,yBAAyB,CAAC,EAAE,OAAO,yBAAyB,CAAC;CAC9D;AA+FD,wBAAgB,oBAAoB,CAAC,IAAI,EAAE,MAAM,EAAE,KAAK,EAAE,OAAO,GAAG,IAAI,CAGvE;AAGD,wBAAgB,2BAA2B,CACzC,IAAI,EAAE,MAAM,EACZ,KAAK,EAAE,MAAM,IAAI,GAChB,IAAI,CAMN;AAED,wBAAgB,4BAA4B,CAC1C,WAAW,EAAE,UAAU,EAAE,EACzB,QAAQ,EAAE,OAAO,EACjB,OAAO,EAAE,OAAO,EAChB,aAAa,EAAE,MAAM,EACrB,QAAQ,EAAE,MAAM,GACf,IAAI,CAIN;AAED,wBAAgB,0BAA0B,CAAC,MAAM,EAAE;IACjD,OAAO,EAAE,OAAO,CAAC;IACjB,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB,GAAG,IAAI,CAMP;AAED,wBAAgB,iCAAiC,CAC/C,WAAW,EAAE,UAAU,EAAE,EACzB,oBAAoB,EAAE,OAAO,EAC7B,iBAAiB,EAAE,MAAM,EACzB,WAAW,EAAE,MAAM,GAClB,IAAI,CAUN;AAGD,wBAAsB,WAAW,CAC/B,OAAO,GAAE;IACP,YAAY,CAAC,EAAE,OAAO,CAAC;IACvB,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,wBAAwB,CAAC,EAAE,OAAO,CAAC;IACnC,2EAA2E;IAC3E,kBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,wEAAwE;IACxE,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB;;;OAGG;IACH,gBAAgB,CAAC,EAAE,gBAAgB,CAAC;IACpC,uEAAuE;IACvE,KAAK,CAAC,EAAE,OAAO,CAAC;CACZ,EACN,OAAO,GAAE,kBAAuB,GAC/B,OAAO,CAAC,UAAU,CAAC,CAipCrB;AAED,OAAO,EAAE,qBAAqB,EAAE,MAAM,qBAAqB,CAAC"}
1
+ {"version":3,"file":"sync.d.ts","sourceRoot":"","sources":["../../src/commands/sync.ts"],"names":[],"mappings":"AA6BA,OAAO,KAAK,EAAE,UAAU,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AA6BjE,OAAO,EAEL,yBAAyB,EAE1B,MAAM,gDAAgD,CAAC;AAGxD,OAAO,EAAE,aAAa,EAAE,MAAM,cAAc,CAAC;AAC7C,OAAO,EACL,KAAK,gBAAgB,EAGtB,MAAM,6BAA6B,CAAC;AAyBrC,OAAO,KAAK,EAAE,4BAA4B,EAAE,MAAM,qBAAqB,CAAC;AAkCxE,qBAAa,SAAU,SAAQ,KAAK;gBACtB,OAAO,EAAE,MAAM;CAI5B;AAmCD,wBAAgB,wBAAwB,CACtC,aAAa,EAAE,MAAM,EACrB,gBAAgB,EAAE,MAAM,EACxB,4BAA4B,UAAQ,EACpC,4BAA4B,GAAE,4BAA4B,EAAO,GAChE,MAAM,EAAE,CAuGV;AAiFD,MAAM,WAAW,UAAW,SAAQ,WAAW;IAC7C,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB;AAED,UAAU,yBAAyB;IACjC,aAAa,EAAE,MAAM,CAAC;IACtB,QAAQ,EAAE,MAAM,CAAC;IACjB,OAAO,EAAE,OAAO,CAAC;IACjB,WAAW,EAAE,MAAM,CAAC;IACpB,YAAY,EAAE,OAAO,CAAC;CACvB;AAED,UAAU,kBAAkB;IAC1B,WAAW,CAAC,EAAE,CAAC,OAAO,EAAE,yBAAyB,KAAK,OAAO,CAAC,IAAI,CAAC,GAAG,IAAI,CAAC;IAC3E,UAAU,CAAC,EAAE,CACX,OAAO,EAAE,yBAAyB,GAAG;QAAE,UAAU,EAAE,OAAO,CAAA;KAAE,KACzD,OAAO,CAAC,IAAI,CAAC,GAAG,IAAI,CAAC;IAC1B,YAAY,CAAC,EAAE,CAAC,OAAO,EAAE;QAAE,OAAO,EAAE,MAAM,CAAA;KAAE,KAAK,aAAa,CAAC;IAC/D,yBAAyB,CAAC,EAAE,OAAO,yBAAyB,CAAC;CAC9D;AA+FD,wBAAgB,oBAAoB,CAAC,IAAI,EAAE,MAAM,EAAE,KAAK,EAAE,OAAO,GAAG,IAAI,CAGvE;AAGD,wBAAgB,2BAA2B,CACzC,IAAI,EAAE,MAAM,EACZ,KAAK,EAAE,MAAM,IAAI,GAChB,IAAI,CAMN;AAED,wBAAgB,4BAA4B,CAC1C,WAAW,EAAE,UAAU,EAAE,EACzB,QAAQ,EAAE,OAAO,EACjB,OAAO,EAAE,OAAO,EAChB,aAAa,EAAE,MAAM,EACrB,QAAQ,EAAE,MAAM,GACf,IAAI,CAIN;AAED,wBAAgB,0BAA0B,CAAC,MAAM,EAAE;IACjD,OAAO,EAAE,OAAO,CAAC;IACjB,KAAK,CAAC,EAAE,MAAM,CAAC;CAChB,GAAG,IAAI,CAMP;AAED,wBAAgB,iCAAiC,CAC/C,WAAW,EAAE,UAAU,EAAE,EACzB,oBAAoB,EAAE,OAAO,EAC7B,iBAAiB,EAAE,MAAM,EACzB,WAAW,EAAE,MAAM,GAClB,IAAI,CAUN;AAGD,wBAAsB,WAAW,CAC/B,OAAO,GAAE;IACP,YAAY,CAAC,EAAE,OAAO,CAAC;IACvB,OAAO,CAAC,EAAE,OAAO,CAAC;IAClB,wBAAwB,CAAC,EAAE,OAAO,CAAC;IACnC,2EAA2E;IAC3E,kBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,wEAAwE;IACxE,aAAa,CAAC,EAAE,MAAM,CAAC;IACvB;;;OAGG;IACH,gBAAgB,CAAC,EAAE,gBAAgB,CAAC;IACpC,uEAAuE;IACvE,KAAK,CAAC,EAAE,OAAO,CAAC;CACZ,EACN,OAAO,GAAE,kBAAuB,GAC/B,OAAO,CAAC,UAAU,CAAC,CA+qCrB;AAED,OAAO,EAAE,qBAAqB,EAAE,MAAM,qBAAqB,CAAC"}
@@ -33,10 +33,10 @@ import { loadEntityPaths } from "../utils/config.js";
33
33
  import { SYNC_CACHE_TTL_MS, SYNC_CACHE_VERSION, SYNC_COMPILER_FINGERPRINT, hashFile, hashManifestWithCoordinates, hashNormalized, readSyncCache, toCacheKey, writeSyncCache, } from "./sync/cache.js";
34
34
  import { clearRecoveredPendingSourceReceipts, discoverSourceFiles, } from "./sync/discovery.js";
35
35
  import { normalizeExtractionSources, processExtractions, } from "./sync/extraction.js";
36
- import { refreshManifestCoordinates } from "./sync/manifest.js";
36
+ import { normalizeManifestLayout, refreshManifestCoordinates, } from "./sync/manifest.js";
37
37
  import { persistEntities, persistRelationships, retractEntitiesById, retractEntitiesForSources, retractEntityRelationshipsById, retractRelationships, } from "./sync/persistence.js";
38
38
  import { atomicPublish, atomicPublishGeneration, cleanupStaging, createUniqueStagingPath, prepareStagingEnvironment, } from "./sync/staging.js";
39
- import { findUntrackedDocumentMatches } from "./sync/untracked-targets.js";
39
+ import { adoptUpsertOnlySymbolManifest, findUntrackedDocumentMatches, } from "./sync/untracked-targets.js";
40
40
  // Manual deletion of a written-but-unstaged source leaves a recovery receipt
41
41
  // behind; sync refuses to guess, so the error must name the way out.
42
42
  const PENDING_SOURCE_RECOVERY_HINT = " If the file was deleted on purpose, run 'kibi branch recover --apply' to rebuild the branch KB from the sources that remain.";
@@ -202,6 +202,32 @@ async function checkpointNoopSync(workspaceRoot, branch) {
202
202
  await engine.terminate();
203
203
  }
204
204
  }
205
+ /** Whether the branch's compiled store already holds any of `ids`. */
206
+ // implements REQ-cli-status-pre-first-sync
207
+ async function storeHoldsAnyEntity(workspaceRoot, branch, ids) {
208
+ const engine = new EngineClient({
209
+ workspaceRoot,
210
+ branch,
211
+ timeout: 120_000,
212
+ });
213
+ try {
214
+ await engine.start();
215
+ for (const id of ids) {
216
+ const found = await engine.queryEntities({ id, limit: 1, offset: 0 });
217
+ if (found.count > 0 || found.entities.length > 0)
218
+ return true;
219
+ }
220
+ return false;
221
+ }
222
+ catch {
223
+ // Adoption is best effort: an unreadable store adopts nothing and the
224
+ // compile below reports the store itself.
225
+ return false;
226
+ }
227
+ finally {
228
+ await engine.terminate();
229
+ }
230
+ }
205
231
  function compilerCacheHasEntityDelta(cache) {
206
232
  return (cache.entityHashes !== undefined && cache.sourceEntityIds !== undefined);
207
233
  }
@@ -354,6 +380,18 @@ export async function syncCommand(options = {}, runtime = {}) {
354
380
  ensureBranchStoreManifest(workspaceRoot, currentBranch);
355
381
  await ensureJournaledBranchStoreAsync(livePathForEngine);
356
382
  }
383
+ // implements REQ-cli-status-pre-first-sync
384
+ // An untracked symbol manifest that only kb_upsert ever wrote (older Kibi
385
+ // left it without a pending-source receipt) gets the receipt here, so
386
+ // this sync compiles it and records its content hash. Without it the
387
+ // sources its symbols reference read as newer after every clone.
388
+ if (!validateOnly &&
389
+ recoveryBackupPath === undefined &&
390
+ options.detachedSnapshot === undefined &&
391
+ runtime.createProlog === undefined) {
392
+ const branch = currentBranch;
393
+ await adoptUpsertOnlySymbolManifest(workspaceRoot, (ids) => storeHoldsAnyEntity(workspaceRoot, branch, ids));
394
+ }
357
395
  const needsExclusiveGenerationPublish = !validateOnly && (rebuild || recoveryBackupPath !== undefined);
358
396
  if (needsExclusiveGenerationPublish) {
359
397
  // Recovery intentionally avoids attaching the broken live store. The
@@ -413,6 +451,17 @@ export async function syncCommand(options = {}, runtime = {}) {
413
451
  const relationshipShardFiles = existsSync(relationshipsDir)
414
452
  ? trackedRelationshipFiles(workspaceRoot, relationshipsDir, recoveryBackupPath !== undefined, recoveredPendingReceiptPaths)
415
453
  : [];
454
+ // A manifest an older writer left in flow layout is rewritten as block
455
+ // YAML before anything hashes it, ahead of the no-op fast path below, so
456
+ // a project whose cache is already fresh still gets it on the next sync.
457
+ if (!validateOnly) {
458
+ for (const file of manifestFiles) {
459
+ const normalized = normalizeManifestLayout(file);
460
+ if (normalized !== null) {
461
+ console.log(`\u2713 Rewrote ${path.relative(workspaceRoot, file)} in block layout (${normalized} symbol${normalized === 1 ? "" : "s"})`);
462
+ }
463
+ }
464
+ }
416
465
  // No-op is a first-class compiler result. Hashing the configured inputs is
417
466
  // sufficient when normalized entity/shard inventories are already fresh;
418
467
  // avoid rebuilding maps and rediscovering RDF state for the common path.
@@ -1 +1 @@
1
- {"version":3,"file":"engine.d.ts","sourceRoot":"","sources":["../src/engine.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"engine.d.ts","sourceRoot":"","sources":["../src/engine.ts"],"names":[],"mappings":"AAgCA,OAAO,EAEL,KAAK,iBAAiB,EAMvB,MAAM,oBAAoB,CAAC;AAC5B,OAAO,KAAK,EACV,wBAAwB,EACxB,eAAe,EAEhB,MAAM,mBAAmB,CAAC;AAG3B,OAAO,EAAE,aAAa,EAAmB,MAAM,aAAa,CAAC;AAa7D,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,sCAAsC,CAAC;AAC9E,OAAO,KAAK,EACV,sBAAsB,EACtB,uBAAuB,EACvB,sBAAsB,EACtB,uBAAuB,EACxB,MAAM,sCAAsC,CAAC;AAQ9C,YAAY,EACV,wBAAwB,EACxB,eAAe,EACf,aAAa,GACd,MAAM,mBAAmB,CAAC;AAC3B,OAAO,EACL,qBAAqB,EACrB,yBAAyB,EACzB,oBAAoB,GACrB,MAAM,oBAAoB,CAAC;AAC5B,YAAY,EACV,mBAAmB,EACnB,iBAAiB,GAClB,MAAM,oBAAoB,CAAC;AAU5B,eAAO,MAAM,uBAAuB,IAAI,CAAC;AACzC,eAAO,MAAM,sBAAsB,QAAiB,CAAC;AACrD,2EAA2E;AAC3E,eAAO,MAAM,6BAA6B,QAAY,CAAC;AACvD,qEAAqE;AACrE,eAAO,MAAM,2BAA2B,OAAO,CAAC;AAEhD;;;;;GAKG;AAEH,wBAAgB,qBAAqB,IAAI,MAAM,CAE9C;AAED,6EAA6E;AAC7E,eAAO,MAAM,uBAAuB,QAAwB,CAAC;AAE7D;;;;GAIG;AAEH,wBAAgB,mBAAmB,IAAI,MAAM,CAE5C;AAQD,wBAAgB,2BAA2B,CACzC,QAAQ,EAAE,MAAM,OAAO,GACtB,MAAM,IAAI,CAIZ;AAED,wBAAgB,qBAAqB,CAAC,UAAU,EAAE,MAAM,GAAG,MAAM,CAKhE;AAED,wBAAgB,4BAA4B,CAC1C,UAAU,EAAE,MAAM,GACjB,wBAAwB,GAAG,IAAI,CAgBjC;AAED,wBAAgB,6BAA6B,CAC3C,UAAU,EAAE,MAAM,GAAG,SAAS,GAC7B,wBAAwB,GAAG,IAAI,CAyBjC;AAED,wBAAgB,sBAAsB,CACpC,QAAQ,EAAE,wBAAwB,GAAG,IAAI,EACzC,QAAQ,EAAE,wBAAwB,GAAG,IAAI,GACxC,OAAO,CAWT;AAED,wBAAgB,8BAA8B,CAC5C,SAAS,EAAE,MAAM,EACjB,QAAQ,EAAE,wBAAwB,GAAG,IAAI,EACzC,QAAQ,EAAE,wBAAwB,GAAG,IAAI,GACxC,MAAM,CASR;AA8LD,wBAAgB,gBAAgB,IAAI,MAAM,CAgFzC;AAaD;;;;;GAKG;AAEH,wBAAgB,yBAAyB,CAAC,UAAU,EAAE,MAAM,GAAG,IAAI,CAuBlE;AAGD,wBAAgB,gBAAgB,CAC9B,aAAa,EAAE,MAAM,EACrB,MAAM,EAAE,MAAM,GACb,MAAM,CAYR;AAED,wBAAgB,aAAa,CAAC,aAAa,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,GAAG,MAAM,CAW3E;AAED,wBAAgB,mBAAmB,CACjC,aAAa,EAAE,MAAM,EACrB,MAAM,EAAE,MAAM,GACb,MAAM,CAUR;AAED;;;;GAIG;AACH,wBAAgB,yBAAyB,CACvC,aAAa,EAAE,MAAM,EACrB,MAAM,EAAE,MAAM,GACb,MAAM,CAER;AA2DD,MAAM,MAAM,sBAAsB,GAAG,QAAQ,CAAC;IAC5C,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,OAAO,EAAE,MAAM,IAAI,CAAC;CAC9B,CAAC,CAAC;AAEH,wBAAgB,6BAA6B,CAC3C,aAAa,EAAE,MAAM,EACrB,MAAM,EAAE,MAAM,GACb,sBAAsB,CAuDxB;AA8LD,mDAAmD;AACnD,MAAM,MAAM,oBAAoB,GAAG,QAAQ,CAAC;IAC1C,cAAc,EAAE,MAAM,GAAG,IAAI,CAAC;IAC9B,eAAe,EAAE,MAAM,GAAG,IAAI,CAAC;CAChC,CAAC,CAAC;AAEH,MAAM,MAAM,mBAAmB,GAAG;IAChC,QAAQ,CAAC,aAAa,EAAE,MAAM,CAAC;IAC/B,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IACxB,QAAQ,CAAC,OAAO,CAAC,EAAE,MAAM,CAAC;IAC1B,8EAA8E;IAC9E,QAAQ,CAAC,oBAAoB,CAAC,EAAE,OAAO,CAAC;IACxC;;;;OAIG;IACH,QAAQ,CAAC,UAAU,CAAC,EAAE,iBAAiB,GAAG,IAAI,CAAC;CAChD,CAAC;AAEF,2EAA2E;AAE3E,qBAAa,YAAY;IACvB,OAAO,CAAC,QAAQ,CAAC,aAAa,CAAS;IACvC,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAS;IAChC,OAAO,CAAC,QAAQ,CAAC,OAAO,CAAS;IACjC,OAAO,CAAC,QAAQ,CAAC,oBAAoB,CAAU;IAC/C,OAAO,CAAC,QAAQ,CAAC,UAAU,CAAgC;IAC3D,OAAO,CAAC,MAAM,CAA2B;IACzC,OAAO,CAAC,MAAM,CAA6B;IAC3C,OAAO,CAAC,WAAW,CAA4C;IAC/D,OAAO,CAAC,SAAS,CAAK;IACtB,OAAO,CAAC,OAAO,CAAqC;IACpD,OAAO,CAAC,WAAW,CAAoC;IACvD,OAAO,CAAC,UAAU,CAAkC;IACpD,OAAO,CAAC,oBAAoB,CAAS;gBAEzB,OAAO,EAAE,mBAAmB;IAclC,KAAK,CAAC,UAAU,UAAO,GAAG,OAAO,CAAC,IAAI,CAAC;YA4B/B,OAAO;IAiHrB,OAAO,CAAC,YAAY;IAkCpB,uEAAuE;IACvE,OAAO,CAAC,aAAa;IAOrB,OAAO,CAAC,cAAc;YAkBR,OAAO;IA+Ef,KAAK,CAAC,IAAI,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,WAAW,GAAG,OAAO,CAAC,iBAAiB,CAAC;IAS3E;uEACmE;IAC7D,OAAO,CAAC,CAAC,GAAG,iBAAiB,EACjC,OAAO,EAAE,eAAe,EACxB,MAAM,CAAC,EAAE,WAAW,GACnB,OAAO,CAAC,CAAC,CAAC;IAIP,UAAU,CAAC,KAAK,EAAE,SAAS,MAAM,EAAE,GAAG,OAAO,CAAC,iBAAiB,CAAC;IAKhE,aAAa,CACjB,KAAK,EAAE,sBAAsB,EAC7B,MAAM,CAAC,EAAE,WAAW,GACnB,OAAO,CAAC,uBAAuB,CAAC;YASrB,gBAAgB;IAgCxB,cAAc,CAClB,KAAK,EAAE,sBAAsB,EAC7B,MAAM,CAAC,EAAE,WAAW,GACnB,OAAO,CAAC,uBAAuB,CAAC;IAyBnC,qDAAqD;IACrD,MAAM,CAAC,SAAS,EAAE,MAAM,GAAG,IAAI;IAmBzB,YAAY,IAAI,OAAO,CAAC,iBAAiB,GAAG,IAAI,CAAC;IAMjD,IAAI,CAAC,MAAM,CAAC,EAAE,WAAW,GAAG,OAAO,CAAC,iBAAiB,CAAC;IAItD,aAAa,IAAI,OAAO,CAAC,iBAAiB,CAAC;IAI3C,UAAU,IAAI,OAAO,CAAC,iBAAiB,CAAC;IAIxC,eAAe,CAAC,MAAM,CAAC,EAAE,WAAW,GAAG,OAAO,CAAC,iBAAiB,CAAC;IAOjE,OAAO,IAAI,OAAO,CAAC,iBAAiB,CAAC;IAIrC,aAAa,CAAC,eAAe,EAAE,MAAM,GAAG,OAAO,CAAC,iBAAiB,CAAC;IAOxE,eAAe,IAAI,IAAI;IAIvB,SAAS,IAAI,OAAO;YAIN,oBAAoB;IAMlC,wEAAwE;YAC1D,eAAe;IAgB7B;;;OAGG;IAEG,iBAAiB,IAAI,OAAO,CAAC,oBAAoB,GAAG,IAAI,CAAC;IAW/D,0EAA0E;YAC5D,qBAAqB;IAUnC;;;;;;;OAOG;YAEW,gBAAgB;YAkBhB,mBAAmB;YA0BnB,uBAAuB;IA0CrC,MAAM,IAAI,MAAM;IASV,IAAI,CAAC,cAAc,UAAO,GAAG,OAAO,CAAC,IAAI,CAAC;IAkB1C,SAAS,IAAI,OAAO,CAAC,IAAI,CAAC;CASjC;AAGD,wBAAsB,+BAA+B,CACnD,UAAU,EAAE,MAAM,GACjB,OAAO,CAAC,IAAI,CAAC,CAoJf;AAsGD;;;;;;GAMG;AAEH,qBAAa,aAAa;IAItB,OAAO,CAAC,QAAQ,CAAC,MAAM;IACvB,OAAO,CAAC,QAAQ,CAAC,UAAU;IAJ7B,OAAO,CAAC,QAAQ,CAAC,OAAO,CAAyC;gBAG9C,MAAM,EAAE,aAAa,EACrB,UAAU,EAAE,MAAM;IAY/B,IAAI,IAAI,OAAO,CAAC,IAAI,CAAC;IA8B3B,yEAAyE;IACzE,gBAAgB,CAAC,IAAI,EAAE,MAAM,EAAE,MAAM,EAAE,iBAAiB,GAAG,IAAI;IAW/D,YAAY,IAAI,OAAO;IAIvB;;;OAGG;IACG,UAAU,IAAI,OAAO,CAAC,OAAO,CAAC;CAgBrC;AAGD,wBAAsB,eAAe,CAAC,gBAAgB,EAAE;IACtD,QAAQ,CAAC,aAAa,EAAE,MAAM,CAAC;IAC/B,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IACxB,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;IAC5B,sEAAsE;IACtE,QAAQ,CAAC,cAAc,CAAC,EAAE,MAAM,CAAC;CAClC,GAAG,OAAO,CAAC,IAAI,CAAC,CA0wBhB"}
package/dist/engine.js CHANGED
@@ -18,7 +18,7 @@ import { kibiPackageVersions } from "./package-versions.js";
18
18
  import { writePerformanceTraceEvent } from "./performance-trace.js";
19
19
  import { PrologProcess, resolveKbPlPath } from "./prolog.js";
20
20
  import { parseEntityFromList, parseListOfLists } from "./prolog/codec.js";
21
- import { retryAttachAfterBreakingStaleLock } from "./prolog/store-lock.js";
21
+ import { decideStoreLockTakeover, isProcessAlive, noteDeadHolderBeforeAttach, readRdfLockPid, readStoreLockOwner, recordStoreLockTakeover, retryAttachAfterBreakingStaleLock, } from "./prolog/store-lock.js";
22
22
  import { resolveSwipl, swiplIdentity } from "./prolog/swipl-resolver.js";
23
23
  import { queryEntityChunks } from "./public/operations/discovery-entities.js";
24
24
  import { isValidBranchName } from "./utils/branch-resolver.js";
@@ -632,35 +632,41 @@ function releaseStartLock(lockPath, descriptor) {
632
632
  // Another starter may already have cleaned the lock.
633
633
  }
634
634
  }
635
+ // implements REQ-core-journaled-engine-persistence
635
636
  function recoverStaleJournalLock(branchPath) {
636
637
  const lockPath = path.join(branchPath, "rdf", "lock");
637
638
  if (!existsSync(lockPath))
638
639
  return;
639
- let contents = "";
640
- try {
641
- contents = readFileSync(lockPath, "utf8");
642
- }
643
- catch {
640
+ const pid = readRdfLockPid(lockPath);
641
+ if (pid === null || pid === process.pid)
644
642
  return;
643
+ let reason;
644
+ if (!isProcessAlive(pid)) {
645
+ reason = decideStoreLockTakeover({ pid }).reason;
646
+ }
647
+ else {
648
+ // A live pid still loses the lock when the lock and its journal were
649
+ // copied in from another workspace: that pid holds the original store,
650
+ // never this copy.
651
+ const journal = readStoreLockOwner(branchPath)?.owner ?? null;
652
+ if (journal === null || journal.pid !== pid)
653
+ return;
654
+ const decision = decideStoreLockTakeover(journal, {
655
+ storePath: branchPath,
656
+ });
657
+ if (decision.action !== "break")
658
+ return;
659
+ reason = decision.reason;
645
660
  }
646
- const match = /pid\((\d+)\)/.exec(contents);
647
- if (!match)
648
- return;
649
- const pid = Number.parseInt(match[1] ?? "", 10);
650
- if (!Number.isFinite(pid) || pid <= 0 || pid === process.pid)
651
- return;
661
+ // Breaking a stale holder's lock is a takeover; record it for kb_status
662
+ // and kibi doctor instead of healing silently.
663
+ recordStoreLockTakeover(branchPath, pid, reason);
652
664
  try {
653
- process.kill(pid, 0);
654
- return;
665
+ rmSync(lockPath, { force: true });
655
666
  }
656
667
  catch {
657
- try {
658
- rmSync(lockPath, { force: true });
659
- }
660
- catch {
661
- // Let rdf_attach_db report the lock error if another process wins the
662
- // race between the liveness probe and removal.
663
- }
668
+ // Let rdf_attach_db report the lock error if another process wins the
669
+ // race between the liveness probe and removal.
664
670
  }
665
671
  }
666
672
  function daemonEntry() {
@@ -1565,8 +1571,13 @@ export class EngineSession {
1565
1571
  }
1566
1572
  async boot() {
1567
1573
  await this.prolog.start();
1574
+ // A killed holder never makes kb_attach fail (its OS lock died with it),
1575
+ // so a dead-holder takeover must be noted before the attach succeeds.
1576
+ const recordTakeover = noteDeadHolderBeforeAttach(this.branchPath);
1568
1577
  const attached = await this.prolog.query(`kb_attach('${quoteProlog(this.branchPath)}')`);
1569
- if (!attached.success) {
1578
+ if (attached.success)
1579
+ recordTakeover();
1580
+ else {
1570
1581
  // The daemon hosts the branch store for every later request, so a
1571
1582
  // store-locked startup with a provably dead holder is auto-healed here
1572
1583
  // exactly like the CLI runtime path; live holders abort the startup
@@ -42,6 +42,13 @@ export type IntentSearchAnalysis = Readonly<{
42
42
  acceptedCount: number;
43
43
  topScore: number | null;
44
44
  topTwoMargin: number | null;
45
+ /**
46
+ * Margin between the top match and the best match it is not linked to in
47
+ * the traceability graph. A requirement and its own scenario, facts or
48
+ * tests tie without competing, so `ambiguous` reads this margin, not
49
+ * `topTwoMargin`.
50
+ */
51
+ topRivalMargin: number | null;
45
52
  abstained: boolean;
46
53
  ambiguous: boolean;
47
54
  }>;
@@ -1 +1 @@
1
- {"version":3,"file":"intent-search.d.ts","sourceRoot":"","sources":["../src/intent-search.ts"],"names":[],"mappings":"AAKA,OAAO,EACL,KAAK,kBAAkB,EAIxB,MAAM,2CAA2C,CAAC;AACnD,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,sCAAsC,CAAC;AACvE,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,qBAAqB,CAAC;AAIvD,MAAM,MAAM,qBAAqB,GAC7B,QAAQ,GACR,SAAS,GACT,SAAS,GACT,aAAa,GACb,SAAS,CAAC;AAGd,MAAM,MAAM,kBAAkB,GAAG,QAAQ,CACvC,OAAO,CAAC,MAAM,CAAC,qBAAqB,EAAE,SAAS,MAAM,EAAE,CAAC,CAAC,CAC1D,CAAC;AAGF,MAAM,MAAM,cAAc,GAAG,QAAQ,CAAC;IACpC,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,MAAM,CAAC,EAAE,MAAM,CAAC;CACjB,CAAC,CAAC;AAGH,MAAM,MAAM,mBAAmB,GAAG,QAAQ,CAAC;IACzC,KAAK,EAAE,MAAM,CAAC;IACd,IAAI,CAAC,EAAE,CAAC,OAAO,kBAAkB,CAAC,CAAC,MAAM,CAAC,GAAG,MAAM,CAAC;IACpD,cAAc,CAAC,EAAE,kBAAkB,CAAC;IACpC,eAAe,CAAC,EAAE,SAAS,cAAc,EAAE,CAAC;IAC5C,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB,CAAC,CAAC;AAGH,MAAM,MAAM,iBAAiB,GAAG,QAAQ,CAAC;IACvC,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB,CAAC,CAAC;AAGH,MAAM,MAAM,eAAe,GAAG,QAAQ,CAAC;IACrC,IAAI,EAAE,MAAM,CAAC;IACb,aAAa,EAAE,SAAS,MAAM,EAAE,CAAC;IACjC,EAAE,EAAE,MAAM,CAAC;CACZ,CAAC,CAAC;AAGH,MAAM,MAAM,oBAAoB,GAAG,QAAQ,CAAC;IAC1C,eAAe,EAAE,MAAM,CAAC;IACxB,aAAa,EAAE,SAAS,MAAM,EAAE,CAAC;IACjC,aAAa,EAAE,SAAS,iBAAiB,EAAE,CAAC;IAC5C,UAAU,EAAE,SAAS,eAAe,EAAE,CAAC;IACvC,kBAAkB,EAAE,OAAO,CAAC;CAC7B,CAAC,CAAC;AAGH,MAAM,MAAM,iBAAiB,GAAG,WAAW,GAAG;IAC5C,QAAQ,CAAC,QAAQ,EAAE,oBAAoB,CAAC;CACzC,CAAC;AAGF,MAAM,MAAM,oBAAoB,GAAG,QAAQ,CAAC;IAC1C,WAAW,EAAE,WAAW,CAAC;IACzB,cAAc,EAAE,MAAM,CAAC;IACvB,aAAa,EAAE,MAAM,CAAC;IACtB,QAAQ,EAAE,MAAM,GAAG,IAAI,CAAC;IACxB,YAAY,EAAE,MAAM,GAAG,IAAI,CAAC;IAC5B,SAAS,EAAE,OAAO,CAAC;IACnB,SAAS,EAAE,OAAO,CAAC;CACpB,CAAC,CAAC;AAGH,MAAM,MAAM,kBAAkB,GAAG,QAAQ,CAAC;IACxC,OAAO,EAAE,SAAS,iBAAiB,EAAE,CAAC;IACtC,QAAQ,EAAE,oBAAoB,CAAC;CAChC,CAAC,CAAC;AAEH,KAAK,SAAS,GAAG,QAAQ,CAAC;IACxB,YAAY,EAAE,MAAM,CAAC;IACrB,IAAI,EAAE,MAAM,CAAC;IACb,EAAE,EAAE,MAAM,CAAC;CACZ,CAAC,CAAC;AA2bH,2EAA2E;AAE3E,MAAM,MAAM,iBAAiB,GAAG,GAAG,CAAC,MAAM,EAAE,MAAM,GAAG,IAAI,CAAC,CAAC;AA8B3D,wBAAsB,kBAAkB,CACtC,QAAQ,EAAE,SAAS,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAAE,EAC5C,OAAO,EAAE,mBAAmB,EAC5B,aAAa,EAAE,MAAM,EACrB,UAAU,GAAE,SAAS,SAAS,EAAO,EACrC,SAAS,GAAE,iBAA6B,GACvC,OAAO,CAAC,kBAAkB,CAAC,CA2G7B;AAED,wBAAgB,SAAS,CAAC,OAAO,EAAE,SAAS,MAAM,EAAE,EAAE,KAAK,EAAE,CAAC,GAAG,CAAC,GAAG,MAAM,CAO1E;AA8FD,wBAAsB,mBAAmB,CACvC,OAAO,EAAE,mBAAmB,EAC5B,MAAM,EAAE,UAAU,EAClB,aAAa,EAAE,MAAM,GACpB,OAAO,CAAC,kBAAkB,CAAC,CAoD7B;AAGD,wBAAgB,yBAAyB,CAAC,KAAK,EAAE,mBAAmB,GAAG,IAAI,CA0C1E"}
1
+ {"version":3,"file":"intent-search.d.ts","sourceRoot":"","sources":["../src/intent-search.ts"],"names":[],"mappings":"AAKA,OAAO,EACL,KAAK,kBAAkB,EAIxB,MAAM,2CAA2C,CAAC;AACnD,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,sCAAsC,CAAC;AACvE,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,qBAAqB,CAAC;AAIvD,MAAM,MAAM,qBAAqB,GAC7B,QAAQ,GACR,SAAS,GACT,SAAS,GACT,aAAa,GACb,SAAS,CAAC;AAGd,MAAM,MAAM,kBAAkB,GAAG,QAAQ,CACvC,OAAO,CAAC,MAAM,CAAC,qBAAqB,EAAE,SAAS,MAAM,EAAE,CAAC,CAAC,CAC1D,CAAC;AAGF,MAAM,MAAM,cAAc,GAAG,QAAQ,CAAC;IACpC,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,MAAM,CAAC,EAAE,MAAM,CAAC;CACjB,CAAC,CAAC;AAGH,MAAM,MAAM,mBAAmB,GAAG,QAAQ,CAAC;IACzC,KAAK,EAAE,MAAM,CAAC;IACd,IAAI,CAAC,EAAE,CAAC,OAAO,kBAAkB,CAAC,CAAC,MAAM,CAAC,GAAG,MAAM,CAAC;IACpD,cAAc,CAAC,EAAE,kBAAkB,CAAC;IACpC,eAAe,CAAC,EAAE,SAAS,cAAc,EAAE,CAAC;IAC5C,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB,CAAC,CAAC;AAGH,MAAM,MAAM,iBAAiB,GAAG,QAAQ,CAAC;IACvC,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB,CAAC,CAAC;AAGH,MAAM,MAAM,eAAe,GAAG,QAAQ,CAAC;IACrC,IAAI,EAAE,MAAM,CAAC;IACb,aAAa,EAAE,SAAS,MAAM,EAAE,CAAC;IACjC,EAAE,EAAE,MAAM,CAAC;CACZ,CAAC,CAAC;AAGH,MAAM,MAAM,oBAAoB,GAAG,QAAQ,CAAC;IAC1C,eAAe,EAAE,MAAM,CAAC;IACxB,aAAa,EAAE,SAAS,MAAM,EAAE,CAAC;IACjC,aAAa,EAAE,SAAS,iBAAiB,EAAE,CAAC;IAC5C,UAAU,EAAE,SAAS,eAAe,EAAE,CAAC;IACvC,kBAAkB,EAAE,OAAO,CAAC;CAC7B,CAAC,CAAC;AAGH,MAAM,MAAM,iBAAiB,GAAG,WAAW,GAAG;IAC5C,QAAQ,CAAC,QAAQ,EAAE,oBAAoB,CAAC;CACzC,CAAC;AAGF,MAAM,MAAM,oBAAoB,GAAG,QAAQ,CAAC;IAC1C,WAAW,EAAE,WAAW,CAAC;IACzB,cAAc,EAAE,MAAM,CAAC;IACvB,aAAa,EAAE,MAAM,CAAC;IACtB,QAAQ,EAAE,MAAM,GAAG,IAAI,CAAC;IACxB,YAAY,EAAE,MAAM,GAAG,IAAI,CAAC;IAC5B;;;;;OAKG;IACH,cAAc,EAAE,MAAM,GAAG,IAAI,CAAC;IAC9B,SAAS,EAAE,OAAO,CAAC;IACnB,SAAS,EAAE,OAAO,CAAC;CACpB,CAAC,CAAC;AAGH,MAAM,MAAM,kBAAkB,GAAG,QAAQ,CAAC;IACxC,OAAO,EAAE,SAAS,iBAAiB,EAAE,CAAC;IACtC,QAAQ,EAAE,oBAAoB,CAAC;CAChC,CAAC,CAAC;AAEH,KAAK,SAAS,GAAG,QAAQ,CAAC;IACxB,YAAY,EAAE,MAAM,CAAC;IACrB,IAAI,EAAE,MAAM,CAAC;IACb,EAAE,EAAE,MAAM,CAAC;CACZ,CAAC,CAAC;AA2bH,2EAA2E;AAE3E,MAAM,MAAM,iBAAiB,GAAG,GAAG,CAAC,MAAM,EAAE,MAAM,GAAG,IAAI,CAAC,CAAC;AA8B3D,wBAAsB,kBAAkB,CACtC,QAAQ,EAAE,SAAS,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAAE,EAC5C,OAAO,EAAE,mBAAmB,EAC5B,aAAa,EAAE,MAAM,EACrB,UAAU,GAAE,SAAS,SAAS,EAAO,EACrC,SAAS,GAAE,iBAA6B,GACvC,OAAO,CAAC,kBAAkB,CAAC,CA8I7B;AAoCD,wBAAgB,SAAS,CAAC,OAAO,EAAE,SAAS,MAAM,EAAE,EAAE,KAAK,EAAE,CAAC,GAAG,CAAC,GAAG,MAAM,CAO1E;AA8FD,wBAAsB,mBAAmB,CACvC,OAAO,EAAE,mBAAmB,EAC5B,MAAM,EAAE,UAAU,EAClB,aAAa,EAAE,MAAM,GACpB,OAAO,CAAC,kBAAkB,CAAC,CAoD7B;AAGD,wBAAgB,yBAAyB,CAAC,KAAK,EAAE,mBAAmB,GAAG,IAAI,CA0C1E"}