@statelyai/agent 1.1.6 → 2.0.0-next.1

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.
Files changed (62) hide show
  1. package/.changeset/cyan-carpets-perform.md +5 -0
  2. package/.changeset/fast-donkeys-argue.md +5 -0
  3. package/.changeset/light-hats-drive.md +9 -0
  4. package/.changeset/old-jobs-check.md +5 -0
  5. package/.changeset/pre.json +13 -0
  6. package/.vscode/launch.json +6 -0
  7. package/CHANGELOG.md +22 -0
  8. package/dist/index.d.mts +262 -171
  9. package/dist/index.d.ts +262 -171
  10. package/dist/index.js +383 -274
  11. package/dist/index.mjs +386 -272
  12. package/examples/chatbot-alt.ts +57 -0
  13. package/examples/chatbot.ts +12 -17
  14. package/examples/cot.ts +26 -23
  15. package/examples/customer-service-sim.ts +107 -0
  16. package/examples/email.ts +37 -41
  17. package/examples/example.ts +6 -6
  18. package/examples/executor.ts +66 -0
  19. package/examples/goal.ts +12 -12
  20. package/examples/helpers/helpers.ts +26 -14
  21. package/examples/joke.ts +79 -76
  22. package/examples/jugs.ts +125 -0
  23. package/examples/multi.ts +5 -5
  24. package/examples/newspaper.ts +98 -104
  25. package/examples/number.ts +6 -5
  26. package/examples/raffle.ts +11 -12
  27. package/examples/river-crossing.ts +140 -0
  28. package/examples/sandbox.ts +1 -1
  29. package/examples/simple.ts +5 -3
  30. package/examples/summary.ts +121 -0
  31. package/examples/support.ts +6 -6
  32. package/examples/ticTacToe.ts +86 -45
  33. package/examples/todo.ts +7 -7
  34. package/examples/tutor.ts +15 -15
  35. package/examples/verify.ts +3 -3
  36. package/examples/weather.ts +6 -9
  37. package/examples/wiki.ts +27 -8
  38. package/examples/word.ts +16 -11
  39. package/package.json +16 -11
  40. package/readme.md +1 -1
  41. package/src/agent-experimental.ts +1 -1
  42. package/src/agent.test.ts +243 -214
  43. package/src/agent.ts +286 -95
  44. package/src/decide.test.ts +276 -0
  45. package/src/decide.ts +163 -0
  46. package/src/index.ts +1 -1
  47. package/src/middleware.ts +91 -0
  48. package/src/mockModel.ts +47 -0
  49. package/src/planners/shortestPath.test.ts +94 -0
  50. package/src/planners/shortestPath.ts +177 -0
  51. package/src/planners/simple.ts +105 -0
  52. package/src/strategies/chain-of-note.ts +6 -55
  53. package/src/text.ts +51 -144
  54. package/src/types.ts +187 -212
  55. package/src/utils.ts +48 -4
  56. package/vitest.config.ts +9 -3
  57. package/src/adapters/vercel.ts +0 -7
  58. package/src/decision.test.ts +0 -179
  59. package/src/decision.ts +0 -84
  60. package/src/memory.ts +0 -25
  61. package/src/planners/shortestPathPlanner.ts +0 -22
  62. package/src/planners/simplePlanner.ts +0 -139
package/src/types.ts CHANGED
@@ -1,7 +1,6 @@
1
1
  import {
2
2
  ActorLogic,
3
- ActorRefFrom,
4
- AnyActorRef,
3
+ ActorRefLike,
5
4
  AnyEventObject,
6
5
  AnyStateMachine,
7
6
  EventFrom,
@@ -9,29 +8,32 @@ import {
9
8
  PromiseActorLogic,
10
9
  SnapshotFrom,
11
10
  StateValue,
12
- Subscription,
13
11
  TransitionSnapshot,
14
12
  Values,
15
13
  } from 'xstate';
16
14
  import {
17
15
  CoreMessage,
18
- CoreTool,
16
+ GenerateObjectResult,
19
17
  generateText,
20
18
  GenerateTextResult,
21
19
  LanguageModel,
22
20
  streamText,
23
- StreamTextResult,
24
21
  } from 'ai';
25
22
  import { ZodContextMapping, ZodEventMapping } from './schemas';
26
23
  import { TypeOf } from 'zod';
24
+ import { Agent } from './agent';
27
25
 
28
26
  export type GenerateTextOptions = Parameters<typeof generateText>[0];
29
27
 
30
28
  export type StreamTextOptions = Parameters<typeof streamText>[0];
31
29
 
30
+ export type CostFunction<TEvent extends EventObject> = (
31
+ path: AgentPath<TEvent>
32
+ ) => number;
33
+
32
34
  export type AgentPlanInput<TEvent extends EventObject> = Omit<
33
- GenerateTextOptions,
34
- 'prompt' | 'messages' | 'tools'
35
+ AgentGenerateTextOptions,
36
+ 'prompt' | 'tools'
35
37
  > & {
36
38
  /**
37
39
  * The currently observed state.
@@ -56,20 +58,57 @@ export type AgentPlanInput<TEvent extends EventObject> = Omit<
56
58
  * The previous plan.
57
59
  */
58
60
  previousPlan?: AgentPlan<TEvent>;
61
+
62
+ /**
63
+ * The total cost of the path to the goal state.
64
+ */
65
+ costFunction?: CostFunction<TEvent>;
66
+
67
+ /**
68
+ * The maximum number of attempts to generate a plan.
69
+ * Defaults to 2.
70
+ */
71
+ maxAttempts?: number;
72
+ };
73
+
74
+ export type AgentStep<TEvent extends EventObject> = {
75
+ /** The event to take */
76
+ event: TEvent;
77
+ /** The next expected state after taking the event */
78
+ state: ObservedState | undefined;
79
+ };
80
+
81
+ export type AgentPath<TEvent extends EventObject> = {
82
+ /** The expected ending state of the path */
83
+ state: ObservedState | undefined;
84
+ /** The steps to reach the ending state */
85
+ steps: Array<AgentStep<TEvent>>;
86
+ weight?: number;
59
87
  };
60
88
 
61
89
  export type AgentPlan<TEvent extends EventObject> = {
90
+ /**
91
+ * The planner used to generate the plan
92
+ */
93
+ planner: string;
62
94
  goal: string;
63
- state: ObservedState;
64
- content?: string;
65
95
  /**
66
- * Executes the plan based on the given `state` and resolves with
67
- * a potential next `event` to trigger to achieve the `goal`.
96
+ * The ending state of the plan.
97
+ */
98
+ goalState: ObservedState | undefined;
99
+ /**
100
+ * The next event that the agent decided needs to occur to achieve the `goal`.
101
+ *
102
+ * This next event is chosen from the
68
103
  */
69
- execute: (state: ObservedState) => Promise<TEvent | undefined>;
70
104
  nextEvent: TEvent | undefined;
71
- sessionId: string;
105
+ /**
106
+ * The paths that the agent can take to achieve the goal.
107
+ */
108
+ paths: AgentPath<TEvent>[];
109
+ episodeId: string;
72
110
  timestamp: number;
111
+ // result: GenerateObjectResult<any>;
73
112
  };
74
113
 
75
114
  export interface TransitionData {
@@ -113,19 +152,20 @@ export type AgentPlanner<T extends AnyAgent> = (
113
152
  input: AgentPlanInput<T['types']['events']>
114
153
  ) => Promise<AgentPlan<T['types']['events']> | undefined>;
115
154
 
116
- export type AgentDecideOptions = {
155
+ export type AgentDecideOptions<T extends AnyAgent> = {
117
156
  goal: string;
118
157
  model?: LanguageModel;
119
- context?: any;
120
158
  state: ObservedState;
121
- machine: AnyStateMachine;
159
+ machine?: AnyStateMachine;
122
160
  execute?: (event: AnyEventObject) => Promise<void>;
123
- planner?: AgentPlanner<any>;
161
+ planner?: AgentPlanner<T>;
124
162
  events?: ZodEventMapping;
125
- } & Omit<
126
- Parameters<typeof generateText>[0],
127
- 'model' | 'tools' | 'prompt' | 'messages'
128
- >;
163
+ /**
164
+ * The maximum number of times the agent will attempt to make a decision.
165
+ * Defaults to 2.
166
+ */
167
+ maxAttempts?: number;
168
+ } & Omit<Parameters<typeof generateText>[0], 'model' | 'tools' | 'prompt'>;
129
169
 
130
170
  export interface AgentFeedback {
131
171
  goal?: string;
@@ -133,17 +173,15 @@ export interface AgentFeedback {
133
173
  /**
134
174
  * The message correlation that the feedback is relevant for
135
175
  */
136
- correlationId?: string;
137
176
  attributes: Record<string, any>;
138
177
  reward: number;
139
178
  timestamp: number;
140
- sessionId: string;
179
+ episodeId: string;
141
180
  }
142
181
 
143
182
  export interface AgentFeedbackInput {
144
183
  goal?: string;
145
184
  observationId?: string;
146
- correlationId?: string;
147
185
  attributes?: Record<string, any>;
148
186
  timestamp?: number;
149
187
  reward?: number;
@@ -158,9 +196,122 @@ export type AgentMessage = CoreMessage & {
158
196
  */
159
197
  responseId?: string;
160
198
  result?: GenerateTextResult<any>;
161
- sessionId: string;
162
- correlationId: string;
163
- parentCorrelationId?: string;
199
+ episodeId: string;
200
+ };
201
+
202
+ type JSONObject = {
203
+ [key: string]: JSONValue;
204
+ };
205
+ type JSONArray = JSONValue[];
206
+ type JSONValue = null | string | number | boolean | JSONObject | JSONArray;
207
+
208
+ type LanguageModelV1ProviderMetadata = Record<
209
+ string,
210
+ Record<string, JSONValue>
211
+ >;
212
+
213
+ interface LanguageModelV1ImagePart {
214
+ type: 'image';
215
+ /**
216
+ Image data as a Uint8Array (e.g. from a Blob or Buffer) or a URL.
217
+ */
218
+ image: Uint8Array | URL;
219
+ /**
220
+ Optional mime type of the image.
221
+ */
222
+ mimeType?: string;
223
+ /**
224
+ * Additional provider-specific metadata. They are passed through
225
+ * to the provider from the AI SDK and enable provider-specific
226
+ * functionality that can be fully encapsulated in the provider.
227
+ */
228
+ providerMetadata?: LanguageModelV1ProviderMetadata;
229
+ }
230
+
231
+ export interface LanguageModelV1TextPart {
232
+ type: 'text';
233
+ /**
234
+ The text content.
235
+ */
236
+ text: string;
237
+ /**
238
+ * Additional provider-specific metadata. They are passed through
239
+ * to the provider from the AI SDK and enable provider-specific
240
+ * functionality that can be fully encapsulated in the provider.
241
+ */
242
+ providerMetadata?: LanguageModelV1ProviderMetadata;
243
+ }
244
+
245
+ export interface LanguageModelV1ToolCallPart {
246
+ type: 'tool-call';
247
+ /**
248
+ ID of the tool call. This ID is used to match the tool call with the tool result.
249
+ */
250
+ toolCallId: string;
251
+ /**
252
+ Name of the tool that is being called.
253
+ */
254
+ toolName: string;
255
+ /**
256
+ Arguments of the tool call. This is a JSON-serializable object that matches the tool's input schema.
257
+ */
258
+ args: unknown;
259
+ /**
260
+ * Additional provider-specific metadata. They are passed through
261
+ * to the provider from the AI SDK and enable provider-specific
262
+ * functionality that can be fully encapsulated in the provider.
263
+ */
264
+ providerMetadata?: LanguageModelV1ProviderMetadata;
265
+ }
266
+ interface LanguageModelV1ToolResultPart {
267
+ type: 'tool-result';
268
+ /**
269
+ ID of the tool call that this result is associated with.
270
+ */
271
+ toolCallId: string;
272
+ /**
273
+ Name of the tool that generated this result.
274
+ */
275
+ toolName: string;
276
+ /**
277
+ Result of the tool call. This is a JSON-serializable object.
278
+ */
279
+ result: unknown;
280
+ /**
281
+ Optional flag if the result is an error or an error message.
282
+ */
283
+ isError?: boolean;
284
+ /**
285
+ * Additional provider-specific metadata. They are passed through
286
+ * to the provider from the AI SDK and enable provider-specific
287
+ * functionality that can be fully encapsulated in the provider.
288
+ */
289
+ providerMetadata?: LanguageModelV1ProviderMetadata;
290
+ }
291
+ type LanguageModelV1Message = (
292
+ | {
293
+ role: 'system';
294
+ content: string;
295
+ }
296
+ | {
297
+ role: 'user';
298
+ content: Array<LanguageModelV1TextPart | LanguageModelV1ImagePart>;
299
+ }
300
+ | {
301
+ role: 'assistant';
302
+ content: Array<LanguageModelV1TextPart | LanguageModelV1ToolCallPart>;
303
+ }
304
+ | {
305
+ role: 'tool';
306
+ content: Array<LanguageModelV1ToolResultPart>;
307
+ }
308
+ ) & {
309
+ /**
310
+ * Additional provider-specific metadata. They are passed through
311
+ * to the provider from the AI SDK and enable provider-specific
312
+ * functionality that can be fully encapsulated in the provider.
313
+ */
314
+ providerMetadata?: LanguageModelV1ProviderMetadata;
164
315
  };
165
316
 
166
317
  export type AgentMessageInput = CoreMessage & {
@@ -171,25 +322,23 @@ export type AgentMessageInput = CoreMessage & {
171
322
  * which message this message is responding to, if any.
172
323
  */
173
324
  responseId?: string;
174
- correlationId?: string;
175
- parentCorrelationId?: string;
176
325
  result?: GenerateTextResult<any>;
177
326
  };
178
327
 
179
- export interface AgentObservation<TActor extends AnyActorRef> {
328
+ export interface AgentObservation<TActor extends ActorRefLike> {
180
329
  id: string;
181
330
  prevState: SnapshotFrom<TActor> | undefined;
182
- event: EventFrom<TActor>;
331
+ event: EventFrom<TActor> | undefined;
183
332
  state: SnapshotFrom<TActor>;
184
333
  machineHash: string | undefined;
185
- sessionId: string;
334
+ episodeId: string;
186
335
  timestamp: number;
187
336
  }
188
337
 
189
338
  export interface AgentObservationInput {
190
339
  id?: string;
191
- prevState: ObservedState | undefined;
192
- event: AnyEventObject;
340
+ prevState?: ObservedState;
341
+ event?: AnyEventObject;
193
342
  state: ObservedState;
194
343
  machine?: AnyStateMachine;
195
344
  timestamp?: number;
@@ -198,7 +347,7 @@ export interface AgentObservationInput {
198
347
  export type AgentDecisionInput = {
199
348
  goal: string;
200
349
  model?: LanguageModel;
201
- context?: any;
350
+ context?: Record<string, any>;
202
351
  } & Omit<Parameters<typeof generateText>[0], 'model' | 'tools' | 'prompt'>;
203
352
 
204
353
  export type AgentDecisionLogic<TEvents extends EventObject> = PromiseActorLogic<
@@ -260,151 +409,7 @@ export type ContextFromZodContextMapping<
260
409
  [K in keyof TContextSchema & string]: TypeOf<TContextSchema[K]>;
261
410
  };
262
411
 
263
- export type Agent<TContext, TEvents extends EventObject> = ActorRefFrom<
264
- AgentLogic<TEvents>
265
- > & {
266
- /**
267
- * The name of the agent. All agents with the same name are related and
268
- * able to share experiences (observations, feedback) with each other.
269
- */
270
- name?: string;
271
- /**
272
- * The unique identifier for the agent.
273
- */
274
- id?: string;
275
- description?: string;
276
- events: ZodEventMapping;
277
- types: {
278
- events: TEvents;
279
- context: Compute<TContext>;
280
- };
281
- model: LanguageModel;
282
- defaultOptions: GenerateTextOptions;
283
- memory: AgentLongTermMemory | undefined;
284
- /**
285
- * The adapter used to perform LLM actions such as
286
- * `.generateText(…)` and `.streamText(…)`.
287
- *
288
- * Defaults to the Vercel AI SDK.
289
- */
290
- adapter: AIAdapter;
291
-
292
- /**
293
- * Resolves with an `AgentPlan` based on the information provided in the `options`, including:
294
- *
295
- * - The `goal` for the agent to achieve
296
- * - The observed current `state`
297
- * - The `machine` (e.g. a state machine) that specifies what can happen next
298
- * - Additional `context`
299
- */
300
- decide: (
301
- options: AgentDecideOptions
302
- ) => Promise<AgentPlan<TEvents> | undefined>;
303
-
304
- // Generate text
305
- generateText: (
306
- options: AgentGenerateTextOptions
307
- ) => Promise<AgentGenerateTextResult>;
308
-
309
- // Stream text
310
- streamText: (
311
- options: AgentStreamTextOptions
312
- ) => Promise<AgentStreamTextResult>;
313
-
314
- addObservation: (
315
- observationInput: AgentObservationInput
316
- ) => AgentObservation<any>; // TODO
317
- addMessage: (messageInput: AgentMessageInput) => AgentMessage;
318
- addFeedback: (feedbackInput: AgentFeedbackInput) => AgentFeedback;
319
- addPlan: (plan: AgentPlan<TEvents>) => void;
320
- /**
321
- * Called whenever the agent (LLM assistant) receives or sends a message.
322
- */
323
- onMessage: (callback: (message: AgentMessage) => void) => void;
324
- /**
325
- * Selects agent data from its context.
326
- *
327
- * @deprecated Select from `agent.getSnapshot().context` directly or:
328
- * - `agent.getMessages()`
329
- * - `agent.getObservations()`
330
- * - `agent.getFeedback()`
331
- * - `agent.getPlans()`
332
- */
333
- select: <T>(selector: (context: AgentMemoryContext) => T) => T;
334
-
335
- /**
336
- * Retrieves messages from the agent's short-term (local) memory.
337
- */
338
- getMessages: () => AgentMessage[];
339
-
340
- /**
341
- * Retrieves observations from the agent's short-term (local) memory.
342
- */
343
- getObservations: () => AgentObservation<Agent<TContext, TEvents>>[];
344
-
345
- /**
346
- * Retrieves feedback from the agent's short-term (local) memory.
347
- */
348
- getFeedback: () => AgentFeedback[];
349
-
350
- /**
351
- * Retrieves strategies from the agent's short-term (local) memory.
352
- */
353
- getPlans: () => AgentPlan<TEvents>[];
354
-
355
- /**
356
- * Interacts with this state machine actor by inspecting state transitions and storing them as observations.
357
- *
358
- * Observations contain the `prevState`, `event`, and current `state` of this
359
- * actor, as well as other properties that are useful when recalled.
360
- * These observations are stored in the `agent`'s short-term (local) memory
361
- * and can be retrieved via `agent.getObservations()`.
362
- *
363
- * @example
364
- * ```ts
365
- * // Only observes the actor's state transitions
366
- * agent.interact(actor);
367
- *
368
- * actor.start();
369
- * ```
370
- */
371
- interact<TActor extends AnyActorRef>(actorRef: TActor): Subscription;
372
- /**
373
- * Interacts with this state machine actor by:
374
- * 1. Inspecting state transitions and storing them as observations
375
- * 2. Deciding what to do next (which event to send the actor) based on
376
- * the agent input returned from `getInput(observation)`, if `getInput(…)` is provided as the 2nd argument.
377
- *
378
- * Observations contain the `prevState`, `event`, and current `state` of this
379
- * actor, as well as other properties that are useful when recalled.
380
- * These observations are stored in the `agent`'s short-term (local) memory
381
- * and can be retrieved via `agent.getObservations()`.
382
- *
383
- * @example
384
- * ```ts
385
- * // Observes the actor's state transitions and
386
- * // makes a decision if on the "summarize" state
387
- * agent.interact(actor, observed => {
388
- * if (observed.state.matches('summarize')) {
389
- * return {
390
- * context: observed.state.context,
391
- * goal: 'Summarize the message'
392
- * }
393
- * }
394
- * });
395
- *
396
- * actor.start();
397
- * ```
398
- */
399
- interact<TActor extends AnyActorRef>(
400
- actorRef: TActor,
401
- getInput: (
402
- observation: AgentObservation<TActor>
403
- ) => AgentDecisionInput | undefined
404
- ): Subscription;
405
- };
406
-
407
- export type AnyAgent = Agent<any, any>;
412
+ export type AnyAgent = Agent<any, any, any, any>;
408
413
 
409
414
  export type FromAgent<T> = T | ((agent: AnyAgent) => T | Promise<T>);
410
415
 
@@ -414,13 +419,6 @@ export type CommonTextOptions = {
414
419
  context?: Record<string, any>;
415
420
  messages?: FromAgent<CoreMessage[]>;
416
421
  template?: PromptTemplate<any>;
417
- correlationId?: string;
418
- parentCorrelationId?: string;
419
- };
420
-
421
- export type TextResultMeta = {
422
- correlationId: string;
423
- parentCorrelationId?: string;
424
422
  };
425
423
 
426
424
  export type AgentGenerateTextOptions = Omit<
@@ -429,16 +427,12 @@ export type AgentGenerateTextOptions = Omit<
429
427
  > &
430
428
  CommonTextOptions;
431
429
 
432
- export type AgentGenerateTextResult = GenerateTextResult<any> & TextResultMeta;
433
-
434
430
  export type AgentStreamTextOptions = Omit<
435
431
  StreamTextOptions,
436
432
  'model' | 'prompt' | 'messages'
437
433
  > &
438
434
  CommonTextOptions;
439
435
 
440
- export type AgentStreamTextResult = StreamTextResult<any> & TextResultMeta;
441
-
442
436
  export interface ObservedState {
443
437
  /**
444
438
  * The current state value of the state machine, e.g.
@@ -448,10 +442,10 @@ export interface ObservedState {
448
442
  /**
449
443
  * Additional contextual data related to the current state
450
444
  */
451
- context: Record<string, unknown>;
445
+ context?: Record<string, unknown>;
452
446
  }
453
447
 
454
- export type ObservedStateFrom<TActor extends AnyActorRef> = Pick<
448
+ export type ObservedStateFrom<TActor extends ActorRefLike> = Pick<
455
449
  SnapshotFrom<TActor>,
456
450
  'value' | 'context'
457
451
  >;
@@ -463,20 +457,6 @@ export type AgentMemoryContext = {
463
457
  feedback: AgentFeedback[];
464
458
  };
465
459
 
466
- export type AgentMemory = AppendOnlyStorage<AgentMemoryContext>;
467
-
468
- export interface AppendOnlyStorage<T extends Record<string, any[]>> {
469
- append<K extends keyof T>(
470
- sessionId: string,
471
- key: K,
472
- item: T[K][0]
473
- ): Promise<void>;
474
- getAll<K extends keyof T>(
475
- sessionId: string,
476
- key: K
477
- ): Promise<T[K] | undefined>;
478
- }
479
-
480
460
  export interface AgentLongTermMemory {
481
461
  get<K extends keyof AgentMemoryContext>(
482
462
  key: K
@@ -491,9 +471,4 @@ export interface AgentLongTermMemory {
491
471
  ): Promise<void>;
492
472
  }
493
473
 
494
- export interface AIAdapter {
495
- generateText: typeof generateText;
496
- streamText: typeof streamText;
497
- }
498
-
499
474
  export type Compute<A extends any> = { [K in keyof A]: A[K] } & unknown;
package/src/utils.ts CHANGED
@@ -1,6 +1,12 @@
1
- import { AnyMachineSnapshot, AnyStateMachine, AnyStateNode } from 'xstate';
1
+ import {
2
+ ActorRefLike,
3
+ AnyActorRef,
4
+ AnyMachineSnapshot,
5
+ AnyStateMachine,
6
+ AnyStateNode,
7
+ } from 'xstate';
2
8
  import hash from 'object-hash';
3
- import { TransitionData } from './types';
9
+ import { ObservedState, TransitionData } from './types';
4
10
 
5
11
  export function getAllTransitions(state: AnyMachineSnapshot): TransitionData[] {
6
12
  const nodes = state._nodes;
@@ -53,10 +59,11 @@ export function wrapInXml(tagName: string, content: string): string {
53
59
  return `<${tagName}>${content}</${tagName}>`;
54
60
  }
55
61
 
56
- export function randomId() {
62
+ export function randomId(prefix?: string): string {
57
63
  const timestamp = Date.now().toString(36);
58
64
  const random = Math.random().toString(36).substring(2, 9);
59
- return timestamp + random;
65
+ // return timestamp + random;
66
+ return `${prefix || ''}${timestamp}${random}`;
60
67
  }
61
68
 
62
69
  const machineHashes: WeakMap<AnyStateMachine, string> = new WeakMap();
@@ -70,3 +77,40 @@ export function getMachineHash(machine: AnyStateMachine): string {
70
77
  machineHashes.set(machine, machineHash);
71
78
  return machineHash;
72
79
  }
80
+
81
+ export function isActorRef(
82
+ actorRefLike: ActorRefLike
83
+ ): actorRefLike is AnyActorRef {
84
+ return (
85
+ 'src' in actorRefLike &&
86
+ 'system' in actorRefLike &&
87
+ 'sessionId' in actorRefLike
88
+ );
89
+ }
90
+
91
+ export function getTransitions(
92
+ state: ObservedState,
93
+ machine: AnyStateMachine
94
+ ): TransitionData[] {
95
+ if (!machine) {
96
+ return [];
97
+ }
98
+
99
+ const resolvedState = machine.resolveState({
100
+ ...state,
101
+ // Need this property defined to make TS happy
102
+ context: state.context,
103
+ });
104
+ return getAllTransitions(resolvedState);
105
+ }
106
+
107
+ export function isMachineActor(
108
+ actor: ActorRefLike
109
+ ): actor is typeof actor & { src: AnyStateMachine } {
110
+ return (
111
+ 'src' in actor &&
112
+ typeof actor.src === 'object' &&
113
+ actor.src !== null &&
114
+ 'definition' in actor.src
115
+ );
116
+ }
package/vitest.config.ts CHANGED
@@ -1,9 +1,15 @@
1
- // vitest.config.ts
1
+ import { defineConfig } from 'vitest/config';
2
2
  import dotenv from 'dotenv';
3
3
  dotenv.config();
4
4
 
5
- export default {
5
+ export default defineConfig({
6
6
  test: {
7
7
  testTimeout: 10000, // Global timeout of 10000ms for all tests
8
+ coverage: {
9
+ provider: 'v8',
10
+ reporter: ['text', 'json', 'html'],
11
+ exclude: ['**.test.ts'],
12
+ include: ['src'],
13
+ },
8
14
  },
9
- };
15
+ });
@@ -1,7 +0,0 @@
1
- import { generateText, streamText } from 'ai';
2
- import { AIAdapter } from '../types';
3
-
4
- export const vercelAdapter: AIAdapter = {
5
- generateText,
6
- streamText,
7
- };