@llblab/pi-kit 0.37.0 → 0.38.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 (152) hide show
  1. package/CHANGELOG.md +10 -0
  2. package/README.md +3 -3
  3. package/node_modules/@llblab/pi-state-flow/AGENTS.md +7 -3
  4. package/node_modules/@llblab/pi-state-flow/BACKLOG.md +679 -2
  5. package/node_modules/@llblab/pi-state-flow/CHANGELOG.md +17 -0
  6. package/node_modules/@llblab/pi-state-flow/README.md +30 -14
  7. package/node_modules/@llblab/pi-state-flow/api/modules.ts +11 -0
  8. package/node_modules/@llblab/pi-state-flow/dist/api/modules.d.ts +3 -0
  9. package/node_modules/@llblab/pi-state-flow/dist/api/modules.js +3 -0
  10. package/node_modules/@llblab/pi-state-flow/dist/lib/acquisition.d.ts +7 -4
  11. package/node_modules/@llblab/pi-state-flow/dist/lib/acquisition.js +77 -36
  12. package/node_modules/@llblab/pi-state-flow/dist/lib/artifact.d.ts +2 -0
  13. package/node_modules/@llblab/pi-state-flow/dist/lib/artifact.js +26 -27
  14. package/node_modules/@llblab/pi-state-flow/dist/lib/config.d.ts +3 -0
  15. package/node_modules/@llblab/pi-state-flow/dist/lib/config.js +13 -1
  16. package/node_modules/@llblab/pi-state-flow/dist/lib/context.d.ts +27 -21
  17. package/node_modules/@llblab/pi-state-flow/dist/lib/context.js +144 -46
  18. package/node_modules/@llblab/pi-state-flow/dist/lib/continuation.js +14 -18
  19. package/node_modules/@llblab/pi-state-flow/dist/lib/durable.d.ts +6 -0
  20. package/node_modules/@llblab/pi-state-flow/dist/lib/durable.js +60 -50
  21. package/node_modules/@llblab/pi-state-flow/dist/lib/extension.js +1049 -310
  22. package/node_modules/@llblab/pi-state-flow/dist/lib/history.d.ts +4 -4
  23. package/node_modules/@llblab/pi-state-flow/dist/lib/history.js +15 -3
  24. package/node_modules/@llblab/pi-state-flow/dist/lib/json.d.ts +2 -0
  25. package/node_modules/@llblab/pi-state-flow/dist/lib/json.js +2 -1
  26. package/node_modules/@llblab/pi-state-flow/dist/lib/memory.d.ts +3 -1
  27. package/node_modules/@llblab/pi-state-flow/dist/lib/memory.js +7 -7
  28. package/node_modules/@llblab/pi-state-flow/dist/lib/migration.d.ts +29 -0
  29. package/node_modules/@llblab/pi-state-flow/dist/lib/migration.js +186 -0
  30. package/node_modules/@llblab/pi-state-flow/dist/lib/model-interface.d.ts +17 -0
  31. package/node_modules/@llblab/pi-state-flow/dist/lib/model-interface.js +158 -0
  32. package/node_modules/@llblab/pi-state-flow/dist/lib/module-registry.d.ts +21 -0
  33. package/node_modules/@llblab/pi-state-flow/dist/lib/module-registry.js +108 -0
  34. package/node_modules/@llblab/pi-state-flow/dist/lib/operation.js +3 -2
  35. package/node_modules/@llblab/pi-state-flow/dist/lib/ownership.d.ts +4 -4
  36. package/node_modules/@llblab/pi-state-flow/dist/lib/ownership.js +5 -5
  37. package/node_modules/@llblab/pi-state-flow/dist/lib/planes.d.ts +29 -0
  38. package/node_modules/@llblab/pi-state-flow/dist/lib/planes.js +84 -0
  39. package/node_modules/@llblab/pi-state-flow/dist/lib/protocol.d.ts +6 -3
  40. package/node_modules/@llblab/pi-state-flow/dist/lib/protocol.js +33 -16
  41. package/node_modules/@llblab/pi-state-flow/dist/lib/query.d.ts +21 -4
  42. package/node_modules/@llblab/pi-state-flow/dist/lib/query.js +53 -13
  43. package/node_modules/@llblab/pi-state-flow/dist/lib/recovery.js +5 -2
  44. package/node_modules/@llblab/pi-state-flow/dist/lib/rehydration.d.ts +3 -0
  45. package/node_modules/@llblab/pi-state-flow/dist/lib/rehydration.js +10 -1
  46. package/node_modules/@llblab/pi-state-flow/dist/lib/runtime.d.ts +84 -5
  47. package/node_modules/@llblab/pi-state-flow/dist/lib/runtime.js +570 -20
  48. package/node_modules/@llblab/pi-state-flow/dist/lib/selection.d.ts +10 -0
  49. package/node_modules/@llblab/pi-state-flow/dist/lib/selection.js +32 -0
  50. package/node_modules/@llblab/pi-state-flow/dist/lib/semantic-module.d.ts +79 -0
  51. package/node_modules/@llblab/pi-state-flow/dist/lib/semantic-module.js +187 -0
  52. package/node_modules/@llblab/pi-state-flow/dist/lib/session.d.ts +98 -1
  53. package/node_modules/@llblab/pi-state-flow/dist/lib/session.js +398 -3
  54. package/node_modules/@llblab/pi-state-flow/dist/lib/skills.d.ts +7 -2
  55. package/node_modules/@llblab/pi-state-flow/dist/lib/skills.js +55 -3
  56. package/node_modules/@llblab/pi-state-flow/dist/lib/snapshot.d.ts +67 -14
  57. package/node_modules/@llblab/pi-state-flow/dist/lib/snapshot.js +129 -9
  58. package/node_modules/@llblab/pi-state-flow/dist/lib/state.d.ts +26 -14
  59. package/node_modules/@llblab/pi-state-flow/dist/lib/state.js +61 -19
  60. package/node_modules/@llblab/pi-state-flow/dist/lib/status.d.ts +14 -9
  61. package/node_modules/@llblab/pi-state-flow/dist/lib/status.js +59 -22
  62. package/node_modules/@llblab/pi-state-flow/dist/lib/storage.d.ts +111 -10
  63. package/node_modules/@llblab/pi-state-flow/dist/lib/storage.js +728 -11
  64. package/node_modules/@llblab/pi-state-flow/dist/lib/telegram.d.ts +10 -7
  65. package/node_modules/@llblab/pi-state-flow/dist/lib/telegram.js +50 -14
  66. package/node_modules/@llblab/pi-state-flow/dist/lib/temporal.d.ts +40 -4
  67. package/node_modules/@llblab/pi-state-flow/dist/lib/temporal.js +247 -43
  68. package/node_modules/@llblab/pi-state-flow/dist/lib/transition.d.ts +41 -8
  69. package/node_modules/@llblab/pi-state-flow/dist/lib/transition.js +132 -39
  70. package/node_modules/@llblab/pi-state-flow/dist/package.json +6 -1
  71. package/node_modules/@llblab/pi-state-flow/dist/skills/state-flow-guide/SKILL.md +28 -16
  72. package/node_modules/@llblab/pi-state-flow/dist/skills/state-flow-memory/SKILL.md +12 -8
  73. package/node_modules/@llblab/pi-state-flow/docs/README.md +9 -0
  74. package/node_modules/@llblab/pi-state-flow/docs/architecture.md +76 -43
  75. package/node_modules/@llblab/pi-state-flow/docs/compatibility.md +9 -1
  76. package/node_modules/@llblab/pi-state-flow/docs/fork-contract.md +6 -0
  77. package/node_modules/@llblab/pi-state-flow/docs/lazy-state.md +23 -19
  78. package/node_modules/@llblab/pi-state-flow/docs/protocol-composition-decision.md +66 -0
  79. package/node_modules/@llblab/pi-state-flow/docs/public-module-contract.md +73 -0
  80. package/node_modules/@llblab/pi-state-flow/docs/scope-selection-contract.md +814 -0
  81. package/node_modules/@llblab/pi-state-flow/docs/semantic-compatibility-decision.md +212 -0
  82. package/node_modules/@llblab/pi-state-flow/docs/semantic-extensibility-decision.md +75 -0
  83. package/node_modules/@llblab/pi-state-flow/docs/semantic-handoff-contract.md +174 -0
  84. package/node_modules/@llblab/pi-state-flow/docs/semantic-memory-evaluation.md +166 -0
  85. package/node_modules/@llblab/pi-state-flow/docs/semantic-module-contract.md +84 -0
  86. package/node_modules/@llblab/pi-state-flow/docs/single-scope-interface-contract.md +201 -0
  87. package/node_modules/@llblab/pi-state-flow/docs/temporal-acceptance.md +22 -1
  88. package/node_modules/@llblab/pi-state-flow/docs/usage.md +32 -18
  89. package/node_modules/@llblab/pi-state-flow/lib/acquisition.ts +68 -31
  90. package/node_modules/@llblab/pi-state-flow/lib/artifact.ts +21 -22
  91. package/node_modules/@llblab/pi-state-flow/lib/config.ts +14 -1
  92. package/node_modules/@llblab/pi-state-flow/lib/context.ts +142 -46
  93. package/node_modules/@llblab/pi-state-flow/lib/continuation.ts +14 -17
  94. package/node_modules/@llblab/pi-state-flow/lib/durable.ts +53 -44
  95. package/node_modules/@llblab/pi-state-flow/lib/extension.ts +897 -297
  96. package/node_modules/@llblab/pi-state-flow/lib/history.ts +16 -7
  97. package/node_modules/@llblab/pi-state-flow/lib/json.ts +2 -1
  98. package/node_modules/@llblab/pi-state-flow/lib/memory.ts +10 -9
  99. package/node_modules/@llblab/pi-state-flow/lib/migration.ts +189 -0
  100. package/node_modules/@llblab/pi-state-flow/lib/model-interface.ts +136 -0
  101. package/node_modules/@llblab/pi-state-flow/lib/module-registry.ts +119 -0
  102. package/node_modules/@llblab/pi-state-flow/lib/operation.ts +3 -2
  103. package/node_modules/@llblab/pi-state-flow/lib/ownership.ts +6 -6
  104. package/node_modules/@llblab/pi-state-flow/lib/planes.ts +98 -0
  105. package/node_modules/@llblab/pi-state-flow/lib/protocol.ts +37 -16
  106. package/node_modules/@llblab/pi-state-flow/lib/query.ts +59 -18
  107. package/node_modules/@llblab/pi-state-flow/lib/recovery.ts +5 -2
  108. package/node_modules/@llblab/pi-state-flow/lib/rehydration.ts +10 -1
  109. package/node_modules/@llblab/pi-state-flow/lib/runtime.ts +574 -21
  110. package/node_modules/@llblab/pi-state-flow/lib/selection.ts +39 -0
  111. package/node_modules/@llblab/pi-state-flow/lib/semantic-module.ts +239 -0
  112. package/node_modules/@llblab/pi-state-flow/lib/session.ts +387 -3
  113. package/node_modules/@llblab/pi-state-flow/lib/skills.ts +45 -4
  114. package/node_modules/@llblab/pi-state-flow/lib/snapshot.ts +156 -16
  115. package/node_modules/@llblab/pi-state-flow/lib/state.ts +69 -28
  116. package/node_modules/@llblab/pi-state-flow/lib/status.ts +65 -31
  117. package/node_modules/@llblab/pi-state-flow/lib/storage.ts +770 -18
  118. package/node_modules/@llblab/pi-state-flow/lib/telegram.ts +58 -20
  119. package/node_modules/@llblab/pi-state-flow/lib/temporal.ts +267 -50
  120. package/node_modules/@llblab/pi-state-flow/lib/transition.ts +184 -52
  121. package/node_modules/@llblab/pi-state-flow/package.json +6 -1
  122. package/node_modules/@llblab/pi-state-flow/skills/state-flow-guide/SKILL.md +28 -16
  123. package/node_modules/@llblab/pi-state-flow/skills/state-flow-memory/SKILL.md +12 -8
  124. package/node_modules/@llblab/pi-telegram/AGENTS.md +1 -1
  125. package/node_modules/@llblab/pi-telegram/BACKLOG.md +8 -10
  126. package/node_modules/@llblab/pi-telegram/CHANGELOG.md +10 -0
  127. package/node_modules/@llblab/pi-telegram/dist/lib/outbound-buttons.js +20 -18
  128. package/node_modules/@llblab/pi-telegram/dist/lib/outbound-markup.d.ts +6 -6
  129. package/node_modules/@llblab/pi-telegram/dist/lib/outbound-markup.js +23 -65
  130. package/node_modules/@llblab/pi-telegram/dist/lib/outbound.js +3 -3
  131. package/node_modules/@llblab/pi-telegram/dist/lib/prompts.d.ts +1 -1
  132. package/node_modules/@llblab/pi-telegram/dist/lib/prompts.js +1 -1
  133. package/node_modules/@llblab/pi-telegram/dist/lib/runtime.d.ts +1 -0
  134. package/node_modules/@llblab/pi-telegram/dist/lib/runtime.js +1 -0
  135. package/node_modules/@llblab/pi-telegram/dist/lib/telegram-api.d.ts +4 -2
  136. package/node_modules/@llblab/pi-telegram/dist/lib/telegram-api.js +24 -13
  137. package/node_modules/@llblab/pi-telegram/dist/package.json +1 -1
  138. package/node_modules/@llblab/pi-telegram/dist/skills/telegram-bridge/SKILL.md +5 -5
  139. package/node_modules/@llblab/pi-telegram/docs/architecture.md +5 -5
  140. package/node_modules/@llblab/pi-telegram/docs/compact-matrix-literal.md +1 -1
  141. package/node_modules/@llblab/pi-telegram/docs/generative-apps.md +1 -1
  142. package/node_modules/@llblab/pi-telegram/docs/outbound.md +8 -8
  143. package/node_modules/@llblab/pi-telegram/docs/public-api.md +2 -2
  144. package/node_modules/@llblab/pi-telegram/lib/outbound-buttons.ts +17 -15
  145. package/node_modules/@llblab/pi-telegram/lib/outbound-markup.ts +28 -68
  146. package/node_modules/@llblab/pi-telegram/lib/outbound.ts +3 -3
  147. package/node_modules/@llblab/pi-telegram/lib/prompts.ts +1 -1
  148. package/node_modules/@llblab/pi-telegram/lib/runtime.ts +2 -1
  149. package/node_modules/@llblab/pi-telegram/lib/telegram-api.ts +25 -12
  150. package/node_modules/@llblab/pi-telegram/package.json +1 -1
  151. package/node_modules/@llblab/pi-telegram/skills/telegram-bridge/SKILL.md +5 -5
  152. package/package.json +3 -3
@@ -1,24 +1,27 @@
1
1
  import type { StateFlowMode } from "./snapshot.ts";
2
2
  import type { ScopeRevisions } from "./temporal.ts";
3
+ import { type ScopeSelection } from "./selection.ts";
3
4
  export declare const STATE_FLOW_TELEGRAM_ID = "@llblab/pi-state-flow";
4
5
  /** Resolve the package export or the compiled sibling-extension layout used in local development. */
5
6
  export declare function stateFlowTelegramSectionSpecifiers(moduleUrl?: string): string[];
6
7
  export interface StateFlowTelegramSnapshot {
7
8
  /** The current session's selected mode. */
8
9
  mode: StateFlowMode;
10
+ /** Wanted participating owners, not currently available bodies; omitted legacy ports retain all three. */
11
+ scopes?: ScopeSelection;
9
12
  /** Failed Active restoration fences inference without silently selecting an inactive mode. */
10
13
  inferenceBlocked?: boolean;
11
14
  /** Legacy branch step retained for existing adapter ports; current runtime ports also supply owner revisions. */
12
15
  step: number;
13
- revisions?: ScopeRevisions;
16
+ revisions?: Partial<ScopeRevisions>;
14
17
  bootstrap: boolean;
15
18
  startPending: boolean;
16
19
  }
17
20
  export type StateFlowTelegramScope = "global" | "cwd" | "session" | "effective";
18
21
  export interface StateFlowTelegramState {
19
22
  artifacts?: Record<string, unknown>;
20
- contract?: Record<string, unknown>;
21
- working?: Record<string, unknown>;
23
+ strategy?: Record<string, unknown>;
24
+ tactics?: Record<string, unknown>;
22
25
  intents?: Record<string, unknown>;
23
26
  response?: string;
24
27
  lazy?: unknown;
@@ -87,7 +90,7 @@ export interface StateFlowTelegramControlResult {
87
90
  }
88
91
  export interface StateFlowTelegramInspection {
89
92
  state: StateFlowTelegramState;
90
- revisions: ScopeRevisions;
93
+ revisions: Partial<ScopeRevisions>;
91
94
  /** A selection can revoke a completed observation before the adapter presents it. */
92
95
  signal?: AbortSignal;
93
96
  }
@@ -95,7 +98,7 @@ export interface StateFlowTelegramPort {
95
98
  snapshot(): StateFlowTelegramSnapshot;
96
99
  state(scope: StateFlowTelegramScope): StateFlowTelegramState;
97
100
  /** Optional additive capability; absent legacy ports retain their branch-step presentation. */
98
- revisions?(): ScopeRevisions;
101
+ revisions?(): Partial<ScopeRevisions>;
99
102
  /** Active may need a settled native boundary; inactive modes apply immediately. */
100
103
  canStartNow(): boolean;
101
104
  /** Select the current session's mode through the same lifecycle owners as the terminal commands. */
@@ -114,9 +117,9 @@ export interface StateFlowTelegramAdapter {
114
117
  /** Main-menu section label shows only the current session mode. */
115
118
  export declare function formatStateFlowSectionLabel(snapshot: StateFlowTelegramSnapshot): string;
116
119
  export declare const STATE_FLOW_MODES: readonly ["off", "passive", "active"];
117
- /** One radio-style mode row followed directly by read-only scope actions. */
120
+ /** One radio-style mode row followed by the current participating owners' read-only actions. */
118
121
  export declare function buildStateFlowSectionView(snapshot: StateFlowTelegramSnapshot, callbackData: (action: string, payload?: string) => string): StateFlowTelegramView;
119
- export declare function renderStateFlowRichState(scope: StateFlowTelegramScope, revisions: ScopeRevisions, state: StateFlowTelegramState): StateFlowTelegramRichMessage;
122
+ export declare function renderStateFlowRichState(scope: StateFlowTelegramScope, revisions: Partial<ScopeRevisions>, state: StateFlowTelegramState): StateFlowTelegramRichMessage;
120
123
  /** Default loader; injectable so tests and embedded hosts can control transport presence. */
121
124
  export declare function loadStateFlowTelegramModules(): Promise<StateFlowTelegramModules>;
122
125
  export declare function createStateFlowTelegramAdapter(options: {
@@ -12,6 +12,7 @@ var __rewriteRelativeImportExtension = (this && this.__rewriteRelativeImportExte
12
12
  };
13
13
  import { conciseDiagnostic, diagnosticText } from "./protocol.js";
14
14
  import { formatScopeRevisionVector } from "./status.js";
15
+ import { captureScopeSelection, DEFAULT_SCOPE_SELECTION } from "./selection.js";
15
16
  export const STATE_FLOW_TELEGRAM_ID = "@llblab/pi-state-flow";
16
17
  /** Resolve the package export or the compiled sibling-extension layout used in local development. */
17
18
  export function stateFlowTelegramSectionSpecifiers(moduleUrl = import.meta.url) {
@@ -35,8 +36,28 @@ function modeReceiptNotice(mode, result) {
35
36
  return undefined;
36
37
  return result.message;
37
38
  }
38
- /** One radio-style mode row followed directly by read-only scope actions. */
39
+ function telegramScopes(snapshot) {
40
+ return captureScopeSelection(snapshot.scopes === undefined ? DEFAULT_SCOPE_SELECTION : snapshot.scopes);
41
+ }
42
+ function availableInspection(scope, scopes) {
43
+ return scope === "effective" ? scopes.length > 1 : scopes.includes(scope);
44
+ }
45
+ const STATE_FLOW_SCOPE_DESCRIPTIONS = {
46
+ global: "memory shared across projects and sessions.",
47
+ cwd: "memory shared by sessions in this directory.",
48
+ session: "private memory for this session, kept on resume.",
49
+ };
50
+ /** One radio-style mode row followed by the current participating owners' read-only actions. */
39
51
  export function buildStateFlowSectionView(snapshot, callbackData) {
52
+ const scopes = telegramScopes(snapshot);
53
+ const inspected = [...scopes, ...(scopes.length > 1 ? ["effective"] : [])];
54
+ const inspectionRows = [];
55
+ for (const [index, scope] of inspected.entries()) {
56
+ if (index % 2 === 0)
57
+ inspectionRows.push([]);
58
+ inspectionRows.at(-1).push({ text: STATE_FLOW_SCOPE_LABELS[scope], callback_data: callbackData("inspect", scope) });
59
+ }
60
+ const named = scopes.map(scope => `<code>${scope}</code>`).join(" → ");
40
61
  const modes = STATE_FLOW_MODES.map((mode) => ({
41
62
  text: `${mode === snapshot.mode ? STATE_FLOW_SELECTED_MARKERS[mode] : "⚫️"} ${STATE_FLOW_MODE_LABELS[mode]}`,
42
63
  callback_data: callbackData(mode),
@@ -52,22 +73,23 @@ export function buildStateFlowSectionView(snapshot, callbackData) {
52
73
  "<b>Mode</b> — choose a workflow (switching modes never erases stored memory):",
53
74
  "",
54
75
  "<code>-</code> <code>off</code> (default): regular chat without State Flow memory tools or context.",
55
- "<code>-</code> <code>passive</code>: regular chat with memory tools; available combined memory enters the agent's context.",
76
+ `<code>-</code> <code>passive</code>: regular chat with memory tools; available memory from the selected ${scopes.length === 1 ? "scope" : "scopes"} enters the agent's context.`,
56
77
  "<code>-</code> <code>active</code>: same memory access; each completed answer closes a cycle, and the next request starts from saved state, not the full chat.",
57
78
  "",
58
- "<b>Inspect memory</b> — view stored state even in Off:",
79
+ `<b>Participating scopes:</b> ${named}`,
80
+ ...(!scopes.includes("session") ? ["New answers are delivered, not stored: Session is excluded."] : []),
81
+ "",
82
+ "<b>Inspect participating memory</b> — view available stored state even in Off:",
59
83
  "",
60
- "<code>-</code> <code>global</code>: memory shared across projects and sessions.",
61
- "<code>-</code> <code>cwd</code>: memory shared by sessions in this directory.",
62
- "<code>-</code> <code>session</code>: private memory for this session, kept on resume.",
63
- "<code>-</code> <code>effective</code>: merged Global, CWD and Session state; the agent can use it when memory is enabled and available.",
84
+ ...scopes.map(scope => `<code>-</code> <code>${scope}</code>: ${STATE_FLOW_SCOPE_DESCRIPTIONS[scope]}`),
85
+ ...(scopes.length > 1
86
+ ? [`<code>-</code> <code>effective</code>: validated available ${named} overlay; excluded scopes do not contribute.`]
87
+ : ["This single scope is also the agent's effective state; no separate overlay is needed."]),
64
88
  ].join("\n"),
65
89
  parseMode: "html",
66
90
  replyMarkup: { inline_keyboard: [
67
91
  modes,
68
- ...[["global", "cwd"], ["session", "effective"]].map((row) => row.map((scope) => ({
69
- text: STATE_FLOW_SCOPE_LABELS[scope], callback_data: callbackData("inspect", scope),
70
- }))),
92
+ ...inspectionRows,
71
93
  ] },
72
94
  };
73
95
  }
@@ -106,10 +128,10 @@ function renderStateFlowTelegramField(value) {
106
128
  }
107
129
  export function renderStateFlowRichState(scope, revisions, state) {
108
130
  const fields = scope === "global" || scope === "cwd"
109
- ? ["intents", "contract", "working", "artifacts", "lazy"]
110
- : ["intents", "contract", "working", "artifacts", "response", "lazy"];
131
+ ? ["intents", "strategy", "tactics", "artifacts", "lazy"]
132
+ : ["intents", "strategy", "tactics", "artifacts", "response", "lazy"];
111
133
  const revision = scope === "effective"
112
- ? formatScopeRevisionVector(revisions)
134
+ ? formatScopeRevisionVector(revisions, captureScopeSelection(Object.keys(revisions)))
113
135
  : `#${revisions[scope]}`;
114
136
  return {
115
137
  blocks: [
@@ -149,10 +171,20 @@ function buildStateFlowTelegramSection(port, isActive) {
149
171
  if (ctx.action === "inspect") {
150
172
  if (!isStateFlowTelegramScope(ctx.payload))
151
173
  throw new Error("Unknown State Flow scope");
174
+ const scopes = telegramScopes(port.snapshot());
175
+ if (!availableInspection(ctx.payload, scopes))
176
+ throw new Error(ctx.payload === "effective"
177
+ ? "Effective requires at least two participating scopes; inspect the single owner instead"
178
+ : `State Flow ${ctx.payload} scope is excluded from this menu`);
179
+ const checkSelection = () => {
180
+ if (telegramScopes(port.snapshot()).join(" ") !== scopes.join(" "))
181
+ throw new Error("State Flow inspection selection changed; select the scope again");
182
+ };
152
183
  let observation;
153
184
  if ("inspect" in port) {
154
185
  await ctx.answerCallback("Reading State Flow memory");
155
186
  acknowledged = true;
187
+ checkSelection();
156
188
  observation = await port.inspect(ctx.payload);
157
189
  }
158
190
  else {
@@ -161,9 +193,13 @@ function buildStateFlowTelegramSection(port, isActive) {
161
193
  observation = { state, revisions: port.revisions?.() ?? live.revisions ?? { global: live.step, cwd: live.step, session: live.step } };
162
194
  }
163
195
  observation.signal?.throwIfAborted();
196
+ checkSelection();
164
197
  if (request !== interaction || !isActive())
165
198
  return "handled";
166
- await ctx.openRich(renderStateFlowRichState(ctx.payload, observation.revisions, observation.state));
199
+ const revisions = ctx.payload === "effective"
200
+ ? Object.fromEntries(scopes.filter(scope => Object.hasOwn(observation.revisions, scope)).map(scope => [scope, observation.revisions[scope]]))
201
+ : observation.revisions;
202
+ await ctx.openRich(renderStateFlowRichState(ctx.payload, revisions, observation.state));
167
203
  if (!acknowledged)
168
204
  await ctx.answerCallback();
169
205
  return "handled";
@@ -1,4 +1,6 @@
1
+ import { type ScopeSelection } from "./selection.ts";
1
2
  import { type RecentScopePatch } from "./history.ts";
3
+ import { type RetainedModules } from "./semantic-module.ts";
2
4
  import { type MaterializedState, type SemanticState, type ScopedSemanticStates, type StateScope } from "./state.ts";
3
5
  /** Owns hot temporal algebra; excludes filesystem, Git, identity allocation, and Pi lifecycle. */
4
6
  export interface TransitionBoundary {
@@ -16,6 +18,8 @@ export interface TemporalPatch {
16
18
  patch: RecentScopePatch["patch"];
17
19
  }
18
20
  export interface ScopeStream {
21
+ /** Presence selects metadata4; absent preserves the legacy exact three-key stream. */
22
+ modules?: RetainedModules;
19
23
  /** Monotonic semantic revision owned by this scope; independent of branch-local boundary positions. */
20
24
  revision: number;
21
25
  checkpoint: ScopeCheckpoint;
@@ -26,27 +30,59 @@ export interface TemporalState {
26
30
  lineage: TransitionBoundary[];
27
31
  scopes: Record<StateScope, ScopeStream>;
28
32
  }
33
+ /** Value-only witnesses copied from a validated cohort; not physical store/publication authority. */
34
+ export interface ExcludedTransitionWitness {
35
+ transition: TransitionBoundary;
36
+ owners: ScopeSelection;
37
+ }
38
+ export interface SelectedTemporalState {
39
+ selection: ScopeSelection;
40
+ lineage: TransitionBoundary[];
41
+ scopes: Partial<Record<StateScope, ScopeStream>>;
42
+ /** Only excluded-owner witnesses for retained steps with no selected semantic patch. No values or patches. */
43
+ causalBasis: ExcludedTransitionWitness[];
44
+ }
45
+ type TemporalCohort = TemporalState | SelectedTemporalState;
29
46
  export type ScopeRevisions = Record<StateScope, number>;
30
47
  /** Replay validation is shared by disk codecs and active-lineage materialization. */
31
48
  export declare function validateScopeStream(value: unknown, scope: StateScope, historyLimit?: number): asserts value is ScopeStream;
32
49
  export declare function validateTemporalLineage(value: unknown, historyLimit?: number): asserts value is TransitionBoundary[];
33
50
  /** Bind one owned stream to its runtime lineage without requiring patches from unrelated scopes. */
34
51
  export declare function validateScopeLineage(stream: ScopeStream, scope: StateScope, lineage: readonly TransitionBoundary[], historyLimit?: number): void;
52
+ /** Classify live shared drift only after both stream and lineage have passed their own validators. */
53
+ export declare function scopeLineageMatches(stream: ScopeStream, scope: StateScope, lineage: readonly TransitionBoundary[], historyLimit?: number): boolean;
35
54
  /** Validate one revision-selected cohort. Its older ancestry must be bound by the durable loader. */
36
55
  export declare function validateTemporalState(view: TemporalState, historyLimit?: number): void;
56
+ /** Structural consistency only: storage must additionally bind witnesses to accepted source authority. */
57
+ export declare function validateSelectedTemporalState(view: SelectedTemporalState, historyLimit?: number): void;
37
58
  /** Adopt revision-proven inherited streams without rewriting their checkpoints or tails. */
38
59
  export declare function adoptTemporalStreams(scopes: Record<StateScope, ScopeStream>, id: string, historyLimit?: number): TemporalState;
39
60
  /** New or migrated state starts at a proven current boundary, with no invented past. */
40
61
  export declare function createTemporalState(states: ScopedSemanticStates, id: string, historyLimit?: number): TemporalState;
62
+ /** Restrict a validated value cohort; expanding selection requires separately acquired current streams. */
63
+ export declare function selectTemporalState(source: TemporalCohort, selection: ScopeSelection, historyLimit?: number): SelectedTemporalState;
64
+ /** Complete retained witness skeleton, derived from validated semantic records/basis, never from lineage alone. */
65
+ export declare function temporalCausalWitnesses(view: TemporalCohort, historyLimit?: number): ExcludedTransitionWitness[];
66
+ /** Metadata syntax only; a skeleton is neither semantic replay nor acquisition/publication authority. */
67
+ export declare function captureTemporalWitnesses(lineage: readonly TransitionBoundary[], witnesses: unknown, historyLimit?: number): ExcludedTransitionWitness[];
68
+ /** Reconstruct selected values from caller-bound accepted evidence; this validates syntax/consistency, not physical authority. */
69
+ export declare function restoreSelectedTemporalState(scopes: Partial<Record<StateScope, ScopeStream>>, selection: ScopeSelection, lineage: readonly TransitionBoundary[], witnesses: unknown, historyLimit?: number): SelectedTemporalState;
70
+ /** Explicit selected values at a new origin; this constructor grants no initialization/acquisition permission. */
71
+ export declare function createSelectedTemporalState(states: Partial<ScopedSemanticStates>, selection: ScopeSelection, id: string, historyLimit?: number): SelectedTemporalState;
72
+ /** Adopt explicitly admitted selected streams at current values only, without invented aligned history. */
73
+ export declare function adoptSelectedTemporalStreams(scopes: Partial<Record<StateScope, ScopeStream>>, selection: ScopeSelection, id: string, historyLimit?: number): SelectedTemporalState;
41
74
  /** Fold retained tails to a lower configured limit without inventing history. */
42
- export declare function constrainTemporalState(view: TemporalState, historyLimit: number): TemporalState;
75
+ export declare function constrainTemporalState<T extends TemporalCohort>(view: T, historyLimit: number): T;
43
76
  /** Current independent scope revisions; Effective uses this vector rather than inventing a scalar owner. */
44
77
  export declare function temporalScopeRevisions(view: TemporalState): ScopeRevisions;
78
+ export declare function temporalScopeRevisions(view: SelectedTemporalState): Partial<ScopeRevisions>;
45
79
  /** Exact scope semantics for authored staging; defaults must never become implicit writes. */
46
80
  export declare function readTemporalScopes(view: TemporalState, offset?: number, historyLimit?: number): ScopedSemanticStates;
81
+ export declare function readTemporalScopes(view: SelectedTemporalState, offset?: number, historyLimit?: number): Partial<ScopedSemanticStates>;
47
82
  /** Sparse current/historical view: unknown planes and absent values never become effective data. */
48
- export declare function readTemporalView(view: TemporalState, offset?: number, scope?: StateScope, historyLimit?: number): SemanticState;
83
+ export declare function readTemporalView(view: TemporalCohort, offset?: number, scope?: StateScope, historyLimit?: number): SemanticState;
49
84
  /** Internal defaulted materialization for consumers that require object registries. */
50
- export declare function readTemporalState(view: TemporalState, offset?: number, scope?: StateScope, historyLimit?: number): MaterializedState;
85
+ export declare function readTemporalState(view: TemporalCohort, offset?: number, scope?: StateScope, historyLimit?: number): MaterializedState;
51
86
  /** Allocate the identity outside this algebra; only materially effective patches accept it. */
52
- export declare function advanceTemporalState(view: TemporalState, transitions: readonly RecentScopePatch[], id: string, historyLimit?: number): TemporalState;
87
+ export declare function advanceTemporalState<T extends TemporalCohort>(view: T, transitions: readonly RecentScopePatch[], id: string, historyLimit?: number): T;
88
+ export {};