eve-hub 0.6.33 → 0.6.35

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/CHANGELOG.md CHANGED
@@ -1,5 +1,17 @@
1
1
  # eve-hub
2
2
 
3
+ ## 0.6.35
4
+
5
+ ### Patch Changes
6
+
7
+ - A bot's attach_image carries its images into its reply with their sizes; an oversized upload answers 413 naming both limits.
8
+
9
+ ## 0.6.34
10
+
11
+ ### Patch Changes
12
+
13
+ - Run on eve 0.81.1: the Dash schedule calls eve's `decide` (renamed from `evaluate`), the sandbox handle hooks are onSandboxStop/onSandboxDelete, and the `ai` peer range is ^7.0.137.
14
+
3
15
  ## 0.6.33
4
16
 
5
17
  ### Patch Changes
package/host-sandbox.d.ts CHANGED
@@ -39,8 +39,8 @@ export declare function hostEnvironment(options?: HostOptions): {
39
39
  worktree?: SessionWorktree;
40
40
  };
41
41
  onRuntimeShutdown: () => Promise<void>;
42
- onSessionStop: () => Promise<void>;
43
- onSessionDelete: () => Promise<void>;
42
+ onSandboxStop: () => Promise<void>;
43
+ onSandboxDelete: () => Promise<void>;
44
44
  };
45
45
  state: HostState;
46
46
  }>;
@@ -53,8 +53,8 @@ export declare function hostEnvironment(options?: HostOptions): {
53
53
  worktree?: SessionWorktree;
54
54
  };
55
55
  onRuntimeShutdown: () => Promise<void>;
56
- onSessionStop: () => Promise<void>;
57
- onSessionDelete: () => Promise<void>;
56
+ onSandboxStop: () => Promise<void>;
57
+ onSandboxDelete: () => Promise<void>;
58
58
  }>;
59
59
  };
60
60
  export declare const HostSandbox: import("eve/sandbox/provider").SandboxProvider<HostOptions, undefined, SandboxSession>;
@@ -65,8 +65,8 @@ export declare function hostHandle(rootOrState: string | HostState, sessionId: s
65
65
  worktree?: SessionWorktree;
66
66
  };
67
67
  onRuntimeShutdown: () => Promise<void>;
68
- onSessionStop: () => Promise<void>;
69
- onSessionDelete: () => Promise<void>;
68
+ onSandboxStop: () => Promise<void>;
69
+ onSandboxDelete: () => Promise<void>;
70
70
  };
71
71
  export declare function killTree(child: ChildProcess): void;
72
72
  declare const forkConfig: (sessionId: string) => Promise<{
package/host-sandbox.js CHANGED
@@ -123,8 +123,8 @@ export function hostHandle(rootOrState, sessionId) {
123
123
  return {
124
124
  sandbox: hostSession(root, children, sessionId, { worktree, rootSessionId }),
125
125
  onRuntimeShutdown: killAll,
126
- onSessionStop: killAll,
127
- onSessionDelete: killAll,
126
+ onSandboxStop: killAll,
127
+ onSandboxDelete: killAll,
128
128
  };
129
129
  }
130
130
  // SIGTERM the whole process group; whatever ignores it gets SIGKILL after
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "eve-hub",
3
- "version": "0.6.33",
3
+ "version": "0.6.35",
4
4
  "license": "Apache-2.0",
5
5
  "description": "Bot-side code shared by every hub agent: registry tools, the roster hook, the eve channel, the host sandbox and browser, and model helpers.",
6
6
  "type": "module",
@@ -37,6 +37,6 @@
37
37
  "@vercel/oidc": "4.0.0"
38
38
  },
39
39
  "dependencies": {
40
- "ai": "^7.0.122"
40
+ "ai": "^7.0.137"
41
41
  }
42
42
  }
package/schedules/dash.js CHANGED
@@ -1,12 +1,12 @@
1
1
  // main's dash schedule: every 8 minutes, and off-cron as soon as a bot's turn
2
2
  // ends (the hub fires it, so a question shows on the sidebar within seconds),
3
3
  // the one pass behind the Dash: the human's PRs, a model call per thread
4
- // whose facts changed (openai/gpt-6-luna-decisions through eve's `evaluate`,
4
+ // whose facts changed (openai/gpt-6-luna-decisions through eve`s `decide`,
5
5
  // eve's gateway credentials) and a model call per track with news
6
6
  // (anthropic/claude-sonnet-5.5 through the AI SDK). The pass: runPass in
7
7
  // ./dash-pass.mjs.
8
8
  import { defineSchedule } from "eve/schedules";
9
- import { evaluate } from "eve/ai";
9
+ import { decide as evaluate } from "eve/ai";
10
10
  import { generateText } from "ai";
11
11
  import { createHub } from "./hub.mjs";
12
12
  import { modelClassify } from "./dash-classify.mjs";
package/tools/bash.js CHANGED
@@ -1,12 +1,11 @@
1
1
  import { defineTool } from "eve/tools";
2
- import { bash } from "eve/tools/bash";
3
2
  import { z } from "zod";
4
3
  import { MAX_TIMEOUT_S, bashDescription, runBash, workspaceCode } from "../bash-run.mjs";
5
4
  import { HOST_ROOT } from "../host-sandbox.js";
6
5
  // eve's bash, with a time limit and a pointer to the workspace's code (see
7
6
  // ../bash-run.mjs). Same output shape, plus `timedOut` when the limit fired.
8
7
  export default defineTool({
9
- label: bash.label,
8
+ label: { start: (input) => `Run ${input.command}`.trimEnd() },
10
9
  description: bashDescription({ hostRoot: HOST_ROOT }),
11
10
  inputSchema: z.object({
12
11
  command: z.string().describe("The shell command to execute."),
package/world.mjs CHANGED
@@ -670,6 +670,8 @@ var PENDING_REQUESTS_READ = s(`SELECT r.id, r.session_id, r.thread_id, r.bot, r.
670
670
  var LIVE_TURNS_READ = s(`SELECT thread_id,bot,started_at,reply_text,activity FROM turns WHERE status IN ${OPEN_TURN_STATUSES} ORDER BY started_at`);
671
671
 
672
672
  // ../../hosted-hub/src/store/attachments.ts
673
+ var MAX_ATTACHMENTS = 10;
674
+ var OPEN_TURN = `(SELECT id FROM turns WHERE session_id = ? AND status IN ${OPEN_TURN_STATUSES} ORDER BY started_at DESC LIMIT 1)`;
673
675
  var ATTACHMENTS_READ = s("SELECT message_id, upload_id, name FROM message_attachments ORDER BY message_id, position");
674
676
  var unseenBy = (bot, thread, mid) => {
675
677
  const end = `COALESCE((SELECT rowid FROM messages WHERE id = ${mid}), 9223372036854775807)`;
@@ -27156,6 +27158,7 @@ function fold(state, chunks, now = Date.now()) {
27156
27158
  reduceActivity(open3.activity, { type: "turn.cancelled" }, at, cutOff(open3, "turn.cancelled"));
27157
27159
  Object.assign(open3, { status: open3.status === "cancelling" ? "cancelled" : status, endedAt: at, error: error63 });
27158
27160
  touched.set(open3.id, open3);
27161
+ stmts.push(s("DELETE FROM turn_attachments WHERE turn_id = ?", open3.id));
27159
27162
  log("turn.status", { turnId: open3.id, status: open3.status });
27160
27163
  open3 = null;
27161
27164
  };
@@ -27229,6 +27232,10 @@ function fold(state, chunks, now = Date.now()) {
27229
27232
  break;
27230
27233
  }
27231
27234
  case "action.result": {
27235
+ const attachment = data.result?.output?.attachment;
27236
+ if (data.result?.toolName === "attach_image" && data.status === "completed" && typeof attachment?.id === "string" && typeof attachment.name === "string" && typeof attachment.size === "number")
27237
+ stmts.push(s(`INSERT OR IGNORE INTO turn_attachments (turn_id, position, upload_id, name, size)
27238
+ SELECT ?, n, ?, ?, ? FROM (SELECT count(*) AS n FROM turn_attachments WHERE turn_id = ?) WHERE n < ?`, open3.id, attachment.id, attachment.name, attachment.size, open3.id, MAX_ATTACHMENTS));
27232
27239
  const ls = open3.lastStep, callId = data.result?.callId;
27233
27240
  if (!ls || !callId || ls.calls[callId] !== null) break;
27234
27241
  const postOutput = data.result?.output;
@@ -27242,14 +27249,16 @@ function fold(state, chunks, now = Date.now()) {
27242
27249
  break;
27243
27250
  case "turn.completed": {
27244
27251
  flush();
27245
- const text = open3.text.trim();
27246
- if (open3.status !== "cancelling" && !lastActWasOwnPost(open3.lastStep)) {
27252
+ const text = lastActWasOwnPost(open3.lastStep) ? "" : open3.text.trim();
27253
+ if (open3.status !== "cancelling") {
27247
27254
  const messageId2 = derivedMessageId(open3.id);
27248
27255
  stmts.push(s(`INSERT OR IGNORE INTO messages (id, thread_id, author, author_kind, text, turn_id, created_at)
27249
- SELECT ?, ?, ?, 'agent', ?, ?, ? WHERE ? <> ''
27250
- AND EXISTS (SELECT 1 FROM turns WHERE id = ? AND status NOT IN ('cancelling','cancelled') AND NOT (${REVOKED_TURN}))`, messageId2, session.thread, session.bot, text, open3.id, at, text, open3.id));
27256
+ SELECT ?, ?, ?, 'agent', ?, ?, ? WHERE (? <> '' OR EXISTS (SELECT 1 FROM turn_attachments WHERE turn_id = ?))
27257
+ AND EXISTS (SELECT 1 FROM turns WHERE id = ? AND status NOT IN ('cancelling','cancelled') AND NOT (${REVOKED_TURN}))`, messageId2, session.thread, session.bot, text, open3.id, at, text, open3.id, open3.id));
27251
27258
  log("message.created", { messageId: messageId2, author: session.bot, authorKind: "agent" }, IF_INSERTED);
27252
27259
  stmts.push(...notificationFor(messageId2, "agent", text, state.notify ?? void 0));
27260
+ stmts.push(s(`INSERT OR IGNORE INTO message_attachments (message_id, position, upload_id, name, size)
27261
+ SELECT ?, position, upload_id, name, size FROM turn_attachments WHERE turn_id = ? AND EXISTS (SELECT 1 FROM messages WHERE id = ?) ORDER BY position`, messageId2, open3.id, messageId2));
27253
27262
  const to = recipients(state.roster, text, { name: session.bot, kind: "agent" }, session.thread, state.participants);
27254
27263
  stmts.push(...routingStatements(messageId2, session.thread, to, at, { by: session.bot, joins: true }));
27255
27264
  deliver.push(messageId2);