@trayai/helix-sdk 1.7.0 → 1.13.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.
@@ -1,5 +1,5 @@
1
1
  import { z, ZodType } from 'zod';
2
- import { P as PlatformContext } from './types-CRUtefiq.js';
2
+ import { P as PlatformContext } from './types-CVW_-1wh.js';
3
3
 
4
4
  interface SdkRuntimeConfig {
5
5
  /**
@@ -98,7 +98,10 @@ type AgentSessionsConfig = z.infer<typeof agentSessionsSchema>;
98
98
  * platform authentications carry no service identifier, so the project
99
99
  * declares it here: `aiProviders: { <authAlias>: "<service>" }`. The
100
100
  * `openai-compatible` service (self-hosted vLLM, Ollama, …) additionally
101
- * needs the endpoint base URL, so it uses the object form.
101
+ * needs the endpoint base URL, so it uses the object form. `bedrock` likewise
102
+ * needs the object form: the provider package derives the regional runtime
103
+ * endpoint (`bedrock-runtime.<region>.amazonaws.com`) from `region`, or takes
104
+ * `baseUrl` verbatim for VPC / custom endpoints.
102
105
  *
103
106
  * `baseUrl` must be https: every `ctx.ai` request egresses through the
104
107
  * credentials broker's raw forward proxy, and `createBrokerFetch` rejects
@@ -107,28 +110,51 @@ type AgentSessionsConfig = z.infer<typeof agentSessionsSchema>;
107
110
  * and then fail on every request. Catching it in the schema turns that into
108
111
  * one clear config error instead of a confusing first-call failure.
109
112
  */
110
- declare const AI_SERVICES: readonly ["openai", "anthropic", "google", "mistral", "cohere", "openai-compatible"];
113
+ declare const AI_SERVICES: readonly ["openai", "anthropic", "google", "mistral", "cohere", "bedrock", "openai-compatible"];
111
114
  type AiService = (typeof AI_SERVICES)[number];
112
- declare const aiProviderEntrySchema: z.ZodUnion<[z.ZodEnum<["openai", "anthropic", "google", "mistral", "cohere"]>, z.ZodEffects<z.ZodEffects<z.ZodObject<{
113
- service: z.ZodEnum<["openai", "anthropic", "google", "mistral", "cohere", "openai-compatible"]>;
115
+ declare const aiProviderEntrySchema: z.ZodUnion<[z.ZodEnum<["openai", "anthropic", "google", "mistral", "cohere"]>, z.ZodEffects<z.ZodEffects<z.ZodEffects<z.ZodEffects<z.ZodObject<{
116
+ service: z.ZodEnum<["openai", "anthropic", "google", "mistral", "cohere", "bedrock", "openai-compatible"]>;
114
117
  baseUrl: z.ZodOptional<z.ZodString>;
118
+ region: z.ZodOptional<z.ZodString>;
115
119
  }, "strip", z.ZodTypeAny, {
116
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
120
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
121
+ region?: string | undefined;
122
+ baseUrl?: string | undefined;
123
+ }, {
124
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
125
+ region?: string | undefined;
126
+ baseUrl?: string | undefined;
127
+ }>, {
128
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
129
+ region?: string | undefined;
117
130
  baseUrl?: string | undefined;
118
131
  }, {
119
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
132
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
133
+ region?: string | undefined;
120
134
  baseUrl?: string | undefined;
121
135
  }>, {
122
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
136
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
137
+ region?: string | undefined;
123
138
  baseUrl?: string | undefined;
124
139
  }, {
125
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
140
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
141
+ region?: string | undefined;
126
142
  baseUrl?: string | undefined;
127
143
  }>, {
128
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
144
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
145
+ region?: string | undefined;
129
146
  baseUrl?: string | undefined;
130
147
  }, {
131
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
148
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
149
+ region?: string | undefined;
150
+ baseUrl?: string | undefined;
151
+ }>, {
152
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
153
+ region?: string | undefined;
154
+ baseUrl?: string | undefined;
155
+ }, {
156
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
157
+ region?: string | undefined;
132
158
  baseUrl?: string | undefined;
133
159
  }>]>;
134
160
  type AiProviderEntry = z.infer<typeof aiProviderEntrySchema>;
@@ -172,26 +198,49 @@ declare const trayConfigSchema: z.ZodEffects<z.ZodObject<{
172
198
  table: string;
173
199
  region: string;
174
200
  }>]>>;
175
- aiProviders: z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodUnion<[z.ZodEnum<["openai", "anthropic", "google", "mistral", "cohere"]>, z.ZodEffects<z.ZodEffects<z.ZodObject<{
176
- service: z.ZodEnum<["openai", "anthropic", "google", "mistral", "cohere", "openai-compatible"]>;
201
+ aiProviders: z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodUnion<[z.ZodEnum<["openai", "anthropic", "google", "mistral", "cohere"]>, z.ZodEffects<z.ZodEffects<z.ZodEffects<z.ZodEffects<z.ZodObject<{
202
+ service: z.ZodEnum<["openai", "anthropic", "google", "mistral", "cohere", "bedrock", "openai-compatible"]>;
177
203
  baseUrl: z.ZodOptional<z.ZodString>;
204
+ region: z.ZodOptional<z.ZodString>;
178
205
  }, "strip", z.ZodTypeAny, {
179
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
206
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
207
+ region?: string | undefined;
208
+ baseUrl?: string | undefined;
209
+ }, {
210
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
211
+ region?: string | undefined;
212
+ baseUrl?: string | undefined;
213
+ }>, {
214
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
215
+ region?: string | undefined;
216
+ baseUrl?: string | undefined;
217
+ }, {
218
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
219
+ region?: string | undefined;
220
+ baseUrl?: string | undefined;
221
+ }>, {
222
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
223
+ region?: string | undefined;
180
224
  baseUrl?: string | undefined;
181
225
  }, {
182
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
226
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
227
+ region?: string | undefined;
183
228
  baseUrl?: string | undefined;
184
229
  }>, {
185
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
230
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
231
+ region?: string | undefined;
186
232
  baseUrl?: string | undefined;
187
233
  }, {
188
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
234
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
235
+ region?: string | undefined;
189
236
  baseUrl?: string | undefined;
190
237
  }>, {
191
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
238
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
239
+ region?: string | undefined;
192
240
  baseUrl?: string | undefined;
193
241
  }, {
194
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
242
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
243
+ region?: string | undefined;
195
244
  baseUrl?: string | undefined;
196
245
  }>]>>>;
197
246
  }, "strip", z.ZodTypeAny, {
@@ -211,7 +260,8 @@ declare const trayConfigSchema: z.ZodEffects<z.ZodObject<{
211
260
  region: string;
212
261
  } | undefined;
213
262
  aiProviders?: Record<string, "openai" | "anthropic" | "google" | "mistral" | "cohere" | {
214
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
263
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
264
+ region?: string | undefined;
215
265
  baseUrl?: string | undefined;
216
266
  }> | undefined;
217
267
  }, {
@@ -231,7 +281,8 @@ declare const trayConfigSchema: z.ZodEffects<z.ZodObject<{
231
281
  region: string;
232
282
  } | undefined;
233
283
  aiProviders?: Record<string, "openai" | "anthropic" | "google" | "mistral" | "cohere" | {
234
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
284
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
285
+ region?: string | undefined;
235
286
  baseUrl?: string | undefined;
236
287
  }> | undefined;
237
288
  }>, {
@@ -250,7 +301,8 @@ declare const trayConfigSchema: z.ZodEffects<z.ZodObject<{
250
301
  region: string;
251
302
  } | undefined;
252
303
  aiProviders?: Record<string, "openai" | "anthropic" | "google" | "mistral" | "cohere" | {
253
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
304
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
305
+ region?: string | undefined;
254
306
  baseUrl?: string | undefined;
255
307
  }> | undefined;
256
308
  }, {
@@ -270,7 +322,8 @@ declare const trayConfigSchema: z.ZodEffects<z.ZodObject<{
270
322
  region: string;
271
323
  } | undefined;
272
324
  aiProviders?: Record<string, "openai" | "anthropic" | "google" | "mistral" | "cohere" | {
273
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
325
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
326
+ region?: string | undefined;
274
327
  baseUrl?: string | undefined;
275
328
  }> | undefined;
276
329
  }>;
@@ -311,26 +364,49 @@ declare const loadedTrayConfigSchema: z.ZodDiscriminatedUnion<"kind", [z.ZodObje
311
364
  table: string;
312
365
  region: string;
313
366
  }>]>>;
314
- aiProviders: z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodUnion<[z.ZodEnum<["openai", "anthropic", "google", "mistral", "cohere"]>, z.ZodEffects<z.ZodEffects<z.ZodObject<{
315
- service: z.ZodEnum<["openai", "anthropic", "google", "mistral", "cohere", "openai-compatible"]>;
367
+ aiProviders: z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodUnion<[z.ZodEnum<["openai", "anthropic", "google", "mistral", "cohere"]>, z.ZodEffects<z.ZodEffects<z.ZodEffects<z.ZodEffects<z.ZodObject<{
368
+ service: z.ZodEnum<["openai", "anthropic", "google", "mistral", "cohere", "bedrock", "openai-compatible"]>;
316
369
  baseUrl: z.ZodOptional<z.ZodString>;
370
+ region: z.ZodOptional<z.ZodString>;
317
371
  }, "strip", z.ZodTypeAny, {
318
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
372
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
373
+ region?: string | undefined;
374
+ baseUrl?: string | undefined;
375
+ }, {
376
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
377
+ region?: string | undefined;
378
+ baseUrl?: string | undefined;
379
+ }>, {
380
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
381
+ region?: string | undefined;
382
+ baseUrl?: string | undefined;
383
+ }, {
384
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
385
+ region?: string | undefined;
386
+ baseUrl?: string | undefined;
387
+ }>, {
388
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
389
+ region?: string | undefined;
319
390
  baseUrl?: string | undefined;
320
391
  }, {
321
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
392
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
393
+ region?: string | undefined;
322
394
  baseUrl?: string | undefined;
323
395
  }>, {
324
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
396
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
397
+ region?: string | undefined;
325
398
  baseUrl?: string | undefined;
326
399
  }, {
327
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
400
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
401
+ region?: string | undefined;
328
402
  baseUrl?: string | undefined;
329
403
  }>, {
330
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
404
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
405
+ region?: string | undefined;
331
406
  baseUrl?: string | undefined;
332
407
  }, {
333
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
408
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
409
+ region?: string | undefined;
334
410
  baseUrl?: string | undefined;
335
411
  }>]>>>;
336
412
  } & {
@@ -353,7 +429,8 @@ declare const loadedTrayConfigSchema: z.ZodDiscriminatedUnion<"kind", [z.ZodObje
353
429
  region: string;
354
430
  } | undefined;
355
431
  aiProviders?: Record<string, "openai" | "anthropic" | "google" | "mistral" | "cohere" | {
356
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
432
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
433
+ region?: string | undefined;
357
434
  baseUrl?: string | undefined;
358
435
  }> | undefined;
359
436
  }, {
@@ -373,7 +450,8 @@ declare const loadedTrayConfigSchema: z.ZodDiscriminatedUnion<"kind", [z.ZodObje
373
450
  region: string;
374
451
  } | undefined;
375
452
  aiProviders?: Record<string, "openai" | "anthropic" | "google" | "mistral" | "cohere" | {
376
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
453
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
454
+ region?: string | undefined;
377
455
  baseUrl?: string | undefined;
378
456
  }> | undefined;
379
457
  }>, z.ZodObject<{
@@ -405,26 +483,49 @@ declare const loadedTrayConfigSchema: z.ZodDiscriminatedUnion<"kind", [z.ZodObje
405
483
  table: string;
406
484
  region: string;
407
485
  }>]>>;
408
- aiProviders: z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodUnion<[z.ZodEnum<["openai", "anthropic", "google", "mistral", "cohere"]>, z.ZodEffects<z.ZodEffects<z.ZodObject<{
409
- service: z.ZodEnum<["openai", "anthropic", "google", "mistral", "cohere", "openai-compatible"]>;
486
+ aiProviders: z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodUnion<[z.ZodEnum<["openai", "anthropic", "google", "mistral", "cohere"]>, z.ZodEffects<z.ZodEffects<z.ZodEffects<z.ZodEffects<z.ZodObject<{
487
+ service: z.ZodEnum<["openai", "anthropic", "google", "mistral", "cohere", "bedrock", "openai-compatible"]>;
410
488
  baseUrl: z.ZodOptional<z.ZodString>;
489
+ region: z.ZodOptional<z.ZodString>;
411
490
  }, "strip", z.ZodTypeAny, {
412
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
491
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
492
+ region?: string | undefined;
413
493
  baseUrl?: string | undefined;
414
494
  }, {
415
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
495
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
496
+ region?: string | undefined;
416
497
  baseUrl?: string | undefined;
417
498
  }>, {
418
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
499
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
500
+ region?: string | undefined;
419
501
  baseUrl?: string | undefined;
420
502
  }, {
421
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
503
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
504
+ region?: string | undefined;
422
505
  baseUrl?: string | undefined;
423
506
  }>, {
424
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
507
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
508
+ region?: string | undefined;
425
509
  baseUrl?: string | undefined;
426
510
  }, {
427
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
511
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
512
+ region?: string | undefined;
513
+ baseUrl?: string | undefined;
514
+ }>, {
515
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
516
+ region?: string | undefined;
517
+ baseUrl?: string | undefined;
518
+ }, {
519
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
520
+ region?: string | undefined;
521
+ baseUrl?: string | undefined;
522
+ }>, {
523
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
524
+ region?: string | undefined;
525
+ baseUrl?: string | undefined;
526
+ }, {
527
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
528
+ region?: string | undefined;
428
529
  baseUrl?: string | undefined;
429
530
  }>]>>>;
430
531
  } & {
@@ -445,7 +546,8 @@ declare const loadedTrayConfigSchema: z.ZodDiscriminatedUnion<"kind", [z.ZodObje
445
546
  region: string;
446
547
  } | undefined;
447
548
  aiProviders?: Record<string, "openai" | "anthropic" | "google" | "mistral" | "cohere" | {
448
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
549
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
550
+ region?: string | undefined;
449
551
  baseUrl?: string | undefined;
450
552
  }> | undefined;
451
553
  }, {
@@ -464,7 +566,8 @@ declare const loadedTrayConfigSchema: z.ZodDiscriminatedUnion<"kind", [z.ZodObje
464
566
  region: string;
465
567
  } | undefined;
466
568
  aiProviders?: Record<string, "openai" | "anthropic" | "google" | "mistral" | "cohere" | {
467
- service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "openai-compatible";
569
+ service: "openai" | "anthropic" | "google" | "mistral" | "cohere" | "bedrock" | "openai-compatible";
570
+ region?: string | undefined;
468
571
  baseUrl?: string | undefined;
469
572
  }> | undefined;
470
573
  }>]>;
@@ -549,9 +652,6 @@ declare function requireWorkspaceId(config: LoadedTrayConfig): string;
549
652
  /**
550
653
  * `defineTool` (helix-spec 12) — the subset agents consume (helix-spec 14).
551
654
  *
552
- * **Beta.** Agents and tools are in beta: this API may change in a future
553
- * release without a major version bump.
554
- *
555
655
  * A tool is a *definition*: name, description, input schema, approval policy,
556
656
  * and handler together in one default export. Tools are:
557
657
  *
@@ -611,8 +711,6 @@ interface HelixToolLike {
611
711
  }
612
712
  /**
613
713
  * Define a tool an agent can call (or that your code can invoke in-process).
614
- *
615
- * @beta Agents and tools are in beta and may change in a future release.
616
714
  */
617
715
  declare function defineTool<TSchema extends ZodType>(config: DefineToolConfig<TSchema>): HelixTool<TSchema>;
618
716
  /** Structural check for defineTool output — see TOOL_DEFINITION_KIND. */
@@ -623,9 +721,6 @@ declare function isToolDefinition(value: unknown): value is HelixTool;
623
721
  * `functions/_agents/`, definitions in code, the file system as the source of
624
722
  * truth.
625
723
  *
626
- * **Beta.** Agents and tools are in beta: this API may change in a future
627
- * release without a major version bump.
628
- *
629
724
  * Like `defineSchedule`, the SDK owns the definition + runtime and the
630
725
  * host (dev server, lambda router) owns discovery: importing the module
631
726
  * registers the agent by name.
@@ -794,8 +889,6 @@ interface AgentDefinition extends z.output<typeof agentConfigSchema> {
794
889
  }
795
890
  /**
796
891
  * Define an agent (default export of a file under `functions/_agents/`).
797
- *
798
- * @beta Agents and tools are in beta and may change in a future release.
799
892
  */
800
893
  declare function defineAgent(config: AgentDefinitionConfig): AgentDefinition;
801
894
  /** Structural check for defineAgent output — see AGENT_DEFINITION_KIND. */
package/dist/index.d.ts CHANGED
@@ -1,9 +1,9 @@
1
1
  import * as h3 from 'h3';
2
2
  import { ZodType } from 'zod';
3
- import { F as FunctionHandler, D as DefineFunctionOptions, a as DefineScheduleConfig, S as ScheduleDefinition, P as PlatformContext } from './types-CRUtefiq.js';
4
- export { A as AgentApprovalDecision, b as AgentCallOptions, c as AgentClient, d as AgentPendingApproval, e as AgentResult, f as AgentSession, g as AgentSessionPage, h as AgentSessionPageOptions, i as AgentSessionSummary, j as AgentSessionsList, k as AgentStreamResult, l as AiEmbeddingModelInstance, m as AiImageModelInstance, n as AiLanguageModelInstance, o as AiSpeechModelInstance, p as AiTranscriptionModelInstance, B as BrokerAuthedClient, q as BrokerCallOptions, r as BrokerCallResult, C as CallFunctionAsync, s as DbCallParameters, t as DbClient, u as FileSystemClient, H as HelixAI, v as HelixAIProvider, w as HelixAgent, x as HelixCost, y as HelixResultMeta, z as HttpClient, K as KeyValueStore, L as Logger, E as S3SignOptions, G as S3SignResult, I as ScheduleContext, J as ScheduleHandler, M as ScheduleTrigger, N as SqlBuilder, T as TrayContext, U as UnvalidatedInput } from './types-CRUtefiq.js';
5
- import { T as TrayConfig, L as LoadedTrayConfig, W as WatchErrorPhase } from './define-agent-C0qXub7P.js';
6
- export { A as AGENT_DEFINITION_KIND, a as AI_SERVICES, b as AgentDefinition, c as AgentDefinitionConfig, d as AgentSessionsConfig, e as AiProviderEntry, f as AiService, C as ConfigFileOptions, D as DefineToolConfig, H as HELIX_CONFIG_ENV, g as HelixTool, h as HelixToolLike, P as ProvisionedTrayConfig, S as SdkRuntimeConfig, i as TOOL_DEFINITION_KIND, U as UnprovisionedTrayConfig, j as WORKSPACE_ID_REQUIRED_CODE, k as WorkspaceIdRequiredError, l as agentSessionsSchema, m as aiProviderEntrySchema, n as defineAgent, o as defineTool, p as getSdkConfig, q as isAgentDefinition, r as isToolDefinition, s as loadConfig, t as loadedTrayConfigSchema, u as projectIdSchema, v as requireWorkspaceId, w as resolveConfigFile, x as resolveConfigOverride, y as workspaceIdSchema } from './define-agent-C0qXub7P.js';
3
+ import { F as FunctionHandler, D as DefineFunctionOptions, a as DefineScheduleConfig, S as ScheduleDefinition, P as PlatformContext } from './types-CVW_-1wh.js';
4
+ export { A as AgentApprovalDecision, b as AgentCallOptions, c as AgentClient, d as AgentPendingApproval, e as AgentResult, f as AgentSession, g as AgentSessionPage, h as AgentSessionPageOptions, i as AgentSessionSummary, j as AgentSessionsList, k as AgentStreamResult, l as AiEmbeddingModelInstance, m as AiImageModelInstance, n as AiLanguageModelInstance, o as AiSpeechModelInstance, p as AiTranscriptionModelInstance, B as BrokerAuthedClient, q as BrokerCallOptions, r as BrokerCallResult, C as CallFunctionAsync, s as DbCallParameters, t as DbClient, u as FileSystemClient, H as HelixAI, v as HelixAIProvider, w as HelixAgent, x as HelixCost, y as HelixResultMeta, z as HttpClient, K as KeyValueStore, L as Logger, E as S3SignOptions, G as S3SignResult, I as ScheduleContext, J as ScheduleHandler, M as ScheduleTrigger, N as SqlBuilder, T as TrayContext, U as UnvalidatedInput } from './types-CVW_-1wh.js';
5
+ import { T as TrayConfig, L as LoadedTrayConfig, W as WatchErrorPhase } from './define-agent-DXV_nHvs.js';
6
+ export { A as AGENT_DEFINITION_KIND, a as AI_SERVICES, b as AgentDefinition, c as AgentDefinitionConfig, d as AgentSessionsConfig, e as AiProviderEntry, f as AiService, C as ConfigFileOptions, D as DefineToolConfig, H as HELIX_CONFIG_ENV, g as HelixTool, h as HelixToolLike, P as ProvisionedTrayConfig, S as SdkRuntimeConfig, i as TOOL_DEFINITION_KIND, U as UnprovisionedTrayConfig, j as WORKSPACE_ID_REQUIRED_CODE, k as WorkspaceIdRequiredError, l as agentSessionsSchema, m as aiProviderEntrySchema, n as defineAgent, o as defineTool, p as getSdkConfig, q as isAgentDefinition, r as isToolDefinition, s as loadConfig, t as loadedTrayConfigSchema, u as projectIdSchema, v as requireWorkspaceId, w as resolveConfigFile, x as resolveConfigOverride, y as workspaceIdSchema } from './define-agent-DXV_nHvs.js';
7
7
  export { a as REGION_VALUES, R as Region, r as regionSchema } from './region-schema-COfWyGI9.js';
8
8
  import { StopCondition, ToolSet } from 'ai';
9
9
  export { EmbedManyResult, EmbedResult, EmbeddingModel, FinishReason, GenerateImageResult, GenerateObjectResult, GenerateTextResult, ImageModel, LanguageModel, LanguageModelUsage, ModelMessage, Output, PrepareStepFunction, SpeechModel, SpeechResult, StopCondition, StreamObjectResult, StreamTextResult, TextStreamPart, ToolChoice, ToolSet, TranscriptionModel, TranscriptionResult, UIMessage, convertToModelMessages, cosineSimilarity, dynamicTool, hasToolCall, jsonSchema, smoothStream, stepCountIs, tool, zodSchema } from 'ai';
package/dist/index.js CHANGED
@@ -1,4 +1,4 @@
1
- import{A as le,B as fe,C as pe,D as ge,E as me,F as he,G as ye,H as x,I as k,J as V,K as z,L as y,M as Ce,N as ve,O as B,P as Se,Q as we,R as Ee,Y as _e,Z as xe,_ as ke,ba as Te,ca as G,da as be,ea as Ie,f as A,fa as Re,g as _,ga as Ae,h as P,i as h,j as H,k as F,l as D,m as O,n as ae,o as j,p as M,q,r as N,s as Z,w as K,x as $,y as ue,z as ce}from"./chunk-D44IVAUR.js";import{a as L,b as de}from"./chunk-WUCX7RZO.js";import{d as E,r as W,s as U}from"./chunk-3T2WZMJJ.js";import{randomUUID as We}from"crypto";import{SpanStatusCode as ee,SpanKind as Ue}from"@opentelemetry/api";import{defineEventHandler as qe,getMethod as Ne,getRequestURL as Ze,getHeaders as re,getHeader as te}from"h3";import{readBody as Pe,getQuery as He,getRouterParams as Fe}from"h3";async function J(e,t){let r=await De(e),n=He(e),o=Fe(e)??{},s={...n,...r,...o};return t?Oe(s,t):s}async function De(e){try{let t=await Pe(e);return t&&typeof t=="object"?t:(t!=null&&t!==""&&console.warn("[helix-sdk] Request body present but not a JSON object \u2014 ignored"),{})}catch(t){if(t instanceof Error&&"statusCode"in t&&t.statusCode===400){let n=new Error("Malformed request body");throw n.statusCode=400,n.data={message:"Request body is not valid JSON"},n}let r=e.method?.toUpperCase();if(r==="GET"||r==="HEAD"||r==="DELETE")return{};throw t}}function Oe(e,t){let r=t.safeParse(e);if(!r.success){let n=new Error("Input validation failed");throw n.statusCode=400,n.data=r.error.flatten(),n}return r.data}var C=class extends Error{statusCode;constructor(t,r){super(r),this.statusCode=t,this.name="HttpError"}};function Q(e){return t=>{e.node.res.statusCode=t}}function X(){return(e,t)=>{throw new C(e,t)}}function Y(e,t){let{statusCode:r,message:n}=Le(t.detail);return e.node.res.statusCode=r,{error:n,statusCode:r}}function Le(e){switch(e.kind){case"unknown_alias":return{statusCode:400,message:"Unknown authentication alias"};case"input_validation_failed":return{statusCode:400,message:"Input validation failed"};case"output_validation_failed":return{statusCode:500,message:"Internal server error"};case"config_load_failed":return{statusCode:500,message:"Configuration error"};case"broker_error":return{statusCode:502,message:"Broker error"};case"unsupported_body_type":return{statusCode:400,message:"Unsupported request body type"};case"unsupported_scheme":return{statusCode:400,message:"Unsupported URL scheme"};case"missing_execution_credentials":return{statusCode:401,message:"Missing execution credentials"};case"missing_tray_token":return{statusCode:500,message:"Missing Tray token"};case"db_call_failed":return{statusCode:502,message:e.message};case"db_query_failed":return{statusCode:502,message:`Database query failed: ${e.message}`};case"db_invalid_parameters":return{statusCode:400,message:e.message};case"kv_key_invalid":return{statusCode:400,message:e.message};case"kv_value_invalid":return{statusCode:400,message:e.message};case"kv_value_too_large":return{statusCode:400,message:e.message};case"kv_ttl_invalid":return{statusCode:400,message:e.message};case"kv_not_available":return{statusCode:501,message:"Key-value store is not available in this environment"};case"kv_call_failed":return{statusCode:502,message:"Key-value store request failed"};case"kv_requires_provisioning":return{statusCode:500,message:"Internal server error"};case"files_path_invalid":return{statusCode:400,message:e.message};case"files_value_invalid":return{statusCode:400,message:e.message};case"files_value_too_large":return{statusCode:400,message:e.message};case"files_not_available":return{statusCode:501,message:"File storage is not available in this environment"};case"files_call_failed":return{statusCode:502,message:"File storage request failed"};case"files_requires_provisioning":return{statusCode:500,message:"Internal server error"};case"call_function_path_invalid":return{statusCode:400,message:e.message};case"call_function_call_failed":return{statusCode:502,message:"Async function call failed"};case"call_function_requires_provisioning":return{statusCode:500,message:"Internal server error"};case"call_function_not_available":return{statusCode:501,message:"callFunctionAsync is not available in this environment"};case"call_function_missing_execution_jwt":return{statusCode:401,message:"Missing execution credentials"};case"ai_unsupported_service":case"ai_model_id_required":case"ai_model_instance_required":case"ai_provider_not_configured":case"ai_foreign_model_rejected":case"agent_sessions_failed":return{statusCode:500,message:e.kind==="ai_unsupported_service"?`AI service not supported for alias "${e.alias}"`:"Internal server error"};default:return{statusCode:500,message:`Unhandled error kind: ${e.kind}`}}}var je=["authorization","x-tray-token","set-cookie","x-kong-request-id","traceparent","x-real-ip","cookie"];function Me(e){return e.toLowerCase().includes("tray_lid")}function T(e){let t={};for(let[r,n]of Object.entries(e))if(!je.includes(r.toLowerCase())){if(r.toLowerCase()==="cookie"&&n){let o=n.split(";").map(s=>s.trim()).filter(s=>{let d=s.split("=")[0].trim();return!Me(d)}).join("; ");o&&(t[r]=o);continue}t[r]=n}return t}function Ke(e,t){let{inputSchema:r,outputSchema:n}=Je(t),o=e;return qe(async s=>{let d=E(),{executionId:a,userId:i,deploymentId:f}=Qe(d,s),c=d.mode==="lambda"?d.parentExecutionId??null:null,p=Date.now(),v=new Date().toISOString(),l=Ne(s),u=Ze(s).pathname,g=M(),m=j(),se=`${l} ${u}`;H();let R={hasDb:!1,hasExternal:!1,hasAuth:!1,hasAi:!1,hasError:!1};return $e(()=>_.run(R,()=>A.run(a,async()=>{let S=await Ve(s,r);if(!S.ok)return{response:S.response,errored:!1,errorMessage:null};let ie=Ye(s,S.input,g,m,l,u,a,f,i,c);return ze(o,ie,n,s,m,a,f,{method:l,path:u,rawInput:S.input})})),{executionId:a,deploymentId:f,routeOrJob:se,startedAt:v,startMs:p,userId:i,flags:R})})}async function $e(e,t){let r=!1,n=null;try{let o=await e();return r=o.errored,n=o.errorMessage,o.response}finally{O({...t,errored:r,errorMessage:n}),await F()}}async function Ve(e,t){try{return{ok:!0,input:await J(e,t)}}catch(r){let n=Xe(e,r);if(n)return{ok:!1,response:n};throw r}}async function ze(e,t,r,n,o,s,d,a){return D.startActiveSpan("function",{root:!0,kind:Ue.SERVER,attributes:{method:a.method,route:a.path,executionId:s,...d?{deploymentId:d}:{}}},async i=>{t.traceId=i.spanContext().traceId;let f=T(re(n));h(i,"input",a.rawInput),h(i,"request",{method:a.method,path:a.path,headers:f,body:a.rawInput});let c=!1,p=null,v,l;try{let u=await L.run(t,()=>e(t));if(v=u,u==null)n.node.res.statusCode=204,l="";else if(u instanceof Response)l=u;else if(r){let g=r.safeParse(u);if(!g.success){let m=Object.keys(g.error.flatten().fieldErrors);throw o.error("Output validation failed",{fields:m,executionId:s}),W.outputValidationFailed(m)}l=g.data}else l=u}catch(u){c=!0,p=u instanceof Error?u.message:String(u),P("hasError"),l=Be(u,n,o,s)}finally{Ge(i,n,{errored:c,errorMessage:p,handlerResult:v,response:l})}return{response:l,errored:c,errorMessage:p}})}function Be(e,t,r,n){if(e instanceof C)return t.node.res.statusCode=e.statusCode,{error:e.message,statusCode:e.statusCode};if(U(e))return Y(t,e);r.error("Unhandled error in handler",{error:e instanceof Error?e.message:String(e),executionId:n}),t.node.res.statusCode=500;let o=process.env.NODE_ENV==="development";return{error:o&&e instanceof Error?e.message:"Internal server error",statusCode:500,...o&&e instanceof Error&&e.stack?{stack:e.stack}:{}}}function Ge(e,t,r){e.setAttribute("statusCode",t.node.res.statusCode),!r.errored&&r.handlerResult!==void 0&&h(e,"output",r.handlerResult),h(e,"response",r.response);let n=_.getStore();e.setAttribute("hasAuth",n?.hasAuth??!1),e.setAttribute("hasAi",n?.hasAi??!1),e.setAttribute("hasExternal",n?.hasExternal??!1),e.setAttribute("hasDb",n?.hasDb??!1),e.setAttribute("status",r.errored?"error":"success");let o=r.errored||(n?.hasError??!1);e.setStatus({code:o?ee.ERROR:ee.OK,...r.errorMessage?{message:r.errorMessage}:{}}),e.end()}function Je(e){if(!e)return{inputSchema:void 0,outputSchema:void 0};if(e instanceof Object&&"_def"in e)return{inputSchema:e,outputSchema:void 0};if(typeof e=="object"&&("input"in e||"output"in e)){let t=e;return{inputSchema:t.input,outputSchema:t.output}}return{inputSchema:e,outputSchema:void 0}}function Qe(e,t){let r=e.mode==="lambda",n=(r?e.executionId:te(t,"x-tray-execution-id"))??We(),o=(r?e.userId:te(t,"x-tray-user-id"))??null,s=r?e.deploymentId??null:null;return{executionId:n,userId:o,deploymentId:s}}function Xe(e,t){if(!(t instanceof Error)||!("statusCode"in t)||!("data"in t))return null;let r=t.statusCode,n=t.data;e.node.res.statusCode=r;let o=n&&typeof n=="object"&&"fieldErrors"in n?n.fieldErrors:void 0;return{error:"Input validation failed",statusCode:r,...o?{fields:Object.keys(o)}:{}}}function Ye(e,t,r,n,o,s,d,a,i,f){return{input:t,method:o,path:s,headers:T(re(e)),http:q(),db:c=>N(c),kv:()=>Z(),files:()=>K(),callFunctionAsync:$(),ai:B(),agent:c=>G(c),log:n,config:r,status:Q(e),error:X(),state:{},request:e,executionId:d,deploymentId:a,userId:i,parentExecutionId:f,identity:i!==null?{user:{id:i}}:null,traceId:""}}function et(e){return e}import{existsSync as tt,watch as rt,writeSync as nt}from"fs";import{basename as ot,dirname as st,join as it,resolve as w}from"path";import{watchConfig as at}from"c12";function dt(e,t){let r=e instanceof Error?e.message:String(e);nt(2,`[helix-watch] ${t.phase} error: ${r}
1
+ import{A as le,B as fe,C as pe,D as ge,E as me,F as he,G as ye,H as x,I as k,J as V,K as z,L as y,M as Ce,N as ve,O as B,P as Se,Q as we,R as Ee,Y as _e,Z as xe,_ as ke,ba as Te,ca as G,da as be,ea as Ie,f as A,fa as Re,g as _,ga as Ae,h as P,i as h,j as H,k as F,l as D,m as O,n as ae,o as j,p as M,q,r as N,s as Z,w as K,x as $,y as ue,z as ce}from"./chunk-3WKD2ENP.js";import{a as L,b as de}from"./chunk-WUCX7RZO.js";import{d as E,r as W,s as U}from"./chunk-JKFMPHA4.js";import{randomUUID as We}from"crypto";import{SpanStatusCode as ee,SpanKind as Ue}from"@opentelemetry/api";import{defineEventHandler as qe,getMethod as Ne,getRequestURL as Ze,getHeaders as re,getHeader as te}from"h3";import{readBody as Pe,getQuery as He,getRouterParams as Fe}from"h3";async function J(e,t){let r=await De(e),n=He(e),o=Fe(e)??{},s={...n,...r,...o};return t?Oe(s,t):s}async function De(e){try{let t=await Pe(e);return t&&typeof t=="object"?t:(t!=null&&t!==""&&console.warn("[helix-sdk] Request body present but not a JSON object \u2014 ignored"),{})}catch(t){if(t instanceof Error&&"statusCode"in t&&t.statusCode===400){let n=new Error("Malformed request body");throw n.statusCode=400,n.data={message:"Request body is not valid JSON"},n}let r=e.method?.toUpperCase();if(r==="GET"||r==="HEAD"||r==="DELETE")return{};throw t}}function Oe(e,t){let r=t.safeParse(e);if(!r.success){let n=new Error("Input validation failed");throw n.statusCode=400,n.data=r.error.flatten(),n}return r.data}var C=class extends Error{statusCode;constructor(t,r){super(r),this.statusCode=t,this.name="HttpError"}};function Q(e){return t=>{e.node.res.statusCode=t}}function X(){return(e,t)=>{throw new C(e,t)}}function Y(e,t){let{statusCode:r,message:n}=Le(t.detail);return e.node.res.statusCode=r,{error:n,statusCode:r}}function Le(e){switch(e.kind){case"unknown_alias":return{statusCode:400,message:"Unknown authentication alias"};case"input_validation_failed":return{statusCode:400,message:"Input validation failed"};case"output_validation_failed":return{statusCode:500,message:"Internal server error"};case"config_load_failed":return{statusCode:500,message:"Configuration error"};case"broker_error":return{statusCode:502,message:"Broker error"};case"unsupported_body_type":return{statusCode:400,message:"Unsupported request body type"};case"unsupported_scheme":return{statusCode:400,message:"Unsupported URL scheme"};case"missing_execution_credentials":return{statusCode:401,message:"Missing execution credentials"};case"missing_tray_token":return{statusCode:500,message:"Missing Tray token"};case"db_call_failed":return{statusCode:502,message:e.message};case"db_query_failed":return{statusCode:502,message:`Database query failed: ${e.message}`};case"db_invalid_parameters":return{statusCode:400,message:e.message};case"kv_key_invalid":return{statusCode:400,message:e.message};case"kv_value_invalid":return{statusCode:400,message:e.message};case"kv_value_too_large":return{statusCode:400,message:e.message};case"kv_ttl_invalid":return{statusCode:400,message:e.message};case"kv_not_available":return{statusCode:501,message:"Key-value store is not available in this environment"};case"kv_call_failed":return{statusCode:502,message:"Key-value store request failed"};case"kv_requires_provisioning":return{statusCode:500,message:"Internal server error"};case"files_path_invalid":return{statusCode:400,message:e.message};case"files_value_invalid":return{statusCode:400,message:e.message};case"files_value_too_large":return{statusCode:400,message:e.message};case"files_not_available":return{statusCode:501,message:"File storage is not available in this environment"};case"files_call_failed":return{statusCode:502,message:"File storage request failed"};case"files_requires_provisioning":return{statusCode:500,message:"Internal server error"};case"call_function_path_invalid":return{statusCode:400,message:e.message};case"call_function_call_failed":return{statusCode:502,message:"Async function call failed"};case"call_function_requires_provisioning":return{statusCode:500,message:"Internal server error"};case"call_function_not_available":return{statusCode:501,message:"callFunctionAsync is not available in this environment"};case"call_function_missing_execution_jwt":return{statusCode:401,message:"Missing execution credentials"};case"ai_unsupported_service":case"ai_provider_misconfigured":case"ai_model_id_required":case"ai_model_instance_required":case"ai_provider_not_configured":case"ai_foreign_model_rejected":case"agent_sessions_failed":return{statusCode:500,message:e.kind==="ai_unsupported_service"?`AI service not supported for alias "${e.alias}"`:e.kind==="ai_provider_misconfigured"?`AI provider misconfigured for alias "${e.alias}"`:"Internal server error"};default:return{statusCode:500,message:`Unhandled error kind: ${e.kind}`}}}var je=["authorization","x-tray-token","set-cookie","x-kong-request-id","traceparent","x-real-ip","cookie"];function Me(e){return e.toLowerCase().includes("tray_lid")}function T(e){let t={};for(let[r,n]of Object.entries(e))if(!je.includes(r.toLowerCase())){if(r.toLowerCase()==="cookie"&&n){let o=n.split(";").map(s=>s.trim()).filter(s=>{let d=s.split("=")[0].trim();return!Me(d)}).join("; ");o&&(t[r]=o);continue}t[r]=n}return t}function Ke(e,t){let{inputSchema:r,outputSchema:n}=Je(t),o=e;return qe(async s=>{let d=E(),{executionId:a,userId:i,deploymentId:f}=Qe(d,s),c=d.mode==="lambda"?d.parentExecutionId??null:null,p=Date.now(),v=new Date().toISOString(),l=Ne(s),u=Ze(s).pathname,g=M(),m=j(),se=`${l} ${u}`;H();let R={hasDb:!1,hasExternal:!1,hasAuth:!1,hasAi:!1,hasError:!1};return $e(()=>_.run(R,()=>A.run(a,async()=>{let S=await Ve(s,r);if(!S.ok)return{response:S.response,errored:!1,errorMessage:null};let ie=Ye(s,S.input,g,m,l,u,a,f,i,c);return ze(o,ie,n,s,m,a,f,{method:l,path:u,rawInput:S.input})})),{executionId:a,deploymentId:f,routeOrJob:se,startedAt:v,startMs:p,userId:i,flags:R})})}async function $e(e,t){let r=!1,n=null;try{let o=await e();return r=o.errored,n=o.errorMessage,o.response}finally{O({...t,errored:r,errorMessage:n}),await F()}}async function Ve(e,t){try{return{ok:!0,input:await J(e,t)}}catch(r){let n=Xe(e,r);if(n)return{ok:!1,response:n};throw r}}async function ze(e,t,r,n,o,s,d,a){return D.startActiveSpan("function",{root:!0,kind:Ue.SERVER,attributes:{method:a.method,route:a.path,executionId:s,...d?{deploymentId:d}:{}}},async i=>{t.traceId=i.spanContext().traceId;let f=T(re(n));h(i,"input",a.rawInput),h(i,"request",{method:a.method,path:a.path,headers:f,body:a.rawInput});let c=!1,p=null,v,l;try{let u=await L.run(t,()=>e(t));if(v=u,u==null)n.node.res.statusCode=204,l="";else if(u instanceof Response)l=u;else if(r){let g=r.safeParse(u);if(!g.success){let m=Object.keys(g.error.flatten().fieldErrors);throw o.error("Output validation failed",{fields:m,executionId:s}),W.outputValidationFailed(m)}l=g.data}else l=u}catch(u){c=!0,p=u instanceof Error?u.message:String(u),P("hasError"),l=Be(u,n,o,s)}finally{Ge(i,n,{errored:c,errorMessage:p,handlerResult:v,response:l})}return{response:l,errored:c,errorMessage:p}})}function Be(e,t,r,n){if(e instanceof C)return t.node.res.statusCode=e.statusCode,{error:e.message,statusCode:e.statusCode};if(U(e))return Y(t,e);r.error("Unhandled error in handler",{error:e instanceof Error?e.message:String(e),executionId:n}),t.node.res.statusCode=500;let o=process.env.NODE_ENV==="development";return{error:o&&e instanceof Error?e.message:"Internal server error",statusCode:500,...o&&e instanceof Error&&e.stack?{stack:e.stack}:{}}}function Ge(e,t,r){e.setAttribute("statusCode",t.node.res.statusCode),!r.errored&&r.handlerResult!==void 0&&h(e,"output",r.handlerResult),h(e,"response",r.response);let n=_.getStore();e.setAttribute("hasAuth",n?.hasAuth??!1),e.setAttribute("hasAi",n?.hasAi??!1),e.setAttribute("hasExternal",n?.hasExternal??!1),e.setAttribute("hasDb",n?.hasDb??!1),e.setAttribute("status",r.errored?"error":"success");let o=r.errored||(n?.hasError??!1);e.setStatus({code:o?ee.ERROR:ee.OK,...r.errorMessage?{message:r.errorMessage}:{}}),e.end()}function Je(e){if(!e)return{inputSchema:void 0,outputSchema:void 0};if(e instanceof Object&&"_def"in e)return{inputSchema:e,outputSchema:void 0};if(typeof e=="object"&&("input"in e||"output"in e)){let t=e;return{inputSchema:t.input,outputSchema:t.output}}return{inputSchema:e,outputSchema:void 0}}function Qe(e,t){let r=e.mode==="lambda",n=(r?e.executionId:te(t,"x-tray-execution-id"))??We(),o=(r?e.userId:te(t,"x-tray-user-id"))??null,s=r?e.deploymentId??null:null;return{executionId:n,userId:o,deploymentId:s}}function Xe(e,t){if(!(t instanceof Error)||!("statusCode"in t)||!("data"in t))return null;let r=t.statusCode,n=t.data;e.node.res.statusCode=r;let o=n&&typeof n=="object"&&"fieldErrors"in n?n.fieldErrors:void 0;return{error:"Input validation failed",statusCode:r,...o?{fields:Object.keys(o)}:{}}}function Ye(e,t,r,n,o,s,d,a,i,f){return{input:t,method:o,path:s,headers:T(re(e)),http:q(),db:c=>N(c),kv:()=>Z(),files:()=>K(),callFunctionAsync:$(),ai:B(),agent:c=>G(c),log:n,config:r,status:Q(e),error:X(),state:{},request:e,executionId:d,deploymentId:a,userId:i,parentExecutionId:f,identity:i!==null?{user:{id:i}}:null,traceId:""}}function et(e){return e}import{existsSync as tt,watch as rt,writeSync as nt}from"fs";import{basename as ot,dirname as st,join as it,resolve as w}from"path";import{watchConfig as at}from"c12";function dt(e,t){let r=e instanceof Error?e.message:String(e);nt(2,`[helix-watch] ${t.phase} error: ${r}
2
2
  `)}function b(){return{kind:"unprovisioned",name:"",authentications:{},config:{},region:"us1"}}var ut=/^(?:helix|tray)\.config\.(?:m|c)?[jt]s$/,ne=new Set;function oe(e,t){return k(e,{configFile:t})!==void 0}async function ct(e,t,r){if(oe(e.cwd,t))try{return{current:await y(e.cwd,{configFile:t}),initialLoadSucceeded:!0}}catch(n){return r(n,{phase:"reload"}),{current:b(),initialLoadSucceeded:!1}}if(e.watch){let n=t!==void 0?w(e.cwd,t):w(e.cwd);ne.has(n)||(process.stderr.write(t!==void 0?`warning: config file ${w(e.cwd,t)} not found; tray running with default config
3
3
  `:`warning: no helix.config.ts found at ${e.cwd}; tray running with default config \u2014 create one via \`helix init\`
4
4
  `),ne.add(n))}return{current:b(),initialLoadSucceeded:!1}}var I=class{constructor(t,r,n,o){this.cwd=t;this.configFile=r;this.onError=n;this.emit=o}cwd;configFile;onError;emit;stopped=!1;directoryWatcher=null;c12Unwatch=null;c12AttachPromise=null;updateChain=Promise.resolve();start(t){t?this.attachC12Watcher():this.attachCreationWatcher()}watcherReady(){return this.c12AttachPromise===null?Promise.resolve():this.c12AttachPromise.catch(()=>{})}async stop(){this.stopped=!0,this.directoryWatcher&&(this.directoryWatcher.close(),this.directoryWatcher=null),this.c12AttachPromise&&await this.c12AttachPromise.catch(t=>this.onError(t,{phase:"attach"})),this.c12Unwatch&&(await this.c12Unwatch(),this.c12Unwatch=null)}attachC12Watcher(){this.c12AttachPromise===null&&(this.c12AttachPromise=at({...V(this.cwd,{configFile:this.configFile}),onUpdate:({newConfig:t})=>{this.stopped||(this.updateChain=this.updateChain.then(async()=>{if(this.stopped)return;let r;try{r=z(t.config,this.cwd)}catch(n){this.onError(n,{phase:"validation"});return}try{this.emit(r)}catch(n){this.onError(n,{phase:"reload"})}}))}}).then(async t=>{if(this.stopped){t.unwatch();return}this.c12Unwatch=t.unwatch;let{watch:r}=await import("chokidar"),n=r(this.cwd,{persistent:!1,depth:0});try{await new Promise((o,s)=>{n.once("ready",o),n.once("error",s)})}finally{await n.close()}}).catch(t=>{this.onError(t,{phase:"attach"})}))}attachCreationWatcher(){let t=this.configFile!==void 0?w(this.cwd,this.configFile):void 0,r=t!==void 0?st(t):this.cwd;try{this.directoryWatcher=rt(r,{persistent:!1},(n,o)=>{if(this.stopped||!o)return;let s=o.toString();if(t!==void 0){if(s!==ot(t))return}else if(!ut.test(s))return;tt(it(r,s))&&(this.updateChain=this.updateChain.then(async()=>{if(this.stopped)return;let d;try{d=await y(this.cwd,{configFile:this.configFile})}catch(i){this.onError(i,{phase:"reload"});return}if(this.stopped)return;this.emit(d);let a=this.directoryWatcher;a&&(this.directoryWatcher=null,a.close()),this.attachC12Watcher()}))}),this.directoryWatcher.on("error",n=>{this.onError(n,{phase:"attach"})})}catch(n){this.onError(n,{phase:"attach"})}}};async function lt(e){let t=e.onError??dt,r=new Set,n=x(e.configFile),o=await ct(e,n,t),s=o.current;function d(i){s=i;for(let f of[...r])try{f(i)}catch(c){t(c,{phase:"reload"})}}let a=new I(e.cwd,n,t,d);return e.watch&&a.start(o.initialLoadSucceeded),{get(){return s},async reload(){if(!oe(e.cwd,n)){let i=b();return d(i),i}try{let i=await y(e.cwd,{configFile:n});return d(i),i}catch(i){return t(i,{phase:"reload"}),s}},subscribe(i){return r.add(i),()=>{r.delete(i)}},async stop(){r.clear(),await a.stop()},ready(){return a.watcherReady()}}}import{tool as sr,dynamicTool as ir,jsonSchema as ar,zodSchema as dr,stepCountIs as ur,hasToolCall as cr,convertToModelMessages as lr,cosineSimilarity as fr,smoothStream as pr,Output as gr}from"ai";export{_e as AGENT_DEFINITION_KIND,ge as AI_SERVICES,ye as HELIX_CONFIG_ENV,gr as Output,ue as REGION_VALUES,be as SCHEDULE_DEFINITION_KIND,Ie as ScheduleConfigError,Se as TOOL_DEFINITION_KIND,Ce as WORKSPACE_ID_REQUIRED_CODE,pe as agentSessionsSchema,me as aiProviderEntrySchema,lr as convertToModelMessages,fr as cosineSimilarity,lt as createConfigService,xe as defineAgent,et as defineConfig,Ke as defineFunction,Re as defineSchedule,we as defineTool,ir as dynamicTool,de as getContext,E as getSdkConfig,cr as hasToolCall,ke as isAgentDefinition,Ae as isScheduleDefinition,Ee as isToolDefinition,ar as jsonSchema,y as loadConfig,he as loadedTrayConfigSchema,le as projectIdSchema,ce as regionSchema,ve as requireWorkspaceId,k as resolveConfigFile,x as resolveConfigOverride,ae as runWithinAppSpan,pr as smoothStream,ur as stepCountIs,sr as tool,Te as totalToolCallsIs,fe as workspaceIdSchema,dr as zodSchema};
@@ -1,7 +1,7 @@
1
- import { L as LoadedTrayConfig, b as AgentDefinition } from '../define-agent-C0qXub7P.js';
2
- export { z as SdkConfigInput, B as setSdkConfig } from '../define-agent-C0qXub7P.js';
3
- import { j as AgentSessionsList, b as AgentCallOptions, e as AgentResult } from '../types-CRUtefiq.js';
4
- export { O as SessionExpiredError, Q as clearAgentSessions } from '../types-CRUtefiq.js';
1
+ import { L as LoadedTrayConfig, b as AgentDefinition } from '../define-agent-DXV_nHvs.js';
2
+ export { z as SdkConfigInput, B as setSdkConfig } from '../define-agent-DXV_nHvs.js';
3
+ import { j as AgentSessionsList, b as AgentCallOptions, e as AgentResult } from '../types-CVW_-1wh.js';
4
+ export { O as SessionExpiredError, Q as clearAgentSessions } from '../types-CVW_-1wh.js';
5
5
  import 'zod';
6
6
  import 'h3';
7
7
  import 'ky';
@@ -211,6 +211,11 @@ type SdkErrorDetail = {
211
211
  readonly kind: "ai_provider_not_configured";
212
212
  alias: string;
213
213
  supported: string[];
214
+ } | {
215
+ readonly kind: "ai_provider_misconfigured";
216
+ alias: string;
217
+ service: string;
218
+ message: string;
214
219
  } | {
215
220
  readonly kind: "ai_foreign_model_rejected";
216
221
  } | {
@@ -255,6 +260,7 @@ declare class SdkError extends Error {
255
260
  static aiModelIdRequired(alias: string, operation: string): SdkError;
256
261
  static aiModelInstanceRequired(modelId: string): SdkError;
257
262
  static aiProviderNotConfigured(alias: string, supported: string[]): SdkError;
263
+ static aiProviderMisconfigured(alias: string, service: string, message: string): SdkError;
258
264
  static aiForeignModelRejected(): SdkError;
259
265
  static agentSessionsFailed(message: string): SdkError;
260
266
  }
@@ -1 +1 @@
1
- import{$ as At,O as E,S as ft,T as dt,U as mt,V as gt,W as pt,X as ht,a as J,aa as St,b as V,c as q,ca as l,d as R,e as z,f as g,g as P,ga as v,h as F,i as N,j as p,k as O,l as k,m as j,o as A,p as M,q as S,r as x,s as y,t as lt,u as ct,v as ut,w as I,x as C}from"../chunk-D44IVAUR.js";import{a as h}from"../chunk-WUCX7RZO.js";import{c as G,d as D,g as Q,h as W,i as X,j as Y,k as Z,l as tt,m as et,n as rt,o as ot,p as nt,q as it,r as st,s as at}from"../chunk-3T2WZMJJ.js";import{randomUUID as xt}from"crypto";import{SpanStatusCode as H,SpanKind as yt}from"@opentelemetry/api";var i=class extends Error{constructor(t){super(`runScheduledFunction: ${t}`),this.name="ScheduleInvocationError"}};async function It(e,t){if(typeof t!="object"||t===null)throw new i("`invocation` must be an object");let{schedulePath:r}=t;if(typeof r!="string"||r.length===0)throw new i("`schedulePath` must be a non-empty string");if(typeof t.isManual!="boolean")throw new i("`isManual` must be a boolean");if(!v(e))throw new i(`default export of "${r}" is not a defineSchedule definition`);let c=L("scheduledAt",t.scheduledAt),b=L("firedAt",t.firedAt),a=D(),u=a.executionId??xt(),f=a.deploymentId??null,K=Date.now(),$=new Date().toISOString(),U=M(),_=A();p();let s={hasDb:!1,hasExternal:!1,hasAuth:!1,hasAi:!1,hasError:!1},d=!1,m=null;try{await P.run(s,()=>g.run(u,()=>k.startActiveSpan("schedule",{root:!0,kind:yt.SERVER,attributes:{method:"SCHEDULE",route:r,executionId:u,...f?{deploymentId:f}:{}}},async n=>{let B={type:"schedule",scheduledAt:c,firedAt:b,isManual:t.isManual},w={http:S(),db:o=>x(o),kv:()=>y(),files:()=>I(),callFunctionAsync:C(),ai:E(),agent:o=>l(o),log:_,config:U,state:{},executionId:u,deploymentId:f,traceId:n.spanContext().traceId,parentExecutionId:null,trigger:B};N(n,"input",{scheduledAt:t.scheduledAt,firedAt:t.firedAt,isManual:t.isManual});try{await h.run(w,()=>e.handler(w))}catch(o){throw d=!0,m=o instanceof Error?o.message:String(o),F("hasError"),o}finally{n.setAttribute("hasAuth",s.hasAuth),n.setAttribute("hasAi",s.hasAi),n.setAttribute("hasExternal",s.hasExternal),n.setAttribute("hasDb",s.hasDb),n.setAttribute("status",d?"error":"success");let o=d||s.hasError;n.setStatus({code:o?H.ERROR:H.OK,...m?{message:m}:{}}),n.end()}})))}finally{j({executionId:u,deploymentId:f,triggerType:"schedule",routeOrJob:r,startedAt:$,startMs:K,errored:d,errorMessage:m,userId:null,flags:s}),await O()}}function L(e,t){if(typeof t!="string"||t.length===0)throw new i(`\`${e}\` must be a timestamp string; got ${JSON.stringify(t)}`);let r=new Date(t);if(Number.isNaN(r.getTime()))throw new i(`\`${e}\` must be a Date-parseable timestamp; got ${JSON.stringify(t)}`);return r}function T(e,t){p();let r=R(),c=crypto.randomUUID(),b={http:S(),db:a=>x(a),kv:()=>y(),files:()=>I(),callFunctionAsync:C(),ai:E(),agent:a=>l(a),log:A(),config:r.config??{},state:{},executionId:c,deploymentId:null,traceId:"",parentExecutionId:null,userId:e.userId??null};return g.run(c,()=>h.run(b,t))}async function Ct(e,t,r={}){return T(r,()=>l(e).generate(t))}async function Et(e,t){return T({userId:t.userId},()=>l(e).sessions({...t.first!==void 0?{first:t.first}:{},...t.cursor!==void 0?{cursor:t.cursor}:{}}))}export{ft as AgentCallerError,J as CONFIG_BRIDGE_CHANNEL,V as DEV_TOKEN_BRIDGE_CHANNEL,i as ScheduleInvocationError,st as SdkError,At as SessionExpiredError,lt as assertValidPath,z as clearActiveConfig,ht as clearAgentRegistry,St as clearAgentSessions,ct as contentFilePath,R as getActiveConfig,nt as getAdditionalRegionProfiles,gt as getAgentDefinition,X as getRegionProfile,W as isKnownRegion,at as isSdkError,Et as listAgentSessionsStandalone,pt as listAgents,tt as listExposedRegionNames,Z as listRegionNames,ut as metaFilePath,et as parseExposedRegionName,Q as registerRegionProfile,Y as requireRegionProfile,it as resetRegionRegistryForTests,ot as resolveForcedRegion,Ct as runAgentStandalone,It as runScheduledFunction,q as setActiveConfig,dt as setAgentBaseDir,mt as setAgentInstructions,rt as setForcedRegion,G as setSdkConfig};
1
+ import{$ as At,O as E,S as ft,T as dt,U as mt,V as gt,W as pt,X as ht,a as J,aa as St,b as V,c as q,ca as l,d as R,e as z,f as g,g as P,ga as v,h as F,i as N,j as p,k as O,l as k,m as j,o as A,p as M,q as S,r as x,s as y,t as lt,u as ct,v as ut,w as I,x as C}from"../chunk-3WKD2ENP.js";import{a as h}from"../chunk-WUCX7RZO.js";import{c as G,d as D,g as Q,h as W,i as X,j as Y,k as Z,l as tt,m as et,n as rt,o as ot,p as nt,q as it,r as st,s as at}from"../chunk-JKFMPHA4.js";import{randomUUID as xt}from"crypto";import{SpanStatusCode as H,SpanKind as yt}from"@opentelemetry/api";var i=class extends Error{constructor(t){super(`runScheduledFunction: ${t}`),this.name="ScheduleInvocationError"}};async function It(e,t){if(typeof t!="object"||t===null)throw new i("`invocation` must be an object");let{schedulePath:r}=t;if(typeof r!="string"||r.length===0)throw new i("`schedulePath` must be a non-empty string");if(typeof t.isManual!="boolean")throw new i("`isManual` must be a boolean");if(!v(e))throw new i(`default export of "${r}" is not a defineSchedule definition`);let c=L("scheduledAt",t.scheduledAt),b=L("firedAt",t.firedAt),a=D(),u=a.executionId??xt(),f=a.deploymentId??null,K=Date.now(),$=new Date().toISOString(),U=M(),_=A();p();let s={hasDb:!1,hasExternal:!1,hasAuth:!1,hasAi:!1,hasError:!1},d=!1,m=null;try{await P.run(s,()=>g.run(u,()=>k.startActiveSpan("schedule",{root:!0,kind:yt.SERVER,attributes:{method:"SCHEDULE",route:r,executionId:u,...f?{deploymentId:f}:{}}},async n=>{let B={type:"schedule",scheduledAt:c,firedAt:b,isManual:t.isManual},w={http:S(),db:o=>x(o),kv:()=>y(),files:()=>I(),callFunctionAsync:C(),ai:E(),agent:o=>l(o),log:_,config:U,state:{},executionId:u,deploymentId:f,traceId:n.spanContext().traceId,parentExecutionId:null,trigger:B};N(n,"input",{scheduledAt:t.scheduledAt,firedAt:t.firedAt,isManual:t.isManual});try{await h.run(w,()=>e.handler(w))}catch(o){throw d=!0,m=o instanceof Error?o.message:String(o),F("hasError"),o}finally{n.setAttribute("hasAuth",s.hasAuth),n.setAttribute("hasAi",s.hasAi),n.setAttribute("hasExternal",s.hasExternal),n.setAttribute("hasDb",s.hasDb),n.setAttribute("status",d?"error":"success");let o=d||s.hasError;n.setStatus({code:o?H.ERROR:H.OK,...m?{message:m}:{}}),n.end()}})))}finally{j({executionId:u,deploymentId:f,triggerType:"schedule",routeOrJob:r,startedAt:$,startMs:K,errored:d,errorMessage:m,userId:null,flags:s}),await O()}}function L(e,t){if(typeof t!="string"||t.length===0)throw new i(`\`${e}\` must be a timestamp string; got ${JSON.stringify(t)}`);let r=new Date(t);if(Number.isNaN(r.getTime()))throw new i(`\`${e}\` must be a Date-parseable timestamp; got ${JSON.stringify(t)}`);return r}function T(e,t){p();let r=R(),c=crypto.randomUUID(),b={http:S(),db:a=>x(a),kv:()=>y(),files:()=>I(),callFunctionAsync:C(),ai:E(),agent:a=>l(a),log:A(),config:r.config??{},state:{},executionId:c,deploymentId:null,traceId:"",parentExecutionId:null,userId:e.userId??null};return g.run(c,()=>h.run(b,t))}async function Ct(e,t,r={}){return T(r,()=>l(e).generate(t))}async function Et(e,t){return T({userId:t.userId},()=>l(e).sessions({...t.first!==void 0?{first:t.first}:{},...t.cursor!==void 0?{cursor:t.cursor}:{}}))}export{ft as AgentCallerError,J as CONFIG_BRIDGE_CHANNEL,V as DEV_TOKEN_BRIDGE_CHANNEL,i as ScheduleInvocationError,st as SdkError,At as SessionExpiredError,lt as assertValidPath,z as clearActiveConfig,ht as clearAgentRegistry,St as clearAgentSessions,ct as contentFilePath,R as getActiveConfig,nt as getAdditionalRegionProfiles,gt as getAgentDefinition,X as getRegionProfile,W as isKnownRegion,at as isSdkError,Et as listAgentSessionsStandalone,pt as listAgents,tt as listExposedRegionNames,Z as listRegionNames,ut as metaFilePath,et as parseExposedRegionName,Q as registerRegionProfile,Y as requireRegionProfile,it as resetRegionRegistryForTests,ot as resolveForcedRegion,Ct as runAgentStandalone,It as runScheduledFunction,q as setActiveConfig,dt as setAgentBaseDir,mt as setAgentInstructions,rt as setForcedRegion,G as setSdkConfig};
@@ -1,4 +1,4 @@
1
- import { P as PlatformContext } from '../types-CRUtefiq.js';
1
+ import { P as PlatformContext } from '../types-CVW_-1wh.js';
2
2
  import 'h3';
3
3
  import 'ky';
4
4
  import 'zod';
@@ -392,8 +392,6 @@ type AgentStreamResult = StreamTextReturn & {
392
392
  };
393
393
  /**
394
394
  * What `ctx.agent(name)` returns.
395
- *
396
- * @beta Agents and tools are in beta and may change in a future release.
397
395
  */
398
396
  interface HelixAgent {
399
397
  /** The AI SDK loop + session handling. */
@@ -422,8 +420,6 @@ interface HelixAgent {
422
420
  }
423
421
  /**
424
422
  * `ctx.agent` — look up a registered agent by name.
425
- *
426
- * @beta Agents and tools are in beta and may change in a future release.
427
423
  */
428
424
  type AgentClient = (name: string) => HelixAgent;
429
425
 
@@ -517,8 +513,6 @@ interface ContextCore {
517
513
  ai: HelixAI;
518
514
  /**
519
515
  * Agent client (helix-spec 14): `ctx.agent(name).generate()/.stream()`.
520
- *
521
- * @beta Agents and tools are in beta and may change in a future release.
522
516
  */
523
517
  agent: AgentClient;
524
518
  log: Logger;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@trayai/helix-sdk",
3
- "version": "1.7.0",
3
+ "version": "1.13.0",
4
4
  "description": "Helix SDK runtime — defineFunction, ctx, defineConfig, authed HTTP",
5
5
  "license": "Apache-2.0",
6
6
  "author": "trayio",
@@ -41,13 +41,14 @@
41
41
  "node": ">=24.19.0"
42
42
  },
43
43
  "dependencies": {
44
- "@ai-sdk/anthropic": "^4.0.49",
45
- "@ai-sdk/cohere": "^4.0.37",
46
- "@ai-sdk/google": "^4.0.63",
47
- "@ai-sdk/mistral": "^4.0.39",
48
- "@ai-sdk/openai": "^4.0.58",
49
- "@ai-sdk/openai-compatible": "^3.0.43",
50
- "@ai-sdk/provider": "^4.0.10",
44
+ "@ai-sdk/amazon-bedrock": "^5.0.101",
45
+ "@ai-sdk/anthropic": "^4.0.68",
46
+ "@ai-sdk/cohere": "^4.0.52",
47
+ "@ai-sdk/google": "^4.0.85",
48
+ "@ai-sdk/mistral": "^4.0.54",
49
+ "@ai-sdk/openai": "^4.0.81",
50
+ "@ai-sdk/openai-compatible": "^3.0.59",
51
+ "@ai-sdk/provider": "^4.0.19",
51
52
  "@opentelemetry/api": "^1.9.1",
52
53
  "@opentelemetry/api-logs": "0.220.0",
53
54
  "@opentelemetry/core": ">=2.8.0 <3",
@@ -57,7 +58,7 @@
57
58
  "@opentelemetry/sdk-logs": "0.220.0",
58
59
  "@opentelemetry/sdk-trace-base": "^2.11.0",
59
60
  "@opentelemetry/sdk-trace-node": "^2.11.0",
60
- "ai": "^7.0.92",
61
+ "ai": "^7.0.122",
61
62
  "c12": "^3.3.4",
62
63
  "chokidar": "^5.0.0",
63
64
  "h3": "^1.15.11",