@polpo-ai/server 0.2.4 → 0.2.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.
package/dist/index.d.ts CHANGED
@@ -20,6 +20,8 @@ export { watcherRoutes } from "./routes/watchers.js";
20
20
  export { stateRoutes } from "./routes/state.js";
21
21
  export { healthRoutes } from "./routes/health.js";
22
22
  export { completionRoutes, type CompletionRouteDeps } from "./routes/completions.js";
23
+ export { agentRoutes } from "./routes/agents.js";
24
+ export { eventRoutes, type EventBridge, type EventClient } from "./routes/events.js";
23
25
  export type { TaskRouteDeps, MissionRouteDeps, PlaybookRouteDeps, ApprovalRouteDeps, ChatRouteDeps, VaultRouteDeps, PeerRouteDeps, NotificationRouteDeps, ScheduleRouteDeps, WatcherRouteDeps, StateRouteDeps, ConfigRouteDeps, AuthRouteDeps, FileRouteDeps, SkillRouteDeps, AgentRouteDeps, } from "./deps.js";
24
26
  export { validateParams, instantiatePlaybook } from "./playbook-utils.js";
25
27
  export type { PlaybookParameter, PlaybookDefinition, ValidationResult } from "./playbook-utils.js";
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AAGH,OAAO,EAAE,UAAU,EAAE,MAAM,mBAAmB,CAAC;AAC/C,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AACrD,OAAO,EAAE,cAAc,EAAE,MAAM,uBAAuB,CAAC;AACvD,OAAO,EAAE,cAAc,EAAE,MAAM,uBAAuB,CAAC;AACvD,OAAO,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AAC9C,OAAO,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAChD,OAAO,EAAE,UAAU,EAAE,MAAM,mBAAmB,CAAC;AAC/C,OAAO,EAAE,kBAAkB,EAAE,MAAM,2BAA2B,CAAC;AAC/D,OAAO,EAAE,cAAc,EAAE,MAAM,uBAAuB,CAAC;AACvD,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AACrD,OAAO,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAChD,OAAO,EAAE,YAAY,EAAE,MAAM,oBAAoB,CAAC;AAClD,OAAO,EAAE,gBAAgB,EAAE,KAAK,mBAAmB,EAAE,MAAM,yBAAyB,CAAC;AAGrF,YAAY,EACV,aAAa,EACb,gBAAgB,EAChB,iBAAiB,EACjB,iBAAiB,EACjB,aAAa,EACb,cAAc,EACd,aAAa,EACb,qBAAqB,EACrB,iBAAiB,EACjB,gBAAgB,EAChB,cAAc,EACd,eAAe,EACf,aAAa,EACb,aAAa,EACb,cAAc,EACd,cAAc,GACf,MAAM,WAAW,CAAC;AAGnB,OAAO,EAAE,cAAc,EAAE,mBAAmB,EAAE,MAAM,qBAAqB,CAAC;AAC1E,YAAY,EAAE,iBAAiB,EAAE,kBAAkB,EAAE,gBAAgB,EAAE,MAAM,qBAAqB,CAAC"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AAGH,OAAO,EAAE,UAAU,EAAE,MAAM,mBAAmB,CAAC;AAC/C,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AACrD,OAAO,EAAE,cAAc,EAAE,MAAM,uBAAuB,CAAC;AACvD,OAAO,EAAE,cAAc,EAAE,MAAM,uBAAuB,CAAC;AACvD,OAAO,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AAC9C,OAAO,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAChD,OAAO,EAAE,UAAU,EAAE,MAAM,mBAAmB,CAAC;AAC/C,OAAO,EAAE,kBAAkB,EAAE,MAAM,2BAA2B,CAAC;AAC/D,OAAO,EAAE,cAAc,EAAE,MAAM,uBAAuB,CAAC;AACvD,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AACrD,OAAO,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAChD,OAAO,EAAE,YAAY,EAAE,MAAM,oBAAoB,CAAC;AAClD,OAAO,EAAE,gBAAgB,EAAE,KAAK,mBAAmB,EAAE,MAAM,yBAAyB,CAAC;AACrF,OAAO,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;AACjD,OAAO,EAAE,WAAW,EAAE,KAAK,WAAW,EAAE,KAAK,WAAW,EAAE,MAAM,oBAAoB,CAAC;AAGrF,YAAY,EACV,aAAa,EACb,gBAAgB,EAChB,iBAAiB,EACjB,iBAAiB,EACjB,aAAa,EACb,cAAc,EACd,aAAa,EACb,qBAAqB,EACrB,iBAAiB,EACjB,gBAAgB,EAChB,cAAc,EACd,eAAe,EACf,aAAa,EACb,aAAa,EACb,cAAc,EACd,cAAc,GACf,MAAM,WAAW,CAAC;AAGnB,OAAO,EAAE,cAAc,EAAE,mBAAmB,EAAE,MAAM,qBAAqB,CAAC;AAC1E,YAAY,EAAE,iBAAiB,EAAE,kBAAkB,EAAE,gBAAgB,EAAE,MAAM,qBAAqB,CAAC"}
package/dist/index.js CHANGED
@@ -21,6 +21,8 @@ export { watcherRoutes } from "./routes/watchers.js";
21
21
  export { stateRoutes } from "./routes/state.js";
22
22
  export { healthRoutes } from "./routes/health.js";
23
23
  export { completionRoutes } from "./routes/completions.js";
24
+ export { agentRoutes } from "./routes/agents.js";
25
+ export { eventRoutes } from "./routes/events.js";
24
26
  // Playbook utilities (pure logic, edge-compatible)
25
27
  export { validateParams, instantiatePlaybook } from "./playbook-utils.js";
26
28
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AAEH,kBAAkB;AAClB,OAAO,EAAE,UAAU,EAAE,MAAM,mBAAmB,CAAC;AAC/C,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AACrD,OAAO,EAAE,cAAc,EAAE,MAAM,uBAAuB,CAAC;AACvD,OAAO,EAAE,cAAc,EAAE,MAAM,uBAAuB,CAAC;AACvD,OAAO,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AAC9C,OAAO,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAChD,OAAO,EAAE,UAAU,EAAE,MAAM,mBAAmB,CAAC;AAC/C,OAAO,EAAE,kBAAkB,EAAE,MAAM,2BAA2B,CAAC;AAC/D,OAAO,EAAE,cAAc,EAAE,MAAM,uBAAuB,CAAC;AACvD,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AACrD,OAAO,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAChD,OAAO,EAAE,YAAY,EAAE,MAAM,oBAAoB,CAAC;AAClD,OAAO,EAAE,gBAAgB,EAA4B,MAAM,yBAAyB,CAAC;AAsBrF,mDAAmD;AACnD,OAAO,EAAE,cAAc,EAAE,mBAAmB,EAAE,MAAM,qBAAqB,CAAC"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;;;;GAQG;AAEH,kBAAkB;AAClB,OAAO,EAAE,UAAU,EAAE,MAAM,mBAAmB,CAAC;AAC/C,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AACrD,OAAO,EAAE,cAAc,EAAE,MAAM,uBAAuB,CAAC;AACvD,OAAO,EAAE,cAAc,EAAE,MAAM,uBAAuB,CAAC;AACvD,OAAO,EAAE,UAAU,EAAE,MAAM,kBAAkB,CAAC;AAC9C,OAAO,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAChD,OAAO,EAAE,UAAU,EAAE,MAAM,mBAAmB,CAAC;AAC/C,OAAO,EAAE,kBAAkB,EAAE,MAAM,2BAA2B,CAAC;AAC/D,OAAO,EAAE,cAAc,EAAE,MAAM,uBAAuB,CAAC;AACvD,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AACrD,OAAO,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAChD,OAAO,EAAE,YAAY,EAAE,MAAM,oBAAoB,CAAC;AAClD,OAAO,EAAE,gBAAgB,EAA4B,MAAM,yBAAyB,CAAC;AACrF,OAAO,EAAE,WAAW,EAAE,MAAM,oBAAoB,CAAC;AACjD,OAAO,EAAE,WAAW,EAAsC,MAAM,oBAAoB,CAAC;AAsBrF,mDAAmD;AACnD,OAAO,EAAE,cAAc,EAAE,mBAAmB,EAAE,MAAM,qBAAqB,CAAC"}
@@ -0,0 +1,21 @@
1
+ import { OpenAPIHono } from "@hono/zod-openapi";
2
+ import type { FileSystem } from "@polpo-ai/core";
3
+ /**
4
+ * Agent/team management routes.
5
+ */
6
+ export declare function agentRoutes(getDeps: () => {
7
+ getAgents: () => Promise<any[]>;
8
+ addAgent: (agent: any, teamName?: string) => Promise<void>;
9
+ removeAgent: (name: string) => Promise<boolean>;
10
+ updateAgent: (name: string, updates: any) => Promise<any>;
11
+ getTeams: () => Promise<any[]>;
12
+ getTeam: (name?: string) => Promise<any>;
13
+ addTeam: (team: any) => Promise<void>;
14
+ removeTeam: (name: string) => Promise<boolean>;
15
+ renameTeam: (oldName: string, newName: string) => Promise<void>;
16
+ taskStore: any;
17
+ runStore: any;
18
+ polpoDir: string;
19
+ fs?: FileSystem;
20
+ }): OpenAPIHono;
21
+ //# sourceMappingURL=agents.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"agents.d.ts","sourceRoot":"","sources":["../../src/routes/agents.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAkB,MAAM,mBAAmB,CAAC;AAEhE,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,gBAAgB,CAAC;AAIjD;;GAEG;AACH,wBAAgB,WAAW,CAAC,OAAO,EAAE,MAAM;IACzC,SAAS,EAAE,MAAM,OAAO,CAAC,GAAG,EAAE,CAAC,CAAC;IAChC,QAAQ,EAAE,CAAC,KAAK,EAAE,GAAG,EAAE,QAAQ,CAAC,EAAE,MAAM,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;IAC3D,WAAW,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,OAAO,CAAC,OAAO,CAAC,CAAC;IAChD,WAAW,EAAE,CAAC,IAAI,EAAE,MAAM,EAAE,OAAO,EAAE,GAAG,KAAK,OAAO,CAAC,GAAG,CAAC,CAAC;IAC1D,QAAQ,EAAE,MAAM,OAAO,CAAC,GAAG,EAAE,CAAC,CAAC;IAC/B,OAAO,EAAE,CAAC,IAAI,CAAC,EAAE,MAAM,KAAK,OAAO,CAAC,GAAG,CAAC,CAAC;IACzC,OAAO,EAAE,CAAC,IAAI,EAAE,GAAG,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;IACtC,UAAU,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,OAAO,CAAC,OAAO,CAAC,CAAC;IAC/C,UAAU,EAAE,CAAC,OAAO,EAAE,MAAM,EAAE,OAAO,EAAE,MAAM,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;IAChE,SAAS,EAAE,GAAG,CAAC;IACf,QAAQ,EAAE,GAAG,CAAC;IACd,QAAQ,EAAE,MAAM,CAAC;IACjB,EAAE,CAAC,EAAE,UAAU,CAAC;CACjB,GAAG,WAAW,CAkcd"}
@@ -0,0 +1,421 @@
1
+ import { OpenAPIHono, createRoute, z } from "@hono/zod-openapi";
2
+ import { join, extname } from "node:path";
3
+ import { AddAgentSchema, UpdateAgentSchema, RenameTeamSchema, AddTeamSchema } from "../schemas.js";
4
+ import { redactAgentConfig, redactTeam, sanitizeTranscriptEntry } from "../security.js";
5
+ /**
6
+ * Agent/team management routes.
7
+ */
8
+ export function agentRoutes(getDeps) {
9
+ const app = new OpenAPIHono();
10
+ // GET /agents — list agents
11
+ const listAgentsRoute = createRoute({
12
+ method: "get",
13
+ path: "/",
14
+ tags: ["Agents"],
15
+ summary: "List agents",
16
+ responses: {
17
+ 200: {
18
+ content: { "application/json": { schema: z.object({ ok: z.boolean(), data: z.array(z.any()) }) } },
19
+ description: "List of agents",
20
+ },
21
+ },
22
+ });
23
+ app.openapi(listAgentsRoute, async (c) => {
24
+ const deps = getDeps();
25
+ const agents = await deps.getAgents();
26
+ return c.json({ ok: true, data: agents.map(redactAgentConfig) });
27
+ });
28
+ // POST /agents — add agent
29
+ const addAgentRoute = createRoute({
30
+ method: "post",
31
+ path: "/",
32
+ tags: ["Agents"],
33
+ summary: "Add agent",
34
+ request: {
35
+ body: { content: { "application/json": { schema: AddAgentSchema } } },
36
+ },
37
+ responses: {
38
+ 201: {
39
+ content: { "application/json": { schema: z.object({ ok: z.boolean(), data: z.object({ added: z.boolean() }) }) } },
40
+ description: "Agent added",
41
+ },
42
+ },
43
+ });
44
+ app.openapi(addAgentRoute, async (c) => {
45
+ const deps = getDeps();
46
+ const body = c.req.valid("json");
47
+ const teamName = c.req.query("team");
48
+ await deps.addAgent({
49
+ name: body.name,
50
+ role: body.role,
51
+ model: body.model,
52
+ allowedTools: body.allowedTools,
53
+ systemPrompt: body.systemPrompt,
54
+ skills: body.skills,
55
+ maxTurns: body.maxTurns,
56
+ identity: body.identity,
57
+ reportsTo: body.reportsTo,
58
+ browserProfile: body.browserProfile,
59
+ }, teamName);
60
+ return c.json({ ok: true, data: { added: true } }, 201);
61
+ });
62
+ // DELETE /agents/:name — remove agent
63
+ const deleteAgentRoute = createRoute({
64
+ method: "delete",
65
+ path: "/{name}",
66
+ tags: ["Agents"],
67
+ summary: "Remove agent",
68
+ request: {
69
+ params: z.object({ name: z.string() }),
70
+ },
71
+ responses: {
72
+ 200: {
73
+ content: { "application/json": { schema: z.object({ ok: z.boolean(), data: z.object({ removed: z.boolean() }) }) } },
74
+ description: "Agent removed",
75
+ },
76
+ 404: {
77
+ content: { "application/json": { schema: z.object({ ok: z.boolean(), error: z.string(), code: z.string() }) } },
78
+ description: "Agent not found",
79
+ },
80
+ },
81
+ });
82
+ app.openapi(deleteAgentRoute, async (c) => {
83
+ const deps = getDeps();
84
+ const { name } = c.req.valid("param");
85
+ const removed = await deps.removeAgent(name);
86
+ if (!removed) {
87
+ return c.json({ ok: false, error: "Agent not found", code: "NOT_FOUND" }, 404);
88
+ }
89
+ return c.json({ ok: true, data: { removed: true } }, 200);
90
+ });
91
+ // GET /teams — get all teams
92
+ const getTeamsRoute = createRoute({
93
+ method: "get",
94
+ path: "/teams",
95
+ tags: ["Agents"],
96
+ summary: "List teams",
97
+ responses: {
98
+ 200: {
99
+ content: { "application/json": { schema: z.object({ ok: z.boolean(), data: z.array(z.any()) }) } },
100
+ description: "All teams",
101
+ },
102
+ },
103
+ });
104
+ app.openapi(getTeamsRoute, async (c) => {
105
+ const deps = getDeps();
106
+ const teams = await deps.getTeams();
107
+ return c.json({ ok: true, data: teams.map(redactTeam) });
108
+ });
109
+ // GET /team — get single team (default or by ?name= query)
110
+ const getTeamRoute = createRoute({
111
+ method: "get",
112
+ path: "/team",
113
+ tags: ["Agents"],
114
+ summary: "Get team info",
115
+ responses: {
116
+ 200: {
117
+ content: { "application/json": { schema: z.object({ ok: z.boolean(), data: z.any() }) } },
118
+ description: "Team info",
119
+ },
120
+ },
121
+ });
122
+ app.openapi(getTeamRoute, async (c) => {
123
+ const deps = getDeps();
124
+ const name = c.req.query("name");
125
+ const team = await deps.getTeam(name);
126
+ return c.json({ ok: true, data: team ? redactTeam(team) : null });
127
+ });
128
+ // POST /teams — add a new team
129
+ const addTeamRoute = createRoute({
130
+ method: "post",
131
+ path: "/teams",
132
+ tags: ["Agents"],
133
+ summary: "Add team",
134
+ request: {
135
+ body: { content: { "application/json": { schema: AddTeamSchema } } },
136
+ },
137
+ responses: {
138
+ 201: {
139
+ content: { "application/json": { schema: z.object({ ok: z.boolean(), data: z.object({ added: z.boolean() }) }) } },
140
+ description: "Team added",
141
+ },
142
+ },
143
+ });
144
+ app.openapi(addTeamRoute, async (c) => {
145
+ const deps = getDeps();
146
+ const body = c.req.valid("json");
147
+ await deps.addTeam({ name: body.name, description: body.description, agents: [] });
148
+ return c.json({ ok: true, data: { added: true } }, 201);
149
+ });
150
+ // DELETE /teams/:name — remove a team
151
+ const deleteTeamRoute = createRoute({
152
+ method: "delete",
153
+ path: "/teams/{name}",
154
+ tags: ["Agents"],
155
+ summary: "Remove team",
156
+ request: {
157
+ params: z.object({ name: z.string() }),
158
+ },
159
+ responses: {
160
+ 200: {
161
+ content: { "application/json": { schema: z.object({ ok: z.boolean(), data: z.object({ removed: z.boolean() }) }) } },
162
+ description: "Team removed",
163
+ },
164
+ 404: {
165
+ content: { "application/json": { schema: z.object({ ok: z.boolean(), error: z.string(), code: z.string() }) } },
166
+ description: "Team not found",
167
+ },
168
+ },
169
+ });
170
+ app.openapi(deleteTeamRoute, async (c) => {
171
+ const deps = getDeps();
172
+ const { name } = c.req.valid("param");
173
+ const removed = await deps.removeTeam(name);
174
+ if (!removed) {
175
+ return c.json({ ok: false, error: "Team not found", code: "NOT_FOUND" }, 404);
176
+ }
177
+ return c.json({ ok: true, data: { removed: true } }, 200);
178
+ });
179
+ // PATCH /team — rename team
180
+ const renameTeamRoute = createRoute({
181
+ method: "patch",
182
+ path: "/team",
183
+ tags: ["Agents"],
184
+ summary: "Rename team",
185
+ request: {
186
+ body: { content: { "application/json": { schema: RenameTeamSchema } } },
187
+ },
188
+ responses: {
189
+ 200: {
190
+ content: { "application/json": { schema: z.object({ ok: z.boolean(), data: z.any() }) } },
191
+ description: "Team renamed",
192
+ },
193
+ },
194
+ });
195
+ app.openapi(renameTeamRoute, async (c) => {
196
+ const deps = getDeps();
197
+ const body = c.req.valid("json");
198
+ await deps.renameTeam(body.oldName, body.name);
199
+ const updatedTeam = await deps.getTeam(body.name);
200
+ return c.json({ ok: true, data: updatedTeam ? redactTeam(updatedTeam) : null });
201
+ });
202
+ // GET /processes — active agent processes
203
+ const listProcessesRoute = createRoute({
204
+ method: "get",
205
+ path: "/processes",
206
+ tags: ["Agents"],
207
+ summary: "List processes",
208
+ responses: {
209
+ 200: {
210
+ content: { "application/json": { schema: z.object({ ok: z.boolean(), data: z.array(z.any()) }) } },
211
+ description: "Active processes",
212
+ },
213
+ },
214
+ });
215
+ app.openapi(listProcessesRoute, async (c) => {
216
+ const deps = getDeps();
217
+ const state = await deps.taskStore.getState();
218
+ return c.json({ ok: true, data: state.processes || [] });
219
+ });
220
+ // GET /processes/:taskId/activity — activity history for a task (from run JSONL)
221
+ const getActivityRoute = createRoute({
222
+ method: "get",
223
+ path: "/processes/{taskId}/activity",
224
+ tags: ["Agents"],
225
+ summary: "Get task activity",
226
+ request: {
227
+ params: z.object({ taskId: z.string() }),
228
+ },
229
+ responses: {
230
+ 200: {
231
+ content: { "application/json": { schema: z.object({ ok: z.boolean(), data: z.array(z.any()) }) } },
232
+ description: "Activity entries",
233
+ },
234
+ },
235
+ });
236
+ app.openapi(getActivityRoute, async (c) => {
237
+ const deps = getDeps();
238
+ const { taskId } = c.req.valid("param");
239
+ const fs = deps.fs;
240
+ const logsDir = join(deps.polpoDir, "logs");
241
+ if (!fs || !(await fs.exists(logsDir))) {
242
+ return c.json({ ok: true, data: [] });
243
+ }
244
+ // Strategy: first check active RunStore for the runId, otherwise scan JSONL headers
245
+ let runId;
246
+ const run = await deps.runStore.getRunByTaskId(taskId);
247
+ if (run) {
248
+ runId = run.id;
249
+ }
250
+ else {
251
+ const files = (await fs.readdir(logsDir)).filter((f) => f.startsWith("run-") && f.endsWith(".jsonl"));
252
+ for (const file of files) {
253
+ try {
254
+ const firstLine = (await fs.readFile(join(logsDir, file))).split("\n")[0];
255
+ const header = JSON.parse(firstLine);
256
+ if (header._run && header.taskId === taskId) {
257
+ runId = header.runId;
258
+ break;
259
+ }
260
+ }
261
+ catch { /* skip malformed files */ }
262
+ }
263
+ }
264
+ if (!runId) {
265
+ return c.json({ ok: true, data: [] });
266
+ }
267
+ const logPath = join(logsDir, `run-${runId}.jsonl`);
268
+ if (!(await fs.exists(logPath))) {
269
+ return c.json({ ok: true, data: [] });
270
+ }
271
+ try {
272
+ const lines = (await fs.readFile(logPath)).split("\n").filter(Boolean);
273
+ const entries = lines
274
+ .map((line) => { try {
275
+ return JSON.parse(line);
276
+ }
277
+ catch {
278
+ return null;
279
+ } })
280
+ .filter(Boolean)
281
+ .map(sanitizeTranscriptEntry);
282
+ return c.json({ ok: true, data: entries });
283
+ }
284
+ catch {
285
+ return c.json({ ok: true, data: [] });
286
+ }
287
+ });
288
+ // PATCH /agents/:name — update agent (registered after static routes to avoid conflicts with /team)
289
+ const updateAgentRoute = createRoute({
290
+ method: "patch",
291
+ path: "/{name}",
292
+ tags: ["Agents"],
293
+ summary: "Update agent",
294
+ request: {
295
+ params: z.object({ name: z.string() }),
296
+ body: { content: { "application/json": { schema: UpdateAgentSchema } } },
297
+ },
298
+ responses: {
299
+ 200: {
300
+ content: { "application/json": { schema: z.object({ ok: z.boolean(), data: z.any() }) } },
301
+ description: "Agent updated",
302
+ },
303
+ 404: {
304
+ content: { "application/json": { schema: z.object({ ok: z.boolean(), error: z.string(), code: z.string() }) } },
305
+ description: "Agent not found",
306
+ },
307
+ },
308
+ });
309
+ app.openapi(updateAgentRoute, async (c) => {
310
+ const deps = getDeps();
311
+ const { name } = c.req.valid("param");
312
+ const existing = (await deps.getAgents()).find(a => a.name === name);
313
+ if (!existing) {
314
+ return c.json({ ok: false, error: "Agent not found", code: "NOT_FOUND" }, 404);
315
+ }
316
+ const body = c.req.valid("json");
317
+ // Handle reportsTo: empty string clears it
318
+ let reportsTo = undefined;
319
+ if (typeof body.reportsTo === "string") {
320
+ reportsTo = body.reportsTo.trim() || undefined;
321
+ }
322
+ const updates = {
323
+ ...(body.role !== undefined && { role: body.role }),
324
+ ...(body.model !== undefined && { model: body.model }),
325
+ ...(body.systemPrompt !== undefined && { systemPrompt: body.systemPrompt }),
326
+ ...(body.skills !== undefined && { skills: body.skills }),
327
+ ...(body.allowedPaths !== undefined && { allowedPaths: body.allowedPaths }),
328
+ ...(body.allowedTools !== undefined && { allowedTools: body.allowedTools }),
329
+ ...(typeof body.reportsTo === "string" && { reportsTo }),
330
+ ...(body.reasoning !== undefined && { reasoning: body.reasoning }),
331
+ ...(body.maxTurns !== undefined && { maxTurns: body.maxTurns }),
332
+ ...(body.maxConcurrency !== undefined && { maxConcurrency: body.maxConcurrency }),
333
+ ...(body.browserProfile !== undefined && { browserProfile: body.browserProfile }),
334
+ ...(body.emailAllowedDomains !== undefined && { emailAllowedDomains: body.emailAllowedDomains }),
335
+ ...(body.identity && { identity: { ...(existing.identity ?? {}), ...body.identity } }),
336
+ ...(body.team !== undefined && { team: body.team }),
337
+ };
338
+ await deps.updateAgent(name, updates);
339
+ const updated = (await deps.getAgents()).find(a => a.name === name);
340
+ return c.json({ ok: true, data: updated ? redactAgentConfig(updated) : null }, 200);
341
+ });
342
+ // GET /agents/:name — single agent detail (registered after static routes to avoid conflicts)
343
+ const getAgentRoute = createRoute({
344
+ method: "get",
345
+ path: "/{name}",
346
+ tags: ["Agents"],
347
+ summary: "Get agent",
348
+ request: {
349
+ params: z.object({ name: z.string() }),
350
+ },
351
+ responses: {
352
+ 200: {
353
+ content: { "application/json": { schema: z.object({ ok: z.boolean(), data: z.any() }) } },
354
+ description: "Agent detail",
355
+ },
356
+ 404: {
357
+ content: { "application/json": { schema: z.object({ ok: z.boolean(), error: z.string(), code: z.string() }) } },
358
+ description: "Agent not found",
359
+ },
360
+ },
361
+ });
362
+ app.openapi(getAgentRoute, async (c) => {
363
+ const deps = getDeps();
364
+ const { name } = c.req.valid("param");
365
+ const agent = (await deps.getAgents()).find(a => a.name === name);
366
+ if (!agent) {
367
+ return c.json({ ok: false, error: "Agent not found", code: "NOT_FOUND" }, 404);
368
+ }
369
+ return c.json({ ok: true, data: redactAgentConfig(agent) }, 200);
370
+ });
371
+ // ── POST /agents/:name/avatar — upload agent avatar ──
372
+ app.post("/:name/avatar", async (c) => {
373
+ const deps = getDeps();
374
+ const name = c.req.param("name");
375
+ const agent = (await deps.getAgents()).find(a => a.name === name);
376
+ if (!agent)
377
+ return c.json({ ok: false, error: "Agent not found" }, 404);
378
+ const body = await c.req.parseBody();
379
+ const file = body["file"];
380
+ if (!file || !(file instanceof File)) {
381
+ return c.json({ ok: false, error: "Missing file upload (field: file)" }, 400);
382
+ }
383
+ // Validate image type
384
+ const allowed = new Set(["image/png", "image/jpeg", "image/webp", "image/gif", "image/svg+xml"]);
385
+ if (!allowed.has(file.type)) {
386
+ return c.json({ ok: false, error: `Unsupported image type: ${file.type}. Allowed: png, jpg, webp, gif, svg` }, 400);
387
+ }
388
+ // Save to .polpo/avatars/<name>.<ext>
389
+ const polpoDir = deps.polpoDir;
390
+ const avatarsDir = join(polpoDir, "avatars");
391
+ const fs = deps.fs;
392
+ if (!fs)
393
+ return c.json({ ok: false, error: "Filesystem not available" }, 501);
394
+ await fs.mkdir(avatarsDir);
395
+ const ext = extname(file.name || "avatar.png") || ".png";
396
+ const filename = `${name}${ext}`;
397
+ const avatarPath = join(avatarsDir, filename);
398
+ const relativePath = `.polpo/avatars/${filename}`;
399
+ const buffer = Buffer.from(await file.arrayBuffer());
400
+ await fs.writeFile(avatarPath, buffer.toString("base64"));
401
+ // Update agent identity with avatar path
402
+ const identity = { ...(agent.identity ?? {}), avatar: relativePath };
403
+ await deps.updateAgent(name, { identity });
404
+ return c.json({ ok: true, data: { avatar: relativePath } }, 200);
405
+ });
406
+ // ── DELETE /agents/:name/avatar — remove agent avatar ──
407
+ app.delete("/:name/avatar", async (c) => {
408
+ const deps = getDeps();
409
+ const name = c.req.param("name");
410
+ const agent = (await deps.getAgents()).find(a => a.name === name);
411
+ if (!agent)
412
+ return c.json({ ok: false, error: "Agent not found" }, 404);
413
+ if (agent.identity?.avatar) {
414
+ const identity = { ...agent.identity, avatar: undefined };
415
+ await deps.updateAgent(name, { identity });
416
+ }
417
+ return c.json({ ok: true }, 200);
418
+ });
419
+ return app;
420
+ }
421
+ //# sourceMappingURL=agents.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"agents.js","sourceRoot":"","sources":["../../src/routes/agents.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,18 @@
1
+ import { OpenAPIHono } from "@hono/zod-openapi";
2
+ /** SSE client interface — implemented by the consumer's bridge. */
3
+ export interface EventClient {
4
+ id: string;
5
+ send(event: string, data: unknown, eventId: string): void;
6
+ close(): void;
7
+ }
8
+ /** Event bridge interface — the consumer provides the event source. */
9
+ export interface EventBridge {
10
+ addClient(client: EventClient, lastEventId?: string): void;
11
+ removeClient(id: string): void;
12
+ }
13
+ /**
14
+ * SSE streaming event routes.
15
+ * Accepts any EventBridge implementation (self-hosted SSEBridge, cloud EventEmitter adapter, etc.)
16
+ */
17
+ export declare function eventRoutes(bridge: EventBridge): OpenAPIHono;
18
+ //# sourceMappingURL=events.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"events.d.ts","sourceRoot":"","sources":["../../src/routes/events.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,WAAW,EAAkB,MAAM,mBAAmB,CAAC;AAIhE,mEAAmE;AACnE,MAAM,WAAW,WAAW;IAC1B,EAAE,EAAE,MAAM,CAAC;IACX,IAAI,CAAC,KAAK,EAAE,MAAM,EAAE,IAAI,EAAE,OAAO,EAAE,OAAO,EAAE,MAAM,GAAG,IAAI,CAAC;IAC1D,KAAK,IAAI,IAAI,CAAC;CACf;AAED,uEAAuE;AACvE,MAAM,WAAW,WAAW;IAC1B,SAAS,CAAC,MAAM,EAAE,WAAW,EAAE,WAAW,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IAC3D,YAAY,CAAC,EAAE,EAAE,MAAM,GAAG,IAAI,CAAC;CAChC;AAwBD;;;GAGG;AACH,wBAAgB,WAAW,CAAC,MAAM,EAAE,WAAW,GAAG,WAAW,CAiD5D"}
@@ -0,0 +1,86 @@
1
+ import { OpenAPIHono, createRoute, z } from "@hono/zod-openapi";
2
+ import { streamSSE } from "hono/streaming";
3
+ import { nanoid } from "nanoid";
4
+ // ── Route definitions ─────────────────────────────────────────────────
5
+ const _sseEventStreamRoute = createRoute({
6
+ method: "get",
7
+ path: "/",
8
+ tags: ["Events"],
9
+ summary: "SSE event stream",
10
+ description: "Server-Sent Events stream for real-time events. Supports Last-Event-ID header for replay and ?filter= query parameter for event filtering.",
11
+ request: {
12
+ query: z.object({
13
+ filter: z.string().optional(),
14
+ }),
15
+ },
16
+ responses: {
17
+ 200: {
18
+ description: "SSE event stream (text/event-stream)",
19
+ },
20
+ },
21
+ });
22
+ // ── Route handlers ────────────────────────────────────────────────────
23
+ /**
24
+ * SSE streaming event routes.
25
+ * Accepts any EventBridge implementation (self-hosted SSEBridge, cloud EventEmitter adapter, etc.)
26
+ */
27
+ export function eventRoutes(bridge) {
28
+ const app = new OpenAPIHono();
29
+ app.get("/", (c) => {
30
+ const lastEventId = c.req.header("last-event-id");
31
+ const filterParam = c.req.query("filter");
32
+ const filters = filterParam ? filterParam.split(",").map(f => f.trim()) : null;
33
+ return streamSSE(c, async (stream) => {
34
+ const clientId = nanoid();
35
+ const client = {
36
+ id: clientId,
37
+ send(event, data, eventId) {
38
+ if (filters && !matchesFilter(event, filters))
39
+ return;
40
+ stream.writeSSE({
41
+ event,
42
+ data: JSON.stringify(data),
43
+ id: eventId,
44
+ });
45
+ },
46
+ close() {
47
+ stream.close();
48
+ },
49
+ };
50
+ bridge.addClient(client, lastEventId ?? undefined);
51
+ const heartbeat = setInterval(() => {
52
+ try {
53
+ stream.writeSSE({ event: "heartbeat", data: "" });
54
+ }
55
+ catch {
56
+ clearInterval(heartbeat);
57
+ bridge.removeClient(clientId);
58
+ }
59
+ }, 30_000);
60
+ stream.onAbort(() => {
61
+ clearInterval(heartbeat);
62
+ bridge.removeClient(clientId);
63
+ });
64
+ await new Promise((resolve) => {
65
+ stream.onAbort(() => resolve());
66
+ });
67
+ });
68
+ });
69
+ return app;
70
+ }
71
+ /** Check if an event name matches any of the filter patterns. */
72
+ function matchesFilter(event, filters) {
73
+ for (const filter of filters) {
74
+ if (filter === event)
75
+ return true;
76
+ if (filter.endsWith(":*")) {
77
+ const prefix = filter.slice(0, -1);
78
+ if (event.startsWith(prefix))
79
+ return true;
80
+ }
81
+ if (filter === "*")
82
+ return true;
83
+ }
84
+ return false;
85
+ }
86
+ //# sourceMappingURL=events.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"events.js","sourceRoot":"","sources":["../../src/routes/events.ts"],"names":[],"mappings":"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"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@polpo-ai/server",
3
- "version": "0.2.4",
3
+ "version": "0.2.6",
4
4
  "description": "Polpo API route factories — edge-compatible Hono routes for tasks, agents, missions, vault, and more",
5
5
  "type": "module",
6
6
  "main": "dist/index.js",
@@ -21,7 +21,7 @@
21
21
  ],
22
22
  "dependencies": {
23
23
  "@hono/zod-openapi": ">=1.0.0",
24
- "@polpo-ai/core": ">=0.2.0",
24
+ "@polpo-ai/core": "^0.2.5",
25
25
  "hono": ">=4.0.0",
26
26
  "nanoid": ">=5.0.0"
27
27
  },