electric-ax 0.2.8 → 0.2.9

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.
@@ -2,6 +2,7 @@
2
2
  const require_chunk = require('./chunk-BCwAaXi7.cjs');
3
3
  const omelette = require_chunk.__toESM(require("omelette"));
4
4
  const __electric_sql_client = require_chunk.__toESM(require("@electric-sql/client"));
5
+ const __electric_ax_agents_runtime = require_chunk.__toESM(require("@electric-ax/agents-runtime"));
5
6
 
6
7
  //#region src/shape-fetch.ts
7
8
  /**
@@ -11,7 +12,7 @@ const __electric_sql_client = require_chunk.__toESM(require("@electric-sql/clien
11
12
  */
12
13
  async function fetchShapeRows(baseUrl, table, options) {
13
14
  const stream = new __electric_sql_client.ShapeStream({
14
- url: `${baseUrl}/_electric/electric/v1/shape`,
15
+ url: (0, __electric_ax_agents_runtime.appendPathToUrl)(baseUrl, `/_electric/electric/v1/shape`),
15
16
  params: { table },
16
17
  subscribe: false,
17
18
  signal: options?.signal
@@ -30,6 +31,7 @@ const AGENTS_COMMANDS = [
30
31
  `spawn`,
31
32
  `send`,
32
33
  `observe`,
34
+ `view`,
33
35
  `inspect`,
34
36
  `ps`,
35
37
  `signal`,
@@ -46,6 +48,7 @@ const COMMAND_FLAGS = {
46
48
  spawn: [`--args`],
47
49
  send: [`--type`, `--json`],
48
50
  observe: [`--from`],
51
+ view: [`--from`],
49
52
  signal: [`--reason`, `--payload`],
50
53
  ps: [
51
54
  `--type`,
@@ -77,6 +80,7 @@ function fetchEntityUrls(env) {
77
80
  const ENTITY_URL_COMMANDS = new Set([
78
81
  `send`,
79
82
  `observe`,
83
+ `view`,
80
84
  `inspect`,
81
85
  `signal`,
82
86
  `kill`
@@ -1,5 +1,6 @@
1
1
  import omelette from "omelette";
2
2
  import { Shape, ShapeStream } from "@electric-sql/client";
3
+ import { appendPathToUrl } from "@electric-ax/agents-runtime";
3
4
 
4
5
  //#region src/shape-fetch.ts
5
6
  /**
@@ -9,7 +10,7 @@ import { Shape, ShapeStream } from "@electric-sql/client";
9
10
  */
10
11
  async function fetchShapeRows(baseUrl, table, options) {
11
12
  const stream = new ShapeStream({
12
- url: `${baseUrl}/_electric/electric/v1/shape`,
13
+ url: appendPathToUrl(baseUrl, `/_electric/electric/v1/shape`),
13
14
  params: { table },
14
15
  subscribe: false,
15
16
  signal: options?.signal
@@ -28,6 +29,7 @@ const AGENTS_COMMANDS = [
28
29
  `spawn`,
29
30
  `send`,
30
31
  `observe`,
32
+ `view`,
31
33
  `inspect`,
32
34
  `ps`,
33
35
  `signal`,
@@ -44,6 +46,7 @@ const COMMAND_FLAGS = {
44
46
  spawn: [`--args`],
45
47
  send: [`--type`, `--json`],
46
48
  observe: [`--from`],
49
+ view: [`--from`],
47
50
  signal: [`--reason`, `--payload`],
48
51
  ps: [
49
52
  `--type`,
@@ -75,6 +78,7 @@ function fetchEntityUrls(env) {
75
78
  const ENTITY_URL_COMMANDS = new Set([
76
79
  `send`,
77
80
  `observe`,
81
+ `view`,
78
82
  `inspect`,
79
83
  `signal`,
80
84
  `kill`
@@ -1,4 +1,4 @@
1
- const require_completions = require('./completions-BeohCOLD.cjs');
1
+ const require_completions = require('./completions-BJ1fys8I.cjs');
2
2
 
3
3
  exports.fetchEntityTypeNames = require_completions.fetchEntityTypeNames
4
4
  exports.fetchEntityUrls = require_completions.fetchEntityUrls
@@ -1,4 +1,4 @@
1
- import { ElectricCliEnv } from "./index-DmR3DeFk.cjs";
1
+ import { ElectricCliEnv } from "./index-_AHIJdEA.cjs";
2
2
 
3
3
  //#region src/completions.d.ts
4
4
  declare function fetchEntityTypeNames(env: ElectricCliEnv): Promise<Array<string>>;
@@ -1,4 +1,4 @@
1
- import { ElectricCliEnv } from "./index-BsITLCxF.js";
1
+ import { ElectricCliEnv } from "./index-CQN8S3b9.js";
2
2
 
3
3
  //#region src/completions.d.ts
4
4
  declare function fetchEntityTypeNames(env: ElectricCliEnv): Promise<Array<string>>;
@@ -1,3 +1,3 @@
1
- import { fetchEntityTypeNames, fetchEntityUrls, installCompletions, setupCompletions } from "./completions-3RE2mC2p.js";
1
+ import { fetchEntityTypeNames, fetchEntityUrls, installCompletions, setupCompletions } from "./completions-BkhbBSPI.js";
2
2
 
3
3
  export { fetchEntityTypeNames, fetchEntityUrls, installCompletions, setupCompletions };
@@ -1,14 +1,24 @@
1
- import { entityApiUrl } from "./entity-api-DWMhkYbl.js";
2
- import { createStreamDB } from "@durable-streams/state";
3
1
  import { appendPathToUrl, entityStateSchema } from "@electric-ax/agents-runtime";
2
+ import { createStreamDB } from "@durable-streams/state";
4
3
 
4
+ //#region src/entity-api.ts
5
+ function withLeadingSlash(path) {
6
+ return path.startsWith(`/`) ? path : `/${path}`;
7
+ }
8
+ function entityApiPath(entityUrl, suffix = ``) {
9
+ return `/_electric/entities${withLeadingSlash(entityUrl)}${suffix}`;
10
+ }
11
+ function entityApiUrl(baseUrl, entityUrl, suffix = ``) {
12
+ return appendPathToUrl(baseUrl, entityApiPath(entityUrl, suffix));
13
+ }
14
+
15
+ //#endregion
5
16
  //#region src/entity-stream-db.ts
6
17
  function getMainStreamPath(entityUrl, entity) {
7
18
  return entity.streams?.main ?? `${entityUrl}/main`;
8
19
  }
9
20
  async function createEntityStreamDB(opts) {
10
21
  const { baseUrl, entityUrl, initialOffset, headers: serverHeaders } = opts;
11
- console.log(`[createEntityStreamDB] Creating entity stream DB for ${baseUrl}${entityUrl}`);
12
22
  const requestHeaders = {
13
23
  "content-type": `application/json`,
14
24
  ...serverHeaders
@@ -40,4 +50,4 @@ async function createEntityStreamDB(opts) {
40
50
  }
41
51
 
42
52
  //#endregion
43
- export { createEntityStreamDB };
53
+ export { createEntityStreamDB, entityApiPath, entityApiUrl };
@@ -1,23 +1,33 @@
1
1
  "use strict";
2
2
  const require_chunk = require('./chunk-BCwAaXi7.cjs');
3
- const require_entity_api = require('./entity-api-Cvo55yZx.cjs');
4
- const __durable_streams_state = require_chunk.__toESM(require("@durable-streams/state"));
5
3
  const __electric_ax_agents_runtime = require_chunk.__toESM(require("@electric-ax/agents-runtime"));
4
+ const __durable_streams_state = require_chunk.__toESM(require("@durable-streams/state"));
6
5
 
6
+ //#region src/entity-api.ts
7
+ function withLeadingSlash(path) {
8
+ return path.startsWith(`/`) ? path : `/${path}`;
9
+ }
10
+ function entityApiPath(entityUrl, suffix = ``) {
11
+ return `/_electric/entities${withLeadingSlash(entityUrl)}${suffix}`;
12
+ }
13
+ function entityApiUrl(baseUrl, entityUrl, suffix = ``) {
14
+ return (0, __electric_ax_agents_runtime.appendPathToUrl)(baseUrl, entityApiPath(entityUrl, suffix));
15
+ }
16
+
17
+ //#endregion
7
18
  //#region src/entity-stream-db.ts
8
19
  function getMainStreamPath(entityUrl, entity) {
9
20
  return entity.streams?.main ?? `${entityUrl}/main`;
10
21
  }
11
22
  async function createEntityStreamDB(opts) {
12
23
  const { baseUrl, entityUrl, initialOffset, headers: serverHeaders } = opts;
13
- console.log(`[createEntityStreamDB] Creating entity stream DB for ${baseUrl}${entityUrl}`);
14
24
  const requestHeaders = {
15
25
  "content-type": `application/json`,
16
26
  ...serverHeaders
17
27
  };
18
28
  let res;
19
29
  try {
20
- res = await fetch(require_entity_api.entityApiUrl(baseUrl, entityUrl), { headers: requestHeaders });
30
+ res = await fetch(entityApiUrl(baseUrl, entityUrl), { headers: requestHeaders });
21
31
  } catch (err) {
22
32
  throw new Error(`Could not connect to the Electric Agents server at ${baseUrl} — is it running?\n ${err instanceof Error ? err.message : String(err)}`);
23
33
  }
@@ -47,4 +57,16 @@ Object.defineProperty(exports, 'createEntityStreamDB', {
47
57
  get: function () {
48
58
  return createEntityStreamDB;
49
59
  }
60
+ });
61
+ Object.defineProperty(exports, 'entityApiPath', {
62
+ enumerable: true,
63
+ get: function () {
64
+ return entityApiPath;
65
+ }
66
+ });
67
+ Object.defineProperty(exports, 'entityApiUrl', {
68
+ enumerable: true,
69
+ get: function () {
70
+ return entityApiUrl;
71
+ }
50
72
  });
@@ -1,4 +1,3 @@
1
- require('./entity-api-Cvo55yZx.cjs');
2
- const require_entity_stream_db = require('./entity-stream-db-CIv6uC2d.cjs');
1
+ const require_entity_stream_db = require('./entity-stream-db-DHcwosd1.cjs');
3
2
 
4
3
  exports.createEntityStreamDB = require_entity_stream_db.createEntityStreamDB
@@ -1,2 +1,2 @@
1
- import { EntityStreamDB, createEntityStreamDB$1 as createEntityStreamDB } from "./entity-stream-db-Bl6AT5hR.js";
1
+ import { EntityStreamDB, createEntityStreamDB$1 as createEntityStreamDB } from "./entity-stream-db-BROzlu7p.js";
2
2
  export { EntityStreamDB, createEntityStreamDB };
@@ -1,4 +1,3 @@
1
- import "./entity-api-DWMhkYbl.js";
2
- import { createEntityStreamDB } from "./entity-stream-db-CDOlZYc2.js";
1
+ import { createEntityStreamDB } from "./entity-stream-db-58-SuPa4.js";
3
2
 
4
3
  export { createEntityStreamDB };
@@ -88,6 +88,7 @@ interface ElectricCliHandlers {
88
88
  spawn: (urlPath: string, options: SpawnCommandOptions) => Promise<void>;
89
89
  send: (url: string, message: string, options: SendCommandOptions) => Promise<void>;
90
90
  observe: (url: string, options: ObserveCommandOptions) => Promise<void>;
91
+ view: (url: string, options: ObserveCommandOptions) => Promise<void>;
91
92
  inspect: (url: string) => Promise<void>;
92
93
  ps: (options: PsCommandOptions) => Promise<void>;
93
94
  signal: (url: string, signal: string, options: SignalCommandOptions) => Promise<void>;
@@ -88,6 +88,7 @@ interface ElectricCliHandlers {
88
88
  spawn: (urlPath: string, options: SpawnCommandOptions) => Promise<void>;
89
89
  send: (url: string, message: string, options: SendCommandOptions) => Promise<void>;
90
90
  observe: (url: string, options: ObserveCommandOptions) => Promise<void>;
91
+ view: (url: string, options: ObserveCommandOptions) => Promise<void>;
91
92
  inspect: (url: string) => Promise<void>;
92
93
  ps: (options: PsCommandOptions) => Promise<void>;
93
94
  signal: (url: string, signal: string, options: SignalCommandOptions) => Promise<void>;
package/dist/index.cjs CHANGED
@@ -1,9 +1,9 @@
1
1
  #!/usr/bin/env node
2
2
  "use strict";
3
3
  const require_chunk = require('./chunk-BCwAaXi7.cjs');
4
- const require_completions = require('./completions-BeohCOLD.cjs');
5
- const require_entity_api = require('./entity-api-Cvo55yZx.cjs');
6
- const require_env = require('./env-CFKgT8o2.cjs');
4
+ const require_completions = require('./completions-BJ1fys8I.cjs');
5
+ const require_entity_stream_db = require('./entity-stream-db-DHcwosd1.cjs');
6
+ const require_env = require('./env-BXUgom_C.cjs');
7
7
  const __electric_ax_agents_runtime = require_chunk.__toESM(require("@electric-ax/agents-runtime"));
8
8
  const node_fs = require_chunk.__toESM(require("node:fs"));
9
9
  const node_os = require_chunk.__toESM(require("node:os"));
@@ -136,6 +136,73 @@ function writeApiKeyToDotEnv(key, cwd) {
136
136
  return envPath;
137
137
  }
138
138
 
139
+ //#endregion
140
+ //#region src/view.ts
141
+ const TOOL_RESULT_MAX_LINES = 5;
142
+ const TOOL_RESULT_MAX_COLUMNS = 120;
143
+ function truncate(value, max) {
144
+ return value.length > max ? `${value.slice(0, max - 3)}...` : value;
145
+ }
146
+ function appendIndented(lines, text, prefix) {
147
+ const textLines = text.split(/\r?\n/);
148
+ for (const line of textLines) lines.push(`${prefix}${line}`);
149
+ }
150
+ function appendTextBlock(blocks, label, text) {
151
+ const lines = [`${label}:`];
152
+ appendIndented(lines, text, ` `);
153
+ blocks.push(lines.join(`\n`));
154
+ }
155
+ function wakeReason(section) {
156
+ const { payload } = section;
157
+ if (payload.timeout) return `timeout`;
158
+ if (payload.finished_child) return `child ${payload.finished_child.run_status}`;
159
+ if (payload.changes.length > 0) return `${payload.changes.length} ${payload.changes.length === 1 ? `change` : `changes`}`;
160
+ if (payload.other_children && payload.other_children.length > 0) return `${payload.other_children.length} child ${payload.other_children.length === 1 ? `update` : `updates`}`;
161
+ return payload.source;
162
+ }
163
+ function appendToolCall(lines, item) {
164
+ const status = item.isError ? `failed` : item.status;
165
+ lines.push(` [tool:${item.toolName}] ${status}`);
166
+ if (item.result === void 0) return;
167
+ const resultLines = item.result.split(/\r?\n/);
168
+ for (const line of resultLines.slice(0, TOOL_RESULT_MAX_LINES)) lines.push(` ${truncate(line, TOOL_RESULT_MAX_COLUMNS)}`);
169
+ const remaining = resultLines.length - TOOL_RESULT_MAX_LINES;
170
+ if (remaining > 0) lines.push(` ... ${remaining} more lines`);
171
+ }
172
+ function appendAgentResponse(blocks, section, label) {
173
+ const lines = [`${label}:`];
174
+ for (const item of section.items) {
175
+ if (item.kind === `text`) {
176
+ appendIndented(lines, item.text, ` `);
177
+ continue;
178
+ }
179
+ appendToolCall(lines, item);
180
+ }
181
+ if (section.error) appendIndented(lines, `[error] ${section.error}`, ` `);
182
+ if (lines.length === 1) lines.push(` (no output)`);
183
+ blocks.push(lines.join(`\n`));
184
+ }
185
+ function formatEntityConversationView(data, options) {
186
+ const sections = (0, __electric_ax_agents_runtime.buildSections)(data.runs, data.inbox, data.wakes);
187
+ if (sections.length === 0) return `No conversation events found`;
188
+ const blocks = [];
189
+ for (const section of sections) {
190
+ if (section.kind === `user_message`) {
191
+ appendTextBlock(blocks, section.from ?? `user`, section.text);
192
+ continue;
193
+ }
194
+ if (section.kind === `wake`) {
195
+ appendTextBlock(blocks, `wake`, `${wakeReason(section)} from ${section.payload.source}`);
196
+ continue;
197
+ }
198
+ appendAgentResponse(blocks, section, options.entityUrl);
199
+ }
200
+ return blocks.join(`\n\n`);
201
+ }
202
+ function formatEntityConversationViewFromDB(db, options) {
203
+ return formatEntityConversationView((0, __electric_ax_agents_runtime.buildEntityTimelineData)(db), options);
204
+ }
205
+
139
206
  //#endregion
140
207
  //#region src/index.ts
141
208
  const DEFAULT_ELECTRIC_AGENTS_URL = `http://localhost:4437`;
@@ -414,7 +481,7 @@ async function spawnEntity(env, urlPath, options) {
414
481
  } catch (error) {
415
482
  fail(`--args must be valid JSON: ${getErrorMessage(error)}`);
416
483
  }
417
- const res = await electricAgentsFetch(env, require_entity_api.entityApiPath(urlPath), {
484
+ const res = await electricAgentsFetch(env, require_entity_stream_db.entityApiPath(urlPath), {
418
485
  method: `PUT`,
419
486
  body: JSON.stringify({ args: spawnArgs })
420
487
  });
@@ -431,7 +498,7 @@ async function sendMessage(env, url, message, options) {
431
498
  payload
432
499
  };
433
500
  if (options.type) body.type = options.type;
434
- const res = await electricAgentsFetch(env, require_entity_api.entityApiPath(url, `/send`), {
501
+ const res = await electricAgentsFetch(env, require_entity_stream_db.entityApiPath(url, `/send`), {
435
502
  method: `POST`,
436
503
  body: JSON.stringify(body)
437
504
  });
@@ -452,8 +519,21 @@ async function observeEntity(env, url, options) {
452
519
  initialOffset: options.from
453
520
  });
454
521
  }
522
+ async function viewEntity(env, url, options) {
523
+ const { db, close } = await require_entity_stream_db.createEntityStreamDB({
524
+ entityUrl: url,
525
+ baseUrl: env.electricAgentsUrl,
526
+ headers: env.electricAgentsHeaders,
527
+ initialOffset: options.from
528
+ });
529
+ try {
530
+ console.log(formatEntityConversationViewFromDB(db, { entityUrl: url }));
531
+ } finally {
532
+ close();
533
+ }
534
+ }
455
535
  async function inspectEntity(env, url) {
456
- const res = await electricAgentsFetch(env, require_entity_api.entityApiPath(url));
536
+ const res = await electricAgentsFetch(env, require_entity_stream_db.entityApiPath(url));
457
537
  const data = await parseJsonResponse(res);
458
538
  if (!res.ok) failFromResponse(data, res);
459
539
  console.log(JSON.stringify(data, null, 2));
@@ -478,7 +558,7 @@ async function listEntities(env, options) {
478
558
  }
479
559
  }
480
560
  async function killEntity(env, url) {
481
- const res = await electricAgentsFetch(env, require_entity_api.entityApiPath(url, `/signal`), {
561
+ const res = await electricAgentsFetch(env, require_entity_stream_db.entityApiPath(url, `/signal`), {
482
562
  method: `POST`,
483
563
  body: JSON.stringify({
484
564
  signal: `SIGKILL`,
@@ -496,7 +576,7 @@ async function signalEntity(env, url, rawSignal, options) {
496
576
  const body = { signal };
497
577
  if (options.reason !== void 0) body.reason = options.reason;
498
578
  if (options.payload !== void 0) body.payload = parseJsonOption(`--payload`, options.payload);
499
- const res = await electricAgentsFetch(env, require_entity_api.entityApiPath(url, `/signal`), {
579
+ const res = await electricAgentsFetch(env, require_entity_stream_db.entityApiPath(url, `/signal`), {
500
580
  method: `POST`,
501
581
  body: JSON.stringify(body)
502
582
  });
@@ -533,6 +613,7 @@ function createElectricCliHandlers(env, commandPrefix = commandExample(`electric
533
613
  spawn: (urlPath, options) => spawnEntity(env, urlPath, options),
534
614
  send: (url, message, options) => sendMessage(env, url, message, options),
535
615
  observe: (url, options) => observeEntity(env, url, options),
616
+ view: (url, options) => viewEntity(env, url, options),
536
617
  inspect: (url) => inspectEntity(env, url),
537
618
  ps: (options) => listEntities(env, options),
538
619
  signal: (url, signal, options) => signalEntity(env, url, signal, options),
@@ -635,6 +716,11 @@ function createElectricProgram({ env = getElectricCliEnv(), commandName = `elect
635
716
  const command = getCommandActionArg(actionArgs);
636
717
  await handlers.observe(url, command.opts());
637
718
  });
719
+ agentsCommand.command(`view <url>`).description(`Print an entity conversation once`).option(`--from <offset>`, `Initial offset`).action(async (...actionArgs) => {
720
+ const url = actionArgs[0];
721
+ const command = getCommandActionArg(actionArgs);
722
+ await handlers.view(url, command.opts());
723
+ });
638
724
  agentsCommand.command(`signal <url> <signal>`).description(`Send a lifecycle signal to an entity`).option(`--reason <text>`, `Human-readable signal reason`).option(`--payload <json>`, `JSON payload to attach to the signal`).action(async (...actionArgs) => {
639
725
  const url = actionArgs[0];
640
726
  const signal = actionArgs[1];
package/dist/index.d.cts CHANGED
@@ -1,3 +1,3 @@
1
1
  #!/usr/bin/env node
2
- import { DEFAULT_ELECTRIC_AGENTS_URL, ElectricCliEnv, ElectricCliHandlers, EntitySignal, ObserveCommandOptions, PsCommandOptions, SendCommandOptions, SignalCommandOptions, SpawnCommandOptions, StartBuiltinCommandOptions, StartCommandOptions, StartedBuiltinAgentsEnvironment, StartedDevEnvironment, StopCommandOptions, StoppedDevEnvironment, createElectricCliHandlers, createElectricProgram, formatQuickstartBackendStartedMessage, getElectricCliEnv, resolveCommandPrefix, run } from "./index-DmR3DeFk.cjs";
2
+ import { DEFAULT_ELECTRIC_AGENTS_URL, ElectricCliEnv, ElectricCliHandlers, EntitySignal, ObserveCommandOptions, PsCommandOptions, SendCommandOptions, SignalCommandOptions, SpawnCommandOptions, StartBuiltinCommandOptions, StartCommandOptions, StartedBuiltinAgentsEnvironment, StartedDevEnvironment, StopCommandOptions, StoppedDevEnvironment, createElectricCliHandlers, createElectricProgram, formatQuickstartBackendStartedMessage, getElectricCliEnv, resolveCommandPrefix, run } from "./index-_AHIJdEA.cjs";
3
3
  export { DEFAULT_ELECTRIC_AGENTS_URL, ElectricCliEnv, ElectricCliHandlers, EntitySignal, ObserveCommandOptions, PsCommandOptions, SendCommandOptions, SignalCommandOptions, SpawnCommandOptions, StartBuiltinCommandOptions, StartCommandOptions, StartedBuiltinAgentsEnvironment, StartedDevEnvironment, StopCommandOptions, StoppedDevEnvironment, createElectricCliHandlers, createElectricProgram, formatQuickstartBackendStartedMessage, getElectricCliEnv, resolveCommandPrefix, run };
package/dist/index.d.ts CHANGED
@@ -1,3 +1,3 @@
1
1
  #!/usr/bin/env node
2
- import { DEFAULT_ELECTRIC_AGENTS_URL, ElectricCliEnv, ElectricCliHandlers, EntitySignal, ObserveCommandOptions, PsCommandOptions, SendCommandOptions, SignalCommandOptions, SpawnCommandOptions, StartBuiltinCommandOptions, StartCommandOptions, StartedBuiltinAgentsEnvironment, StartedDevEnvironment, StopCommandOptions, StoppedDevEnvironment, createElectricCliHandlers, createElectricProgram, formatQuickstartBackendStartedMessage, getElectricCliEnv, resolveCommandPrefix, run } from "./index-BsITLCxF.js";
2
+ import { DEFAULT_ELECTRIC_AGENTS_URL, ElectricCliEnv, ElectricCliHandlers, EntitySignal, ObserveCommandOptions, PsCommandOptions, SendCommandOptions, SignalCommandOptions, SpawnCommandOptions, StartBuiltinCommandOptions, StartCommandOptions, StartedBuiltinAgentsEnvironment, StartedDevEnvironment, StopCommandOptions, StoppedDevEnvironment, createElectricCliHandlers, createElectricProgram, formatQuickstartBackendStartedMessage, getElectricCliEnv, resolveCommandPrefix, run } from "./index-CQN8S3b9.js";
3
3
  export { DEFAULT_ELECTRIC_AGENTS_URL, ElectricCliEnv, ElectricCliHandlers, EntitySignal, ObserveCommandOptions, PsCommandOptions, SendCommandOptions, SignalCommandOptions, SpawnCommandOptions, StartBuiltinCommandOptions, StartCommandOptions, StartedBuiltinAgentsEnvironment, StartedDevEnvironment, StopCommandOptions, StoppedDevEnvironment, createElectricCliHandlers, createElectricProgram, formatQuickstartBackendStartedMessage, getElectricCliEnv, resolveCommandPrefix, run };
package/dist/index.js CHANGED
@@ -1,8 +1,8 @@
1
1
  #!/usr/bin/env node
2
- import { installCompletions, setupCompletions } from "./completions-3RE2mC2p.js";
3
- import { entityApiPath } from "./entity-api-DWMhkYbl.js";
4
- import { resolveAnthropicApiKey$1 as resolveAnthropicApiKey } from "./env-DIhTv987.js";
5
- import { appendPathToUrl } from "@electric-ax/agents-runtime";
2
+ import { installCompletions, setupCompletions } from "./completions-BkhbBSPI.js";
3
+ import { createEntityStreamDB, entityApiPath } from "./entity-stream-db-58-SuPa4.js";
4
+ import { resolveAnthropicApiKey$1 as resolveAnthropicApiKey } from "./env-LZtIfFz1.js";
5
+ import { appendPathToUrl, buildEntityTimelineData, buildSections } from "@electric-ax/agents-runtime";
6
6
  import { existsSync, readFileSync, realpathSync, writeFileSync } from "node:fs";
7
7
  import { hostname, userInfo } from "node:os";
8
8
  import { basename, resolve } from "node:path";
@@ -134,6 +134,73 @@ function writeApiKeyToDotEnv(key, cwd) {
134
134
  return envPath;
135
135
  }
136
136
 
137
+ //#endregion
138
+ //#region src/view.ts
139
+ const TOOL_RESULT_MAX_LINES = 5;
140
+ const TOOL_RESULT_MAX_COLUMNS = 120;
141
+ function truncate(value, max) {
142
+ return value.length > max ? `${value.slice(0, max - 3)}...` : value;
143
+ }
144
+ function appendIndented(lines, text, prefix) {
145
+ const textLines = text.split(/\r?\n/);
146
+ for (const line of textLines) lines.push(`${prefix}${line}`);
147
+ }
148
+ function appendTextBlock(blocks, label, text) {
149
+ const lines = [`${label}:`];
150
+ appendIndented(lines, text, ` `);
151
+ blocks.push(lines.join(`\n`));
152
+ }
153
+ function wakeReason(section) {
154
+ const { payload } = section;
155
+ if (payload.timeout) return `timeout`;
156
+ if (payload.finished_child) return `child ${payload.finished_child.run_status}`;
157
+ if (payload.changes.length > 0) return `${payload.changes.length} ${payload.changes.length === 1 ? `change` : `changes`}`;
158
+ if (payload.other_children && payload.other_children.length > 0) return `${payload.other_children.length} child ${payload.other_children.length === 1 ? `update` : `updates`}`;
159
+ return payload.source;
160
+ }
161
+ function appendToolCall(lines, item) {
162
+ const status = item.isError ? `failed` : item.status;
163
+ lines.push(` [tool:${item.toolName}] ${status}`);
164
+ if (item.result === void 0) return;
165
+ const resultLines = item.result.split(/\r?\n/);
166
+ for (const line of resultLines.slice(0, TOOL_RESULT_MAX_LINES)) lines.push(` ${truncate(line, TOOL_RESULT_MAX_COLUMNS)}`);
167
+ const remaining = resultLines.length - TOOL_RESULT_MAX_LINES;
168
+ if (remaining > 0) lines.push(` ... ${remaining} more lines`);
169
+ }
170
+ function appendAgentResponse(blocks, section, label) {
171
+ const lines = [`${label}:`];
172
+ for (const item of section.items) {
173
+ if (item.kind === `text`) {
174
+ appendIndented(lines, item.text, ` `);
175
+ continue;
176
+ }
177
+ appendToolCall(lines, item);
178
+ }
179
+ if (section.error) appendIndented(lines, `[error] ${section.error}`, ` `);
180
+ if (lines.length === 1) lines.push(` (no output)`);
181
+ blocks.push(lines.join(`\n`));
182
+ }
183
+ function formatEntityConversationView(data, options) {
184
+ const sections = buildSections(data.runs, data.inbox, data.wakes);
185
+ if (sections.length === 0) return `No conversation events found`;
186
+ const blocks = [];
187
+ for (const section of sections) {
188
+ if (section.kind === `user_message`) {
189
+ appendTextBlock(blocks, section.from ?? `user`, section.text);
190
+ continue;
191
+ }
192
+ if (section.kind === `wake`) {
193
+ appendTextBlock(blocks, `wake`, `${wakeReason(section)} from ${section.payload.source}`);
194
+ continue;
195
+ }
196
+ appendAgentResponse(blocks, section, options.entityUrl);
197
+ }
198
+ return blocks.join(`\n\n`);
199
+ }
200
+ function formatEntityConversationViewFromDB(db, options) {
201
+ return formatEntityConversationView(buildEntityTimelineData(db), options);
202
+ }
203
+
137
204
  //#endregion
138
205
  //#region src/index.ts
139
206
  const DEFAULT_ELECTRIC_AGENTS_URL = `http://localhost:4437`;
@@ -450,6 +517,19 @@ async function observeEntity(env, url, options) {
450
517
  initialOffset: options.from
451
518
  });
452
519
  }
520
+ async function viewEntity(env, url, options) {
521
+ const { db, close } = await createEntityStreamDB({
522
+ entityUrl: url,
523
+ baseUrl: env.electricAgentsUrl,
524
+ headers: env.electricAgentsHeaders,
525
+ initialOffset: options.from
526
+ });
527
+ try {
528
+ console.log(formatEntityConversationViewFromDB(db, { entityUrl: url }));
529
+ } finally {
530
+ close();
531
+ }
532
+ }
453
533
  async function inspectEntity(env, url) {
454
534
  const res = await electricAgentsFetch(env, entityApiPath(url));
455
535
  const data = await parseJsonResponse(res);
@@ -531,6 +611,7 @@ function createElectricCliHandlers(env, commandPrefix = commandExample(`electric
531
611
  spawn: (urlPath, options) => spawnEntity(env, urlPath, options),
532
612
  send: (url, message, options) => sendMessage(env, url, message, options),
533
613
  observe: (url, options) => observeEntity(env, url, options),
614
+ view: (url, options) => viewEntity(env, url, options),
534
615
  inspect: (url) => inspectEntity(env, url),
535
616
  ps: (options) => listEntities(env, options),
536
617
  signal: (url, signal, options) => signalEntity(env, url, signal, options),
@@ -633,6 +714,11 @@ function createElectricProgram({ env = getElectricCliEnv(), commandName = `elect
633
714
  const command = getCommandActionArg(actionArgs);
634
715
  await handlers.observe(url, command.opts());
635
716
  });
717
+ agentsCommand.command(`view <url>`).description(`Print an entity conversation once`).option(`--from <offset>`, `Initial offset`).action(async (...actionArgs) => {
718
+ const url = actionArgs[0];
719
+ const command = getCommandActionArg(actionArgs);
720
+ await handlers.view(url, command.opts());
721
+ });
636
722
  agentsCommand.command(`signal <url> <signal>`).description(`Send a lifecycle signal to an entity`).option(`--reason <text>`, `Human-readable signal reason`).option(`--payload <json>`, `JSON payload to attach to the signal`).action(async (...actionArgs) => {
637
723
  const url = actionArgs[0];
638
724
  const signal = actionArgs[1];
@@ -1,9 +1,8 @@
1
1
  "use strict";
2
2
  const require_chunk = require('./chunk-BCwAaXi7.cjs');
3
- const require_entity_api = require('./entity-api-Cvo55yZx.cjs');
4
- const require_entity_stream_db = require('./entity-stream-db-CIv6uC2d.cjs');
5
- const __durable_streams_state = require_chunk.__toESM(require("@durable-streams/state"));
3
+ const require_entity_stream_db = require('./entity-stream-db-DHcwosd1.cjs');
6
4
  const __electric_ax_agents_runtime = require_chunk.__toESM(require("@electric-ax/agents-runtime"));
5
+ const __durable_streams_state = require_chunk.__toESM(require("@durable-streams/state"));
7
6
  const react = require_chunk.__toESM(require("react"));
8
7
  const ink = require_chunk.__toESM(require("ink"));
9
8
  const __tanstack_react_db = require_chunk.__toESM(require("@tanstack/react-db"));
@@ -132,7 +131,7 @@ function MessageInput({ db, baseUrl, entityUrl, identity, headers, disabled }) {
132
131
  });
133
132
  },
134
133
  mutationFn: async ({ text }) => {
135
- const res = await fetch(require_entity_api.entityApiUrl(baseUrl, entityUrl, `/send`), {
134
+ const res = await fetch(require_entity_stream_db.entityApiUrl(baseUrl, entityUrl, `/send`), {
136
135
  method: `POST`,
137
136
  headers: {
138
137
  "content-type": `application/json`,
@@ -281,7 +280,12 @@ function ObserveView({ db, entityUrl, baseUrl, identity, headers }) {
281
280
  });
282
281
  const typedRuns = timelineData.runs;
283
282
  const typedInbox = timelineData.inbox;
284
- const timeline = (0, react.useMemo)(() => (0, __electric_ax_agents_runtime.buildSections)(typedRuns, typedInbox), [typedRuns, typedInbox]);
283
+ const typedWakes = timelineData.wakes;
284
+ const timeline = (0, react.useMemo)(() => (0, __electric_ax_agents_runtime.buildSections)(typedRuns, typedInbox, typedWakes), [
285
+ typedRuns,
286
+ typedInbox,
287
+ typedWakes
288
+ ]);
285
289
  const { data: stopped = [] } = (0, __tanstack_react_db.useLiveQuery)((q) => q.from({ entityStopped: db.collections.entityStopped }), [db]);
286
290
  const closed = stopped.length > 0;
287
291
  const lastAgentIndex = (0, react.useMemo)(() => {
@@ -1,4 +1,4 @@
1
- import { EntityStreamDB } from "./entity-stream-db-Bl6AT5hR.js";
1
+ import { EntityStreamDB } from "./entity-stream-db-BROzlu7p.js";
2
2
  import { EntityTimelineContentItem, MessageReceived } from "@electric-ax/agents-runtime";
3
3
  import React from "react";
4
4
 
@@ -1,7 +1,6 @@
1
- import { entityApiUrl } from "./entity-api-DWMhkYbl.js";
2
- import { createEntityStreamDB } from "./entity-stream-db-CDOlZYc2.js";
3
- import { createOptimisticAction } from "@durable-streams/state";
1
+ import { createEntityStreamDB, entityApiUrl } from "./entity-stream-db-58-SuPa4.js";
4
2
  import { buildSections, createEntityIncludesQuery, normalizeEntityTimelineData } from "@electric-ax/agents-runtime";
3
+ import { createOptimisticAction } from "@durable-streams/state";
5
4
  import React, { useEffect, useMemo, useRef, useState } from "react";
6
5
  import { Box, Newline, Text, render, useInput } from "ink";
7
6
  import { useLiveQuery } from "@tanstack/react-db";
@@ -279,7 +278,12 @@ function ObserveView({ db, entityUrl, baseUrl, identity, headers }) {
279
278
  });
280
279
  const typedRuns = timelineData.runs;
281
280
  const typedInbox = timelineData.inbox;
282
- const timeline = useMemo(() => buildSections(typedRuns, typedInbox), [typedRuns, typedInbox]);
281
+ const typedWakes = timelineData.wakes;
282
+ const timeline = useMemo(() => buildSections(typedRuns, typedInbox, typedWakes), [
283
+ typedRuns,
284
+ typedInbox,
285
+ typedWakes
286
+ ]);
283
287
  const { data: stopped = [] } = useLiveQuery((q) => q.from({ entityStopped: db.collections.entityStopped }), [db]);
284
288
  const closed = stopped.length > 0;
285
289
  const lastAgentIndex = useMemo(() => {
package/dist/start.cjs CHANGED
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
  const require_chunk = require('./chunk-BCwAaXi7.cjs');
3
- const require_env = require('./env-CFKgT8o2.cjs');
3
+ const require_env = require('./env-BXUgom_C.cjs');
4
4
  const __electric_ax_agents_runtime = require_chunk.__toESM(require("@electric-ax/agents-runtime"));
5
5
  const node_url = require_chunk.__toESM(require("node:url"));
6
6
  const __electric_ax_agents_server_headers = require_chunk.__toESM(require("@electric-ax/agents/server-headers"));
package/dist/start.d.cts CHANGED
@@ -1,2 +1,2 @@
1
- import { StartedBuiltinAgentsEnvironment, StartedDevEnvironment, StoppedDevEnvironment, getStartedBuiltinAgentsMessage, getStartedEnvironmentMessage, getStoppedEnvironmentMessage, readDotEnvFile, resolveAnthropicApiKey, resolveComposeProjectName, resolveElectricAgentsPort, resolvePullWakeOwnerPrincipal, resolvePullWakeRunnerId, startBuiltinAgentsServer, startElectricAgentsDevEnvironment, stopElectricAgentsDevEnvironment, waitForElectricAgentsServer } from "./index-DmR3DeFk.cjs";
1
+ import { StartedBuiltinAgentsEnvironment, StartedDevEnvironment, StoppedDevEnvironment, getStartedBuiltinAgentsMessage, getStartedEnvironmentMessage, getStoppedEnvironmentMessage, readDotEnvFile, resolveAnthropicApiKey, resolveComposeProjectName, resolveElectricAgentsPort, resolvePullWakeOwnerPrincipal, resolvePullWakeRunnerId, startBuiltinAgentsServer, startElectricAgentsDevEnvironment, stopElectricAgentsDevEnvironment, waitForElectricAgentsServer } from "./index-_AHIJdEA.cjs";
2
2
  export { StartedBuiltinAgentsEnvironment, StartedDevEnvironment, StoppedDevEnvironment, getStartedBuiltinAgentsMessage, getStartedEnvironmentMessage, getStoppedEnvironmentMessage, readDotEnvFile, resolveAnthropicApiKey, resolveComposeProjectName, resolveElectricAgentsPort, resolvePullWakeOwnerPrincipal, resolvePullWakeRunnerId, startBuiltinAgentsServer, startElectricAgentsDevEnvironment, stopElectricAgentsDevEnvironment, waitForElectricAgentsServer };
package/dist/start.d.ts CHANGED
@@ -1,2 +1,2 @@
1
- import { StartedBuiltinAgentsEnvironment, StartedDevEnvironment, StoppedDevEnvironment, getStartedBuiltinAgentsMessage, getStartedEnvironmentMessage, getStoppedEnvironmentMessage, readDotEnvFile, resolveAnthropicApiKey, resolveComposeProjectName, resolveElectricAgentsPort, resolvePullWakeOwnerPrincipal, resolvePullWakeRunnerId, startBuiltinAgentsServer, startElectricAgentsDevEnvironment, stopElectricAgentsDevEnvironment, waitForElectricAgentsServer } from "./index-BsITLCxF.js";
1
+ import { StartedBuiltinAgentsEnvironment, StartedDevEnvironment, StoppedDevEnvironment, getStartedBuiltinAgentsMessage, getStartedEnvironmentMessage, getStoppedEnvironmentMessage, readDotEnvFile, resolveAnthropicApiKey, resolveComposeProjectName, resolveElectricAgentsPort, resolvePullWakeOwnerPrincipal, resolvePullWakeRunnerId, startBuiltinAgentsServer, startElectricAgentsDevEnvironment, stopElectricAgentsDevEnvironment, waitForElectricAgentsServer } from "./index-CQN8S3b9.js";
2
2
  export { StartedBuiltinAgentsEnvironment, StartedDevEnvironment, StoppedDevEnvironment, getStartedBuiltinAgentsMessage, getStartedEnvironmentMessage, getStoppedEnvironmentMessage, readDotEnvFile, resolveAnthropicApiKey, resolveComposeProjectName, resolveElectricAgentsPort, resolvePullWakeOwnerPrincipal, resolvePullWakeRunnerId, startBuiltinAgentsServer, startElectricAgentsDevEnvironment, stopElectricAgentsDevEnvironment, waitForElectricAgentsServer };
package/dist/start.js CHANGED
@@ -1,4 +1,4 @@
1
- import { readDotEnvFile$1 as readDotEnvFile, resolveAnthropicApiKey$1 as resolveAnthropicApiKey } from "./env-DIhTv987.js";
1
+ import { readDotEnvFile$1 as readDotEnvFile, resolveAnthropicApiKey$1 as resolveAnthropicApiKey } from "./env-LZtIfFz1.js";
2
2
  import { appendPathToUrl } from "@electric-ax/agents-runtime";
3
3
  import { fileURLToPath } from "node:url";
4
4
  import { mergeElectricPrincipalHeader } from "@electric-ax/agents/server-headers";
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "electric-ax",
3
- "version": "0.2.8",
3
+ "version": "0.2.9",
4
4
  "description": "CLI for Electric Agents",
5
5
  "author": "ElectricSQL team and contributors",
6
6
  "license": "Apache-2.0",
@@ -46,8 +46,8 @@
46
46
  "ink": "^6.8.0",
47
47
  "omelette": "^0.4.17",
48
48
  "react": "^19.2.0",
49
- "@electric-ax/agents": "0.4.8",
50
- "@electric-ax/agents-runtime": "0.3.4"
49
+ "@electric-ax/agents": "0.4.9",
50
+ "@electric-ax/agents-runtime": "0.3.5"
51
51
  },
52
52
  "devDependencies": {
53
53
  "@vitest/coverage-v8": "^4.1.0",
@@ -1,28 +0,0 @@
1
- "use strict";
2
- const require_chunk = require('./chunk-BCwAaXi7.cjs');
3
- const __electric_ax_agents_runtime = require_chunk.__toESM(require("@electric-ax/agents-runtime"));
4
-
5
- //#region src/entity-api.ts
6
- function withLeadingSlash(path) {
7
- return path.startsWith(`/`) ? path : `/${path}`;
8
- }
9
- function entityApiPath(entityUrl, suffix = ``) {
10
- return `/_electric/entities${withLeadingSlash(entityUrl)}${suffix}`;
11
- }
12
- function entityApiUrl(baseUrl, entityUrl, suffix = ``) {
13
- return (0, __electric_ax_agents_runtime.appendPathToUrl)(baseUrl, entityApiPath(entityUrl, suffix));
14
- }
15
-
16
- //#endregion
17
- Object.defineProperty(exports, 'entityApiPath', {
18
- enumerable: true,
19
- get: function () {
20
- return entityApiPath;
21
- }
22
- });
23
- Object.defineProperty(exports, 'entityApiUrl', {
24
- enumerable: true,
25
- get: function () {
26
- return entityApiUrl;
27
- }
28
- });
@@ -1,15 +0,0 @@
1
- import { appendPathToUrl } from "@electric-ax/agents-runtime";
2
-
3
- //#region src/entity-api.ts
4
- function withLeadingSlash(path) {
5
- return path.startsWith(`/`) ? path : `/${path}`;
6
- }
7
- function entityApiPath(entityUrl, suffix = ``) {
8
- return `/_electric/entities${withLeadingSlash(entityUrl)}${suffix}`;
9
- }
10
- function entityApiUrl(baseUrl, entityUrl, suffix = ``) {
11
- return appendPathToUrl(baseUrl, entityApiPath(entityUrl, suffix));
12
- }
13
-
14
- //#endregion
15
- export { entityApiPath, entityApiUrl };
File without changes
File without changes