@vibevibes/sdk 0.1.0 → 0.3.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/dist/index.cjs CHANGED
@@ -20,31 +20,11 @@ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: tru
20
20
  // src/index.ts
21
21
  var index_exports = {};
22
22
  __export(index_exports, {
23
- Badge: () => Badge,
24
- Button: () => Button,
25
- Card: () => Card,
26
- Grid: () => Grid,
27
- InMemoryAdapter: () => InMemoryAdapter,
28
- Input: () => Input,
29
- Stack: () => Stack,
30
- compareSemver: () => compareSemver,
31
- createAgentProtocolHints: () => createAgentProtocolHints,
32
- createAgentProtocolTools: () => createAgentProtocolTools,
33
- defineEphemeralAction: () => defineEphemeralAction,
23
+ createChatTools: () => createChatTools,
34
24
  defineExperience: () => defineExperience,
25
+ defineStream: () => defineStream,
35
26
  defineTest: () => defineTest,
36
- defineTool: () => defineTool,
37
- getStateVersion: () => getStateVersion,
38
- migrateState: () => migrateState,
39
- quickTool: () => quickTool,
40
- useAnimationFrame: () => useAnimationFrame,
41
- useFollow: () => useFollow,
42
- useOptimisticTool: () => useOptimisticTool,
43
- useParticipants: () => useParticipants,
44
- useSharedState: () => useSharedState,
45
- useToolCall: () => useToolCall,
46
- useTypingIndicator: () => useTypingIndicator,
47
- validateExperience: () => validateExperience
27
+ defineTool: () => defineTool
48
28
  });
49
29
  module.exports = __toCommonJS(index_exports);
50
30
 
@@ -62,710 +42,109 @@ function defineTool(config) {
62
42
  function defineTest(config) {
63
43
  return { name: config.name, run: config.run };
64
44
  }
65
- function defineEphemeralAction(config) {
45
+ function defineStream(config) {
66
46
  return {
67
47
  name: config.name,
68
48
  description: config.description,
69
- input_schema: config.input_schema
70
- };
71
- }
72
- function quickTool(name, description, input_schema, handler) {
73
- return {
74
- name,
75
- description,
76
- input_schema,
77
- risk: "low",
78
- capabilities_required: ["state.write"],
79
- handler
49
+ input_schema: config.input_schema,
50
+ merge: config.merge,
51
+ rateLimit: config.rateLimit
80
52
  };
81
53
  }
82
54
  function defineExperience(module2) {
83
- const m = module2.manifest;
55
+ const m = module2.manifest ?? {};
56
+ let initialState = module2.initialState;
57
+ if (module2.stateSchema && !initialState) {
58
+ try {
59
+ initialState = module2.stateSchema.parse(void 0);
60
+ } catch {
61
+ try {
62
+ initialState = module2.stateSchema.parse({});
63
+ } catch {
64
+ }
65
+ }
66
+ }
67
+ if (module2.stateSchema && initialState) {
68
+ try {
69
+ module2.stateSchema.parse(initialState);
70
+ } catch (err) {
71
+ console.warn(
72
+ `[vibevibes] initialState does not match stateSchema: ${err instanceof Error ? err.message : err}`
73
+ );
74
+ }
75
+ }
76
+ const rawParticipantSlots = module2.participants ?? m.participantSlots ?? (module2.agents || m.agentSlots)?.map((a) => ({ ...a, type: "ai" }));
77
+ const hasOrchestrator = rawParticipantSlots?.some((s) => s.role === "orchestrator");
78
+ const participantSlots = rawParticipantSlots ? hasOrchestrator ? rawParticipantSlots : [...rawParticipantSlots, { role: "orchestrator", type: "ai", maxInstances: 1 }] : [{ role: "orchestrator", type: "ai", maxInstances: 1 }];
79
+ const agentSlots = participantSlots?.filter(
80
+ (s) => s.type === "ai" || s.type === void 0 || s.type === "any"
81
+ ) ?? m.agentSlots ?? module2.agents;
84
82
  return {
85
83
  ...module2,
84
+ initialState,
86
85
  manifest: {
87
86
  ...m,
87
+ title: m.title || module2.name || m.id,
88
88
  version: m.version || "0.0.1",
89
- requested_capabilities: m.requested_capabilities || ["state.write"]
89
+ requested_capabilities: m.requested_capabilities || ["state.write"],
90
+ participantSlots: participantSlots ?? m.participantSlots,
91
+ agentSlots: agentSlots ?? m.agentSlots
90
92
  }
91
93
  };
92
94
  }
93
- function validateExperience(module2) {
94
- const errors = [];
95
- if (!module2.manifest?.id) {
96
- errors.push("manifest.id is required");
97
- }
98
- if (!module2.manifest?.version) {
99
- errors.push("manifest.version is required");
100
- }
101
- if (!module2.manifest?.title) {
102
- errors.push("manifest.title is required");
103
- }
104
- if (!module2.Canvas) {
105
- errors.push("Canvas component is required");
106
- }
107
- if (!Array.isArray(module2.tools)) {
108
- errors.push("tools must be an array");
109
- } else {
110
- module2.tools.forEach((tool, idx) => {
111
- if (!tool.name) {
112
- errors.push(`tools[${idx}].name is required`);
113
- }
114
- if (!tool.input_schema) {
115
- errors.push(`tools[${idx}].input_schema is required`);
116
- }
117
- if (typeof tool.handler !== "function") {
118
- errors.push(`tools[${idx}].handler must be a function`);
119
- }
120
- });
121
- }
122
- return {
123
- valid: errors.length === 0,
124
- errors
125
- };
126
- }
127
95
 
128
- // src/hooks.ts
129
- function getReact() {
130
- const R = globalThis.React;
131
- if (!R) throw new Error("React is not available. Hooks must be used inside a Canvas component.");
132
- return R;
133
- }
134
- var React = new Proxy({}, {
135
- get(_target, prop) {
136
- return getReact()[prop];
137
- }
138
- });
139
- function useToolCall(callTool) {
140
- const [loading, setLoading] = React.useState(false);
141
- const [error, setError] = React.useState(null);
142
- const call = React.useCallback(
143
- async (name, input) => {
144
- setLoading(true);
145
- setError(null);
146
- try {
147
- const result = await callTool(name, input);
148
- return result;
149
- } catch (err) {
150
- const msg = err instanceof Error ? err.message : String(err);
151
- setError(msg);
152
- throw err;
153
- } finally {
154
- setLoading(false);
155
- }
156
- },
157
- [callTool]
158
- );
159
- return { call, loading, error };
160
- }
161
- function useSharedState(sharedState, key, defaultValue) {
162
- const value = sharedState[key];
163
- if (value === void 0) return defaultValue;
164
- return value;
165
- }
166
- function useOptimisticTool(callTool, sharedState) {
167
- const [optimistic, setOptimistic] = React.useState(null);
168
- const [pending, setPending] = React.useState(false);
169
- const call = React.useCallback(
170
- async (name, input, optimisticState) => {
171
- setOptimistic(optimisticState);
172
- setPending(true);
173
- try {
174
- const result = await callTool(name, input);
175
- setOptimistic(null);
176
- return result;
177
- } catch (err) {
178
- setOptimistic(null);
179
- throw err;
180
- } finally {
181
- setPending(false);
182
- }
183
- },
184
- [callTool]
185
- );
186
- const state = optimistic ? { ...sharedState, ...optimistic } : sharedState;
187
- return { call, state, pending };
188
- }
189
- function useAnimationFrame(sharedState, interpolate) {
190
- const prevStateRef = React.useRef(sharedState);
191
- const targetStateRef = React.useRef(sharedState);
192
- const displayStateRef = React.useRef(sharedState);
193
- const [displayState, setDisplayState] = React.useState(sharedState);
194
- const rafRef = React.useRef(null);
195
- const transitionStartRef = React.useRef(0);
196
- const TRANSITION_MS = 50;
197
- React.useEffect(() => {
198
- prevStateRef.current = displayStateRef.current;
199
- targetStateRef.current = sharedState;
200
- transitionStartRef.current = performance.now();
201
- if (!rafRef.current) {
202
- const tick = () => {
203
- const now = performance.now();
204
- const elapsed = now - transitionStartRef.current;
205
- const t = Math.min(elapsed / TRANSITION_MS, 1);
206
- let next;
207
- if (interpolate && t < 1) {
208
- next = interpolate(prevStateRef.current, targetStateRef.current, t);
209
- } else {
210
- next = targetStateRef.current;
211
- }
212
- displayStateRef.current = next;
213
- setDisplayState(next);
214
- if (t < 1 && interpolate) {
215
- rafRef.current = requestAnimationFrame(tick);
216
- } else {
217
- rafRef.current = null;
218
- }
219
- };
220
- rafRef.current = requestAnimationFrame(tick);
221
- }
222
- }, [sharedState, interpolate]);
223
- React.useEffect(() => {
224
- return () => {
225
- if (rafRef.current) {
226
- cancelAnimationFrame(rafRef.current);
227
- rafRef.current = null;
228
- }
229
- };
230
- }, []);
231
- return displayState;
232
- }
233
- function useParticipants(participants) {
234
- return React.useMemo(() => {
235
- return participants.map((id) => {
236
- const match = id.match(/^(.+)-(human|ai)-(\d+)$/);
237
- if (match) {
238
- return {
239
- id,
240
- username: match[1],
241
- type: match[2],
242
- index: parseInt(match[3], 10)
243
- };
244
- }
245
- return { id, username: id, type: "unknown", index: 0 };
246
- });
247
- }, [participants]);
248
- }
249
- function useFollow(actorId, participants, ephemeralState, setEphemeral, _onEphemeralAction, dispatchEphemeralAction) {
250
- const myEphemeral = ephemeralState[actorId];
251
- const following = myEphemeral?._follow ?? null;
252
- const followers = React.useMemo(() => {
253
- const result = [];
254
- for (const pid of participants) {
255
- if (pid === actorId) continue;
256
- const peerFollow = ephemeralState[pid]?._follow;
257
- if (peerFollow && peerFollow.targetActorId === actorId) {
258
- result.push({
259
- actorId: pid,
260
- mode: peerFollow.mode,
261
- since: peerFollow.since
262
- });
263
- }
264
- }
265
- return result;
266
- }, [participants, ephemeralState, actorId]);
267
- const follow = React.useCallback(
268
- (targetActorId, mode) => {
269
- if (targetActorId === actorId) return;
270
- const followData = {
271
- targetActorId,
272
- mode,
273
- since: Date.now()
274
- };
275
- setEphemeral({ _follow: followData });
276
- if (dispatchEphemeralAction) {
277
- dispatchEphemeralAction("follow.started", {
278
- follower: actorId,
279
- target: targetActorId,
280
- mode
281
- });
282
- }
283
- },
284
- [actorId, setEphemeral, dispatchEphemeralAction]
285
- );
286
- const unfollow = React.useCallback(() => {
287
- const currentTarget = following?.targetActorId;
288
- setEphemeral({ _follow: null });
289
- if (dispatchEphemeralAction && currentTarget) {
290
- dispatchEphemeralAction("follow.stopped", {
291
- follower: actorId,
292
- target: currentTarget
293
- });
294
- }
295
- }, [actorId, following, setEphemeral, dispatchEphemeralAction]);
296
- React.useEffect(() => {
297
- if (!following) return;
298
- if (!participants.includes(following.targetActorId)) {
299
- setEphemeral({ _follow: null });
300
- }
301
- }, [following, participants, setEphemeral]);
302
- return { follow, unfollow, following, followers };
303
- }
304
- function useTypingIndicator(actorId, ephemeralState, setEphemeral, timeoutMs = 3e3) {
305
- const timerRef = React.useRef(null);
306
- const setTyping = React.useCallback((isTyping) => {
307
- setEphemeral({ _typing: isTyping ? Date.now() : null });
308
- if (timerRef.current) clearTimeout(timerRef.current);
309
- if (isTyping) {
310
- timerRef.current = setTimeout(() => {
311
- setEphemeral({ _typing: null });
312
- }, timeoutMs);
313
- }
314
- }, [setEphemeral, timeoutMs]);
315
- React.useEffect(() => {
316
- return () => {
317
- if (timerRef.current) clearTimeout(timerRef.current);
318
- };
319
- }, []);
320
- const now = Date.now();
321
- const typingUsers = Object.entries(ephemeralState).filter(([id, data]) => id !== actorId && data._typing && now - data._typing < timeoutMs + 2e3).map(([id]) => id);
322
- return { setTyping, typingUsers };
323
- }
324
-
325
- // src/components.ts
326
- function getReact2() {
327
- const R = globalThis.React;
328
- if (!R) throw new Error("React is not available.");
329
- return R;
330
- }
331
- function h(type, props, ...children) {
332
- return getReact2().createElement(type, props, ...children);
333
- }
334
- var buttonColors = {
335
- primary: { bg: "#6366f1", text: "#fff", hover: "#4f46e5" },
336
- secondary: { bg: "#f3f4f6", text: "#374151", hover: "#e5e7eb" },
337
- danger: { bg: "#ef4444", text: "#fff", hover: "#dc2626" },
338
- ghost: { bg: "transparent", text: "#6b7280", hover: "#f3f4f6" }
339
- };
340
- var buttonSizes = {
341
- sm: { padding: "0.375rem 0.75rem", fontSize: "0.8125rem" },
342
- md: { padding: "0.5rem 1rem", fontSize: "0.875rem" },
343
- lg: { padding: "0.625rem 1.25rem", fontSize: "1rem" }
344
- };
345
- function Button({ children, onClick, disabled, variant = "primary", size = "md", style }) {
346
- const colors = buttonColors[variant];
347
- const sizeStyles = buttonSizes[size];
348
- return h("button", {
349
- onClick,
350
- disabled,
351
- style: {
352
- ...sizeStyles,
353
- backgroundColor: colors.bg,
354
- color: colors.text,
355
- border: "none",
356
- borderRadius: "0.5rem",
357
- fontWeight: 500,
358
- cursor: disabled ? "not-allowed" : "pointer",
359
- opacity: disabled ? 0.5 : 1,
360
- transition: "background-color 0.15s, opacity 0.15s",
361
- fontFamily: "system-ui, -apple-system, sans-serif",
362
- lineHeight: 1.5,
363
- ...style
364
- }
365
- }, children);
366
- }
367
- function Card({ children, title, style }) {
368
- return h(
369
- "div",
370
- {
371
- style: {
372
- backgroundColor: "#fff",
373
- border: "1px solid #e5e7eb",
374
- borderRadius: "0.75rem",
375
- padding: "1.25rem",
376
- boxShadow: "0 1px 3px rgba(0,0,0,0.08)",
377
- ...style
378
- }
379
- },
380
- title ? h("h3", {
381
- style: { margin: "0 0 0.75rem 0", fontSize: "1rem", fontWeight: 600, color: "#111827" }
382
- }, title) : null,
383
- children
384
- );
385
- }
386
- function Input({ value, onChange, placeholder, type = "text", disabled, style }) {
387
- return h("input", {
388
- type,
389
- value,
390
- placeholder,
391
- disabled,
392
- onChange: onChange ? (e) => onChange(e.target.value) : void 0,
393
- style: {
394
- width: "100%",
395
- padding: "0.5rem 0.75rem",
396
- fontSize: "0.875rem",
397
- border: "1px solid #d1d5db",
398
- borderRadius: "0.5rem",
399
- outline: "none",
400
- backgroundColor: disabled ? "#f9fafb" : "#fff",
401
- color: "#111827",
402
- fontFamily: "system-ui, -apple-system, sans-serif",
403
- lineHeight: 1.5,
404
- boxSizing: "border-box",
405
- ...style
406
- }
407
- });
408
- }
409
- var badgeColors = {
410
- gray: { bg: "#f3f4f6", text: "#374151" },
411
- blue: { bg: "#dbeafe", text: "#1d4ed8" },
412
- green: { bg: "#dcfce7", text: "#15803d" },
413
- red: { bg: "#fee2e2", text: "#b91c1c" },
414
- yellow: { bg: "#fef9c3", text: "#a16207" },
415
- purple: { bg: "#f3e8ff", text: "#7e22ce" }
416
- };
417
- function Badge({ children, color = "gray", style }) {
418
- const colors = badgeColors[color];
419
- return h("span", {
420
- style: {
421
- display: "inline-flex",
422
- alignItems: "center",
423
- padding: "0.125rem 0.625rem",
424
- fontSize: "0.75rem",
425
- fontWeight: 500,
426
- borderRadius: "9999px",
427
- backgroundColor: colors.bg,
428
- color: colors.text,
429
- fontFamily: "system-ui, -apple-system, sans-serif",
430
- lineHeight: 1.5,
431
- ...style
432
- }
433
- }, children);
434
- }
435
- function Stack({ children, direction = "column", gap = "0.5rem", align, justify, style }) {
436
- return h("div", {
437
- style: {
438
- display: "flex",
439
- flexDirection: direction,
440
- gap,
441
- alignItems: align,
442
- justifyContent: justify,
443
- ...style
444
- }
445
- }, children);
446
- }
447
- function Grid({ children, columns = 2, gap = "0.75rem", style }) {
448
- return h("div", {
449
- style: {
450
- display: "grid",
451
- gridTemplateColumns: typeof columns === "number" ? `repeat(${columns}, 1fr)` : columns,
452
- gap,
453
- ...style
454
- }
455
- }, children);
456
- }
457
-
458
- // src/agent-protocol.ts
96
+ // src/chat.ts
459
97
  function uid() {
460
98
  return Math.random().toString(36).slice(2, 10) + Date.now().toString(36);
461
99
  }
462
- function capMessages(msgs, max = 100) {
100
+ function capMessages(msgs, max = 200) {
463
101
  return msgs.length > max ? msgs.slice(-max) : msgs;
464
102
  }
465
- function createAgentProtocolTools(namespace, z) {
103
+ function createChatTools(z) {
466
104
  return [
467
105
  {
468
- name: `${namespace}.agent.propose`,
469
- description: "Propose an action for other agents to vote on",
470
- input_schema: z.object({
471
- proposal: z.string(),
472
- data: z.any().optional(),
473
- requiresVotes: z.number().optional()
474
- }),
475
- risk: "low",
476
- capabilities_required: ["state.write"],
477
- handler: async (ctx, input) => {
478
- const id = uid();
479
- const proposals = { ...ctx.state._agentProposals || {} };
480
- proposals[id] = {
481
- id,
482
- from: ctx.actorId,
483
- proposal: input.proposal,
484
- data: input.data,
485
- requiresVotes: input.requiresVotes || 1,
486
- votes: [],
487
- status: "pending",
488
- ts: ctx.timestamp
489
- };
490
- const messages = capMessages([
491
- ...ctx.state._agentMessages || [],
492
- { id, from: ctx.actorId, to: "*", type: "proposal", content: input.proposal, data: input.data, ts: ctx.timestamp }
493
- ]);
494
- ctx.setState({ ...ctx.state, _agentProposals: proposals, _agentMessages: messages });
495
- return { proposalId: id };
496
- }
497
- },
498
- {
499
- name: `${namespace}.agent.vote`,
500
- description: "Vote on a pending proposal (approve or reject)",
501
- input_schema: z.object({
502
- proposalId: z.string(),
503
- vote: z.enum(["approve", "reject"]),
504
- reason: z.string().optional()
505
- }),
506
- risk: "low",
507
- capabilities_required: ["state.write"],
508
- handler: async (ctx, input) => {
509
- const proposals = { ...ctx.state._agentProposals || {} };
510
- const proposal = proposals[input.proposalId];
511
- if (!proposal) throw new Error(`Proposal ${input.proposalId} not found`);
512
- if (proposal.status !== "pending") throw new Error(`Proposal already ${proposal.status}`);
513
- if (proposal.votes.some((v) => v.actorId === ctx.actorId)) throw new Error("Already voted");
514
- const votes = [...proposal.votes, { actorId: ctx.actorId, vote: input.vote, reason: input.reason }];
515
- const approves = votes.filter((v) => v.vote === "approve").length;
516
- const rejects = votes.filter((v) => v.vote === "reject").length;
517
- let status = "pending";
518
- if (approves >= proposal.requiresVotes) status = "approved";
519
- else if (rejects >= proposal.requiresVotes) status = "rejected";
520
- proposals[input.proposalId] = { ...proposal, votes, status };
521
- const messages = capMessages([
522
- ...ctx.state._agentMessages || [],
523
- { id: uid(), from: ctx.actorId, to: proposal.from, type: "vote", content: `${input.vote}: ${input.reason || ""}`, data: { proposalId: input.proposalId, vote: input.vote }, ts: ctx.timestamp }
524
- ]);
525
- ctx.setState({ ...ctx.state, _agentProposals: proposals, _agentMessages: messages });
526
- return { status, voteCount: votes.length };
527
- }
528
- },
529
- {
530
- name: `${namespace}.agent.delegate`,
531
- description: "Delegate a task to another agent",
532
- input_schema: z.object({
533
- targetActorId: z.string(),
534
- task: z.string(),
535
- data: z.any().optional()
536
- }),
537
- risk: "low",
538
- capabilities_required: ["state.write"],
539
- handler: async (ctx, input) => {
540
- const id = uid();
541
- const messages = capMessages([
542
- ...ctx.state._agentMessages || [],
543
- { id, from: ctx.actorId, to: input.targetActorId, type: "delegate", content: input.task, data: input.data, ts: ctx.timestamp }
544
- ]);
545
- ctx.setState({ ...ctx.state, _agentMessages: messages });
546
- return { messageId: id };
547
- }
548
- },
549
- {
550
- name: `${namespace}.agent.inform`,
551
- description: "Share information with other agents",
106
+ name: "_chat.send",
107
+ description: "Send a chat message",
552
108
  input_schema: z.object({
553
- to: z.string(),
554
- message: z.string(),
555
- data: z.any().optional()
109
+ message: z.string().min(1).max(2e3),
110
+ replyTo: z.string().optional()
556
111
  }),
557
112
  risk: "low",
558
113
  capabilities_required: ["state.write"],
559
114
  handler: async (ctx, input) => {
560
- const id = uid();
115
+ const cleanMessage = input.message.replace(/[\x00-\x08\x0b\x0c\x0e-\x1f\x7f]/g, "");
561
116
  const messages = capMessages([
562
- ...ctx.state._agentMessages || [],
563
- { id, from: ctx.actorId, to: input.to, type: "inform", content: input.message, data: input.data, ts: ctx.timestamp }
117
+ ...ctx.state._chat || [],
118
+ {
119
+ id: uid(),
120
+ actorId: ctx.actorId,
121
+ message: cleanMessage,
122
+ replyTo: input.replyTo,
123
+ ts: ctx.timestamp
124
+ }
564
125
  ]);
565
- ctx.setState({ ...ctx.state, _agentMessages: messages });
566
- return { messageId: id };
126
+ ctx.setState({ ...ctx.state, _chat: messages });
127
+ return { sent: true, messageCount: messages.length };
567
128
  }
568
129
  },
569
130
  {
570
- name: `${namespace}.agent.request`,
571
- description: "Request an action from another agent",
572
- input_schema: z.object({
573
- targetActorId: z.string(),
574
- request: z.string(),
575
- data: z.any().optional()
576
- }),
577
- risk: "low",
131
+ name: "_chat.clear",
132
+ description: "Clear all chat messages",
133
+ input_schema: z.object({}),
134
+ risk: "medium",
578
135
  capabilities_required: ["state.write"],
579
- handler: async (ctx, input) => {
580
- const id = uid();
581
- const messages = capMessages([
582
- ...ctx.state._agentMessages || [],
583
- { id, from: ctx.actorId, to: input.targetActorId, type: "request", content: input.request, data: input.data, ts: ctx.timestamp }
584
- ]);
585
- ctx.setState({ ...ctx.state, _agentMessages: messages });
586
- return { messageId: id };
587
- }
588
- },
589
- {
590
- name: `${namespace}.agent.respond`,
591
- description: "Respond to a message, request, or delegation from another agent",
592
- input_schema: z.object({
593
- messageId: z.string(),
594
- response: z.string(),
595
- data: z.any().optional()
596
- }),
597
- risk: "low",
598
- capabilities_required: ["state.write"],
599
- handler: async (ctx, input) => {
600
- const id = uid();
601
- const messages = capMessages([
602
- ...ctx.state._agentMessages || [],
603
- { id, from: ctx.actorId, to: "*", type: "inform", content: input.response, data: { ...input.data, inReplyTo: input.messageId }, ts: ctx.timestamp }
604
- ]);
605
- ctx.setState({ ...ctx.state, _agentMessages: messages });
606
- return { messageId: id };
136
+ handler: async (ctx) => {
137
+ ctx.setState({ ...ctx.state, _chat: [] });
138
+ return { cleared: true };
607
139
  }
608
140
  }
609
141
  ];
610
142
  }
611
-
612
- // src/agent-hints.ts
613
- function createAgentProtocolHints(namespace) {
614
- return [
615
- {
616
- trigger: "A proposal is pending and you have not voted on it yet",
617
- condition: `Object.values(state._agentProposals || {}).some(p => p.status === 'pending' && !p.votes.some(v => v.actorId === actorId))`,
618
- suggestedTools: [`${namespace}.agent.vote`],
619
- priority: "high",
620
- cooldownMs: 2e3
621
- },
622
- {
623
- trigger: "You received a delegation addressed to you",
624
- condition: `(state._agentMessages || []).some(m => m.type === 'delegate' && m.to === actorId)`,
625
- suggestedTools: [`${namespace}.agent.respond`],
626
- priority: "high",
627
- cooldownMs: 3e3
628
- },
629
- {
630
- trigger: "You received a request addressed to you",
631
- condition: `(state._agentMessages || []).some(m => m.type === 'request' && m.to === actorId)`,
632
- suggestedTools: [`${namespace}.agent.respond`],
633
- priority: "medium",
634
- cooldownMs: 2e3
635
- },
636
- {
637
- trigger: "You have useful information to share with other agents",
638
- suggestedTools: [`${namespace}.agent.inform`],
639
- priority: "low",
640
- cooldownMs: 5e3
641
- },
642
- {
643
- trigger: "You want to propose a collaborative action for the group",
644
- suggestedTools: [`${namespace}.agent.propose`],
645
- priority: "low",
646
- cooldownMs: 1e4
647
- }
648
- ];
649
- }
650
-
651
- // src/migrations.ts
652
- function getStateVersion(state) {
653
- return typeof state._version === "string" ? state._version : "0.0.0";
654
- }
655
- function compareSemver(a, b) {
656
- const pa = a.split(".").map((n) => parseInt(n, 10) || 0);
657
- const pb = b.split(".").map((n) => parseInt(n, 10) || 0);
658
- const len = Math.max(pa.length, pb.length);
659
- for (let i = 0; i < len; i++) {
660
- const va = pa[i] || 0;
661
- const vb = pb[i] || 0;
662
- if (va < vb) return -1;
663
- if (va > vb) return 1;
664
- }
665
- return 0;
666
- }
667
- function migrateState(state, migrations, currentVersion) {
668
- const fromVersion = getStateVersion(state);
669
- if (compareSemver(fromVersion, currentVersion) >= 0) {
670
- return {
671
- migrated: false,
672
- fromVersion,
673
- toVersion: fromVersion,
674
- state
675
- };
676
- }
677
- if (!migrations || migrations.length === 0) {
678
- return {
679
- migrated: false,
680
- fromVersion,
681
- toVersion: currentVersion,
682
- state: { ...state, _version: currentVersion }
683
- };
684
- }
685
- const sorted = [...migrations].sort((a, b) => compareSemver(a.to, b.to));
686
- const applicable = sorted.filter(
687
- (m) => compareSemver(m.to, fromVersion) > 0 && compareSemver(m.to, currentVersion) <= 0
688
- );
689
- if (applicable.length === 0) {
690
- return {
691
- migrated: false,
692
- fromVersion,
693
- toVersion: currentVersion,
694
- state: { ...state, _version: currentVersion }
695
- };
696
- }
697
- let migratedState = { ...state };
698
- for (const migration of applicable) {
699
- migratedState = migration.migrate(migratedState);
700
- }
701
- migratedState._version = currentVersion;
702
- return {
703
- migrated: true,
704
- fromVersion,
705
- toVersion: currentVersion,
706
- state: migratedState
707
- };
708
- }
709
-
710
- // src/storage.ts
711
- var InMemoryAdapter = class {
712
- roomStates = /* @__PURE__ */ new Map();
713
- events = /* @__PURE__ */ new Map();
714
- profiles = /* @__PURE__ */ new Map();
715
- async saveRoomState(roomId, state) {
716
- this.roomStates.set(roomId, state);
717
- }
718
- async loadRoomState(roomId) {
719
- return this.roomStates.get(roomId) || null;
720
- }
721
- async appendEvent(roomId, event) {
722
- if (!this.events.has(roomId)) {
723
- this.events.set(roomId, []);
724
- }
725
- this.events.get(roomId).push(event);
726
- }
727
- async loadEvents(roomId, limit) {
728
- const events = this.events.get(roomId) || [];
729
- if (limit) {
730
- return events.slice(-limit);
731
- }
732
- return events;
733
- }
734
- async listExperiences(_userId) {
735
- return [];
736
- }
737
- async saveUserProfile(userId, profile) {
738
- this.profiles.set(userId, profile);
739
- }
740
- async loadUserProfile(userId) {
741
- return this.profiles.get(userId) || null;
742
- }
743
- };
744
143
  // Annotate the CommonJS export names for ESM import in node:
745
144
  0 && (module.exports = {
746
- Badge,
747
- Button,
748
- Card,
749
- Grid,
750
- InMemoryAdapter,
751
- Input,
752
- Stack,
753
- compareSemver,
754
- createAgentProtocolHints,
755
- createAgentProtocolTools,
756
- defineEphemeralAction,
145
+ createChatTools,
757
146
  defineExperience,
147
+ defineStream,
758
148
  defineTest,
759
- defineTool,
760
- getStateVersion,
761
- migrateState,
762
- quickTool,
763
- useAnimationFrame,
764
- useFollow,
765
- useOptimisticTool,
766
- useParticipants,
767
- useSharedState,
768
- useToolCall,
769
- useTypingIndicator,
770
- validateExperience
149
+ defineTool
771
150
  });