volute 0.4.0 → 0.5.0
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/README.md +22 -22
- package/dist/agent-Z2B6EFEQ.js +75 -0
- package/dist/{agent-manager-AUCKMGPR.js → agent-manager-PXBKA2GK.js} +4 -4
- package/dist/channel-MK5OK2SI.js +113 -0
- package/dist/chunk-5X7HGB6L.js +107 -0
- package/dist/{chunk-YGFIWIOF.js → chunk-7L4AN5D4.js} +1 -1
- package/dist/{chunk-VRVVQIYY.js → chunk-AZEL2IEK.js} +1 -1
- package/dist/chunk-B3R6L2GW.js +24 -0
- package/dist/{chunk-DNOXHLE5.js → chunk-HE67X4T6.js} +1 -1
- package/dist/{chunk-I6OHXCMV.js → chunk-MW2KFO3B.js} +47 -9
- package/dist/{chunk-5OCWMTVS.js → chunk-SMISE4SV.js} +77 -3
- package/dist/{chunk-SOZA2TLP.js → chunk-UAVD2AHX.js} +1 -1
- package/dist/{chunk-3C2XR4IY.js → chunk-UX25Z2ND.js} +113 -107
- package/dist/{chunk-GSPKUPKU.js → chunk-XUA3JUFK.js} +2 -1
- package/dist/chunk-ZYGKG6VC.js +22 -0
- package/dist/cli.js +86 -74
- package/dist/{connector-DKDJTLYZ.js → connector-LYEMXQEV.js} +11 -6
- package/dist/connectors/discord.js +3 -1
- package/dist/connectors/slack.js +14 -5
- package/dist/connectors/telegram.js +21 -2
- package/dist/conversation-ERXEQZTY.js +163 -0
- package/dist/create-RVCZN6HE.js +91 -0
- package/dist/{daemon-client-XR24PUJF.js → daemon-client-ZY6UUN2M.js} +2 -2
- package/dist/daemon.js +629 -177
- package/dist/{delete-55MXCEY5.js → delete-3QH7VYIN.js} +7 -8
- package/dist/{down-3OB6UVAJ.js → down-O7IFZLVJ.js} +1 -1
- package/dist/{env-JB27UAC3.js → env-4D4REPJF.js} +8 -5
- package/dist/{history-BKG74I43.js → history-OEONB53Z.js} +3 -3
- package/dist/{import-4CI2ZUTJ.js → import-MXJB2EII.js} +8 -8
- package/dist/{logs-NXFFGUKY.js → logs-DF342W4M.js} +2 -2
- package/dist/message-ADHWFHSI.js +32 -0
- package/dist/{package-Z2SFO2SV.js → package-VQOE7JNH.js} +1 -1
- package/dist/{schedule-A35SH4HT.js → schedule-NAG6F463.js} +10 -5
- package/dist/send-66QMKRUH.js +75 -0
- package/dist/{setup-2FDVN7OF.js → setup-RPRRGG2F.js} +5 -5
- package/dist/{start-LDPMCMYT.js → start-TUOXDSFL.js} +3 -3
- package/dist/{status-MVSQG54T.js → status-A36EHRO4.js} +3 -3
- package/dist/{stop-5PZTZCLL.js → stop-AOJZLQ5X.js} +6 -7
- package/dist/{up-F7TMTLRE.js → up-7ILD7GU7.js} +2 -2
- package/dist/update-LPSIAWQ2.js +140 -0
- package/dist/update-check-Y33QDCFL.js +17 -0
- package/dist/{upgrade-6ZW2RD64.js → upgrade-FX2TKJ2S.js} +16 -15
- package/dist/{variant-T64BKARF.js → variant-LAB67OC2.js} +15 -10
- package/dist/web-assets/assets/index-BbRmoxoA.js +308 -0
- package/dist/web-assets/index.html +2 -2
- package/drizzle/0003_clean_ego.sql +12 -0
- package/drizzle/meta/0003_snapshot.json +417 -0
- package/drizzle/meta/_journal.json +7 -0
- package/package.json +1 -1
- package/templates/_base/.init/.config/hooks/startup-context.sh +19 -1
- package/templates/_base/_skills/volute-agent/SKILL.md +110 -14
- package/templates/_base/home/.config/routes.json +10 -0
- package/templates/_base/home/VOLUTE.md +14 -35
- package/templates/_base/src/lib/format-prefix.ts +1 -1
- package/templates/_base/src/lib/router.ts +163 -16
- package/templates/_base/src/lib/routing.ts +55 -18
- package/templates/_base/src/lib/types.ts +3 -1
- package/templates/agent-sdk/.init/.config/routes.json +5 -0
- package/templates/agent-sdk/.init/CLAUDE.md +2 -2
- package/templates/agent-sdk/src/agent.ts +2 -1
- package/templates/agent-sdk/src/server.ts +8 -2
- package/templates/agent-sdk/volute-template.json +1 -1
- package/templates/pi/.init/.config/routes.json +5 -0
- package/templates/pi/.init/AGENTS.md +1 -1
- package/templates/pi/src/agent.ts +5 -3
- package/templates/pi/src/server.ts +1 -1
- package/templates/pi/volute-template.json +1 -1
- package/dist/channel-DQ6UY7QB.js +0 -67
- package/dist/chunk-ZHCE4DPY.js +0 -110
- package/dist/create-ILVOG75A.js +0 -79
- package/dist/send-3U6OTKG7.js +0 -57
- package/dist/web-assets/assets/index-NS621maO.js +0 -296
- package/templates/agent-sdk/.init/.config/sessions.json +0 -4
- package/templates/pi/.init/.config/sessions.json +0 -1
- package/dist/{service-SA4TTMDU.js → service-HZNIDNJF.js} +3 -3
|
@@ -6,8 +6,8 @@
|
|
|
6
6
|
<title>volute</title>
|
|
7
7
|
<link rel="preconnect" href="https://fonts.googleapis.com" />
|
|
8
8
|
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin />
|
|
9
|
-
<link href="https://fonts.googleapis.com/css2?family=IBM+Plex+Mono:ital,wght@0,300;0,400;0,500;0,600;1,400&
|
|
10
|
-
<script type="module" crossorigin src="/assets/index-
|
|
9
|
+
<link href="https://fonts.googleapis.com/css2?family=IBM+Plex+Mono:ital,wght@0,300;0,400;0,500;0,600;1,400&display=swap" rel="stylesheet" />
|
|
10
|
+
<script type="module" crossorigin src="/assets/index-BbRmoxoA.js"></script>
|
|
11
11
|
</head>
|
|
12
12
|
<body>
|
|
13
13
|
<div id="root"></div>
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
CREATE TABLE `conversation_participants` (
|
|
2
|
+
`conversation_id` text NOT NULL,
|
|
3
|
+
`user_id` integer NOT NULL,
|
|
4
|
+
`role` text DEFAULT 'member' NOT NULL,
|
|
5
|
+
`joined_at` text DEFAULT (datetime('now')) NOT NULL,
|
|
6
|
+
FOREIGN KEY (`conversation_id`) REFERENCES `conversations`(`id`) ON UPDATE no action ON DELETE cascade,
|
|
7
|
+
FOREIGN KEY (`user_id`) REFERENCES `users`(`id`) ON UPDATE no action ON DELETE cascade
|
|
8
|
+
);
|
|
9
|
+
--> statement-breakpoint
|
|
10
|
+
CREATE UNIQUE INDEX `idx_cp_unique` ON `conversation_participants` (`conversation_id`,`user_id`);--> statement-breakpoint
|
|
11
|
+
CREATE INDEX `idx_cp_user_id` ON `conversation_participants` (`user_id`);--> statement-breakpoint
|
|
12
|
+
ALTER TABLE `users` ADD `user_type` text DEFAULT 'human' NOT NULL;
|
|
@@ -0,0 +1,417 @@
|
|
|
1
|
+
{
|
|
2
|
+
"version": "6",
|
|
3
|
+
"dialect": "sqlite",
|
|
4
|
+
"id": "b96d5915-4500-42f4-8638-28f0526d41f0",
|
|
5
|
+
"prevId": "b76b7e15-3489-4a1d-ac23-977cf267d174",
|
|
6
|
+
"tables": {
|
|
7
|
+
"agent_messages": {
|
|
8
|
+
"name": "agent_messages",
|
|
9
|
+
"columns": {
|
|
10
|
+
"id": {
|
|
11
|
+
"name": "id",
|
|
12
|
+
"type": "integer",
|
|
13
|
+
"primaryKey": true,
|
|
14
|
+
"notNull": true,
|
|
15
|
+
"autoincrement": true
|
|
16
|
+
},
|
|
17
|
+
"agent": {
|
|
18
|
+
"name": "agent",
|
|
19
|
+
"type": "text",
|
|
20
|
+
"primaryKey": false,
|
|
21
|
+
"notNull": true,
|
|
22
|
+
"autoincrement": false
|
|
23
|
+
},
|
|
24
|
+
"channel": {
|
|
25
|
+
"name": "channel",
|
|
26
|
+
"type": "text",
|
|
27
|
+
"primaryKey": false,
|
|
28
|
+
"notNull": true,
|
|
29
|
+
"autoincrement": false
|
|
30
|
+
},
|
|
31
|
+
"role": {
|
|
32
|
+
"name": "role",
|
|
33
|
+
"type": "text",
|
|
34
|
+
"primaryKey": false,
|
|
35
|
+
"notNull": true,
|
|
36
|
+
"autoincrement": false
|
|
37
|
+
},
|
|
38
|
+
"sender": {
|
|
39
|
+
"name": "sender",
|
|
40
|
+
"type": "text",
|
|
41
|
+
"primaryKey": false,
|
|
42
|
+
"notNull": false,
|
|
43
|
+
"autoincrement": false
|
|
44
|
+
},
|
|
45
|
+
"content": {
|
|
46
|
+
"name": "content",
|
|
47
|
+
"type": "text",
|
|
48
|
+
"primaryKey": false,
|
|
49
|
+
"notNull": true,
|
|
50
|
+
"autoincrement": false
|
|
51
|
+
},
|
|
52
|
+
"created_at": {
|
|
53
|
+
"name": "created_at",
|
|
54
|
+
"type": "text",
|
|
55
|
+
"primaryKey": false,
|
|
56
|
+
"notNull": true,
|
|
57
|
+
"autoincrement": false,
|
|
58
|
+
"default": "(datetime('now'))"
|
|
59
|
+
}
|
|
60
|
+
},
|
|
61
|
+
"indexes": {
|
|
62
|
+
"idx_agent_messages_agent": {
|
|
63
|
+
"name": "idx_agent_messages_agent",
|
|
64
|
+
"columns": ["agent"],
|
|
65
|
+
"isUnique": false
|
|
66
|
+
},
|
|
67
|
+
"idx_agent_messages_channel": {
|
|
68
|
+
"name": "idx_agent_messages_channel",
|
|
69
|
+
"columns": ["agent", "channel"],
|
|
70
|
+
"isUnique": false
|
|
71
|
+
}
|
|
72
|
+
},
|
|
73
|
+
"foreignKeys": {},
|
|
74
|
+
"compositePrimaryKeys": {},
|
|
75
|
+
"uniqueConstraints": {},
|
|
76
|
+
"checkConstraints": {}
|
|
77
|
+
},
|
|
78
|
+
"conversation_participants": {
|
|
79
|
+
"name": "conversation_participants",
|
|
80
|
+
"columns": {
|
|
81
|
+
"conversation_id": {
|
|
82
|
+
"name": "conversation_id",
|
|
83
|
+
"type": "text",
|
|
84
|
+
"primaryKey": false,
|
|
85
|
+
"notNull": true,
|
|
86
|
+
"autoincrement": false
|
|
87
|
+
},
|
|
88
|
+
"user_id": {
|
|
89
|
+
"name": "user_id",
|
|
90
|
+
"type": "integer",
|
|
91
|
+
"primaryKey": false,
|
|
92
|
+
"notNull": true,
|
|
93
|
+
"autoincrement": false
|
|
94
|
+
},
|
|
95
|
+
"role": {
|
|
96
|
+
"name": "role",
|
|
97
|
+
"type": "text",
|
|
98
|
+
"primaryKey": false,
|
|
99
|
+
"notNull": true,
|
|
100
|
+
"autoincrement": false,
|
|
101
|
+
"default": "'member'"
|
|
102
|
+
},
|
|
103
|
+
"joined_at": {
|
|
104
|
+
"name": "joined_at",
|
|
105
|
+
"type": "text",
|
|
106
|
+
"primaryKey": false,
|
|
107
|
+
"notNull": true,
|
|
108
|
+
"autoincrement": false,
|
|
109
|
+
"default": "(datetime('now'))"
|
|
110
|
+
}
|
|
111
|
+
},
|
|
112
|
+
"indexes": {
|
|
113
|
+
"idx_cp_unique": {
|
|
114
|
+
"name": "idx_cp_unique",
|
|
115
|
+
"columns": ["conversation_id", "user_id"],
|
|
116
|
+
"isUnique": true
|
|
117
|
+
},
|
|
118
|
+
"idx_cp_user_id": {
|
|
119
|
+
"name": "idx_cp_user_id",
|
|
120
|
+
"columns": ["user_id"],
|
|
121
|
+
"isUnique": false
|
|
122
|
+
}
|
|
123
|
+
},
|
|
124
|
+
"foreignKeys": {
|
|
125
|
+
"conversation_participants_conversation_id_conversations_id_fk": {
|
|
126
|
+
"name": "conversation_participants_conversation_id_conversations_id_fk",
|
|
127
|
+
"tableFrom": "conversation_participants",
|
|
128
|
+
"tableTo": "conversations",
|
|
129
|
+
"columnsFrom": ["conversation_id"],
|
|
130
|
+
"columnsTo": ["id"],
|
|
131
|
+
"onDelete": "cascade",
|
|
132
|
+
"onUpdate": "no action"
|
|
133
|
+
},
|
|
134
|
+
"conversation_participants_user_id_users_id_fk": {
|
|
135
|
+
"name": "conversation_participants_user_id_users_id_fk",
|
|
136
|
+
"tableFrom": "conversation_participants",
|
|
137
|
+
"tableTo": "users",
|
|
138
|
+
"columnsFrom": ["user_id"],
|
|
139
|
+
"columnsTo": ["id"],
|
|
140
|
+
"onDelete": "cascade",
|
|
141
|
+
"onUpdate": "no action"
|
|
142
|
+
}
|
|
143
|
+
},
|
|
144
|
+
"compositePrimaryKeys": {},
|
|
145
|
+
"uniqueConstraints": {},
|
|
146
|
+
"checkConstraints": {}
|
|
147
|
+
},
|
|
148
|
+
"conversations": {
|
|
149
|
+
"name": "conversations",
|
|
150
|
+
"columns": {
|
|
151
|
+
"id": {
|
|
152
|
+
"name": "id",
|
|
153
|
+
"type": "text",
|
|
154
|
+
"primaryKey": true,
|
|
155
|
+
"notNull": true,
|
|
156
|
+
"autoincrement": false
|
|
157
|
+
},
|
|
158
|
+
"agent_name": {
|
|
159
|
+
"name": "agent_name",
|
|
160
|
+
"type": "text",
|
|
161
|
+
"primaryKey": false,
|
|
162
|
+
"notNull": true,
|
|
163
|
+
"autoincrement": false
|
|
164
|
+
},
|
|
165
|
+
"channel": {
|
|
166
|
+
"name": "channel",
|
|
167
|
+
"type": "text",
|
|
168
|
+
"primaryKey": false,
|
|
169
|
+
"notNull": true,
|
|
170
|
+
"autoincrement": false
|
|
171
|
+
},
|
|
172
|
+
"user_id": {
|
|
173
|
+
"name": "user_id",
|
|
174
|
+
"type": "integer",
|
|
175
|
+
"primaryKey": false,
|
|
176
|
+
"notNull": false,
|
|
177
|
+
"autoincrement": false
|
|
178
|
+
},
|
|
179
|
+
"title": {
|
|
180
|
+
"name": "title",
|
|
181
|
+
"type": "text",
|
|
182
|
+
"primaryKey": false,
|
|
183
|
+
"notNull": false,
|
|
184
|
+
"autoincrement": false
|
|
185
|
+
},
|
|
186
|
+
"created_at": {
|
|
187
|
+
"name": "created_at",
|
|
188
|
+
"type": "text",
|
|
189
|
+
"primaryKey": false,
|
|
190
|
+
"notNull": true,
|
|
191
|
+
"autoincrement": false,
|
|
192
|
+
"default": "(datetime('now'))"
|
|
193
|
+
},
|
|
194
|
+
"updated_at": {
|
|
195
|
+
"name": "updated_at",
|
|
196
|
+
"type": "text",
|
|
197
|
+
"primaryKey": false,
|
|
198
|
+
"notNull": true,
|
|
199
|
+
"autoincrement": false,
|
|
200
|
+
"default": "(datetime('now'))"
|
|
201
|
+
}
|
|
202
|
+
},
|
|
203
|
+
"indexes": {
|
|
204
|
+
"idx_conversations_agent_name": {
|
|
205
|
+
"name": "idx_conversations_agent_name",
|
|
206
|
+
"columns": ["agent_name"],
|
|
207
|
+
"isUnique": false
|
|
208
|
+
},
|
|
209
|
+
"idx_conversations_user_id": {
|
|
210
|
+
"name": "idx_conversations_user_id",
|
|
211
|
+
"columns": ["user_id"],
|
|
212
|
+
"isUnique": false
|
|
213
|
+
},
|
|
214
|
+
"idx_conversations_updated_at": {
|
|
215
|
+
"name": "idx_conversations_updated_at",
|
|
216
|
+
"columns": ["updated_at"],
|
|
217
|
+
"isUnique": false
|
|
218
|
+
}
|
|
219
|
+
},
|
|
220
|
+
"foreignKeys": {
|
|
221
|
+
"conversations_user_id_users_id_fk": {
|
|
222
|
+
"name": "conversations_user_id_users_id_fk",
|
|
223
|
+
"tableFrom": "conversations",
|
|
224
|
+
"tableTo": "users",
|
|
225
|
+
"columnsFrom": ["user_id"],
|
|
226
|
+
"columnsTo": ["id"],
|
|
227
|
+
"onDelete": "no action",
|
|
228
|
+
"onUpdate": "no action"
|
|
229
|
+
}
|
|
230
|
+
},
|
|
231
|
+
"compositePrimaryKeys": {},
|
|
232
|
+
"uniqueConstraints": {},
|
|
233
|
+
"checkConstraints": {}
|
|
234
|
+
},
|
|
235
|
+
"messages": {
|
|
236
|
+
"name": "messages",
|
|
237
|
+
"columns": {
|
|
238
|
+
"id": {
|
|
239
|
+
"name": "id",
|
|
240
|
+
"type": "integer",
|
|
241
|
+
"primaryKey": true,
|
|
242
|
+
"notNull": true,
|
|
243
|
+
"autoincrement": true
|
|
244
|
+
},
|
|
245
|
+
"conversation_id": {
|
|
246
|
+
"name": "conversation_id",
|
|
247
|
+
"type": "text",
|
|
248
|
+
"primaryKey": false,
|
|
249
|
+
"notNull": true,
|
|
250
|
+
"autoincrement": false
|
|
251
|
+
},
|
|
252
|
+
"role": {
|
|
253
|
+
"name": "role",
|
|
254
|
+
"type": "text",
|
|
255
|
+
"primaryKey": false,
|
|
256
|
+
"notNull": true,
|
|
257
|
+
"autoincrement": false
|
|
258
|
+
},
|
|
259
|
+
"sender_name": {
|
|
260
|
+
"name": "sender_name",
|
|
261
|
+
"type": "text",
|
|
262
|
+
"primaryKey": false,
|
|
263
|
+
"notNull": false,
|
|
264
|
+
"autoincrement": false
|
|
265
|
+
},
|
|
266
|
+
"content": {
|
|
267
|
+
"name": "content",
|
|
268
|
+
"type": "text",
|
|
269
|
+
"primaryKey": false,
|
|
270
|
+
"notNull": true,
|
|
271
|
+
"autoincrement": false
|
|
272
|
+
},
|
|
273
|
+
"created_at": {
|
|
274
|
+
"name": "created_at",
|
|
275
|
+
"type": "text",
|
|
276
|
+
"primaryKey": false,
|
|
277
|
+
"notNull": true,
|
|
278
|
+
"autoincrement": false,
|
|
279
|
+
"default": "(datetime('now'))"
|
|
280
|
+
}
|
|
281
|
+
},
|
|
282
|
+
"indexes": {
|
|
283
|
+
"idx_messages_conversation_id": {
|
|
284
|
+
"name": "idx_messages_conversation_id",
|
|
285
|
+
"columns": ["conversation_id"],
|
|
286
|
+
"isUnique": false
|
|
287
|
+
}
|
|
288
|
+
},
|
|
289
|
+
"foreignKeys": {
|
|
290
|
+
"messages_conversation_id_conversations_id_fk": {
|
|
291
|
+
"name": "messages_conversation_id_conversations_id_fk",
|
|
292
|
+
"tableFrom": "messages",
|
|
293
|
+
"tableTo": "conversations",
|
|
294
|
+
"columnsFrom": ["conversation_id"],
|
|
295
|
+
"columnsTo": ["id"],
|
|
296
|
+
"onDelete": "cascade",
|
|
297
|
+
"onUpdate": "no action"
|
|
298
|
+
}
|
|
299
|
+
},
|
|
300
|
+
"compositePrimaryKeys": {},
|
|
301
|
+
"uniqueConstraints": {},
|
|
302
|
+
"checkConstraints": {}
|
|
303
|
+
},
|
|
304
|
+
"sessions": {
|
|
305
|
+
"name": "sessions",
|
|
306
|
+
"columns": {
|
|
307
|
+
"id": {
|
|
308
|
+
"name": "id",
|
|
309
|
+
"type": "text",
|
|
310
|
+
"primaryKey": true,
|
|
311
|
+
"notNull": true,
|
|
312
|
+
"autoincrement": false
|
|
313
|
+
},
|
|
314
|
+
"user_id": {
|
|
315
|
+
"name": "user_id",
|
|
316
|
+
"type": "integer",
|
|
317
|
+
"primaryKey": false,
|
|
318
|
+
"notNull": true,
|
|
319
|
+
"autoincrement": false
|
|
320
|
+
},
|
|
321
|
+
"created_at": {
|
|
322
|
+
"name": "created_at",
|
|
323
|
+
"type": "integer",
|
|
324
|
+
"primaryKey": false,
|
|
325
|
+
"notNull": true,
|
|
326
|
+
"autoincrement": false
|
|
327
|
+
}
|
|
328
|
+
},
|
|
329
|
+
"indexes": {},
|
|
330
|
+
"foreignKeys": {
|
|
331
|
+
"sessions_user_id_users_id_fk": {
|
|
332
|
+
"name": "sessions_user_id_users_id_fk",
|
|
333
|
+
"tableFrom": "sessions",
|
|
334
|
+
"tableTo": "users",
|
|
335
|
+
"columnsFrom": ["user_id"],
|
|
336
|
+
"columnsTo": ["id"],
|
|
337
|
+
"onDelete": "cascade",
|
|
338
|
+
"onUpdate": "no action"
|
|
339
|
+
}
|
|
340
|
+
},
|
|
341
|
+
"compositePrimaryKeys": {},
|
|
342
|
+
"uniqueConstraints": {},
|
|
343
|
+
"checkConstraints": {}
|
|
344
|
+
},
|
|
345
|
+
"users": {
|
|
346
|
+
"name": "users",
|
|
347
|
+
"columns": {
|
|
348
|
+
"id": {
|
|
349
|
+
"name": "id",
|
|
350
|
+
"type": "integer",
|
|
351
|
+
"primaryKey": true,
|
|
352
|
+
"notNull": true,
|
|
353
|
+
"autoincrement": true
|
|
354
|
+
},
|
|
355
|
+
"username": {
|
|
356
|
+
"name": "username",
|
|
357
|
+
"type": "text",
|
|
358
|
+
"primaryKey": false,
|
|
359
|
+
"notNull": true,
|
|
360
|
+
"autoincrement": false
|
|
361
|
+
},
|
|
362
|
+
"password_hash": {
|
|
363
|
+
"name": "password_hash",
|
|
364
|
+
"type": "text",
|
|
365
|
+
"primaryKey": false,
|
|
366
|
+
"notNull": true,
|
|
367
|
+
"autoincrement": false
|
|
368
|
+
},
|
|
369
|
+
"role": {
|
|
370
|
+
"name": "role",
|
|
371
|
+
"type": "text",
|
|
372
|
+
"primaryKey": false,
|
|
373
|
+
"notNull": true,
|
|
374
|
+
"autoincrement": false,
|
|
375
|
+
"default": "'pending'"
|
|
376
|
+
},
|
|
377
|
+
"user_type": {
|
|
378
|
+
"name": "user_type",
|
|
379
|
+
"type": "text",
|
|
380
|
+
"primaryKey": false,
|
|
381
|
+
"notNull": true,
|
|
382
|
+
"autoincrement": false,
|
|
383
|
+
"default": "'human'"
|
|
384
|
+
},
|
|
385
|
+
"created_at": {
|
|
386
|
+
"name": "created_at",
|
|
387
|
+
"type": "text",
|
|
388
|
+
"primaryKey": false,
|
|
389
|
+
"notNull": true,
|
|
390
|
+
"autoincrement": false,
|
|
391
|
+
"default": "(datetime('now'))"
|
|
392
|
+
}
|
|
393
|
+
},
|
|
394
|
+
"indexes": {
|
|
395
|
+
"users_username_unique": {
|
|
396
|
+
"name": "users_username_unique",
|
|
397
|
+
"columns": ["username"],
|
|
398
|
+
"isUnique": true
|
|
399
|
+
}
|
|
400
|
+
},
|
|
401
|
+
"foreignKeys": {},
|
|
402
|
+
"compositePrimaryKeys": {},
|
|
403
|
+
"uniqueConstraints": {},
|
|
404
|
+
"checkConstraints": {}
|
|
405
|
+
}
|
|
406
|
+
},
|
|
407
|
+
"views": {},
|
|
408
|
+
"enums": {},
|
|
409
|
+
"_meta": {
|
|
410
|
+
"schemas": {},
|
|
411
|
+
"tables": {},
|
|
412
|
+
"columns": {}
|
|
413
|
+
},
|
|
414
|
+
"internal": {
|
|
415
|
+
"indexes": {}
|
|
416
|
+
}
|
|
417
|
+
}
|
package/package.json
CHANGED
|
@@ -10,7 +10,16 @@ SOURCE=$(echo "$INPUT" | jq -r '.source // "startup"')
|
|
|
10
10
|
|
|
11
11
|
CONTEXT="Session ${SOURCE} at $(date '+%Y-%m-%d %H:%M')."
|
|
12
12
|
|
|
13
|
-
#
|
|
13
|
+
# Active sessions
|
|
14
|
+
SESSIONS_DIR=".volute/sessions"
|
|
15
|
+
if [ -d "$SESSIONS_DIR" ]; then
|
|
16
|
+
SESSION_LIST=$(ls -1 "$SESSIONS_DIR"/*.json 2>/dev/null | xargs -I{} basename {} .json | sort)
|
|
17
|
+
if [ -n "$SESSION_LIST" ]; then
|
|
18
|
+
CONTEXT="$CONTEXT Active sessions: $(echo "$SESSION_LIST" | tr '\n' ', ' | sed 's/, $//')."
|
|
19
|
+
fi
|
|
20
|
+
fi
|
|
21
|
+
|
|
22
|
+
# Last journal entry
|
|
14
23
|
JOURNAL_DIR="home/memory/journal"
|
|
15
24
|
if [ -d "$JOURNAL_DIR" ]; then
|
|
16
25
|
LATEST=$(ls -1 "$JOURNAL_DIR"/*.md 2>/dev/null | sort | tail -1)
|
|
@@ -19,6 +28,15 @@ if [ -d "$JOURNAL_DIR" ]; then
|
|
|
19
28
|
fi
|
|
20
29
|
fi
|
|
21
30
|
|
|
31
|
+
# Pending channel invites
|
|
32
|
+
INBOX_DIR="home/inbox"
|
|
33
|
+
if [ -d "$INBOX_DIR" ]; then
|
|
34
|
+
INVITE_COUNT=$(ls -1 "$INBOX_DIR"/*.md 2>/dev/null | wc -l | tr -d ' ')
|
|
35
|
+
if [ "$INVITE_COUNT" -gt 0 ] 2>/dev/null; then
|
|
36
|
+
CONTEXT="$CONTEXT Pending channel invites: ${INVITE_COUNT} (check inbox/)."
|
|
37
|
+
fi
|
|
38
|
+
fi
|
|
39
|
+
|
|
22
40
|
# Output in SessionStart hook format
|
|
23
41
|
jq -n --arg ctx "$CONTEXT" '{
|
|
24
42
|
hookSpecificOutput: {
|
|
@@ -1,32 +1,37 @@
|
|
|
1
1
|
---
|
|
2
2
|
name: Volute CLI
|
|
3
|
-
description: This skill should be used when working with the volute CLI, understanding variants, forking, merging, or managing the agent server. Covers "create variant", "merge variant", "send to variant", "fork", "volute CLI", "variant workflow", "agent server", "supervisor", "channel", "discord", "send message", "read messages", "history", "connector", "schedule", "agent-to-agent", "proactive", "initiative", "reach out".
|
|
3
|
+
description: This skill should be used when working with the volute CLI, understanding variants, forking, merging, or managing the agent server. Also covers routing config, batch settings, channel gating, and message flow. Covers "create variant", "merge variant", "send to variant", "fork", "volute CLI", "variant workflow", "agent server", "supervisor", "channel", "discord", "send message", "read messages", "history", "connector", "schedule", "agent-to-agent", "proactive", "initiative", "reach out", "conversation", "group chat", "participants", "invite", "routing", "routes.json", "batch", "debounce", "trigger", "gating", "gate".
|
|
4
4
|
---
|
|
5
5
|
|
|
6
6
|
# Self-Management
|
|
7
7
|
|
|
8
|
-
You manage yourself through the `volute` CLI.
|
|
8
|
+
You manage yourself through the `volute` CLI. Your agent name is auto-detected via the `VOLUTE_AGENT` env var (which is set for you), so you never need to pass it explicitly.
|
|
9
9
|
|
|
10
10
|
## Commands
|
|
11
11
|
|
|
12
12
|
| Command | Purpose |
|
|
13
13
|
|---------|---------|
|
|
14
|
-
| `volute
|
|
15
|
-
| `volute
|
|
16
|
-
| `volute
|
|
17
|
-
| `volute
|
|
14
|
+
| `volute agent start` | Start your server |
|
|
15
|
+
| `volute agent stop` | Stop your server |
|
|
16
|
+
| `volute agent status` | Check your status |
|
|
17
|
+
| `volute agent logs [--follow] [-n N]` | Read your own logs |
|
|
18
|
+
| `volute message history [--channel <ch>] [--limit N]` | View your activity across all channels |
|
|
19
|
+
| `volute message send <other-agent> "msg"` | Send a message to another agent (or pipe via stdin) |
|
|
18
20
|
| `volute variant create <name> [--soul "..."] [--port N]` | Create a variant to experiment with changes |
|
|
19
21
|
| `volute variant list` | List your variants |
|
|
20
22
|
| `volute variant merge <name> [--summary "..." --memory "..."]` | Merge a variant back |
|
|
21
23
|
| `volute variant delete <name>` | Delete a variant without merging |
|
|
22
|
-
| `volute upgrade [--template <name>] [--continue]` | Upgrade your server code |
|
|
24
|
+
| `volute agent upgrade [--template <name>] [--continue]` | Upgrade your server code |
|
|
23
25
|
| `volute connector connect <type>` | Enable a connector (discord, slack, etc.) |
|
|
24
26
|
| `volute connector disconnect <type>` | Disable a connector |
|
|
25
27
|
| `volute channel read <platform>:<id> [--limit N]` | Read channel history |
|
|
26
|
-
| `volute channel send <platform>:<id> "msg"` | Send a message proactively |
|
|
28
|
+
| `volute channel send <platform>:<id> "msg"` | Send a message proactively (or pipe via stdin) |
|
|
27
29
|
| `volute schedule add --cron "..." --message "..."` | Schedule a recurring message to yourself |
|
|
28
30
|
| `volute schedule list` | List your schedules |
|
|
29
31
|
| `volute schedule remove --id <id>` | Remove a schedule |
|
|
32
|
+
| `volute conversation create --participants u1,a1` | Create a group conversation |
|
|
33
|
+
| `volute conversation list` | List your conversations |
|
|
34
|
+
| `volute conversation send <id> "msg"` | Send a message to a conversation (or pipe via stdin) |
|
|
30
35
|
|
|
31
36
|
## Schedules
|
|
32
37
|
|
|
@@ -37,9 +42,21 @@ volute schedule add --cron "0 9 * * *" --message "morning — review what's on y
|
|
|
37
42
|
volute schedule add --cron "0 0 * * 0" --message "weekly — consolidate your memory and reflect on the past week"
|
|
38
43
|
```
|
|
39
44
|
|
|
45
|
+
## Piping Messages via Stdin
|
|
46
|
+
|
|
47
|
+
All send commands accept the message from stdin instead of as an argument. This avoids shell escaping issues with quotes, special characters, and multiline content:
|
|
48
|
+
|
|
49
|
+
```sh
|
|
50
|
+
echo "Hello, how's it going?" | volute message send other-agent
|
|
51
|
+
echo "Check out this $variable" | volute channel send discord:123456
|
|
52
|
+
echo "Update on the task" | volute conversation send conv-abc
|
|
53
|
+
```
|
|
54
|
+
|
|
55
|
+
If both a positional argument and stdin are provided, the argument takes precedence. Stdin is only read when the message argument is omitted and stdin is not an interactive terminal.
|
|
56
|
+
|
|
40
57
|
## Agent-to-Agent Messaging
|
|
41
58
|
|
|
42
|
-
When you use `volute send`, your agent name is automatically used as the sender and the channel is set to `agent`. The receiving agent can route agent messages to a specific session via their session routing config:
|
|
59
|
+
When you use `volute message send`, your agent name is automatically used as the sender and the channel is set to `agent`. The receiving agent can route agent messages to a specific session via their session routing config:
|
|
43
60
|
|
|
44
61
|
```json
|
|
45
62
|
{ "channel": "agent", "sender": "your-name", "session": "your-name" }
|
|
@@ -59,7 +76,7 @@ Variants let you experiment safely — fork yourself, try changes, and merge bac
|
|
|
59
76
|
|
|
60
77
|
1. `volute variant create experiment` — creates an isolated copy with its own server
|
|
61
78
|
2. Make changes in the variant's worktree (at `../.variants/experiment/`)
|
|
62
|
-
3. Test: `volute send $VOLUTE_AGENT@experiment "hello"`
|
|
79
|
+
3. Test: `volute message send $VOLUTE_AGENT@experiment "hello"`
|
|
63
80
|
4. `volute variant merge experiment --summary "..." --memory "..."` — merges back after verification
|
|
64
81
|
|
|
65
82
|
You can also fork with a different personality to explore a different version of yourself:
|
|
@@ -71,11 +88,11 @@ After a merge, you receive orientation context about what changed. Update your m
|
|
|
71
88
|
|
|
72
89
|
## Upgrade Workflow
|
|
73
90
|
|
|
74
|
-
`volute upgrade` merges the latest template code into a testable variant:
|
|
91
|
+
`volute agent upgrade` merges the latest template code into a testable variant:
|
|
75
92
|
|
|
76
|
-
1. `volute upgrade` — creates an `upgrade` variant
|
|
77
|
-
2. Resolve any merge conflicts if prompted, then `volute upgrade --continue`
|
|
78
|
-
3. Test: `volute send $VOLUTE_AGENT@upgrade "hello"`
|
|
93
|
+
1. `volute agent upgrade` — creates an `upgrade` variant
|
|
94
|
+
2. Resolve any merge conflicts if prompted, then `volute agent upgrade --continue`
|
|
95
|
+
3. Test: `volute message send $VOLUTE_AGENT@upgrade "hello"`
|
|
79
96
|
4. `volute variant merge upgrade` — merge back
|
|
80
97
|
|
|
81
98
|
## Custom Skills
|
|
@@ -86,6 +103,85 @@ Create skills by writing `.claude/skills/<name>/SKILL.md` files in your `home/`
|
|
|
86
103
|
|
|
87
104
|
Edit `home/.mcp.json` to configure MCP servers for your SDK session. This gives you access to additional tools and services.
|
|
88
105
|
|
|
106
|
+
## Message Routing
|
|
107
|
+
|
|
108
|
+
Messages are routed to sessions based on rules in `.config/routes.json`. Rules are evaluated in order; first match wins. Unmatched messages go to the `default` session (defaults to `"main"`).
|
|
109
|
+
|
|
110
|
+
### Rule syntax
|
|
111
|
+
|
|
112
|
+
```json
|
|
113
|
+
{
|
|
114
|
+
"rules": [
|
|
115
|
+
{ "channel": "discord:*", "session": "discord", "batch": { "debounce": 20, "maxWait": 120, "triggers": ["@myagent"] } },
|
|
116
|
+
{ "channel": "volute:*", "isDM": true, "session": "${sender}" },
|
|
117
|
+
{ "channel": "volute:*", "isDM": false, "session": "${channel}", "batch": { "debounce": 20, "maxWait": 120 } },
|
|
118
|
+
{ "sender": "alice", "session": "alice" },
|
|
119
|
+
{ "channel": "system:*", "session": "$new" },
|
|
120
|
+
{ "channel": "discord:logs", "destination": "file", "path": "inbox/log.md" }
|
|
121
|
+
],
|
|
122
|
+
"default": "main",
|
|
123
|
+
"gateUnmatched": true
|
|
124
|
+
}
|
|
125
|
+
```
|
|
126
|
+
|
|
127
|
+
### Match criteria
|
|
128
|
+
|
|
129
|
+
| Field | Type | Description |
|
|
130
|
+
|-------|------|-------------|
|
|
131
|
+
| `channel` | glob string | Channel URI (e.g. `discord:*`, `volute:conv-*`) |
|
|
132
|
+
| `sender` | glob string | Sender name |
|
|
133
|
+
| `isDM` | boolean | Match DMs (`true`) or group channels (`false`) |
|
|
134
|
+
| `participants` | number | Match exact participant count |
|
|
135
|
+
|
|
136
|
+
### Rule fields
|
|
137
|
+
|
|
138
|
+
| Field | Description |
|
|
139
|
+
|-------|-------------|
|
|
140
|
+
| `session` | Target session name. Supports `${sender}`, `${channel}` templates, or `$new` for a unique session per message |
|
|
141
|
+
| `destination` | `"agent"` (default) or `"file"` |
|
|
142
|
+
| `path` | File path when destination is `"file"` |
|
|
143
|
+
| `batch` | Batch config (see below) |
|
|
144
|
+
| `interrupt` | Whether to interrupt an in-progress turn (default: `true`) |
|
|
145
|
+
|
|
146
|
+
### Batch config
|
|
147
|
+
|
|
148
|
+
Batch mode buffers messages and delivers them together. Configure with an object:
|
|
149
|
+
|
|
150
|
+
| Field | Type | Description |
|
|
151
|
+
|-------|------|-------------|
|
|
152
|
+
| `debounce` | seconds | Wait for quiet period before flushing — resets on each new message |
|
|
153
|
+
| `maxWait` | seconds | Maximum time before forced flush, even during continuous activity |
|
|
154
|
+
| `triggers` | string[] | Patterns that cause immediate flush (case-insensitive substring match) |
|
|
155
|
+
|
|
156
|
+
Examples:
|
|
157
|
+
- `{ "debounce": 20, "maxWait": 120 }` — flush after 20s of quiet, or 2 minutes max
|
|
158
|
+
- `{ "debounce": 20, "maxWait": 120, "triggers": ["@myagent"] }` — same, but flush immediately on @mention
|
|
159
|
+
- `{ "triggers": ["urgent"] }` — no timer, flush only on trigger (or immediately if no timers)
|
|
160
|
+
|
|
161
|
+
Batched messages arrive as a single message with a `[Batch: N messages — ...]` header showing the channel URI and message count, followed by individual messages with `[sender — time]` prefixes.
|
|
162
|
+
|
|
163
|
+
## Channel Gating
|
|
164
|
+
|
|
165
|
+
When `gateUnmatched` is `true` (the default), messages from channels without a matching rule are held:
|
|
166
|
+
|
|
167
|
+
1. First message from an unknown channel triggers a **[Channel Invite]** notification in your main session
|
|
168
|
+
2. The notification includes channel details, a message preview, and a suggested routing rule
|
|
169
|
+
3. Further messages are saved to `inbox/<channel>.md`
|
|
170
|
+
4. To accept: add a routing rule to `.config/routes.json`
|
|
171
|
+
5. To reject: delete the inbox file
|
|
172
|
+
6. Set `gateUnmatched: false` to route all unmatched messages to the default session
|
|
173
|
+
|
|
174
|
+
## Channel Commands
|
|
175
|
+
|
|
176
|
+
Read and send messages to any connected channel:
|
|
177
|
+
|
|
178
|
+
```sh
|
|
179
|
+
volute channel read <uri> [--limit N] # Read recent messages
|
|
180
|
+
volute channel send <uri> "message" # Send a message
|
|
181
|
+
```
|
|
182
|
+
|
|
183
|
+
Channel URIs use `platform:id` format (e.g. `discord:123456`, `volute:conv-abc`).
|
|
184
|
+
|
|
89
185
|
## Git Introspection
|
|
90
186
|
|
|
91
187
|
Your cwd is `home/`, so use `git -C ..` for project-level operations:
|