openbot 0.3.0 → 0.3.2
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/app/cli.js +1 -1
- package/dist/app/server.js +1 -4
- package/dist/bus/services.js +222 -15
- package/dist/harness/context.js +205 -26
- package/dist/harness/queue-processor.js +44 -110
- package/dist/harness/runtime-factory.js +11 -7
- package/dist/harness/todo-advance.js +93 -0
- package/dist/plugins/ai-sdk/index.js +0 -3
- package/dist/plugins/ai-sdk/runtime.js +78 -13
- package/dist/plugins/ai-sdk/system-prompt.js +18 -3
- package/dist/plugins/delegation/index.js +7 -46
- package/dist/plugins/memory/index.js +71 -0
- package/dist/plugins/storage-tools/index.js +2 -11
- package/dist/plugins/todo/index.js +54 -0
- package/dist/plugins/workflow/index.js +65 -0
- package/dist/registry/plugins.js +4 -2
- package/dist/services/memory.js +152 -0
- package/dist/services/storage.js +9 -31
- package/dist/workflow/service.js +106 -0
- package/dist/workflow/types.js +3 -0
- package/docs/agents.md +15 -1
- package/docs/plugins.md +0 -1
- package/package.json +1 -1
- package/src/app/cli.ts +1 -1
- package/src/app/server.ts +3 -4
- package/src/app/types.ts +140 -45
- package/src/bus/plugin.ts +0 -2
- package/src/bus/services.ts +258 -17
- package/src/bus/types.ts +13 -4
- package/src/harness/context.ts +233 -37
- package/src/harness/queue-processor.ts +54 -143
- package/src/harness/runtime-factory.ts +11 -7
- package/src/harness/todo-advance.ts +128 -0
- package/src/plugins/ai-sdk/index.ts +0 -3
- package/src/plugins/ai-sdk/runtime.ts +356 -298
- package/src/plugins/ai-sdk/system-prompt.ts +18 -4
- package/src/plugins/delegation/index.ts +7 -50
- package/src/plugins/memory/index.ts +85 -0
- package/src/plugins/storage-tools/index.ts +8 -19
- package/src/plugins/todo/index.ts +64 -0
- package/src/registry/plugins.ts +4 -3
- package/src/services/memory.ts +213 -0
- package/src/services/storage.ts +9 -49
package/dist/services/storage.js
CHANGED
|
@@ -7,6 +7,7 @@ import { aiSdkPlugin } from '../plugins/ai-sdk/index.js';
|
|
|
7
7
|
import { AI_SDK_SYSTEM_PROMPT } from '../plugins/ai-sdk/system-prompt.js';
|
|
8
8
|
import { listBuiltInPlugins, parsePluginModule } from '../registry/plugins.js';
|
|
9
9
|
import { processService } from '../harness/process.js';
|
|
10
|
+
import { memoryService } from './memory.js';
|
|
10
11
|
import { pathToFileURL } from 'node:url';
|
|
11
12
|
const resolveBaseDir = () => {
|
|
12
13
|
const config = loadConfig();
|
|
@@ -62,16 +63,17 @@ const SYSTEM_DEFAULT_PLUGINS = [
|
|
|
62
63
|
{ id: 'storage-tools' },
|
|
63
64
|
// { id: 'mcp' },
|
|
64
65
|
{ id: 'shell' },
|
|
65
|
-
{ id: '
|
|
66
|
+
{ id: 'todo' },
|
|
66
67
|
// { id: 'ui' },
|
|
67
68
|
{ id: 'approval' },
|
|
69
|
+
{ id: 'memory' },
|
|
68
70
|
];
|
|
69
71
|
function getSystemAgentDetails(overrides) {
|
|
70
72
|
const defaults = {
|
|
71
73
|
id: SYSTEM_AGENT_ID,
|
|
72
74
|
name: 'OpenBot',
|
|
73
75
|
image: undefined,
|
|
74
|
-
description: 'First-party orchestration agent for OpenBot. Coordinates other agents via handoff
|
|
76
|
+
description: 'First-party orchestration agent for OpenBot. Coordinates other agents via handoff.',
|
|
75
77
|
instructions: AI_SDK_SYSTEM_PROMPT,
|
|
76
78
|
plugins: SYSTEM_DEFAULT_PLUGINS.map((ref) => ref.id),
|
|
77
79
|
pluginRefs: SYSTEM_DEFAULT_PLUGINS,
|
|
@@ -160,7 +162,6 @@ const listBuiltInPluginDescriptors = async () => {
|
|
|
160
162
|
description: plugin.description,
|
|
161
163
|
builtIn: true,
|
|
162
164
|
image: plugin.image,
|
|
163
|
-
defaultInstructions: plugin.defaultInstructions,
|
|
164
165
|
configSchema: plugin.configSchema,
|
|
165
166
|
createdAt: new Date(),
|
|
166
167
|
updatedAt: new Date(),
|
|
@@ -228,7 +229,6 @@ const listPluginsFromDisk = async () => {
|
|
|
228
229
|
description: parsed.description || '',
|
|
229
230
|
builtIn: false,
|
|
230
231
|
image: parsed.image || image,
|
|
231
|
-
defaultInstructions: parsed.defaultInstructions,
|
|
232
232
|
configSchema: parsed.configSchema,
|
|
233
233
|
createdAt: new Date(),
|
|
234
234
|
updatedAt: new Date(),
|
|
@@ -355,7 +355,7 @@ export const storageService = {
|
|
|
355
355
|
`# ${normalizedChannelId}\n\nDefine the goals and rules for this channel here.\n`);
|
|
356
356
|
await fs.writeFile(statePath, JSON.stringify(finalState, null, 2));
|
|
357
357
|
},
|
|
358
|
-
createThread: async ({ channelId, threadId, threadTitle,
|
|
358
|
+
createThread: async ({ channelId, threadId, threadTitle, initialState, }) => {
|
|
359
359
|
const normalizedChannelId = channelId.trim();
|
|
360
360
|
const normalizedThreadId = threadId.trim();
|
|
361
361
|
if (!normalizedChannelId)
|
|
@@ -363,7 +363,6 @@ export const storageService = {
|
|
|
363
363
|
if (!normalizedThreadId)
|
|
364
364
|
throw new Error('threadId is required');
|
|
365
365
|
const threadDir = getConversationDir(normalizedChannelId, normalizedThreadId);
|
|
366
|
-
const specPath = `${threadDir}/SPEC.md`;
|
|
367
366
|
const statePath = `${threadDir}/state.json`;
|
|
368
367
|
try {
|
|
369
368
|
await fs.access(threadDir);
|
|
@@ -380,8 +379,6 @@ export const storageService = {
|
|
|
380
379
|
baseState.generatedName = threadTitle.trim();
|
|
381
380
|
}
|
|
382
381
|
await fs.mkdir(threadDir, { recursive: true });
|
|
383
|
-
await fs.writeFile(specPath, spec?.trim() ||
|
|
384
|
-
`# ${normalizedThreadId}\n\nDefine the goals and plan for this thread here.\n`);
|
|
385
382
|
await fs.writeFile(statePath, JSON.stringify(baseState, null, 2));
|
|
386
383
|
},
|
|
387
384
|
getThreads: async ({ channelId }) => {
|
|
@@ -423,17 +420,7 @@ export const storageService = {
|
|
|
423
420
|
},
|
|
424
421
|
getThreadDetails: async ({ channelId, threadId, }) => {
|
|
425
422
|
const threadDir = getConversationDir(channelId, threadId);
|
|
426
|
-
const specPath = `${threadDir}/SPEC.md`;
|
|
427
423
|
const statePath = `${threadDir}/state.json`;
|
|
428
|
-
let spec = '';
|
|
429
|
-
try {
|
|
430
|
-
spec = await fs.readFile(specPath, 'utf-8');
|
|
431
|
-
}
|
|
432
|
-
catch (error) {
|
|
433
|
-
if (error?.code !== 'ENOENT') {
|
|
434
|
-
console.error(`Failed to read thread spec for channel ${channelId} thread ${threadId}`, error);
|
|
435
|
-
}
|
|
436
|
-
}
|
|
437
424
|
let state = {};
|
|
438
425
|
try {
|
|
439
426
|
const stateContent = await fs.readFile(statePath, 'utf-8');
|
|
@@ -451,7 +438,6 @@ export const storageService = {
|
|
|
451
438
|
id: threadId,
|
|
452
439
|
name: generatedName || threadId,
|
|
453
440
|
channelId,
|
|
454
|
-
spec,
|
|
455
441
|
state,
|
|
456
442
|
};
|
|
457
443
|
},
|
|
@@ -537,18 +523,6 @@ export const storageService = {
|
|
|
537
523
|
throw error;
|
|
538
524
|
}
|
|
539
525
|
},
|
|
540
|
-
patchThreadSpec: async ({ channelId, threadId, spec, }) => {
|
|
541
|
-
const threadDir = getConversationDir(channelId, threadId);
|
|
542
|
-
const specPath = `${threadDir}/SPEC.md`;
|
|
543
|
-
try {
|
|
544
|
-
await fs.mkdir(threadDir, { recursive: true });
|
|
545
|
-
await fs.writeFile(specPath, spec);
|
|
546
|
-
}
|
|
547
|
-
catch (error) {
|
|
548
|
-
console.error(`Failed to patch thread spec for channel ${channelId} thread ${threadId}`, error);
|
|
549
|
-
throw error;
|
|
550
|
-
}
|
|
551
|
-
},
|
|
552
526
|
getAgents: async () => {
|
|
553
527
|
const agentsDir = resolvePath(resolveBaseDir() + '/' + DEFAULT_AGENTS_DIR);
|
|
554
528
|
try {
|
|
@@ -935,6 +909,10 @@ export const storageService = {
|
|
|
935
909
|
}
|
|
936
910
|
return fs.readFile(targetFile, 'utf-8');
|
|
937
911
|
},
|
|
912
|
+
appendMemory: memoryService.appendMemory,
|
|
913
|
+
listMemories: memoryService.listMemories,
|
|
914
|
+
deleteMemory: memoryService.deleteMemory,
|
|
915
|
+
updateMemory: memoryService.updateMemory,
|
|
938
916
|
/**
|
|
939
917
|
* Hydrates the full OpenBot state from disk/storage before a run.
|
|
940
918
|
*/
|
|
@@ -0,0 +1,106 @@
|
|
|
1
|
+
import { generateId } from 'melony';
|
|
2
|
+
import { storageService } from '../services/storage.js';
|
|
3
|
+
import { WORKFLOW_SCHEMA_VERSION, WORKFLOW_THREAD_STATE_KEY, } from './types.js';
|
|
4
|
+
const asRecord = (value) => value && typeof value === 'object' && !Array.isArray(value)
|
|
5
|
+
? value
|
|
6
|
+
: {};
|
|
7
|
+
const isTodoStatus = (value) => value === 'pending' || value === 'done' || value === 'failed';
|
|
8
|
+
const parseTodo = (value) => {
|
|
9
|
+
const record = asRecord(value);
|
|
10
|
+
if (typeof record.id !== 'string' || !record.id)
|
|
11
|
+
return null;
|
|
12
|
+
if (typeof record.text !== 'string' || !record.text)
|
|
13
|
+
return null;
|
|
14
|
+
if (!isTodoStatus(record.status))
|
|
15
|
+
return null;
|
|
16
|
+
return {
|
|
17
|
+
id: record.id,
|
|
18
|
+
text: record.text,
|
|
19
|
+
status: record.status,
|
|
20
|
+
summary: typeof record.summary === 'string' ? record.summary : undefined,
|
|
21
|
+
};
|
|
22
|
+
};
|
|
23
|
+
export const parseThreadWorkflow = (state) => {
|
|
24
|
+
const record = asRecord(state);
|
|
25
|
+
const raw = record[WORKFLOW_THREAD_STATE_KEY];
|
|
26
|
+
const workflow = asRecord(raw);
|
|
27
|
+
if (typeof workflow.id !== 'string' || !workflow.id)
|
|
28
|
+
return null;
|
|
29
|
+
if (!Array.isArray(workflow.todos))
|
|
30
|
+
return null;
|
|
31
|
+
const todos = workflow.todos
|
|
32
|
+
.map((todo) => parseTodo(todo))
|
|
33
|
+
.filter((todo) => todo !== null);
|
|
34
|
+
if (todos.length === 0 && !workflow.title)
|
|
35
|
+
return null;
|
|
36
|
+
return {
|
|
37
|
+
version: typeof workflow.version === 'number' ? workflow.version : WORKFLOW_SCHEMA_VERSION,
|
|
38
|
+
id: workflow.id,
|
|
39
|
+
title: typeof workflow.title === 'string' ? workflow.title : undefined,
|
|
40
|
+
todos,
|
|
41
|
+
updatedAt: typeof workflow.updatedAt === 'string' ? workflow.updatedAt : new Date().toISOString(),
|
|
42
|
+
};
|
|
43
|
+
};
|
|
44
|
+
export const loadThreadWorkflow = async (channelId, threadId) => {
|
|
45
|
+
const details = await storageService.getThreadDetails({ channelId, threadId });
|
|
46
|
+
return parseThreadWorkflow(details.state);
|
|
47
|
+
};
|
|
48
|
+
export const persistWorkflow = async (channelId, threadId, workflow) => {
|
|
49
|
+
const next = {
|
|
50
|
+
...workflow,
|
|
51
|
+
version: WORKFLOW_SCHEMA_VERSION,
|
|
52
|
+
updatedAt: new Date().toISOString(),
|
|
53
|
+
};
|
|
54
|
+
await storageService.patchThreadState({
|
|
55
|
+
channelId,
|
|
56
|
+
threadId,
|
|
57
|
+
state: { [WORKFLOW_THREAD_STATE_KEY]: next },
|
|
58
|
+
});
|
|
59
|
+
return next;
|
|
60
|
+
};
|
|
61
|
+
export const setWorkflowPlan = async (options) => {
|
|
62
|
+
const { channelId, threadId, plan } = options;
|
|
63
|
+
const workflow = {
|
|
64
|
+
version: WORKFLOW_SCHEMA_VERSION,
|
|
65
|
+
id: `wf_${generateId()}`,
|
|
66
|
+
title: plan.title,
|
|
67
|
+
todos: plan.todos.map((t) => ({
|
|
68
|
+
id: t.id || `todo_${generateId()}`,
|
|
69
|
+
text: t.text,
|
|
70
|
+
status: 'pending',
|
|
71
|
+
})),
|
|
72
|
+
updatedAt: new Date().toISOString(),
|
|
73
|
+
};
|
|
74
|
+
return persistWorkflow(channelId, threadId, workflow);
|
|
75
|
+
};
|
|
76
|
+
export const updateWorkflowTodo = async (options) => {
|
|
77
|
+
const { channelId, threadId, update } = options;
|
|
78
|
+
const workflow = await loadThreadWorkflow(channelId, threadId);
|
|
79
|
+
if (!workflow)
|
|
80
|
+
throw new Error('No active workflow found.');
|
|
81
|
+
const todos = workflow.todos.map((todo) => {
|
|
82
|
+
if (todo.id !== update.todoId)
|
|
83
|
+
return todo;
|
|
84
|
+
return {
|
|
85
|
+
...todo,
|
|
86
|
+
...(update.status ? { status: update.status } : {}),
|
|
87
|
+
...(update.summary !== undefined ? { summary: update.summary } : {}),
|
|
88
|
+
};
|
|
89
|
+
});
|
|
90
|
+
return persistWorkflow(channelId, threadId, { ...workflow, todos });
|
|
91
|
+
};
|
|
92
|
+
export const formatWorkflowForPrompt = (workflow) => {
|
|
93
|
+
const lines = [
|
|
94
|
+
'## Current Workflow Plan',
|
|
95
|
+
workflow.title ? `Title: ${workflow.title}` : '',
|
|
96
|
+
'This plan is for your internal coordination. Update it as you progress.',
|
|
97
|
+
'',
|
|
98
|
+
].filter(Boolean);
|
|
99
|
+
for (const todo of workflow.todos) {
|
|
100
|
+
lines.push(`- [${todo.status}] ${todo.id}: ${todo.text}`);
|
|
101
|
+
if (todo.summary) {
|
|
102
|
+
lines.push(` Result: ${todo.summary}`);
|
|
103
|
+
}
|
|
104
|
+
}
|
|
105
|
+
return lines.join('\n');
|
|
106
|
+
};
|
package/docs/agents.md
CHANGED
|
@@ -47,7 +47,21 @@ plugins like `shell` or `mcp` to them has no effect. Pair tool plugins with
|
|
|
47
47
|
|
|
48
48
|
OpenBot ships a built-in `system` agent (the orchestrator) with the
|
|
49
49
|
`ai-sdk` runtime plus the standard tool plugins (storage, shell, mcp,
|
|
50
|
-
delegation, ui, approval). It cannot be deleted.
|
|
50
|
+
delegation, ui, approval, memory). It cannot be deleted.
|
|
51
|
+
|
|
52
|
+
## Memory
|
|
53
|
+
|
|
54
|
+
The `memory` plugin gives every agent three tools — `remember`, `recall`,
|
|
55
|
+
`forget` — backed by an append-only JSONL log at `~/.openbot/memory/log.jsonl`.
|
|
56
|
+
Memories are scoped:
|
|
57
|
+
|
|
58
|
+
- `global` (default) — visible to every agent everywhere.
|
|
59
|
+
- `agent` — visible only to the agent that wrote it.
|
|
60
|
+
- `channel` — visible only inside the active channel.
|
|
61
|
+
|
|
62
|
+
On every LLM turn the runtime injects matching memories into the system prompt
|
|
63
|
+
via the `MemoryProvider` in the context engine, so the model treats remembered
|
|
64
|
+
facts as ground truth without needing to call `recall` first.
|
|
51
65
|
|
|
52
66
|
## Installing community agents
|
|
53
67
|
|
package/docs/plugins.md
CHANGED
package/package.json
CHANGED
package/src/app/cli.ts
CHANGED
package/src/app/server.ts
CHANGED
|
@@ -289,9 +289,8 @@ export async function startServer(options: ServerOptions = {}) {
|
|
|
289
289
|
|
|
290
290
|
app.listen(PORT, () => {
|
|
291
291
|
console.log(`\x1b[32mOpenBot server listening at http://localhost:${PORT}\x1b[0m`);
|
|
292
|
-
console.log(
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
console.log(` - State endpoint: GET /api/state`);
|
|
292
|
+
console.log(
|
|
293
|
+
`🌐 Visit \x1b[96m\x1b[1mhttps://openbot.one\x1b[0m to connect to this runtime and manage everything from there. ✨`,
|
|
294
|
+
);
|
|
296
295
|
});
|
|
297
296
|
}
|
package/src/app/types.ts
CHANGED
|
@@ -8,6 +8,7 @@ import {
|
|
|
8
8
|
ThreadDetails,
|
|
9
9
|
} from '../bus/types.js';
|
|
10
10
|
import type { PluginRef } from '../bus/plugin.js';
|
|
11
|
+
import type { MemoryRecord } from '../services/memory.js';
|
|
11
12
|
|
|
12
13
|
export interface OpenBotState {
|
|
13
14
|
agentId: string;
|
|
@@ -289,7 +290,6 @@ export type PatchThreadDetailsEvent = BaseEvent & {
|
|
|
289
290
|
type: 'action:patch_thread_details';
|
|
290
291
|
data: {
|
|
291
292
|
state?: Record<string, unknown>;
|
|
292
|
-
spec?: string;
|
|
293
293
|
};
|
|
294
294
|
};
|
|
295
295
|
|
|
@@ -297,7 +297,7 @@ export type PatchThreadDetailsResultEvent = BaseEvent & {
|
|
|
297
297
|
type: 'action:patch_thread_details:result';
|
|
298
298
|
data: {
|
|
299
299
|
success: boolean;
|
|
300
|
-
updatedFields: ('state'
|
|
300
|
+
updatedFields: ('state')[];
|
|
301
301
|
};
|
|
302
302
|
};
|
|
303
303
|
|
|
@@ -380,7 +380,6 @@ export type CreateThreadEvent = BaseEvent & {
|
|
|
380
380
|
type: 'action:create_thread';
|
|
381
381
|
data: {
|
|
382
382
|
threadTitle: string;
|
|
383
|
-
spec?: string;
|
|
384
383
|
initialState?: Record<string, unknown>;
|
|
385
384
|
};
|
|
386
385
|
meta: {
|
|
@@ -569,34 +568,7 @@ export type HandoffResultEvent = BaseEvent & {
|
|
|
569
568
|
};
|
|
570
569
|
};
|
|
571
570
|
|
|
572
|
-
|
|
573
|
-
type: 'action:delegate';
|
|
574
|
-
data: {
|
|
575
|
-
agentId: string;
|
|
576
|
-
content: string;
|
|
577
|
-
};
|
|
578
|
-
meta?: {
|
|
579
|
-
toolCallId?: string;
|
|
580
|
-
[key: string]: any;
|
|
581
|
-
};
|
|
582
|
-
};
|
|
583
|
-
|
|
584
|
-
export type DelegateResultEvent = BaseEvent & {
|
|
585
|
-
type: 'action:delegate:result';
|
|
586
|
-
data: {
|
|
587
|
-
success: boolean;
|
|
588
|
-
agentId: string;
|
|
589
|
-
summary: string;
|
|
590
|
-
};
|
|
591
|
-
meta: {
|
|
592
|
-
toolCallId: string;
|
|
593
|
-
agentId: string;
|
|
594
|
-
threadId?: string;
|
|
595
|
-
[key: string]: any;
|
|
596
|
-
};
|
|
597
|
-
};
|
|
598
|
-
|
|
599
|
-
/** Internal routing: delegation plugin → orchestrator only (not stored or broadcast). */
|
|
571
|
+
/** Internal routing: handoff plugin → orchestrator only (not stored or broadcast). */
|
|
600
572
|
export type HandoffRequestEvent = BaseEvent & {
|
|
601
573
|
type: 'handoff:request';
|
|
602
574
|
data: {
|
|
@@ -606,16 +578,6 @@ export type HandoffRequestEvent = BaseEvent & {
|
|
|
606
578
|
meta?: Record<string, unknown>;
|
|
607
579
|
};
|
|
608
580
|
|
|
609
|
-
/** Internal routing: delegation plugin → orchestrator only (not stored or broadcast). */
|
|
610
|
-
export type DelegationRequestEvent = BaseEvent & {
|
|
611
|
-
type: 'delegation:request';
|
|
612
|
-
data: {
|
|
613
|
-
agentId: string;
|
|
614
|
-
content: string;
|
|
615
|
-
};
|
|
616
|
-
meta?: Record<string, unknown>;
|
|
617
|
-
};
|
|
618
|
-
|
|
619
581
|
export type MCPListToolsEvent = BaseEvent & {
|
|
620
582
|
type: 'action:mcp_list_tools';
|
|
621
583
|
data: {
|
|
@@ -766,6 +728,132 @@ export type InstallAgentResultEvent = BaseEvent & {
|
|
|
766
728
|
};
|
|
767
729
|
};
|
|
768
730
|
|
|
731
|
+
export type MemoryScopeAlias = 'global' | 'agent' | 'channel';
|
|
732
|
+
|
|
733
|
+
export type RememberEvent = BaseEvent & {
|
|
734
|
+
type: 'action:remember';
|
|
735
|
+
data: {
|
|
736
|
+
content: string;
|
|
737
|
+
scope?: MemoryScopeAlias;
|
|
738
|
+
tags?: string[];
|
|
739
|
+
};
|
|
740
|
+
};
|
|
741
|
+
|
|
742
|
+
export type RememberResultEvent = BaseEvent & {
|
|
743
|
+
type: 'action:remember:result';
|
|
744
|
+
data: {
|
|
745
|
+
success: boolean;
|
|
746
|
+
record?: MemoryRecord;
|
|
747
|
+
error?: string;
|
|
748
|
+
};
|
|
749
|
+
};
|
|
750
|
+
|
|
751
|
+
export type RecallEvent = BaseEvent & {
|
|
752
|
+
type: 'action:recall';
|
|
753
|
+
data: {
|
|
754
|
+
query?: string;
|
|
755
|
+
tag?: string;
|
|
756
|
+
scope?: MemoryScopeAlias | 'all';
|
|
757
|
+
limit?: number;
|
|
758
|
+
};
|
|
759
|
+
};
|
|
760
|
+
|
|
761
|
+
export type RecallResultEvent = BaseEvent & {
|
|
762
|
+
type: 'action:recall:result';
|
|
763
|
+
data: {
|
|
764
|
+
success: boolean;
|
|
765
|
+
records: MemoryRecord[];
|
|
766
|
+
error?: string;
|
|
767
|
+
};
|
|
768
|
+
};
|
|
769
|
+
|
|
770
|
+
export type ForgetEvent = BaseEvent & {
|
|
771
|
+
type: 'action:forget';
|
|
772
|
+
data: { id: string };
|
|
773
|
+
};
|
|
774
|
+
|
|
775
|
+
export type ForgetResultEvent = BaseEvent & {
|
|
776
|
+
type: 'action:forget:result';
|
|
777
|
+
data: {
|
|
778
|
+
success: boolean;
|
|
779
|
+
deleted: boolean;
|
|
780
|
+
error?: string;
|
|
781
|
+
};
|
|
782
|
+
};
|
|
783
|
+
|
|
784
|
+
export type TodoStatus = 'pending' | 'in_progress' | 'done' | 'cancelled';
|
|
785
|
+
|
|
786
|
+
/**
|
|
787
|
+
* A single unit of work tracked in thread state. Todos are owned by the
|
|
788
|
+
* system (bus services); agents can only mutate them by calling the
|
|
789
|
+
* `todo_write` / `todo_update` tools so every change is observable on the
|
|
790
|
+
* event stream and audit-friendly.
|
|
791
|
+
*/
|
|
792
|
+
export interface TodoItem {
|
|
793
|
+
id: string;
|
|
794
|
+
content: string;
|
|
795
|
+
status: TodoStatus;
|
|
796
|
+
/** Optional agent id responsible for this item — drives autonomous handoffs. */
|
|
797
|
+
assignee?: string;
|
|
798
|
+
/** Agent id that created the todo (or "system"). */
|
|
799
|
+
createdBy: string;
|
|
800
|
+
createdAt: number;
|
|
801
|
+
updatedAt: number;
|
|
802
|
+
/**
|
|
803
|
+
* Captured final reply when this item reaches `done` (last `agent:output`
|
|
804
|
+
* from the assignee for that run). Lets downstream agents rely on thread
|
|
805
|
+
* state instead of merged short-term messages.
|
|
806
|
+
*/
|
|
807
|
+
result?: string;
|
|
808
|
+
}
|
|
809
|
+
|
|
810
|
+
export type TodoWriteInput = {
|
|
811
|
+
id?: string;
|
|
812
|
+
content: string;
|
|
813
|
+
status?: TodoStatus;
|
|
814
|
+
assignee?: string;
|
|
815
|
+
};
|
|
816
|
+
|
|
817
|
+
export type TodoWriteEvent = BaseEvent & {
|
|
818
|
+
type: 'action:todo_write';
|
|
819
|
+
data: {
|
|
820
|
+
todos: TodoWriteInput[];
|
|
821
|
+
};
|
|
822
|
+
meta?: { toolCallId?: string; agentId?: string; threadId?: string };
|
|
823
|
+
};
|
|
824
|
+
|
|
825
|
+
export type TodoWriteResultEvent = BaseEvent & {
|
|
826
|
+
type: 'action:todo_write:result';
|
|
827
|
+
data: {
|
|
828
|
+
success: boolean;
|
|
829
|
+
todos: TodoItem[];
|
|
830
|
+
error?: string;
|
|
831
|
+
};
|
|
832
|
+
meta?: { toolCallId?: string; agentId?: string; threadId?: string };
|
|
833
|
+
};
|
|
834
|
+
|
|
835
|
+
export type TodoUpdateEvent = BaseEvent & {
|
|
836
|
+
type: 'action:todo_update';
|
|
837
|
+
data: {
|
|
838
|
+
id: string;
|
|
839
|
+
status?: TodoStatus;
|
|
840
|
+
content?: string;
|
|
841
|
+
assignee?: string;
|
|
842
|
+
};
|
|
843
|
+
meta?: { toolCallId?: string; agentId?: string; threadId?: string };
|
|
844
|
+
};
|
|
845
|
+
|
|
846
|
+
export type TodoUpdateResultEvent = BaseEvent & {
|
|
847
|
+
type: 'action:todo_update:result';
|
|
848
|
+
data: {
|
|
849
|
+
success: boolean;
|
|
850
|
+
todo?: TodoItem;
|
|
851
|
+
todos: TodoItem[];
|
|
852
|
+
error?: string;
|
|
853
|
+
};
|
|
854
|
+
meta?: { toolCallId?: string; agentId?: string; threadId?: string };
|
|
855
|
+
};
|
|
856
|
+
|
|
769
857
|
export type OpenBotEvent =
|
|
770
858
|
| UserInputEvent
|
|
771
859
|
| AgentInvokeEvent
|
|
@@ -825,10 +913,7 @@ export type OpenBotEvent =
|
|
|
825
913
|
| UIWidgetResponseEvent
|
|
826
914
|
| HandoffEvent
|
|
827
915
|
| HandoffResultEvent
|
|
828
|
-
| DelegateEvent
|
|
829
|
-
| DelegateResultEvent
|
|
830
916
|
| HandoffRequestEvent
|
|
831
|
-
| DelegationRequestEvent
|
|
832
917
|
| MCPListToolsEvent
|
|
833
918
|
| MCPListToolsResultEvent
|
|
834
919
|
| MCPCallEvent
|
|
@@ -842,4 +927,14 @@ export type OpenBotEvent =
|
|
|
842
927
|
| ListMarketplaceAgentsEvent
|
|
843
928
|
| ListMarketplaceAgentsResultEvent
|
|
844
929
|
| InstallAgentEvent
|
|
845
|
-
| InstallAgentResultEvent
|
|
930
|
+
| InstallAgentResultEvent
|
|
931
|
+
| RememberEvent
|
|
932
|
+
| RememberResultEvent
|
|
933
|
+
| RecallEvent
|
|
934
|
+
| RecallResultEvent
|
|
935
|
+
| ForgetEvent
|
|
936
|
+
| ForgetResultEvent
|
|
937
|
+
| TodoWriteEvent
|
|
938
|
+
| TodoWriteResultEvent
|
|
939
|
+
| TodoUpdateEvent
|
|
940
|
+
| TodoUpdateResultEvent;
|
package/src/bus/plugin.ts
CHANGED
|
@@ -56,8 +56,6 @@ export interface Plugin {
|
|
|
56
56
|
name: string;
|
|
57
57
|
description: string;
|
|
58
58
|
image?: string;
|
|
59
|
-
/** Optional system-prompt body suggested when this plugin is used as the runtime. */
|
|
60
|
-
defaultInstructions?: string;
|
|
61
59
|
/** JSON-schema-like description of `config` accepted in AGENT.md `plugins[].config`. */
|
|
62
60
|
configSchema?: ConfigSchema;
|
|
63
61
|
/** Tool definitions contributed to any runtime plugin attached to the same agent. */
|