apps 0.0.1-beta.0 → 0.0.1-beta.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (114) hide show
  1. package/README.md +97 -4
  2. package/framework-reference.json +1 -1
  3. package/js/browser-XIPJGLH2.js +65 -0
  4. package/js/{chunk-SBKHUC5L.js → chunk-4LPG6RCH.js} +2 -2
  5. package/js/chunk-5MQZEB6Y.js +172 -0
  6. package/js/{chunk-7JXHF5IF.js → chunk-BMOIAIVR.js} +1 -1
  7. package/js/chunk-CZ7CSFO4.js +39 -0
  8. package/js/chunk-D47C7KG5.js +172 -0
  9. package/js/{chunk-YDR4CPJA.js → chunk-EVJUVWN2.js} +8 -8
  10. package/js/chunk-FDNTX5QJ.js +78 -0
  11. package/js/{chunk-2OTCEKL2.js → chunk-FW5HBOIK.js} +2352 -1493
  12. package/js/{chunk-EP6AEUZO.js → chunk-FZJOYIZO.js} +1 -1
  13. package/js/{chunk-VFUZI3NY.js → chunk-HDJH3RPR.js} +4 -4
  14. package/js/{chunk-WIDTG42X.js → chunk-HDTGZWP2.js} +79 -26
  15. package/js/{chunk-Q2FD5IBM.js → chunk-J7O55ZV7.js} +298 -37
  16. package/js/{chunk-X3YBZCJW.js → chunk-JN55AYQH.js} +8 -41
  17. package/js/chunk-LGIYBDWA.js +85 -0
  18. package/js/{chunk-D6BKYP2L.js → chunk-M6ZRRIBI.js} +4 -4
  19. package/js/{chunk-HP7E42X6.js → chunk-MYYEW3RA.js} +767 -249
  20. package/js/{chunk-3ANFZFCV.js → chunk-OHRT55C4.js} +15 -15
  21. package/js/{chunk-R6JMJSVT.js → chunk-PLCMJREA.js} +2 -2
  22. package/js/{chunk-C24KEZXR.js → chunk-PYUYJRSK.js} +36 -2
  23. package/js/{chunk-W7Q5EOTS.js → chunk-QKHR7BMF.js} +32 -32
  24. package/js/{chunk-KWTCHVLT.js → chunk-RN2MXB4R.js} +47 -51
  25. package/js/{chunk-36DNRFZQ.js → chunk-SATWJKN6.js} +1 -1
  26. package/js/chunk-SWPD52J7.js +35 -0
  27. package/js/{chunk-BKVL7XAJ.js → chunk-TE4KO4HI.js} +1 -1
  28. package/js/chunk-UVL56Z6E.js +6641 -0
  29. package/js/chunk-W7D7WVSY.js +18 -0
  30. package/js/{chunk-BPEFS4YF.js → chunk-WFSQXYUT.js} +109 -17
  31. package/js/chunk-YEJOQEII.js +104 -0
  32. package/js/{chunk-LOKGDT6B.js → chunk-Z5NMEGJN.js} +5 -4
  33. package/js/{chunk-OWD2YICM.js → chunk-ZCAMUXSG.js} +116 -87
  34. package/js/chunk-ZJWDMTE3.js +63 -0
  35. package/js/client.js +11 -11
  36. package/js/contracts.js +88 -25
  37. package/js/effect.js +21 -15
  38. package/js/es-APDZKREY.js +40968 -0
  39. package/js/graphql.js +224 -121
  40. package/js/host.js +76 -19
  41. package/js/index.js +193 -51
  42. package/js/mcp/effect.js +25 -17
  43. package/js/mcp/stdio.js +23 -17
  44. package/js/mcp.js +110 -24
  45. package/js/openapi.js +3045 -105
  46. package/js/operations/approval.js +1 -1
  47. package/js/react.js +4 -4
  48. package/js/skills/effect.js +11 -0
  49. package/js/skills.js +894 -0
  50. package/js/storage/facet.js +7 -7
  51. package/js/ui/auth/contracts.js +6 -6
  52. package/js/ui/auth.js +8 -8
  53. package/js/ui/contracts.js +5 -5
  54. package/js/ui/serving.js +12 -12
  55. package/package.json +9 -1
  56. package/runtime.json +1 -1
  57. package/types/app-cache/src/contracts/cache.d.ts +119 -0
  58. package/types/app-cache/src/index.d.ts +93 -0
  59. package/types/apps/src/contracts/api-response-error.d.ts +43 -0
  60. package/types/apps/src/contracts/app.d.ts +11 -0
  61. package/types/apps/src/contracts/cache.d.ts +44 -0
  62. package/types/apps/src/contracts/dynamic-skills.d.ts +10 -0
  63. package/types/apps/src/contracts/dynamic-tools.d.ts +13 -0
  64. package/types/apps/src/contracts/graphql.d.ts +18 -1
  65. package/types/apps/src/contracts/host.d.ts +54 -525
  66. package/types/apps/src/contracts/mcp.d.ts +3 -1
  67. package/types/apps/src/contracts/openapi-compile.d.ts +11 -0
  68. package/types/apps/src/contracts/openapi-document.d.ts +53 -0
  69. package/types/apps/src/contracts/openapi.d.ts +156 -30
  70. package/types/apps/src/contracts/protocol-version.d.ts +6 -0
  71. package/types/apps/src/contracts/protocols/1.d.ts +1575 -0
  72. package/types/apps/src/contracts/provider-error.d.ts +15 -0
  73. package/types/apps/src/contracts/provider.d.ts +18 -1
  74. package/types/apps/src/contracts/skills.d.ts +122 -0
  75. package/types/apps/src/contracts/swagger-client.d.ts +29 -0
  76. package/types/apps/src/graphql.d.ts +6 -6
  77. package/types/apps/src/host.d.ts +1 -0
  78. package/types/apps/src/implementation/account-operations.d.ts +122 -3
  79. package/types/apps/src/implementation/app.d.ts +1 -1
  80. package/types/apps/src/implementation/cache-session.d.ts +7 -0
  81. package/types/apps/src/implementation/cache.d.ts +8 -0
  82. package/types/apps/src/implementation/catalog-cache.d.ts +29 -0
  83. package/types/apps/src/implementation/dynamic-skills.d.ts +7 -0
  84. package/types/apps/src/implementation/dynamic-tools.d.ts +8 -0
  85. package/types/apps/src/implementation/elicitation.d.ts +12 -12
  86. package/types/apps/src/implementation/git.d.ts +25 -0
  87. package/types/apps/src/implementation/graphql-catalog.d.ts +10 -0
  88. package/types/apps/src/implementation/graphql.d.ts +81 -3
  89. package/types/apps/src/implementation/inflate.d.ts +16 -0
  90. package/types/apps/src/implementation/input-problems.d.ts +3 -0
  91. package/types/apps/src/implementation/mcp-call.d.ts +3 -2
  92. package/types/apps/src/implementation/mcp-catalog.d.ts +12 -0
  93. package/types/apps/src/implementation/mcp-client.d.ts +9 -8
  94. package/types/apps/src/implementation/mcp-stdio.d.ts +1 -1
  95. package/types/apps/src/implementation/mcp-tools.d.ts +6 -3
  96. package/types/apps/src/implementation/mcp.d.ts +39 -2
  97. package/types/apps/src/implementation/openapi-compile.d.ts +119 -0
  98. package/types/apps/src/implementation/openapi-document.d.ts +51 -0
  99. package/types/apps/src/implementation/openapi-names.d.ts +18 -0
  100. package/types/apps/src/implementation/openapi-request.d.ts +10 -4
  101. package/types/apps/src/implementation/openapi-source.d.ts +40 -0
  102. package/types/apps/src/implementation/openapi.d.ts +39 -3
  103. package/types/apps/src/implementation/provider-error.d.ts +10 -0
  104. package/types/apps/src/implementation/schema.d.ts +6 -5
  105. package/types/apps/src/implementation/skill-files.d.ts +10 -0
  106. package/types/apps/src/implementation/skills.d.ts +43 -0
  107. package/types/apps/src/implementation/swagger-client.d.ts +28 -0
  108. package/types/apps/src/index.d.ts +7 -0
  109. package/types/apps/src/mcp.d.ts +5 -5
  110. package/types/apps/src/openapi.d.ts +3 -1
  111. package/types/apps/src/skills.d.ts +75 -0
  112. package/types/telemetry/src/config.d.ts +2 -0
  113. package/js/chunk-22WRQZT7.js +0 -389
  114. package/js/chunk-MLKGABMK.js +0 -9
@@ -1,16 +1,29 @@
1
+ import {
2
+ makeCache
3
+ } from "./chunk-D47C7KG5.js";
4
+ import {
5
+ folderSkillsEffect
6
+ } from "./chunk-FDNTX5QJ.js";
1
7
  import {
2
8
  authorDatabase,
3
9
  isApp,
4
10
  toEffectApp,
5
- toPromise,
6
11
  unavailableStorage
7
- } from "./chunk-X3YBZCJW.js";
12
+ } from "./chunk-JN55AYQH.js";
13
+ import {
14
+ fromPromise,
15
+ nativeOperation,
16
+ toPromise
17
+ } from "./chunk-PYUYJRSK.js";
8
18
  import {
9
- nativeOperation
10
- } from "./chunk-C24KEZXR.js";
19
+ parseProviderError
20
+ } from "./chunk-ZJWDMTE3.js";
11
21
  import {
12
22
  DeclaredProvider,
13
23
  DeclaredRequirements,
24
+ ElicitationFailed,
25
+ ElicitationResponse,
26
+ FormElicitation,
14
27
  HostAccountsInvalid,
15
28
  HostDeclarationInvalid,
16
29
  HostError,
@@ -26,22 +39,19 @@ import {
26
39
  HostToolNotFound,
27
40
  HostToolPolicyFailed,
28
41
  HostedTool,
42
+ HostedToolSummary,
29
43
  HostedWebhook,
44
+ HostedWorkflow,
45
+ InvocationDeadline,
30
46
  ManualWebhookSetup,
47
+ ManyAccounts,
48
+ McpError,
49
+ NonRetryableError,
31
50
  OperationToolPrefixes,
32
51
  ResolvedAccounts,
33
52
  ToolResultObservation,
34
53
  TrustedToolApproval,
35
54
  WebhookResponseData,
36
- defaultWebhookTransportLimits
37
- } from "./chunk-22WRQZT7.js";
38
- import {
39
- ElicitationFailed,
40
- ElicitationResponse,
41
- FormElicitation,
42
- HostedWorkflow,
43
- ManyAccounts,
44
- NonRetryableError,
45
55
  WorkflowDuration,
46
56
  WorkflowFailure,
47
57
  WorkflowName,
@@ -49,30 +59,46 @@ import {
49
59
  WorkflowStepOptions,
50
60
  WorkflowValue,
51
61
  approvalElicitation,
62
+ defaultWebhookTransportLimits,
63
+ maxInputProblems,
52
64
  workflowDurationMillis
53
- } from "./chunk-HP7E42X6.js";
65
+ } from "./chunk-MYYEW3RA.js";
66
+ import {
67
+ CacheError
68
+ } from "./chunk-LGIYBDWA.js";
69
+ import {
70
+ AppSkills,
71
+ SkillFile,
72
+ SkillLoadFailed
73
+ } from "./chunk-YEJOQEII.js";
74
+ import {
75
+ OpenapiResponseError
76
+ } from "./chunk-SWPD52J7.js";
54
77
  import {
55
78
  captureTelemetry,
56
79
  invocationFetch
57
- } from "./chunk-OWD2YICM.js";
80
+ } from "./chunk-ZCAMUXSG.js";
58
81
  import {
82
+ decoderOf,
59
83
  importedJsonSchema,
60
84
  jsonSchemaDecoder
61
- } from "./chunk-BPEFS4YF.js";
85
+ } from "./chunk-WFSQXYUT.js";
62
86
  import {
63
87
  JsonObject,
64
88
  JsonValue
65
- } from "./chunk-36DNRFZQ.js";
89
+ } from "./chunk-SATWJKN6.js";
66
90
  import {
67
91
  Cause_exports,
92
+ Clock_exports,
68
93
  Effect_exports,
69
94
  Encoding_exports,
70
95
  Match_exports,
71
96
  Option_exports,
72
97
  Redacted_exports,
98
+ SchemaIssue_exports,
73
99
  Schema_exports,
74
100
  Stream_exports
75
- } from "./chunk-2OTCEKL2.js";
101
+ } from "./chunk-FW5HBOIK.js";
76
102
 
77
103
  // src/implementation/elicitation.ts
78
104
  var prepareElicitation = (input) => Effect_exports.gen(function* () {
@@ -156,7 +182,11 @@ var makeWorkflowContext = (execution, definition, fresh, signal) => Effect_expor
156
182
  Effect_exports.timeout(timeout),
157
183
  Effect_exports.catchTag(
158
184
  "TimeoutError",
159
- () => Effect_exports.fail(new WorkflowFailure({ reason: "execution", retryable: true }))
185
+ () => (
186
+ // Both the capability deadline and the native engine deadline describe
187
+ // the same cancellation, regardless of which timer fires first.
188
+ Effect_exports.fail(new WorkflowFailure({ reason: "engine", retryable: true }))
189
+ )
160
190
  )
161
191
  );
162
192
  };
@@ -253,6 +283,23 @@ var makeWorkflowContext = (execution, definition, fresh, signal) => Effect_expor
253
283
  return { runId: execution.runId, step };
254
284
  });
255
285
 
286
+ // src/implementation/input-problems.ts
287
+ var leafHook = (issue) => SchemaIssue_exports.hasInput(issue) ? "Invalid value" : SchemaIssue_exports.defaultLeafHook(issue);
288
+ var checkHook = (issue) => SchemaIssue_exports.hasInput(issue) || SchemaIssue_exports.hasInput(issue.issue) ? SchemaIssue_exports.defaultCheckHook(issue) ?? "Invalid value" : SchemaIssue_exports.defaultCheckHook(issue);
289
+ var format = SchemaIssue_exports.makeFormatterStandardSchemaV1({ leafHook, checkHook });
290
+ var segment = (key) => typeof key === "number" ? `[${key}]` : typeof key === "string" && /^[A-Za-z_$][\w$-]{0,63}$/.test(key) ? `.${key}` : "[key]";
291
+ var inputInvalid = (error) => {
292
+ if (!Schema_exports.isSchemaError(error)) return new HostInputInvalid();
293
+ const problems = format(error.issue).issues.slice(0, maxInputProblems).map(({ path, message }) => {
294
+ const location = (path ?? []).map((key) => segment(typeof key === "object" ? key.key : key));
295
+ return `${location.length === 0 ? "input" : `input${location.join("")}`}: ${message}`.slice(
296
+ 0,
297
+ 512
298
+ );
299
+ });
300
+ return new HostInputInvalid({ problems });
301
+ };
302
+
256
303
  // src/implementation/webhooks.ts
257
304
  var safe = (work, error) => Effect_exports.suspend(work).pipe(
258
305
  Effect_exports.catchCause(
@@ -407,6 +454,74 @@ var dispatchWebhook = (definition, command, context, accounts) => Effect_exports
407
454
  );
408
455
  });
409
456
 
457
+ // src/implementation/cache.ts
458
+ var unavailableCache = {
459
+ transport: () => Effect_exports.fail(new CacheError({ reason: "unavailable" })),
460
+ background: () => Effect_exports.die(new Error("Cache background runner is unavailable"))
461
+ };
462
+ var authorCache = (host, accounts, signal, deadline) => {
463
+ const scoped = (scope, callerSignal = signal) => {
464
+ const cache = makeCache(host.transport, host.background, scope, deadline);
465
+ const load = (method, options) => cache[method]({
466
+ key: options.key,
467
+ schema: decoderOf(options.schema),
468
+ freshFor: options.freshFor,
469
+ ...options.staleFor === void 0 ? {} : { staleFor: options.staleFor },
470
+ load: Effect_exports.acquireUseRelease(
471
+ Effect_exports.sync(() => new AbortController()),
472
+ (controller) => invocationFetch(controller.signal).pipe(
473
+ Effect_exports.flatMap(
474
+ (fetch) => fromPromise(options.load)({
475
+ fetch,
476
+ signal: controller.signal,
477
+ cache: scoped(scope, controller.signal)
478
+ })
479
+ )
480
+ ),
481
+ (controller) => Effect_exports.sync(() => controller.abort())
482
+ )
483
+ });
484
+ return {
485
+ get: toPromise((options) => load("get", options), callerSignal),
486
+ revalidate: toPromise(
487
+ (options) => load("revalidate", options),
488
+ callerSignal
489
+ ),
490
+ read: toPromise(
491
+ (key, schema) => cache.read([key]).pipe(
492
+ Effect_exports.flatMap((entries) => {
493
+ const entry = entries[0];
494
+ return entry === void 0 || entry === null ? Effect_exports.succeed(void 0) : Schema_exports.decodeUnknownEffect(decoderOf(schema))(entry.value);
495
+ })
496
+ ),
497
+ callerSignal
498
+ ),
499
+ readMany: toPromise(
500
+ (keys, schema) => cache.read(keys).pipe(
501
+ Effect_exports.flatMap(
502
+ (entries) => Effect_exports.forEach(
503
+ entries,
504
+ (entry) => entry === null ? Effect_exports.succeed(void 0) : Schema_exports.decodeUnknownEffect(decoderOf(schema))(entry.value)
505
+ )
506
+ )
507
+ ),
508
+ callerSignal
509
+ ),
510
+ write: toPromise(cache.write, callerSignal),
511
+ invalidate: toPromise(cache.invalidate, callerSignal),
512
+ forAccount: (account) => {
513
+ const bound = Object.values(accounts).flatMap((value) => Array.isArray(value) ? value : [value]).find((value) => value.id === account.id);
514
+ if (bound === void 0) throw new CacheError({ reason: "invalid" });
515
+ return scoped(
516
+ { account: bound.id, method: bound.method, generation: bound.generation },
517
+ callerSignal
518
+ );
519
+ }
520
+ };
521
+ };
522
+ return scoped("shared");
523
+ };
524
+
410
525
  // src/implementation/host.ts
411
526
  function safe2(work, failure) {
412
527
  return Effect_exports.suspend(work).pipe(
@@ -415,6 +530,18 @@ function safe2(work, failure) {
415
530
  )
416
531
  );
417
532
  }
533
+ var evaluationSafe = (work) => work.pipe(
534
+ Effect_exports.catchCause((cause) => {
535
+ if (Cause_exports.hasInterrupts(cause)) return Effect_exports.interrupt;
536
+ const error = Cause_exports.squash(cause);
537
+ const provider = parseProviderError(error);
538
+ const skills = parseSkillLoadFailed(error);
539
+ const mcp = parseMcpError(error);
540
+ return Effect_exports.fail(
541
+ Option_exports.isSome(provider) ? provider.value : Option_exports.isSome(skills) ? skills.value : Option_exports.isSome(mcp) ? mcp.value : new HostEvaluationFailed()
542
+ );
543
+ })
544
+ );
418
545
  function jsonSchema(decoder) {
419
546
  const imported = importedJsonSchema(decoder);
420
547
  if (imported !== void 0) return Schema_exports.decodeUnknownEffect(JsonObject)(imported);
@@ -468,6 +595,7 @@ function requirements(slots, database) {
468
595
  }
469
596
  return yield* Schema_exports.decodeUnknownEffect(DeclaredRequirements)({
470
597
  accounts: Object.fromEntries(accounts),
598
+ capabilities: { skills: true, toolIndex: true, skillSources: true, scheduledTools: true },
471
599
  ...database === void 0 ? {} : { database }
472
600
  }).pipe(Effect_exports.mapError(() => new HostDeclarationInvalid()));
473
601
  });
@@ -541,6 +669,26 @@ function dispatch(app, request, context, signal) {
541
669
  (controller) => Effect_exports.sync(() => controller.abort())
542
670
  );
543
671
  const invocationSignal = AbortSignal.any([signal, lifetime.signal]);
672
+ const deadline = context.deadline === void 0 ? void 0 : yield* safe2(
673
+ () => Schema_exports.decodeUnknownEffect(InvocationDeadline)(context.deadline),
674
+ new HostInputInvalid()
675
+ );
676
+ const withinDeadline = (work) => Effect_exports.gen(function* () {
677
+ if (deadline === void 0) return yield* work;
678
+ const remaining = deadline - (yield* Clock_exports.currentTimeMillis);
679
+ if (remaining <= 0)
680
+ return yield* new WorkflowFailure({ reason: "engine", retryable: true });
681
+ const result = yield* work.pipe(
682
+ Effect_exports.timeout(remaining),
683
+ Effect_exports.catchTag(
684
+ "TimeoutError",
685
+ () => Effect_exports.fail(new WorkflowFailure({ reason: "engine", retryable: true }))
686
+ )
687
+ );
688
+ if ((yield* Clock_exports.currentTimeMillis) >= deadline)
689
+ return yield* new WorkflowFailure({ reason: "engine", retryable: true });
690
+ return result;
691
+ });
544
692
  let running;
545
693
  let transactionOpen = false;
546
694
  const delivery = (request2, signal2) => Effect_exports.suspend(
@@ -572,7 +720,17 @@ function dispatch(app, request, context, signal) {
572
720
  get: workflowControls.get,
573
721
  list: workflowControls.list
574
722
  };
723
+ const files = yield* Schema_exports.decodeUnknownEffect(Schema_exports.Array(SkillFile))(
724
+ context.files ?? []
725
+ ).pipe(Effect_exports.mapError(() => new HostDeclarationInvalid()));
575
726
  const bound = {
727
+ cache: authorCache(
728
+ context.cache ?? unavailableCache,
729
+ Redacted_exports.value(context.accounts),
730
+ invocationSignal,
731
+ deadline
732
+ ),
733
+ files,
576
734
  ...yield* bindAccounts(native.accounts, declared, context).pipe(
577
735
  Effect_exports.withSpan("app.accounts.bind")
578
736
  ),
@@ -581,10 +739,22 @@ function dispatch(app, request, context, signal) {
581
739
  fetch: yield* invocationFetch(invocationSignal),
582
740
  elicit: makeElicit(delivery, invocationSignal)
583
741
  };
584
- const definition = yield* safe2(
585
- () => native.evaluate(bound).pipe(Effect_exports.withSpan("app.evaluate")),
586
- new HostEvaluationFailed()
742
+ const definition = yield* evaluationSafe(native.evaluate(bound)).pipe(
743
+ Effect_exports.withSpan("app.evaluate")
587
744
  );
745
+ if (request.operation === "skills") {
746
+ const declared2 = definition.skills ?? (yield* folderSkillsEffect({ files }).pipe(
747
+ Effect_exports.mapError(() => new HostDeclarationInvalid())
748
+ ));
749
+ const source2 = definition.dynamicSkills;
750
+ const dynamic = source2 === void 0 ? [] : yield* evaluationSafe(Effect_exports.suspend(source2.list)).pipe(
751
+ Effect_exports.withSpan("app.skills.load")
752
+ );
753
+ const skills = yield* Schema_exports.decodeUnknownEffect(AppSkills)([...declared2, ...dynamic]).pipe(
754
+ Effect_exports.mapError(() => new HostDeclarationInvalid())
755
+ );
756
+ return request.sources === true ? { skills, dynamic: source2 !== void 0 } : skills;
757
+ }
588
758
  if (request.operation === "workflows") {
589
759
  return yield* Effect_exports.forEach(
590
760
  Object.entries(definition.workflows ?? {}),
@@ -628,6 +798,12 @@ function dispatch(app, request, context, signal) {
628
798
  );
629
799
  return {
630
800
  ...accounts,
801
+ cache: authorCache(
802
+ context.cache ?? unavailableCache,
803
+ Redacted_exports.value(current.accounts),
804
+ signal2
805
+ ),
806
+ files,
631
807
  fetch: yield* invocationFetch(signal2),
632
808
  signal: signal2,
633
809
  runId: execution.runId,
@@ -649,24 +825,34 @@ function dispatch(app, request, context, signal) {
649
825
  );
650
826
  }
651
827
  if (request.operation === "inspect") {
828
+ const summary = request.detail === "summary";
829
+ const wanted = request.tools === void 0 ? void 0 : new Set(request.tools);
652
830
  const metadata = [];
653
831
  for (const [prefix, readOnly, catalog2] of [
654
832
  [OperationToolPrefixes.query, true, definition.queries],
655
833
  [OperationToolPrefixes.mutate, false, definition.mutations]
656
834
  ]) {
657
835
  for (const [name2, operation] of Object.entries(catalog2 ?? {})) {
836
+ if (wanted !== void 0 && !wanted.has(`${prefix}${name2}`)) continue;
837
+ const schedules = Object.entries(definition.schedules ?? {}).filter(([, schedule]) => schedule.tool === `${prefix}${name2}`).map(([name3, { tool: _tool, ...schedule }]) => ({ name: name3, ...schedule }));
838
+ if (request.scheduled === true && schedules.length === 0) continue;
658
839
  metadata.push(
659
840
  yield* safe2(
660
841
  () => Effect_exports.gen(function* () {
661
- return yield* Schema_exports.decodeUnknownEffect(HostedTool)({
842
+ const fields = {
662
843
  name: `${prefix}${name2}`,
663
- schedules: Object.entries(definition.schedules ?? {}).filter(([, schedule]) => schedule.tool === `${prefix}${name2}`).map(([name3, { tool: _tool, ...schedule }]) => ({ name: name3, ...schedule })),
844
+ schedules,
664
845
  description: operation.description ?? `${readOnly ? "Query" : "Mutate"} ${name2}`,
665
846
  ...operation.title === void 0 ? {} : { title: operation.title },
847
+ readOnly,
848
+ annotations: { ...operation.annotations, readOnlyHint: readOnly }
849
+ };
850
+ if (summary)
851
+ return yield* Schema_exports.decodeUnknownEffect(HostedToolSummary)(fields);
852
+ return yield* Schema_exports.decodeUnknownEffect(HostedTool)({
853
+ ...fields,
666
854
  inputSchema: yield* jsonSchema(operation.input),
667
855
  ...operation.output === void 0 ? operation.outputSchema === void 0 ? {} : { outputSchema: operation.outputSchema } : { outputSchema: yield* jsonSchema(operation.output) },
668
- readOnly,
669
- annotations: { ...operation.annotations, readOnlyHint: readOnly },
670
856
  ...operation._meta === void 0 ? {} : { _meta: operation._meta }
671
857
  });
672
858
  }),
@@ -675,6 +861,43 @@ function dispatch(app, request, context, signal) {
675
861
  );
676
862
  }
677
863
  }
864
+ const dynamic = request.scheduled === true ? void 0 : definition.dynamicTools;
865
+ if (dynamic !== void 0 && (wanted === void 0 || metadata.length < wanted.size)) {
866
+ const declared2 = new Set(metadata.map((tool2) => tool2.name));
867
+ const discover = () => {
868
+ if (summary && dynamic.summaries !== void 0) return dynamic.summaries();
869
+ if (wanted !== void 0 && dynamic.describe !== void 0) {
870
+ const describe = dynamic.describe;
871
+ return Effect_exports.forEach(
872
+ [...wanted].filter((name2) => !declared2.has(name2)),
873
+ (name2) => describe(name2),
874
+ { concurrency: "unbounded" }
875
+ ).pipe(Effect_exports.map((tools) => tools.filter((tool2) => tool2 !== void 0)));
876
+ }
877
+ return dynamic.list();
878
+ };
879
+ const discovered = yield* evaluationSafe(discover()).pipe(
880
+ Effect_exports.flatMap(
881
+ (value) => safe2(
882
+ () => summary ? Schema_exports.decodeUnknownEffect(Schema_exports.Array(HostedToolSummary))(value) : Schema_exports.decodeUnknownEffect(Schema_exports.Array(HostedTool))(value),
883
+ new HostDeclarationInvalid()
884
+ )
885
+ )
886
+ );
887
+ const names = new Set(declared2);
888
+ for (const tool2 of discovered) {
889
+ const readOnly = tool2.name.startsWith(OperationToolPrefixes.query);
890
+ if (!readOnly && !tool2.name.startsWith(OperationToolPrefixes.mutate) || tool2.name === OperationToolPrefixes.query || tool2.name === OperationToolPrefixes.mutate || names.has(tool2.name))
891
+ return yield* new HostDeclarationInvalid();
892
+ names.add(tool2.name);
893
+ if (wanted !== void 0 && !wanted.has(tool2.name)) continue;
894
+ metadata.push({
895
+ ...tool2,
896
+ readOnly,
897
+ annotations: { ...tool2.annotations, readOnlyHint: readOnly }
898
+ });
899
+ }
900
+ }
678
901
  return metadata;
679
902
  }
680
903
  if (request.operation === "webhook-complete" || request.operation === "webhook-validate" || request.operation === "webhooks" || request.operation === "webhook-register" || request.operation === "webhook-handle" || request.operation === "webhook-unregister") {
@@ -682,6 +905,8 @@ function dispatch(app, request, context, signal) {
682
905
  definition,
683
906
  request,
684
907
  {
908
+ files,
909
+ cache: bound.cache,
685
910
  accounts: bound.accounts,
686
911
  workflows: workflowControls,
687
912
  signal: bound.signal,
@@ -708,12 +933,20 @@ function dispatch(app, request, context, signal) {
708
933
  const name = request.operation === "call" ? request.tool.slice(OperationToolPrefixes[kind].length) : request.name;
709
934
  const toolName = `${OperationToolPrefixes[kind]}${name}`;
710
935
  const catalog = kind === "query" ? definition.queries : definition.mutations;
711
- const tool = catalog !== void 0 && Object.hasOwn(catalog, name) ? catalog[name] : void 0;
936
+ const declaredTool = catalog !== void 0 && Object.hasOwn(catalog, name) ? catalog[name] : void 0;
937
+ const source = definition.dynamicTools;
938
+ const resolvedTool = source === void 0 || declaredTool !== void 0 ? void 0 : yield* evaluationSafe(source.resolve(toolName));
939
+ const tool = declaredTool ?? resolvedTool;
940
+ if (tool !== void 0 && tool.kind !== (kind === "query" ? "query" : "mutation"))
941
+ return yield* new HostDeclarationInvalid();
712
942
  if (tool === void 0)
713
943
  return yield* request.operation === "call" ? new HostToolNotFound() : new HostOperationNotFound();
714
- const input = yield* safe2(
715
- () => Schema_exports.decodeUnknownEffect(tool.input)(request.input),
716
- new HostInputInvalid()
944
+ const input = yield* Effect_exports.suspend(
945
+ () => Schema_exports.decodeUnknownEffect(tool.input)(request.input)
946
+ ).pipe(
947
+ Effect_exports.catchCause(
948
+ (cause) => Cause_exports.hasInterrupts(cause) ? Effect_exports.interrupt : Effect_exports.fail(inputInvalid(Cause_exports.squash(cause)))
949
+ )
717
950
  );
718
951
  if (context.approval !== void 0) {
719
952
  const approved = yield* safe2(
@@ -779,9 +1012,6 @@ function dispatch(app, request, context, signal) {
779
1012
  input
780
1013
  );
781
1014
  }).pipe(
782
- Effect_exports.withSpan("app.operation.execute", {
783
- attributes: { "executor.tool.name": toolName, "executor.operation": kind }
784
- }),
785
1015
  Effect_exports.ensuring(
786
1016
  Effect_exports.sync(() => {
787
1017
  running = void 0;
@@ -789,10 +1019,21 @@ function dispatch(app, request, context, signal) {
789
1019
  ),
790
1020
  Effect_exports.catchCause((cause) => {
791
1021
  if (Cause_exports.hasInterrupts(cause)) return Effect_exports.interrupt;
792
- const failure = Schema_exports.decodeUnknownOption(ElicitationFailed)(Cause_exports.squash(cause));
1022
+ const error = Cause_exports.squash(cause);
1023
+ const provider = parseProviderError(error);
1024
+ const response = Schema_exports.decodeUnknownOption(OpenapiResponseError)(error);
1025
+ const failure = Schema_exports.decodeUnknownOption(ElicitationFailed)(error);
793
1026
  return Effect_exports.fail(
794
- Option_exports.isSome(failure) ? failure.value : new HostOperationFailed()
1027
+ Option_exports.isSome(provider) ? provider.value : Option_exports.isSome(response) ? new OpenapiResponseError({
1028
+ code: response.value.code,
1029
+ status: response.value.status,
1030
+ message: response.value.message,
1031
+ ...response.value.recovery === void 0 ? {} : { recovery: response.value.recovery }
1032
+ }) : Option_exports.isSome(failure) ? failure.value : new HostOperationFailed()
795
1033
  );
1034
+ }),
1035
+ Effect_exports.withSpan("app.operation.execute", {
1036
+ attributes: { "executor.tool.name": toolName, "executor.operation": kind }
796
1037
  })
797
1038
  );
798
1039
  const outputSchema = tool.output;
@@ -810,11 +1051,13 @@ function dispatch(app, request, context, signal) {
810
1051
  new HostInputInvalid()
811
1052
  );
812
1053
  if (replay !== void 0 && kind !== "mutate") return yield* new HostInputInvalid();
813
- if (native.database === void 0) return yield* execute();
1054
+ if (native.database === void 0) return yield* withinDeadline(execute());
814
1055
  const storage = context.storage ?? unavailableStorage;
815
1056
  return yield* storage[kind === "query" ? "read" : "mutate"](
816
1057
  native.database.schema,
817
- (db) => replay === void 0 ? execute(db) : db.once(replay.key, replay.fingerprint, () => execute(db))
1058
+ (db) => withinDeadline(
1059
+ replay === void 0 ? execute(db) : db.once(replay.key, replay.fingerprint, () => execute(db))
1060
+ )
818
1061
  ).pipe(
819
1062
  Effect_exports.catchTags({
820
1063
  AppDatabaseError: () => Effect_exports.fail(new HostOperationFailed()),
@@ -825,8 +1068,26 @@ function dispatch(app, request, context, signal) {
825
1068
  })
826
1069
  );
827
1070
  }
1071
+ var parseSkillLoadFailed = (error) => Schema_exports.decodeUnknownOption(SkillLoadFailed)(error).pipe(
1072
+ Option_exports.map(
1073
+ ({ reason, message, status }) => new SkillLoadFailed({
1074
+ reason,
1075
+ ...message ? { message } : {},
1076
+ ...status === void 0 ? {} : { status }
1077
+ })
1078
+ )
1079
+ );
1080
+ var parseMcpError = (error) => Schema_exports.decodeUnknownOption(McpError)(error).pipe(
1081
+ Option_exports.map(
1082
+ ({ phase, reason, status }) => new McpError({ phase, reason, ...status === void 0 ? {} : { status } })
1083
+ )
1084
+ );
828
1085
  var errorStatus = Match_exports.type().pipe(
829
1086
  Match_exports.tagsExhaustive({
1087
+ ProviderError: () => 502,
1088
+ McpError: () => 502,
1089
+ SkillLoadFailed: () => 502,
1090
+ OpenapiResponseError: () => 502,
830
1091
  WorkflowFailure: () => 422,
831
1092
  HostRequestInvalid: () => 400,
832
1093
  HostAccountsInvalid: () => 422,
@@ -1,60 +1,29 @@
1
1
  import {
2
2
  parseDatabaseSchema,
3
3
  promiseTable
4
- } from "./chunk-R6JMJSVT.js";
4
+ } from "./chunk-PLCMJREA.js";
5
5
  import {
6
+ fromPromise,
6
7
  nativeOperation
7
- } from "./chunk-C24KEZXR.js";
8
+ } from "./chunk-PYUYJRSK.js";
8
9
  import {
9
10
  ScheduleTiming
10
- } from "./chunk-HP7E42X6.js";
11
+ } from "./chunk-MYYEW3RA.js";
11
12
  import {
12
13
  decoderOf,
13
14
  isSchema,
14
15
  storageFieldOf
15
- } from "./chunk-BPEFS4YF.js";
16
+ } from "./chunk-WFSQXYUT.js";
16
17
  import {
17
18
  AppStorageUnavailable
18
- } from "./chunk-EP6AEUZO.js";
19
+ } from "./chunk-FZJOYIZO.js";
19
20
  import {
20
21
  JsonValue
21
- } from "./chunk-36DNRFZQ.js";
22
+ } from "./chunk-SATWJKN6.js";
22
23
  import {
23
24
  Effect_exports,
24
25
  Schema_exports
25
- } from "./chunk-2OTCEKL2.js";
26
-
27
- // src/implementation/authoring.ts
28
- var NativeCallback = /* @__PURE__ */ Symbol("apps.NativeCallback");
29
- var fromPromise = (callback) => (...args) => {
30
- if (NativeCallback in callback) {
31
- const native = callback[NativeCallback];
32
- return native(...args);
33
- }
34
- return Effect_exports.tryPromise({ try: () => callback(...args), catch: (error) => error });
35
- };
36
- var toPromise = (operation, signal) => {
37
- const native = (...args) => Effect_exports.suspend(() => {
38
- if (signal === void 0) return operation(...args);
39
- if (signal.aborted) return Effect_exports.interrupt;
40
- const cancelled = Effect_exports.callback((resume) => {
41
- if (signal.aborted) {
42
- resume(Effect_exports.interrupt);
43
- return;
44
- }
45
- const abort = () => resume(Effect_exports.interrupt);
46
- signal.addEventListener("abort", abort, { once: true });
47
- return Effect_exports.sync(() => signal.removeEventListener("abort", abort));
48
- });
49
- return Effect_exports.raceFirst(
50
- cancelled,
51
- Effect_exports.suspend(() => operation(...args))
52
- );
53
- });
54
- return Object.assign((...args) => Effect_exports.runPromise(native(...args)), {
55
- [NativeCallback]: native
56
- });
57
- };
26
+ } from "./chunk-FW5HBOIK.js";
58
27
 
59
28
  // src/implementation/workflows.ts
60
29
  var NativeWorkflow = /* @__PURE__ */ Symbol("apps.Workflow");
@@ -233,8 +202,6 @@ var unavailableStorage = {
233
202
  };
234
203
 
235
204
  export {
236
- fromPromise,
237
- toPromise,
238
205
  workflow,
239
206
  isApp,
240
207
  toEffectApp,
@@ -0,0 +1,85 @@
1
+ import {
2
+ Schema_exports
3
+ } from "./chunk-FW5HBOIK.js";
4
+
5
+ // ../app-cache/src/contracts/cache.ts
6
+ var CacheError = class extends Schema_exports.TaggedError()("CacheError", {
7
+ reason: Schema_exports.Literals(["unavailable", "storage", "invalid", "capacity", "timeout"])
8
+ }) {
9
+ };
10
+ var cacheLimits = {
11
+ keyBytes: 8192,
12
+ entryBytes: 2e6,
13
+ batchBytes: 8e6,
14
+ batchEntries: 128,
15
+ totalBytes: 128e6,
16
+ totalEntries: 1e5,
17
+ retentionMs: 7 * 24 * 60 * 60 * 1e3,
18
+ loadTimeoutMs: 9e4,
19
+ /**
20
+ * A loader's lease lapses this long after its host last renewed it. Hosts renew every
21
+ * `renewMs` while the invocation that claimed it runs, so a stalled or lost holder frees the
22
+ * key well inside an MCP execute budget.
23
+ */
24
+ leaseMs: 15e3,
25
+ renewMs: 5e3,
26
+ /** The longest a caller waits on another loader before loading for itself without publishing. */
27
+ waitMs: 1e4,
28
+ /** Bound for one command to a host store; a lost reply fails instead of holding its caller. */
29
+ commandTimeoutMs: 1e4
30
+ };
31
+ var Key = Schema_exports.String.check(Schema_exports.isPattern(/^[a-f0-9]{64}$/));
32
+ var Time = Schema_exports.Finite.check(Schema_exports.isGreaterThanOrEqualTo(0));
33
+ var CacheEntry = Schema_exports.Struct({
34
+ value: Schema_exports.Json,
35
+ version: Schema_exports.String,
36
+ freshUntil: Time,
37
+ staleUntil: Time
38
+ });
39
+ var CacheAcquired = Schema_exports.Struct({
40
+ entry: Schema_exports.NullOr(CacheEntry),
41
+ lease: Schema_exports.NullOr(Schema_exports.String)
42
+ });
43
+ var CacheCommand = Schema_exports.Union([
44
+ Schema_exports.Struct({ operation: Schema_exports.Literal("read"), keys: Schema_exports.Array(Key) }),
45
+ Schema_exports.Struct({
46
+ operation: Schema_exports.Literal("acquire"),
47
+ key: Key,
48
+ /** Claim even a fresh entry, as an explicit refresh does. */
49
+ refresh: Schema_exports.Boolean,
50
+ /** Claim only while the entry still has this version. Absent accepts the current one. */
51
+ version: Schema_exports.optionalKey(Schema_exports.NullOr(Schema_exports.String))
52
+ }),
53
+ Schema_exports.Struct({
54
+ operation: Schema_exports.Literal("claim"),
55
+ key: Key,
56
+ version: Schema_exports.NullOr(Schema_exports.String)
57
+ }),
58
+ Schema_exports.Struct({
59
+ operation: Schema_exports.Literal("publish"),
60
+ key: Key,
61
+ lease: Schema_exports.String,
62
+ entry: CacheEntry
63
+ }),
64
+ Schema_exports.Struct({ operation: Schema_exports.Literal("release"), key: Key, lease: Schema_exports.String }),
65
+ /** Extend a lease its holder still owns. Replies false once the lease lapsed or was replaced. */
66
+ Schema_exports.Struct({ operation: Schema_exports.Literal("renew"), key: Key, lease: Schema_exports.String }),
67
+ Schema_exports.Struct({
68
+ operation: Schema_exports.Literal("write"),
69
+ entries: Schema_exports.Array(Schema_exports.Struct({ key: Key, entry: CacheEntry }))
70
+ }),
71
+ Schema_exports.Struct({ operation: Schema_exports.Literal("invalidate"), key: Key })
72
+ ]);
73
+ var CacheReply = Schema_exports.Union([
74
+ Schema_exports.Struct({ ok: Schema_exports.Literal(true), value: Schema_exports.Json }),
75
+ Schema_exports.Struct({ ok: Schema_exports.Literal(false), error: CacheError })
76
+ ]);
77
+
78
+ export {
79
+ CacheError,
80
+ cacheLimits,
81
+ CacheEntry,
82
+ CacheAcquired,
83
+ CacheCommand,
84
+ CacheReply
85
+ };