@brainpilot/runtime 0.0.5 → 0.0.6

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 (74) hide show
  1. package/README.md +61 -0
  2. package/dist/agent-error.d.ts +51 -0
  3. package/dist/agent-error.d.ts.map +1 -0
  4. package/dist/agent-error.js +163 -0
  5. package/dist/agent-error.js.map +1 -0
  6. package/dist/agent-factory.d.ts.map +1 -1
  7. package/dist/agent-factory.js +36 -6
  8. package/dist/agent-factory.js.map +1 -1
  9. package/dist/events.d.ts +18 -0
  10. package/dist/events.d.ts.map +1 -1
  11. package/dist/events.js +24 -0
  12. package/dist/events.js.map +1 -1
  13. package/dist/extensions/agent-status.d.ts +91 -0
  14. package/dist/extensions/agent-status.d.ts.map +1 -0
  15. package/dist/extensions/agent-status.js +103 -0
  16. package/dist/extensions/agent-status.js.map +1 -0
  17. package/dist/extensions/trace-reminder.d.ts +94 -0
  18. package/dist/extensions/trace-reminder.d.ts.map +1 -0
  19. package/dist/extensions/trace-reminder.js +153 -0
  20. package/dist/extensions/trace-reminder.js.map +1 -0
  21. package/dist/index.d.ts +2 -0
  22. package/dist/index.d.ts.map +1 -1
  23. package/dist/index.js +1 -0
  24. package/dist/index.js.map +1 -1
  25. package/dist/mailbox.d.ts +37 -1
  26. package/dist/mailbox.d.ts.map +1 -1
  27. package/dist/mailbox.js +79 -2
  28. package/dist/mailbox.js.map +1 -1
  29. package/dist/mas-agent.d.ts +74 -12
  30. package/dist/mas-agent.d.ts.map +1 -1
  31. package/dist/mas-agent.js +158 -33
  32. package/dist/mas-agent.js.map +1 -1
  33. package/dist/materialize-skills.d.ts +40 -0
  34. package/dist/materialize-skills.d.ts.map +1 -0
  35. package/dist/materialize-skills.js +141 -0
  36. package/dist/materialize-skills.js.map +1 -0
  37. package/dist/mock-agent.d.ts.map +1 -1
  38. package/dist/mock-agent.js +13 -1
  39. package/dist/mock-agent.js.map +1 -1
  40. package/dist/personas.d.ts +16 -0
  41. package/dist/personas.d.ts.map +1 -1
  42. package/dist/personas.js +651 -8
  43. package/dist/personas.js.map +1 -1
  44. package/dist/pi-provider.d.ts +5 -0
  45. package/dist/pi-provider.d.ts.map +1 -1
  46. package/dist/pi-provider.js +7 -1
  47. package/dist/pi-provider.js.map +1 -1
  48. package/dist/provider-config.d.ts +5 -0
  49. package/dist/provider-config.d.ts.map +1 -1
  50. package/dist/provider-config.js +2 -0
  51. package/dist/provider-config.js.map +1 -1
  52. package/dist/server.d.ts +2 -2
  53. package/dist/server.d.ts.map +1 -1
  54. package/dist/server.js +82 -8
  55. package/dist/server.js.map +1 -1
  56. package/dist/session-manager.d.ts +311 -8
  57. package/dist/session-manager.d.ts.map +1 -1
  58. package/dist/session-manager.js +896 -39
  59. package/dist/session-manager.js.map +1 -1
  60. package/dist/tools/skill-search.d.ts +53 -0
  61. package/dist/tools/skill-search.d.ts.map +1 -0
  62. package/dist/tools/skill-search.js +269 -0
  63. package/dist/tools/skill-search.js.map +1 -0
  64. package/dist/tools/system-tools.d.ts +22 -1
  65. package/dist/tools/system-tools.d.ts.map +1 -1
  66. package/dist/tools/system-tools.js +149 -21
  67. package/dist/tools/system-tools.js.map +1 -1
  68. package/dist/trace.d.ts +27 -1
  69. package/dist/trace.d.ts.map +1 -1
  70. package/dist/trace.js +60 -3
  71. package/dist/trace.js.map +1 -1
  72. package/dist/types.d.ts +51 -5
  73. package/dist/types.d.ts.map +1 -1
  74. package/package.json +6 -2
package/README.md ADDED
@@ -0,0 +1,61 @@
1
+ # @brainpilot/runtime
2
+
3
+ The orchestration runtime for **BrainPilot** — the open-source, single-user
4
+ multi-agent platform built on TypeScript + the [Pi SDK](https://pi.dev). This
5
+ package owns the agent lifecycle and is the **state authority**: a Principal
6
+ agent coordinating specialist agents over a file-based mailbox, exposed as a
7
+ Hono + SSE server.
8
+
9
+ It is consumed by `@brainpilot/backend-core` (which proxies to it as a stateless
10
+ byte-passthrough) and, in hosted deployments, by the platform layer.
11
+
12
+ ## What lives here
13
+
14
+ - `SessionManager` — session lifecycle, agent registry, **state authority**
15
+ (`status = idle | running | error | stopped`), `metrics()`.
16
+ - `MasAgent` — per-agent wrapper over a Pi `AgentSession`; emits AG-UI events.
17
+ - System tools + access control, the external-MCP bridge, Graph-of-Trace.
18
+ - The Hono server (`./server`) with the SSE event stream.
19
+
20
+ All wire types come from `@brainpilot/protocol` (the zod SSOT).
21
+
22
+ ## Liveness contract (R-3)
23
+
24
+ The runtime imposes **no fixed wall-clock cap on a single agent turn.** A
25
+ multi-hour research run is never killed by a timer. Liveness is
26
+ **activity-based, not duration-based.**
27
+
28
+ **Guarantees:**
29
+
30
+ 1. **No per-turn / per-prompt hard timeout.** There is no `120s`-style cap; the
31
+ TS runtime has no turn cap at all. (The only `timeout` in this package is the
32
+ provider connectivity **probe**, unrelated to agent turns.)
33
+ 2. **A turn ends only on a real terminal condition** — the agent finishes the
34
+ run, the run errors, or it is **explicitly aborted** via
35
+ `SessionManager.interrupt(sessionId, agentName?)` (user stop) or
36
+ `SessionManager.evictSession(sessionId)` (idle reclaim / shutdown). The
37
+ runtime never aborts a turn on a timer of its own.
38
+ 3. **No inactivity timeout either.** Silence is not treated as death.
39
+
40
+ **Liveness signal** — `SessionManager.metrics()` (served at `GET /metrics`) is
41
+ the authority a hosting layer should use:
42
+
43
+ | field | meaning |
44
+ |-------|---------|
45
+ | `runningAgents` | count of agents currently in `status === "running"` |
46
+ | `lastActivityAt` | ISO timestamp, advanced on **every** emitted event / state change (prompt accepted, status transition, run finished, …) |
47
+
48
+ **"Still alive" = `runningAgents > 0`, or a recently-advanced `lastActivityAt`.**
49
+ An idle reaper must key off these — never off elapsed wall-clock since the
50
+ prompt started. As long as a long-running agent keeps `runningAgents > 0` (or
51
+ keeps advancing `lastActivityAt`), it must not be reaped.
52
+
53
+ **Bash / tool calls** run inside the Pi SDK. The runtime adds no bash tool of
54
+ its own and configures no Pi turn/tool timeout. A separately configurable
55
+ per-tool timeout (e.g. a ~30min bash default) would belong at the Pi-SDK tool
56
+ layer and would not change the turn-liveness contract above.
57
+
58
+ **Validate end-to-end:** start a session, issue a prompt that runs longer than
59
+ any historical timeout, and poll `GET /metrics` — the run stays alive
60
+ (`runningAgents > 0`, `lastActivityAt` advancing) until the agent itself
61
+ completes, with no runtime-initiated abort.
@@ -0,0 +1,51 @@
1
+ /**
2
+ * agent-error.ts — normalize raw agent/SDK error messages before they reach
3
+ * the user-facing event stream and events.jsonl (issues #45, #97).
4
+ *
5
+ * Three jobs:
6
+ * 1. Recognize the "no provider / no API key" case and replace the raw Pi SDK
7
+ * guidance (which points at `/login` and absolute node_modules doc paths)
8
+ * with a product-level message that points at BrainPilot's own Settings →
9
+ * Providers flow.
10
+ * 2. Recognize a provider HTTP error (e.g. `401 {"error":{...}}`) and split it
11
+ * into a concise, localized headline (`message`) and the full raw blob
12
+ * (`details`), so the chat bubble shows a short line and tucks the provider
13
+ * internals / request id behind an expandable section instead of dumping
14
+ * escaped JSON into the primary transcript (#97).
15
+ * 3. Redact local filesystem leakage (absolute node_modules paths, `/login`
16
+ * hints) from any other error, so we never persist or display internal
17
+ * install paths.
18
+ *
19
+ * Language follows the existing runtime system_message convention (Chinese) for
20
+ * the BrainPilot-authored shell; the provider's own error text is preserved
21
+ * verbatim (we don't translate third-party messages — that loses fidelity).
22
+ */
23
+ /** Normalized error: a short headline plus optional expandable raw detail. */
24
+ export interface NormalizedAgentError {
25
+ /** Concise, user-facing headline (chat bubble body). */
26
+ message: string;
27
+ /** Full raw error for the expandable "details" section, when worth keeping. */
28
+ details?: string;
29
+ }
30
+ /**
31
+ * #97 error path — coarse recoverability class for an agent/provider error.
32
+ * - `retryable`: transient (rate limit, 5xx, timeout, network reset). Re-running
33
+ * the same prompt may succeed, so the delivery loop self-retries the expert.
34
+ * - `fatal`: re-running is pointless (auth/401/403, missing key/provider,
35
+ * permission denied). Escalate to the principal immediately, no retry.
36
+ */
37
+ export type AgentErrorKind = "retryable" | "fatal";
38
+ /**
39
+ * Classify a raw agent/SDK error string for the delivery-loop error path (#97).
40
+ * Defaults to `retryable` for the unknown case so a transient failure we didn't
41
+ * pattern-match still gets the benefit of a retry before escalation.
42
+ */
43
+ export declare function classifyAgentError(raw: string): AgentErrorKind;
44
+ /**
45
+ * Normalize a raw agent error message for user display + persistence.
46
+ * - No-provider/no-key errors → a product-level Settings → Providers message.
47
+ * - Provider HTTP errors (`401 {...}`) → concise headline + raw blob in details.
48
+ * - Everything else → the original message with local paths / `/login` redacted.
49
+ */
50
+ export declare function normalizeAgentError(raw: string): NormalizedAgentError;
51
+ //# sourceMappingURL=agent-error.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"agent-error.d.ts","sourceRoot":"","sources":["../src/agent-error.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;GAqBG;AAEH,8EAA8E;AAC9E,MAAM,WAAW,oBAAoB;IACnC,wDAAwD;IACxD,OAAO,EAAE,MAAM,CAAC;IAChB,+EAA+E;IAC/E,OAAO,CAAC,EAAE,MAAM,CAAC;CAClB;AAED;;;;;;GAMG;AACH,MAAM,MAAM,cAAc,GAAG,WAAW,GAAG,OAAO,CAAC;AAiBnD;;;;GAIG;AACH,wBAAgB,kBAAkB,CAAC,GAAG,EAAE,MAAM,GAAG,cAAc,CAK9D;AAuGD;;;;;GAKG;AACH,wBAAgB,mBAAmB,CAAC,GAAG,EAAE,MAAM,GAAG,oBAAoB,CAMrE"}
@@ -0,0 +1,163 @@
1
+ /**
2
+ * agent-error.ts — normalize raw agent/SDK error messages before they reach
3
+ * the user-facing event stream and events.jsonl (issues #45, #97).
4
+ *
5
+ * Three jobs:
6
+ * 1. Recognize the "no provider / no API key" case and replace the raw Pi SDK
7
+ * guidance (which points at `/login` and absolute node_modules doc paths)
8
+ * with a product-level message that points at BrainPilot's own Settings →
9
+ * Providers flow.
10
+ * 2. Recognize a provider HTTP error (e.g. `401 {"error":{...}}`) and split it
11
+ * into a concise, localized headline (`message`) and the full raw blob
12
+ * (`details`), so the chat bubble shows a short line and tucks the provider
13
+ * internals / request id behind an expandable section instead of dumping
14
+ * escaped JSON into the primary transcript (#97).
15
+ * 3. Redact local filesystem leakage (absolute node_modules paths, `/login`
16
+ * hints) from any other error, so we never persist or display internal
17
+ * install paths.
18
+ *
19
+ * Language follows the existing runtime system_message convention (Chinese) for
20
+ * the BrainPilot-authored shell; the provider's own error text is preserved
21
+ * verbatim (we don't translate third-party messages — that loses fidelity).
22
+ */
23
+ /**
24
+ * Auth / configuration failures where a retry cannot help: a wrong or missing
25
+ * key, a forbidden/unauthorized response, or no provider configured. Matched
26
+ * BEFORE the retryable set so a "401 ... rate limit ..." blob is fatal.
27
+ */
28
+ const FATAL_RE = /\b(401|403)\b|invalid api key|no api key|api key (?:found|for)|no provider|unauthor|forbidden|authentication|permission denied/i;
29
+ /**
30
+ * Transient failures worth a retry: explicit 408/429/5xx status codes, timeouts,
31
+ * overload, and the common Node socket/network error codes.
32
+ */
33
+ const RETRYABLE_RE = /\b(408|429|5\d{2})\b|timeout|timed out|temporar|overloaded|rate.?limit|econnreset|etimedout|enotfound|econnrefused|network|fetch failed|socket hang up|connection/i;
34
+ /**
35
+ * Classify a raw agent/SDK error string for the delivery-loop error path (#97).
36
+ * Defaults to `retryable` for the unknown case so a transient failure we didn't
37
+ * pattern-match still gets the benefit of a retry before escalation.
38
+ */
39
+ export function classifyAgentError(raw) {
40
+ if (!raw)
41
+ return "retryable";
42
+ if (FATAL_RE.test(raw))
43
+ return "fatal";
44
+ if (RETRYABLE_RE.test(raw))
45
+ return "retryable";
46
+ return "retryable";
47
+ }
48
+ /** Product-level recovery message for a missing provider/key. */
49
+ const NO_PROVIDER_MESSAGE = "未配置任何 provider。请打开 设置 → Providers 添加一个 provider。";
50
+ /** Heuristics for the "no key / no provider configured" class of error. */
51
+ function isNoProviderError(raw) {
52
+ return /no api key|no provider|api key found|api key for the selected model/i.test(raw);
53
+ }
54
+ /**
55
+ * Detect a provider HTTP error and build a concise headline + raw details.
56
+ *
57
+ * Real shape (observed in #97):
58
+ * `401 {"error":{"message":"invalid api key (request id: ...)", ...}}`
59
+ * i.e. a leading HTTP status code followed by a JSON body. We extract the
60
+ * status code and, when possible, the provider's own `error.message`, and keep
61
+ * the entire original blob as `details` so the request id stays available
62
+ * behind the expandable section.
63
+ *
64
+ * Returns undefined when the string doesn't look like a provider HTTP error,
65
+ * so the caller falls through to plain redaction.
66
+ */
67
+ function parseProviderError(raw) {
68
+ // Observed shape is always `<status> {json}` — require BOTH a 4xx/5xx code
69
+ // and a JSON body, so a plain message that happens to contain a 3-digit
70
+ // number ("retry in 500ms") is NOT misclassified as a provider error.
71
+ if (!raw.includes("{"))
72
+ return undefined;
73
+ const m = raw.match(/\b(4\d{2}|5\d{2})\b/);
74
+ if (!m)
75
+ return undefined;
76
+ const status = m[1];
77
+ let providerMsg = extractProviderMessage(raw);
78
+ // Guard against echoing the whole blob back as the "message" — if the
79
+ // extracted text still looks like a JSON dump, drop it and keep only the code.
80
+ if (providerMsg && /[{}]/.test(providerMsg))
81
+ providerMsg = undefined;
82
+ const headline = providerMsg
83
+ ? `provider 拒绝请求 (${status}): ${providerMsg}`
84
+ : `provider 拒绝请求 (HTTP ${status})。详情见下方展开。`;
85
+ return { message: headline, details: raw.trim() };
86
+ }
87
+ /**
88
+ * Best-effort pull of the provider's own human-readable message out of an
89
+ * error blob. Tries to JSON.parse a `{...}` substring and read common shapes
90
+ * (`error.message`, `message`, `error` as string); falls back to undefined.
91
+ */
92
+ function extractProviderMessage(raw) {
93
+ const start = raw.indexOf("{");
94
+ const end = raw.lastIndexOf("}");
95
+ if (start === -1 || end === -1 || end <= start)
96
+ return undefined;
97
+ try {
98
+ const obj = JSON.parse(raw.slice(start, end + 1));
99
+ const msg = pickMessage(obj);
100
+ return msg?.trim() || undefined;
101
+ }
102
+ catch {
103
+ return undefined;
104
+ }
105
+ }
106
+ function pickMessage(obj) {
107
+ if (!obj || typeof obj !== "object")
108
+ return undefined;
109
+ const o = obj;
110
+ if (typeof o.message === "string")
111
+ return o.message;
112
+ const err = o.error;
113
+ if (typeof err === "string")
114
+ return err;
115
+ if (err && typeof err === "object") {
116
+ const e = err;
117
+ if (typeof e.message === "string")
118
+ return e.message;
119
+ }
120
+ return undefined;
121
+ }
122
+ /**
123
+ * Strip local-path / `/login` leakage from an arbitrary error string while
124
+ * keeping its semantic content. Best-effort — drops lines that are purely an
125
+ * absolute node_modules doc path or a `/login` hint, and scrubs any inline
126
+ * absolute path that reaches into node_modules.
127
+ */
128
+ function redact(raw) {
129
+ return raw
130
+ .split("\n")
131
+ .filter((line) => {
132
+ const t = line.trim();
133
+ if (/use \/login/i.test(t))
134
+ return false;
135
+ // A line that is just an absolute path into node_modules (doc pointer).
136
+ if (/^\/?\S*node_modules\/\S+$/.test(t))
137
+ return false;
138
+ return true;
139
+ })
140
+ .map((line) =>
141
+ // Scrub any remaining inline absolute node_modules path.
142
+ line.replace(/\/\S*node_modules\/\S+/g, "").trimEnd())
143
+ .join("\n")
144
+ .replace(/\n{2,}/g, "\n")
145
+ .trim();
146
+ }
147
+ /**
148
+ * Normalize a raw agent error message for user display + persistence.
149
+ * - No-provider/no-key errors → a product-level Settings → Providers message.
150
+ * - Provider HTTP errors (`401 {...}`) → concise headline + raw blob in details.
151
+ * - Everything else → the original message with local paths / `/login` redacted.
152
+ */
153
+ export function normalizeAgentError(raw) {
154
+ if (!raw)
155
+ return { message: raw };
156
+ if (isNoProviderError(raw))
157
+ return { message: NO_PROVIDER_MESSAGE };
158
+ const provider = parseProviderError(raw);
159
+ if (provider)
160
+ return provider;
161
+ return { message: redact(raw) };
162
+ }
163
+ //# sourceMappingURL=agent-error.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"agent-error.js","sourceRoot":"","sources":["../src/agent-error.ts"],"names":[],"mappings":"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"}
@@ -1 +1 @@
1
- {"version":3,"file":"agent-factory.d.ts","sourceRoot":"","sources":["../src/agent-factory.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;GAeG;AACH,OAAO,KAAK,EAAE,mBAAmB,EAA2C,MAAM,YAAY,CAAC;AAI/F,wBAAgB,UAAU,CAAC,GAAG,GAAE,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,SAAS,CAAe,GAAG,OAAO,CAEzF;AAED,eAAO,MAAM,gBAAgB,EAAE,mBAE9B,CAAC;AAEF;;;GAGG;AACH,eAAO,MAAM,gBAAgB,EAAE,mBAkD9B,CAAC;AAEF,wBAAgB,aAAa,IAAI,mBAAmB,CAEnD"}
1
+ {"version":3,"file":"agent-factory.d.ts","sourceRoot":"","sources":["../src/agent-factory.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;GAeG;AACH,OAAO,KAAK,EAAE,mBAAmB,EAA2C,MAAM,YAAY,CAAC;AAM/F,wBAAgB,UAAU,CAAC,GAAG,GAAE,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,SAAS,CAAe,GAAG,OAAO,CAEzF;AAED,eAAO,MAAM,gBAAgB,EAAE,mBAE9B,CAAC;AAEF;;;GAGG;AACH,eAAO,MAAM,gBAAgB,EAAE,mBA8E9B,CAAC;AAEF,wBAAgB,aAAa,IAAI,mBAAmB,CAEnD"}
@@ -1,5 +1,7 @@
1
1
  import { MockAgentSession } from "./mock-agent.js";
2
2
  import { resolveGatewayModel, resolveSessionModel } from "./pi-provider.js";
3
+ import { makeTraceReminderExt } from "./extensions/trace-reminder.js";
4
+ import { makeAgentStatusExt } from "./extensions/agent-status.js";
3
5
  export function isMockMode(env = process.env) {
4
6
  return env.BP_MOCK === "1" || env.BP_MOCK === "true";
5
7
  }
@@ -30,17 +32,45 @@ export const realAgentFactory = async (params) => {
30
32
  // Skills: Pi's DefaultResourceLoader otherwise auto-discovers skills from the
31
33
  // HOST machine's global dirs (~/.pi/agent/skills, ~/.agents/skills), which
32
34
  // makes agent behaviour depend on whoever runs the runtime — not reproducible.
33
- // We set `noSkills: true` to drop that implicit discovery and load skills ONLY
34
- // from BrainPilot's own app-controlled dirs (`bp_template/skills/` shared +
35
- // `.bp/<sid>/skills/` per-session, passed as `skillPaths`). `additionalSkillPaths`
36
- // bypasses Pi's project-trust gate, so this works in our non-interactive runtime.
37
- // Custom loaders are NOT auto-reloaded by the SDK, so we must reload() before use.
35
+ // We set `noSkills: true` to drop that implicit discovery, then load ONLY our
36
+ // controlled skill dir(s) via `additionalSkillPaths` (honored even with
37
+ // noSkills, verified against Pi v0.79 source). Pi's native skill pipeline
38
+ // already does progressive disclosure: each skill's name+description goes into
39
+ // the system prompt and the body is read on demand. The built-in skill content
40
+ // (@brainpilot/skills) is materialized into `<dataRoot>/bp_template/skills`,
41
+ // which the SessionManager passes here as `params.skillPaths`.
42
+ // Context files: for the SAME reproducibility reason we set `noContextFiles: true`.
43
+ // Pi would otherwise walk cwd→root collecting every AGENTS.md / CLAUDE.md and
44
+ // inject them as project context. Agents run with cwd under the host repo, so
45
+ // they'd absorb whatever AGENTS.md/CLAUDE.md happen to sit in the ancestry —
46
+ // e.g. the legacy "MAS Platform Phase 1" doc — and mis-identify themselves.
47
+ // Agent identity must come ONLY from the per-role persona below.
48
+ // Pi-native hooks: register the trace-reminder extension per AgentSession (its
49
+ // closure state is naturally per-agent). Only the real factory loads it — the
50
+ // mock factory has no Pi event loop, so behavioural hooks are verified in real
51
+ // mode (design §7 / T2).
52
+ const traceReminder = makeTraceReminderExt({
53
+ role: params.role,
54
+ name: params.agentName,
55
+ onUnreplied: params.onUnreplied ?? (() => { }),
56
+ });
57
+ // #97: inject a fresh team-status block at the top of every turn, but only for
58
+ // the agent the host supplied a renderer for (the principal). The `context`
59
+ // hook recomputes per turn and the rewrite is ephemeral (never persisted).
60
+ const extensionFactories = [traceReminder];
61
+ if (params.renderAgentStatus) {
62
+ extensionFactories.push(makeAgentStatusExt({ renderStatus: params.renderAgentStatus }));
63
+ }
38
64
  const resourceLoader = new DefaultResourceLoader({
39
65
  cwd: params.cwd,
40
66
  agentDir,
41
67
  noSkills: true,
42
- additionalSkillPaths: params.skillPaths,
68
+ noContextFiles: true,
69
+ ...(params.skillPaths && params.skillPaths.length > 0
70
+ ? { additionalSkillPaths: params.skillPaths }
71
+ : {}),
43
72
  appendSystemPrompt: params.systemPrompt ? [params.systemPrompt] : [],
73
+ extensionFactories,
44
74
  });
45
75
  await resourceLoader.reload();
46
76
  const { session } = await createAgentSession({
@@ -1 +1 @@
1
- {"version":3,"file":"agent-factory.js","sourceRoot":"","sources":["../src/agent-factory.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"agent-factory.js","sourceRoot":"","sources":["../src/agent-factory.ts"],"names":[],"mappings":"AAiBA,OAAO,EAAE,gBAAgB,EAAE,MAAM,iBAAiB,CAAC;AACnD,OAAO,EAAE,mBAAmB,EAAE,mBAAmB,EAAsB,MAAM,kBAAkB,CAAC;AAChG,OAAO,EAAE,oBAAoB,EAAE,MAAM,gCAAgC,CAAC;AACtE,OAAO,EAAE,kBAAkB,EAAE,MAAM,8BAA8B,CAAC;AAElE,MAAM,UAAU,UAAU,CAAC,MAA0C,OAAO,CAAC,GAAG;IAC9E,OAAO,GAAG,CAAC,OAAO,KAAK,GAAG,IAAI,GAAG,CAAC,OAAO,KAAK,MAAM,CAAC;AACvD,CAAC;AAED,MAAM,CAAC,MAAM,gBAAgB,GAAwB,KAAK,EAAE,EAAE,SAAS,EAAE,SAAS,EAAE,WAAW,EAAE,EAAE,EAAE;IACnG,OAAO,IAAI,gBAAgB,CAAC,EAAE,SAAS,EAAE,SAAS,EAAE,WAAW,EAAE,CAAC,CAAC;AACrE,CAAC,CAAC;AAEF;;;GAGG;AACH,MAAM,CAAC,MAAM,gBAAgB,GAAwB,KAAK,EAAE,MAAM,EAAE,EAAE;IACpE,MAAM,GAAG,GAAG,CAAC,MAAM,MAAM,CAAC,iCAAiC,CAAC,CAAqB,CAAC;IAClF,MAAM,EAAE,kBAAkB,EAAE,UAAU,EAAE,cAAc,EAAE,qBAAqB,EAAE,WAAW,EAAE,GAAG,GAAG,CAAC;IAEnG,MAAM,WAAW,GAAG,MAAM,CAAC,WAAW,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,SAAS,CAAC,UAAU,EAAE,CAAC,CAAC,CAAC,CAAC;IAE5E,MAAM,QAAQ,GAAG,WAAW,EAAE,CAAC;IAE/B,6EAA6E;IAC7E,wEAAwE;IACxE,uEAAuE;IACvE,MAAM,QAAQ,GAAG,MAAM,CAAC,cAAc;QACpC,CAAC,CAAC,mBAAmB,CAAC,GAA+B,EAAE,QAAQ,EAAE,MAAM,CAAC,cAAc,CAAC;QACvF,CAAC,CAAC,mBAAmB,CAAC,GAA+B,EAAE,QAAQ,CAAC,CAAC;IACnE,MAAM,EAAE,KAAK,EAAE,aAAa,EAAE,WAAW,EAAE,GAAG,QAAQ,CAAC;IAEvD,yEAAyE;IACzE,uEAAuE;IACvE,0EAA0E;IAC1E,mEAAmE;IACnE,EAAE;IACF,8EAA8E;IAC9E,2EAA2E;IAC3E,+EAA+E;IAC/E,8EAA8E;IAC9E,wEAAwE;IACxE,0EAA0E;IAC1E,+EAA+E;IAC/E,+EAA+E;IAC/E,6EAA6E;IAC7E,+DAA+D;IAC/D,oFAAoF;IACpF,8EAA8E;IAC9E,8EAA8E;IAC9E,6EAA6E;IAC7E,4EAA4E;IAC5E,iEAAiE;IACjE,+EAA+E;IAC/E,8EAA8E;IAC9E,+EAA+E;IAC/E,yBAAyB;IACzB,MAAM,aAAa,GAAG,oBAAoB,CAAC;QACzC,IAAI,EAAE,MAAM,CAAC,IAAI;QACjB,IAAI,EAAE,MAAM,CAAC,SAAS;QACtB,WAAW,EAAE,MAAM,CAAC,WAAW,IAAI,CAAC,GAAG,EAAE,GAAE,CAAC,CAAC;KAC9C,CAAC,CAAC;IACH,+EAA+E;IAC/E,4EAA4E;IAC5E,2EAA2E;IAC3E,MAAM,kBAAkB,GAAc,CAAC,aAAa,CAAC,CAAC;IACtD,IAAI,MAAM,CAAC,iBAAiB,EAAE,CAAC;QAC7B,kBAAkB,CAAC,IAAI,CAAC,kBAAkB,CAAC,EAAE,YAAY,EAAE,MAAM,CAAC,iBAAiB,EAAE,CAAC,CAAC,CAAC;IAC1F,CAAC;IACD,MAAM,cAAc,GAAG,IAAI,qBAAqB,CAAC;QAC/C,GAAG,EAAE,MAAM,CAAC,GAAG;QACf,QAAQ;QACR,QAAQ,EAAE,IAAI;QACd,cAAc,EAAE,IAAI;QACpB,GAAG,CAAC,MAAM,CAAC,UAAU,IAAI,MAAM,CAAC,UAAU,CAAC,MAAM,GAAG,CAAC;YACnD,CAAC,CAAC,EAAE,oBAAoB,EAAE,MAAM,CAAC,UAAU,EAAE;YAC7C,CAAC,CAAC,EAAE,CAAC;QACP,kBAAkB,EAAE,MAAM,CAAC,YAAY,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,YAAY,CAAC,CAAC,CAAC,CAAC,EAAE;QACpE,kBAAkB;KACnB,CAAC,CAAC;IACH,MAAM,cAAc,CAAC,MAAM,EAAE,CAAC;IAE9B,MAAM,EAAE,OAAO,EAAE,GAAG,MAAM,kBAAkB,CAAC;QAC3C,GAAG,EAAE,MAAM,CAAC,GAAG;QACf,KAAK,EAAE,MAAM,CAAC,gBAAgB;QAC9B,WAAW;QACX,cAAc;QACd,cAAc,EAAE,cAAc,CAAC,IAAI,CAAC,MAAM,CAAC,WAAW,CAAC;QACvD,GAAG,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,KAAK,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;QAC3B,GAAG,CAAC,aAAa,CAAC,CAAC,CAAC,EAAE,aAAa,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;QAC3C,GAAG,CAAC,WAAW,CAAC,CAAC,CAAC,EAAE,WAAW,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;KACxC,CAAC,CAAC;IAEH,OAAO,IAAI,gBAAgB,CAAC,OAAO,CAAC,CAAC;AACvC,CAAC,CAAC;AAEF,MAAM,UAAU,aAAa;IAC3B,OAAO,UAAU,EAAE,CAAC,CAAC,CAAC,gBAAgB,CAAC,CAAC,CAAC,gBAAgB,CAAC;AAC5D,CAAC;AAED,qEAAqE;AACrE,SAAS,SAAS,CAAC,UAA+B,EAAE,IAAgB;IAClE,OAAO,UAAU,CAAC;QAChB,IAAI,EAAE,IAAI,CAAC,IAAI;QACf,wEAAwE;QACxE,KAAK,EAAE,IAAI,CAAC,IAAI;QAChB,WAAW,EAAE,IAAI,CAAC,WAAW;QAC7B,UAAU,EAAE,IAAI,CAAC,UAAU;QAC3B,OAAO,EAAE,KAAK,EAAE,WAAmB,EAAE,MAA+B,EAAE,EAAE;YACtE,MAAM,GAAG,GAAG,MAAM,IAAI,CAAC,OAAO,CAAC,MAAM,IAAI,EAAE,CAAC,CAAC;YAC7C,mEAAmE;YACnE,sEAAsE;YACtE,oEAAoE;YACpE,uCAAuC;YACvC,IAAI,GAAG,CAAC,OAAO,EAAE,CAAC;gBAChB,MAAM,IAAI,GAAG,GAAG,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;gBACvD,MAAM,IAAI,KAAK,CAAC,IAAI,IAAI,GAAG,IAAI,CAAC,IAAI,SAAS,CAAC,CAAC;YACjD,CAAC;YACD,OAAO,EAAE,OAAO,EAAE,GAAG,CAAC,OAAO,EAAE,OAAO,EAAE,EAAE,EAAE,CAAC;QAC/C,CAAC;KACF,CAAC,CAAC;AACL,CAAC;AAED,6EAA6E;AAC7E,MAAM,gBAAgB;IACS;IAA7B,YAA6B,CAAY;QAAZ,MAAC,GAAD,CAAC,CAAW;IAAG,CAAC;IAC7C,IAAI,SAAS;QACX,OAAO,IAAI,CAAC,CAAC,CAAC,SAAS,CAAC;IAC1B,CAAC;IACD,SAAS,CAAC,QAAmC;QAC3C,OAAO,IAAI,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAU,EAAE,EAAE,CAAC,QAAQ,CAAC,CAAiB,CAAC,CAAC,CAAC;IACvE,CAAC;IACD,MAAM,CAAC,IAAY;QACjB,OAAO,IAAI,CAAC,CAAC,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;IAC7B,CAAC;IACD,KAAK;QACH,OAAO,IAAI,CAAC,CAAC,CAAC,KAAK,EAAE,CAAC;IACxB,CAAC;IACD,OAAO;QACL,IAAI,CAAC,CAAC,CAAC,OAAO,EAAE,CAAC;IACnB,CAAC;CACF"}
package/dist/events.d.ts CHANGED
@@ -14,6 +14,17 @@ export declare const ev: {
14
14
  textMessageStart(ctx: Ctx, messageId: string, role?: string): AgUiEvent;
15
15
  textMessageContent(ctx: Ctx, messageId: string, delta: string): AgUiEvent;
16
16
  textMessageEnd(ctx: Ctx, messageId: string): AgUiEvent;
17
+ /**
18
+ * Atomic text message (issue #42). CHUNK is the AG-UI shorthand for the
19
+ * START→CONTENT→END triad; the client transformer/reducer expands it. We use
20
+ * it with role:"user" to persist + replay the user's own prompt as a bubble
21
+ * in the event stream. AG-UI's canonical carrier for user input is
22
+ * `RunAgentInput.messages`/`MESSAGES_SNAPSHOT`, but BrainPilot's whole
23
+ * history/replay path is the events.jsonl stream, and the spec explicitly
24
+ * permits a single role:"user" CHUNK to echo a user bubble into the output
25
+ * stream — which is exactly this case.
26
+ */
27
+ textMessageChunk(ctx: Ctx, messageId: string, delta: string, role?: string): AgUiEvent;
17
28
  reasoningMessageStart(ctx: Ctx, messageId: string): AgUiEvent;
18
29
  reasoningMessageContent(ctx: Ctx, messageId: string, delta: string): AgUiEvent;
19
30
  reasoningMessageEnd(ctx: Ctx, messageId: string): AgUiEvent;
@@ -30,6 +41,13 @@ export declare const ev: {
30
41
  consecutiveCount: number;
31
42
  };
32
43
  }): AgUiEvent;
44
+ userInputRequest(ctx: Ctx, req: {
45
+ request_id: string;
46
+ agent: string;
47
+ question: string;
48
+ options?: string[];
49
+ allow_free_text?: boolean;
50
+ }): AgUiEvent;
33
51
  systemMessage(sessionId: string, level: "info" | "warning" | "error" | "fatal", message: string, opts?: {
34
52
  agent?: string;
35
53
  details?: string;
@@ -1 +1 @@
1
- {"version":3,"file":"events.d.ts","sourceRoot":"","sources":["../src/events.ts"],"names":[],"mappings":"AAUA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,sBAAsB,CAAC;AAMtD,UAAU,GAAG;IACX,SAAS,EAAE,MAAM,CAAC;IAClB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB;AAgBD,wBAAgB,YAAY,IAAI,MAAM,CAErC;AACD,wBAAgB,QAAQ,IAAI,MAAM,CAEjC;AAED,eAAO,MAAM,EAAE;oBACG,GAAG,gBAAgB,MAAM,GAAG,SAAS;qBAGpC,GAAG,WAAW,OAAO,GAAG,SAAS;kBAGpC,GAAG,WAAW,MAAM,kBAA2B,SAAS;0BAGhD,GAAG,aAAa,MAAM,kBAAuB,SAAS;4BAGpD,GAAG,aAAa,MAAM,SAAS,MAAM,GAAG,SAAS;wBAGrD,GAAG,aAAa,MAAM,GAAG,SAAS;+BAG3B,GAAG,aAAa,MAAM,GAAG,SAAS;iCAGhC,GAAG,aAAa,MAAM,SAAS,MAAM,GAAG,SAAS;6BAGrD,GAAG,aAAa,MAAM,GAAG,SAAS;uBAGxC,GAAG,cAAc,MAAM,YAAY,MAAM,oBAAoB,MAAM,GAAG,SAAS;sBAShF,GAAG,cAAc,MAAM,SAAS,MAAM,GAAG,SAAS;qBAGnD,GAAG,cAAc,MAAM,GAAG,SAAS;wBAGhC,GAAG,cAAc,MAAM,WAAW,MAAM,iCAA+B,MAAM,GAAG,SAAS;2BAWtG,GAAG,QACF,MAAM,UACJ,MAAM,GAAG,SAAS,GAAG,OAAO,GAAG,SAAS,UACxC;QACN,WAAW,CAAC,EAAE,MAAM,CAAC;QACrB,oBAAoB,CAAC,EAAE,MAAM,EAAE,CAAC;QAChC,SAAS,CAAC,EAAE;YAAE,OAAO,EAAE,MAAM,CAAC;YAAC,SAAS,EAAE,MAAM,CAAC;YAAC,gBAAgB,EAAE,MAAM,CAAA;SAAE,CAAC;KAC9E,GACA,SAAS;6BAoBC,MAAM,SACV,MAAM,GAAG,SAAS,GAAG,OAAO,GAAG,OAAO,WACpC,MAAM,SACR;QAAE,KAAK,CAAC,EAAE,MAAM,CAAC;QAAC,OAAO,CAAC,EAAE,MAAM,CAAC;QAAC,WAAW,CAAC,EAAE,OAAO,CAAA;KAAE,GACjE,SAAS;gBAYA,GAAG,QAAQ,MAAM,SAAS,OAAO,GAAG,SAAS;CAG1D,CAAC"}
1
+ {"version":3,"file":"events.d.ts","sourceRoot":"","sources":["../src/events.ts"],"names":[],"mappings":"AAUA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,sBAAsB,CAAC;AAMtD,UAAU,GAAG;IACX,SAAS,EAAE,MAAM,CAAC;IAClB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB;AAgBD,wBAAgB,YAAY,IAAI,MAAM,CAErC;AACD,wBAAgB,QAAQ,IAAI,MAAM,CAEjC;AAED,eAAO,MAAM,EAAE;oBACG,GAAG,gBAAgB,MAAM,GAAG,SAAS;qBAGpC,GAAG,WAAW,OAAO,GAAG,SAAS;kBAGpC,GAAG,WAAW,MAAM,kBAA2B,SAAS;0BAGhD,GAAG,aAAa,MAAM,kBAAuB,SAAS;4BAGpD,GAAG,aAAa,MAAM,SAAS,MAAM,GAAG,SAAS;wBAGrD,GAAG,aAAa,MAAM,GAAG,SAAS;IAGtD;;;;;;;;;OASG;0BACmB,GAAG,aAAa,MAAM,SAAS,MAAM,kBAAuB,SAAS;+BAGhE,GAAG,aAAa,MAAM,GAAG,SAAS;iCAGhC,GAAG,aAAa,MAAM,SAAS,MAAM,GAAG,SAAS;6BAGrD,GAAG,aAAa,MAAM,GAAG,SAAS;uBAGxC,GAAG,cAAc,MAAM,YAAY,MAAM,oBAAoB,MAAM,GAAG,SAAS;sBAShF,GAAG,cAAc,MAAM,SAAS,MAAM,GAAG,SAAS;qBAGnD,GAAG,cAAc,MAAM,GAAG,SAAS;wBAGhC,GAAG,cAAc,MAAM,WAAW,MAAM,iCAA+B,MAAM,GAAG,SAAS;2BAWtG,GAAG,QACF,MAAM,UACJ,MAAM,GAAG,SAAS,GAAG,OAAO,GAAG,SAAS,UACxC;QACN,WAAW,CAAC,EAAE,MAAM,CAAC;QACrB,oBAAoB,CAAC,EAAE,MAAM,EAAE,CAAC;QAChC,SAAS,CAAC,EAAE;YAAE,OAAO,EAAE,MAAM,CAAC;YAAC,SAAS,EAAE,MAAM,CAAC;YAAC,gBAAgB,EAAE,MAAM,CAAA;SAAE,CAAC;KAC9E,GACA,SAAS;0BAoBL,GAAG,OACH;QAAE,UAAU,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE,MAAM,CAAC;QAAC,QAAQ,EAAE,MAAM,CAAC;QAAC,OAAO,CAAC,EAAE,MAAM,EAAE,CAAC;QAAC,eAAe,CAAC,EAAE,OAAO,CAAA;KAAE,GAC1G,SAAS;6BAYC,MAAM,SACV,MAAM,GAAG,SAAS,GAAG,OAAO,GAAG,OAAO,WACpC,MAAM,SACR;QAAE,KAAK,CAAC,EAAE,MAAM,CAAC;QAAC,OAAO,CAAC,EAAE,MAAM,CAAC;QAAC,WAAW,CAAC,EAAE,OAAO,CAAA;KAAE,GACjE,SAAS;gBAYA,GAAG,QAAQ,MAAM,SAAS,OAAO,GAAG,SAAS;CAG1D,CAAC"}
package/dist/events.js CHANGED
@@ -46,6 +46,19 @@ export const ev = {
46
46
  textMessageEnd(ctx, messageId) {
47
47
  return { type: "TEXT_MESSAGE_END", ...envelope(ctx), message_id: messageId };
48
48
  },
49
+ /**
50
+ * Atomic text message (issue #42). CHUNK is the AG-UI shorthand for the
51
+ * START→CONTENT→END triad; the client transformer/reducer expands it. We use
52
+ * it with role:"user" to persist + replay the user's own prompt as a bubble
53
+ * in the event stream. AG-UI's canonical carrier for user input is
54
+ * `RunAgentInput.messages`/`MESSAGES_SNAPSHOT`, but BrainPilot's whole
55
+ * history/replay path is the events.jsonl stream, and the spec explicitly
56
+ * permits a single role:"user" CHUNK to echo a user bubble into the output
57
+ * stream — which is exactly this case.
58
+ */
59
+ textMessageChunk(ctx, messageId, delta, role = "assistant") {
60
+ return { type: "TEXT_MESSAGE_CHUNK", ...envelope(ctx), message_id: messageId, role, delta };
61
+ },
49
62
  reasoningMessageStart(ctx, messageId) {
50
63
  return { type: "REASONING_MESSAGE_START", ...envelope(ctx), message_id: messageId };
51
64
  },
@@ -100,6 +113,17 @@ export const ev = {
100
113
  }
101
114
  return e;
102
115
  },
116
+ userInputRequest(ctx, req) {
117
+ return {
118
+ type: "user_input_request",
119
+ ...envelope(ctx),
120
+ request_id: req.request_id,
121
+ agent: req.agent,
122
+ question: req.question,
123
+ options: req.options,
124
+ allow_free_text: req.allow_free_text,
125
+ };
126
+ },
103
127
  systemMessage(sessionId, level, message, opts) {
104
128
  return {
105
129
  type: "system_message",
@@ -1 +1 @@
1
- {"version":3,"file":"events.js","sourceRoot":"","sources":["../src/events.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AACH,OAAO,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AAGzC,SAAS,EAAE;IACT,OAAO,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE,CAAC;AAClC,CAAC;AASD,SAAS,QAAQ,CAAC,GAAQ;IAOxB,MAAM,CAAC,GAAgC,EAAE,UAAU,EAAE,GAAG,CAAC,SAAS,EAAE,GAAG,EAAE,EAAE,EAAE,EAAE,CAAC;IAChF,IAAI,GAAG,CAAC,SAAS,KAAK,SAAS;QAAE,CAAC,CAAC,UAAU,GAAG,GAAG,CAAC,SAAS,CAAC;IAC9D,IAAI,GAAG,CAAC,KAAK,KAAK,SAAS;QAAE,CAAC,CAAC,MAAM,GAAG,GAAG,CAAC,KAAK,CAAC;IAClD,IAAI,GAAG,CAAC,QAAQ,KAAK,SAAS;QAAE,CAAC,CAAC,SAAS,GAAG,GAAG,CAAC,QAAQ,CAAC;IAC3D,OAAO,CAAC,CAAC;AACX,CAAC;AAED,MAAM,UAAU,YAAY;IAC1B,OAAO,OAAO,UAAU,EAAE,EAAE,CAAC;AAC/B,CAAC;AACD,MAAM,UAAU,QAAQ;IACtB,OAAO,OAAO,UAAU,EAAE,EAAE,CAAC;AAC/B,CAAC;AAED,MAAM,CAAC,MAAM,EAAE,GAAG;IAChB,UAAU,CAAC,GAAQ,EAAE,WAAoB;QACvC,OAAO,EAAE,IAAI,EAAE,aAAa,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,aAAa,EAAE,WAAW,EAAe,CAAC;IAC5F,CAAC;IACD,WAAW,CAAC,GAAQ,EAAE,MAAgB;QACpC,OAAO,EAAE,IAAI,EAAE,cAAc,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,MAAM,EAAe,CAAC;IACzE,CAAC;IACD,QAAQ,CAAC,GAAQ,EAAE,OAAe,EAAE,IAAI,GAAG,eAAe;QACxD,OAAO,EAAE,IAAI,EAAE,WAAW,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,OAAO,EAAE,IAAI,EAAe,CAAC;IAC7E,CAAC;IACD,gBAAgB,CAAC,GAAQ,EAAE,SAAiB,EAAE,IAAI,GAAG,WAAW;QAC9D,OAAO,EAAE,IAAI,EAAE,oBAAoB,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,UAAU,EAAE,SAAS,EAAE,IAAI,EAAe,CAAC;IACpG,CAAC;IACD,kBAAkB,CAAC,GAAQ,EAAE,SAAiB,EAAE,KAAa;QAC3D,OAAO,EAAE,IAAI,EAAE,sBAAsB,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,UAAU,EAAE,SAAS,EAAE,KAAK,EAAe,CAAC;IACvG,CAAC;IACD,cAAc,CAAC,GAAQ,EAAE,SAAiB;QACxC,OAAO,EAAE,IAAI,EAAE,kBAAkB,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,UAAU,EAAE,SAAS,EAAe,CAAC;IAC5F,CAAC;IACD,qBAAqB,CAAC,GAAQ,EAAE,SAAiB;QAC/C,OAAO,EAAE,IAAI,EAAE,yBAAyB,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,UAAU,EAAE,SAAS,EAAe,CAAC;IACnG,CAAC;IACD,uBAAuB,CAAC,GAAQ,EAAE,SAAiB,EAAE,KAAa;QAChE,OAAO,EAAE,IAAI,EAAE,2BAA2B,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,UAAU,EAAE,SAAS,EAAE,KAAK,EAAe,CAAC;IAC5G,CAAC;IACD,mBAAmB,CAAC,GAAQ,EAAE,SAAiB;QAC7C,OAAO,EAAE,IAAI,EAAE,uBAAuB,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,UAAU,EAAE,SAAS,EAAe,CAAC;IACjG,CAAC;IACD,aAAa,CAAC,GAAQ,EAAE,UAAkB,EAAE,QAAgB,EAAE,eAAwB;QACpF,OAAO;YACL,IAAI,EAAE,iBAAiB;YACvB,GAAG,QAAQ,CAAC,GAAG,CAAC;YAChB,YAAY,EAAE,UAAU;YACxB,cAAc,EAAE,QAAQ;YACxB,iBAAiB,EAAE,eAAe;SACtB,CAAC;IACjB,CAAC;IACD,YAAY,CAAC,GAAQ,EAAE,UAAkB,EAAE,KAAa;QACtD,OAAO,EAAE,IAAI,EAAE,gBAAgB,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,YAAY,EAAE,UAAU,EAAE,KAAK,EAAe,CAAC;IACpG,CAAC;IACD,WAAW,CAAC,GAAQ,EAAE,UAAkB;QACtC,OAAO,EAAE,IAAI,EAAE,eAAe,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,YAAY,EAAE,UAAU,EAAe,CAAC;IAC5F,CAAC;IACD,cAAc,CAAC,GAAQ,EAAE,UAAkB,EAAE,OAAe,EAAE,OAAO,GAAG,KAAK,EAAE,SAAkB;QAC/F,OAAO;YACL,IAAI,EAAE,kBAAkB;YACxB,GAAG,QAAQ,CAAC,GAAG,CAAC;YAChB,YAAY,EAAE,UAAU;YACxB,UAAU,EAAE,SAAS,IAAI,YAAY,EAAE;YACvC,OAAO;YACP,QAAQ,EAAE,OAAO;SACL,CAAC;IACjB,CAAC;IACD,iBAAiB,CACf,GAAQ,EACR,IAAY,EACZ,MAAgD,EAChD,KAIC;QAED,MAAM,CAAC,GAA4B;YACjC,IAAI,EAAE,qBAAqB;YAC3B,GAAG,QAAQ,CAAC,EAAE,GAAG,GAAG,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC;YACxC,IAAI;YACJ,MAAM;SACP,CAAC;QACF,IAAI,KAAK,EAAE,WAAW,KAAK,SAAS;YAAE,CAAC,CAAC,aAAa,GAAG,KAAK,CAAC,WAAW,CAAC;QAC1E,IAAI,KAAK,EAAE,oBAAoB,IAAI,KAAK,CAAC,oBAAoB,CAAC,MAAM;YAClE,CAAC,CAAC,sBAAsB,GAAG,KAAK,CAAC,oBAAoB,CAAC;QACxD,IAAI,KAAK,EAAE,SAAS,EAAE,CAAC;YACrB,CAAC,CAAC,UAAU,GAAG;gBACb,OAAO,EAAE,KAAK,CAAC,SAAS,CAAC,OAAO;gBAChC,SAAS,EAAE,KAAK,CAAC,SAAS,CAAC,SAAS;gBACpC,iBAAiB,EAAE,KAAK,CAAC,SAAS,CAAC,gBAAgB;aACpD,CAAC;QACJ,CAAC;QACD,OAAO,CAAc,CAAC;IACxB,CAAC;IACD,aAAa,CACX,SAAiB,EACjB,KAA6C,EAC7C,OAAe,EACf,IAAkE;QAElE,OAAO;YACL,IAAI,EAAE,gBAAgB;YACtB,UAAU,EAAE,SAAS;YACrB,KAAK,EAAE,IAAI,EAAE,KAAK;YAClB,KAAK;YACL,OAAO;YACP,OAAO,EAAE,IAAI,EAAE,OAAO;YACtB,SAAS,EAAE,EAAE,EAAE;YACf,WAAW,EAAE,IAAI,EAAE,WAAW,IAAI,IAAI;SAC1B,CAAC;IACjB,CAAC;IACD,MAAM,CAAC,GAAQ,EAAE,IAAY,EAAE,KAAc;QAC3C,OAAO,EAAE,IAAI,EAAE,QAAQ,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,IAAI,EAAE,KAAK,EAAe,CAAC;IACxE,CAAC;CACF,CAAC"}
1
+ {"version":3,"file":"events.js","sourceRoot":"","sources":["../src/events.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AACH,OAAO,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AAGzC,SAAS,EAAE;IACT,OAAO,IAAI,IAAI,EAAE,CAAC,WAAW,EAAE,CAAC;AAClC,CAAC;AASD,SAAS,QAAQ,CAAC,GAAQ;IAOxB,MAAM,CAAC,GAAgC,EAAE,UAAU,EAAE,GAAG,CAAC,SAAS,EAAE,GAAG,EAAE,EAAE,EAAE,EAAE,CAAC;IAChF,IAAI,GAAG,CAAC,SAAS,KAAK,SAAS;QAAE,CAAC,CAAC,UAAU,GAAG,GAAG,CAAC,SAAS,CAAC;IAC9D,IAAI,GAAG,CAAC,KAAK,KAAK,SAAS;QAAE,CAAC,CAAC,MAAM,GAAG,GAAG,CAAC,KAAK,CAAC;IAClD,IAAI,GAAG,CAAC,QAAQ,KAAK,SAAS;QAAE,CAAC,CAAC,SAAS,GAAG,GAAG,CAAC,QAAQ,CAAC;IAC3D,OAAO,CAAC,CAAC;AACX,CAAC;AAED,MAAM,UAAU,YAAY;IAC1B,OAAO,OAAO,UAAU,EAAE,EAAE,CAAC;AAC/B,CAAC;AACD,MAAM,UAAU,QAAQ;IACtB,OAAO,OAAO,UAAU,EAAE,EAAE,CAAC;AAC/B,CAAC;AAED,MAAM,CAAC,MAAM,EAAE,GAAG;IAChB,UAAU,CAAC,GAAQ,EAAE,WAAoB;QACvC,OAAO,EAAE,IAAI,EAAE,aAAa,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,aAAa,EAAE,WAAW,EAAe,CAAC;IAC5F,CAAC;IACD,WAAW,CAAC,GAAQ,EAAE,MAAgB;QACpC,OAAO,EAAE,IAAI,EAAE,cAAc,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,MAAM,EAAe,CAAC;IACzE,CAAC;IACD,QAAQ,CAAC,GAAQ,EAAE,OAAe,EAAE,IAAI,GAAG,eAAe;QACxD,OAAO,EAAE,IAAI,EAAE,WAAW,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,OAAO,EAAE,IAAI,EAAe,CAAC;IAC7E,CAAC;IACD,gBAAgB,CAAC,GAAQ,EAAE,SAAiB,EAAE,IAAI,GAAG,WAAW;QAC9D,OAAO,EAAE,IAAI,EAAE,oBAAoB,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,UAAU,EAAE,SAAS,EAAE,IAAI,EAAe,CAAC;IACpG,CAAC;IACD,kBAAkB,CAAC,GAAQ,EAAE,SAAiB,EAAE,KAAa;QAC3D,OAAO,EAAE,IAAI,EAAE,sBAAsB,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,UAAU,EAAE,SAAS,EAAE,KAAK,EAAe,CAAC;IACvG,CAAC;IACD,cAAc,CAAC,GAAQ,EAAE,SAAiB;QACxC,OAAO,EAAE,IAAI,EAAE,kBAAkB,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,UAAU,EAAE,SAAS,EAAe,CAAC;IAC5F,CAAC;IACD;;;;;;;;;OASG;IACH,gBAAgB,CAAC,GAAQ,EAAE,SAAiB,EAAE,KAAa,EAAE,IAAI,GAAG,WAAW;QAC7E,OAAO,EAAE,IAAI,EAAE,oBAAoB,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,UAAU,EAAE,SAAS,EAAE,IAAI,EAAE,KAAK,EAAe,CAAC;IAC3G,CAAC;IACD,qBAAqB,CAAC,GAAQ,EAAE,SAAiB;QAC/C,OAAO,EAAE,IAAI,EAAE,yBAAyB,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,UAAU,EAAE,SAAS,EAAe,CAAC;IACnG,CAAC;IACD,uBAAuB,CAAC,GAAQ,EAAE,SAAiB,EAAE,KAAa;QAChE,OAAO,EAAE,IAAI,EAAE,2BAA2B,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,UAAU,EAAE,SAAS,EAAE,KAAK,EAAe,CAAC;IAC5G,CAAC;IACD,mBAAmB,CAAC,GAAQ,EAAE,SAAiB;QAC7C,OAAO,EAAE,IAAI,EAAE,uBAAuB,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,UAAU,EAAE,SAAS,EAAe,CAAC;IACjG,CAAC;IACD,aAAa,CAAC,GAAQ,EAAE,UAAkB,EAAE,QAAgB,EAAE,eAAwB;QACpF,OAAO;YACL,IAAI,EAAE,iBAAiB;YACvB,GAAG,QAAQ,CAAC,GAAG,CAAC;YAChB,YAAY,EAAE,UAAU;YACxB,cAAc,EAAE,QAAQ;YACxB,iBAAiB,EAAE,eAAe;SACtB,CAAC;IACjB,CAAC;IACD,YAAY,CAAC,GAAQ,EAAE,UAAkB,EAAE,KAAa;QACtD,OAAO,EAAE,IAAI,EAAE,gBAAgB,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,YAAY,EAAE,UAAU,EAAE,KAAK,EAAe,CAAC;IACpG,CAAC;IACD,WAAW,CAAC,GAAQ,EAAE,UAAkB;QACtC,OAAO,EAAE,IAAI,EAAE,eAAe,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,YAAY,EAAE,UAAU,EAAe,CAAC;IAC5F,CAAC;IACD,cAAc,CAAC,GAAQ,EAAE,UAAkB,EAAE,OAAe,EAAE,OAAO,GAAG,KAAK,EAAE,SAAkB;QAC/F,OAAO;YACL,IAAI,EAAE,kBAAkB;YACxB,GAAG,QAAQ,CAAC,GAAG,CAAC;YAChB,YAAY,EAAE,UAAU;YACxB,UAAU,EAAE,SAAS,IAAI,YAAY,EAAE;YACvC,OAAO;YACP,QAAQ,EAAE,OAAO;SACL,CAAC;IACjB,CAAC;IACD,iBAAiB,CACf,GAAQ,EACR,IAAY,EACZ,MAAgD,EAChD,KAIC;QAED,MAAM,CAAC,GAA4B;YACjC,IAAI,EAAE,qBAAqB;YAC3B,GAAG,QAAQ,CAAC,EAAE,GAAG,GAAG,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC;YACxC,IAAI;YACJ,MAAM;SACP,CAAC;QACF,IAAI,KAAK,EAAE,WAAW,KAAK,SAAS;YAAE,CAAC,CAAC,aAAa,GAAG,KAAK,CAAC,WAAW,CAAC;QAC1E,IAAI,KAAK,EAAE,oBAAoB,IAAI,KAAK,CAAC,oBAAoB,CAAC,MAAM;YAClE,CAAC,CAAC,sBAAsB,GAAG,KAAK,CAAC,oBAAoB,CAAC;QACxD,IAAI,KAAK,EAAE,SAAS,EAAE,CAAC;YACrB,CAAC,CAAC,UAAU,GAAG;gBACb,OAAO,EAAE,KAAK,CAAC,SAAS,CAAC,OAAO;gBAChC,SAAS,EAAE,KAAK,CAAC,SAAS,CAAC,SAAS;gBACpC,iBAAiB,EAAE,KAAK,CAAC,SAAS,CAAC,gBAAgB;aACpD,CAAC;QACJ,CAAC;QACD,OAAO,CAAc,CAAC;IACxB,CAAC;IACD,gBAAgB,CACd,GAAQ,EACR,GAA2G;QAE3G,OAAO;YACL,IAAI,EAAE,oBAAoB;YAC1B,GAAG,QAAQ,CAAC,GAAG,CAAC;YAChB,UAAU,EAAE,GAAG,CAAC,UAAU;YAC1B,KAAK,EAAE,GAAG,CAAC,KAAK;YAChB,QAAQ,EAAE,GAAG,CAAC,QAAQ;YACtB,OAAO,EAAE,GAAG,CAAC,OAAO;YACpB,eAAe,EAAE,GAAG,CAAC,eAAe;SACxB,CAAC;IACjB,CAAC;IACD,aAAa,CACX,SAAiB,EACjB,KAA6C,EAC7C,OAAe,EACf,IAAkE;QAElE,OAAO;YACL,IAAI,EAAE,gBAAgB;YACtB,UAAU,EAAE,SAAS;YACrB,KAAK,EAAE,IAAI,EAAE,KAAK;YAClB,KAAK;YACL,OAAO;YACP,OAAO,EAAE,IAAI,EAAE,OAAO;YACtB,SAAS,EAAE,EAAE,EAAE;YACf,WAAW,EAAE,IAAI,EAAE,WAAW,IAAI,IAAI;SAC1B,CAAC;IACjB,CAAC;IACD,MAAM,CAAC,GAAQ,EAAE,IAAY,EAAE,KAAc;QAC3C,OAAO,EAAE,IAAI,EAAE,QAAQ,EAAE,GAAG,QAAQ,CAAC,GAAG,CAAC,EAAE,IAAI,EAAE,KAAK,EAAe,CAAC;IACxE,CAAC;CACF,CAAC"}
@@ -0,0 +1,91 @@
1
+ /**
2
+ * agent-status — a Pi-native extension that injects a fresh team-status block
3
+ * at the top of EVERY turn for the agent it is registered on (#97).
4
+ *
5
+ * Why an extension / the `context` hook (not the system prompt):
6
+ * - The per-role persona is injected via `appendSystemPrompt`, which Pi
7
+ * evaluates ONCE at session creation. A team-status snapshot put there would
8
+ * be frozen at "session start" and go stale immediately.
9
+ * - Pi's `context` hook fires before EACH LLM call (every turn within a run)
10
+ * and lets an extension non-destructively rewrite the `messages` array that
11
+ * is sent to the model. That rewrite is per-turn EPHEMERAL — it is applied to
12
+ * a local copy and is NOT persisted to the session history (events.jsonl).
13
+ * So a status block injected here is recomputed and current on every turn,
14
+ * and never accumulates stale snapshots on disk.
15
+ *
16
+ * Mechanism (Pi SDK, verified against the docs corpus):
17
+ * - Registered per-AgentSession via DefaultResourceLoader.extensionFactories,
18
+ * same as trace-reminder. Closure state is naturally per-agent.
19
+ * - `context` handler receives `{ messages }` (a safe-to-mutate copy) and may
20
+ * return `{ messages }` to replace what the model sees this turn.
21
+ * - Because the host appends a NEW block each turn, we first STRIP any block we
22
+ * injected on a previous turn (identified by the `<agent_status>` opener) so
23
+ * the model only ever sees the latest snapshot, not a pile of old ones.
24
+ *
25
+ * Only the real factory loads this — the mock has no Pi event loop, so the
26
+ * behavioural injection is verified in real mode. The pure block renderer
27
+ * (`renderAgentStatusBlock`) and the strip/inject logic are unit-tested here via
28
+ * a fake `pi`.
29
+ */
30
+ /** One agent's live state, as seen by the status block. */
31
+ export interface AgentStatusLine {
32
+ name: string;
33
+ /** Authoritative status: idle | running | error | stopped. */
34
+ status: string;
35
+ /** Inbound messages still queued unread in this agent's inbox. */
36
+ unread: number;
37
+ }
38
+ /**
39
+ * Build the team-status block as a natural-language list (#97, option B). The
40
+ * wording is self-explanatory so the model needs no schema knowledge: each line
41
+ * names an agent, its status, and how many messages are still waiting unread in
42
+ * its inbox. Returns "" when there is nothing to report (caller skips injection).
43
+ *
44
+ * `lines` should already be filtered by the caller (trace agent excluded,
45
+ * stopped agents excluded). Order is preserved.
46
+ */
47
+ export declare function renderAgentStatusBlock(lines: readonly AgentStatusLine[]): string;
48
+ /** Minimal structural surface of an agent the collector reads. */
49
+ export interface StatusAgentLike {
50
+ name: string;
51
+ role: string;
52
+ status: string;
53
+ }
54
+ /**
55
+ * Collect the status lines for a team snapshot from the live agents (#97).
56
+ * Includes every agent — INCLUDING the principal, so it sees its own backlog —
57
+ * except the trace agent (an internal recorder) and any stopped agent
58
+ * (destroyed; irrelevant to coordination). `unreadOf` returns the number of
59
+ * messages still queued unread in that agent's inbox. Order follows iteration.
60
+ */
61
+ export declare function collectAgentStatusLines(agents: Iterable<StatusAgentLike>, unreadOf: (name: string) => number): AgentStatusLine[];
62
+ /** Minimal structural surface of Pi's ExtensionAPI we depend on. */
63
+ interface PiContextMessage {
64
+ role: string;
65
+ content: Array<{
66
+ type: string;
67
+ text?: string;
68
+ }>;
69
+ timestamp?: number;
70
+ }
71
+ interface PiExtensionApi {
72
+ on(event: "context", handler: (e: {
73
+ messages: PiContextMessage[];
74
+ }) => {
75
+ messages: PiContextMessage[];
76
+ } | void): void;
77
+ }
78
+ export interface AgentStatusDeps {
79
+ /**
80
+ * Compute the current status block. Called once per turn. Returns "" when
81
+ * there is nothing to inject (the handler then only strips any stale block).
82
+ */
83
+ renderStatus: () => string;
84
+ }
85
+ /**
86
+ * Build the extension factory for one agent. The returned function is what Pi
87
+ * calls with the per-session `ExtensionAPI`.
88
+ */
89
+ export declare function makeAgentStatusExt(deps: AgentStatusDeps): (pi: PiExtensionApi) => void;
90
+ export {};
91
+ //# sourceMappingURL=agent-status.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"agent-status.d.ts","sourceRoot":"","sources":["../../src/extensions/agent-status.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA4BG;AAEH,2DAA2D;AAC3D,MAAM,WAAW,eAAe;IAC9B,IAAI,EAAE,MAAM,CAAC;IACb,8DAA8D;IAC9D,MAAM,EAAE,MAAM,CAAC;IACf,kEAAkE;IAClE,MAAM,EAAE,MAAM,CAAC;CAChB;AAMD;;;;;;;;GAQG;AACH,wBAAgB,sBAAsB,CAAC,KAAK,EAAE,SAAS,eAAe,EAAE,GAAG,MAAM,CAehF;AAED,kEAAkE;AAClE,MAAM,WAAW,eAAe;IAC9B,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC;IACb,MAAM,EAAE,MAAM,CAAC;CAChB;AAED;;;;;;GAMG;AACH,wBAAgB,uBAAuB,CACrC,MAAM,EAAE,QAAQ,CAAC,eAAe,CAAC,EACjC,QAAQ,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,MAAM,GACjC,eAAe,EAAE,CAQnB;AAED,oEAAoE;AACpE,UAAU,gBAAgB;IACxB,IAAI,EAAE,MAAM,CAAC;IACb,OAAO,EAAE,KAAK,CAAC;QAAE,IAAI,EAAE,MAAM,CAAC;QAAC,IAAI,CAAC,EAAE,MAAM,CAAA;KAAE,CAAC,CAAC;IAChD,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AACD,UAAU,cAAc;IACtB,EAAE,CACA,KAAK,EAAE,SAAS,EAChB,OAAO,EAAE,CAAC,CAAC,EAAE;QACX,QAAQ,EAAE,gBAAgB,EAAE,CAAC;KAC9B,KAAK;QAAE,QAAQ,EAAE,gBAAgB,EAAE,CAAA;KAAE,GAAG,IAAI,GAC5C,IAAI,CAAC;CACT;AAED,MAAM,WAAW,eAAe;IAC9B;;;OAGG;IACH,YAAY,EAAE,MAAM,MAAM,CAAC;CAC5B;AAUD;;;GAGG;AACH,wBAAgB,kBAAkB,CAAC,IAAI,EAAE,eAAe,GAAG,CAAC,EAAE,EAAE,cAAc,KAAK,IAAI,CAoBtF"}