@domino-sdk/relay 1.62.0 → 1.63.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.
Files changed (74) hide show
  1. package/CHANGELOG.md +120 -0
  2. package/dist/{accounts-CCqCKCVx.d.ts → accounts-nz3mzfRQ.d.ts} +21 -3
  3. package/dist/{attempt-captures-Cm-5G0PC.d.ts → attempt-captures-DMi8oR9T.d.ts} +1 -1
  4. package/dist/authoring.d.ts +54 -20
  5. package/dist/authoring.js +58 -24
  6. package/dist/{automatic-outcomes-pAsOyIVp.d.ts → automatic-outcomes-C_LLQU1p.d.ts} +11 -1
  7. package/dist/avatar.d.ts +1 -1
  8. package/dist/browser.d.ts +9 -9
  9. package/dist/browser.js +15 -13
  10. package/dist/capability-error-CuI_F7yM.d.ts +296 -0
  11. package/dist/{catalog--ZIlskAo.d.ts → catalog-BaTOKpNw.d.ts} +21 -10
  12. package/dist/{chunk-3PYYGFSB.js → chunk-3RFP6GT5.js} +3 -3
  13. package/dist/{chunk-HTZHBTIL.js → chunk-4GQW43UU.js} +193 -357
  14. package/dist/{chunk-D26YNACF.js → chunk-4NOFSGAL.js} +56 -56
  15. package/dist/{chunk-UW5232GG.js → chunk-5XLZ34PV.js} +5 -5
  16. package/dist/{chunk-QYPMPWVX.js → chunk-7X67QLPB.js} +43 -43
  17. package/dist/{chunk-5TEYFX6X.js → chunk-7Z4SZ6YM.js} +2 -2
  18. package/dist/{chunk-Y322OTCH.js → chunk-AQOL3SK5.js} +1 -1
  19. package/dist/{chunk-CICDIBOF.js → chunk-EHUSD3O2.js} +76 -72
  20. package/dist/chunk-FO2LCZTL.js +19 -0
  21. package/dist/{chunk-3KLC4AMA.js → chunk-FU5CGNTR.js} +135 -173
  22. package/dist/{chunk-K2KS3JLY.js → chunk-GLH6MEI2.js} +7 -2
  23. package/dist/chunk-ICXZZNPS.js +199 -0
  24. package/dist/{chunk-MK425RXJ.js → chunk-ID3BZXFZ.js} +709 -640
  25. package/dist/{chunk-UAKYDVT3.js → chunk-KP2MCX3R.js} +111 -89
  26. package/dist/{chunk-GKIFABGN.js → chunk-LZWXCBUB.js} +74 -247
  27. package/dist/{chunk-6WCIWXUV.js → chunk-MTKRIQEU.js} +2 -2
  28. package/dist/{chunk-4OC7REYX.js → chunk-MWMCQLCG.js} +3 -3
  29. package/dist/{chunk-XJFYAXET.js → chunk-N4BDKS6Y.js} +19 -19
  30. package/dist/{chunk-E6IKQHTX.js → chunk-N4LNEGQX.js} +2 -2
  31. package/dist/chunk-NQDEWJWE.js +554 -0
  32. package/dist/{chunk-GTDW453U.js → chunk-QR6HH4DI.js} +100 -114
  33. package/dist/chunk-TLSQETTY.js +41 -0
  34. package/dist/{chunk-CZFXGGEK.js → chunk-U66GUVSG.js} +2 -2
  35. package/dist/{chunk-KDR2VAJP.js → chunk-UYVJZR33.js} +2 -2
  36. package/dist/chunk-UZ765UGH.js +18 -0
  37. package/dist/{chunk-XNKSSE32.js → chunk-VWQGWGCH.js} +7 -7
  38. package/dist/{chunk-WSBYWVTZ.js → chunk-W7YSMSGC.js} +166 -158
  39. package/dist/{client-B-hbHX30.d.ts → client-DHmG7rn6.d.ts} +25 -61
  40. package/dist/{capability-error-DFMwSuSf.d.ts → dashboards-CLemT6kj.d.ts} +14 -294
  41. package/dist/{deployments-M4OHn7G3.d.ts → deployments-DTULi7dF.d.ts} +46 -3
  42. package/dist/{identity-integration-3mX6b5iH.d.ts → identity-integration-DOeNZaxF.d.ts} +32 -2
  43. package/dist/index.d.ts +10 -10
  44. package/dist/index.js +13 -11
  45. package/dist/internal.d.ts +27 -13
  46. package/dist/internal.js +41 -13
  47. package/dist/{analytics-BwAKLi7O.d.ts → limits-kNzYdZ00.d.ts} +124 -3
  48. package/dist/{offers-DhAtss4_.d.ts → offers-CYeN_I0Y.d.ts} +3 -2
  49. package/dist/portal-proxy.d.ts +19 -3
  50. package/dist/portal-proxy.js +64 -22
  51. package/dist/react/index.d.ts +21 -14
  52. package/dist/react/index.js +55 -29
  53. package/dist/{pages-B8q8Y_dQ.d.ts → reward-deliveries-drp-x1G-.d.ts} +300 -233
  54. package/dist/runtime/authoring.js +1 -1
  55. package/dist/runtime/chunks/UGDV5W4N.js +1 -0
  56. package/dist/runtime/manifest.json +3 -3
  57. package/dist/runtime/schema.js +1 -1
  58. package/dist/schema.d.ts +193 -18
  59. package/dist/schema.js +31 -26
  60. package/dist/server/index.d.ts +13 -13
  61. package/dist/server/index.js +5885 -6224
  62. package/dist/{sign-in-providers-BkjcDsFF.d.ts → sign-in-providers-B1Q9eDRm.d.ts} +7 -2
  63. package/dist/{submission-input-DHGKhXfp.d.ts → submission-input-DZCbjQUH.d.ts} +3 -2
  64. package/dist/{telegram-browser-BCE7zdOb.d.ts → telegram-browser-NL0Asmsi.d.ts} +4 -4
  65. package/dist/telegram.d.ts +8 -8
  66. package/dist/telegram.js +2 -2
  67. package/dist/testing.d.ts +228 -26
  68. package/dist/testing.js +137 -92
  69. package/dist/{tracker-data-Hb1uQnk5.d.ts → tracker-data-esm3WG8R.d.ts} +34 -8
  70. package/dist/{transport-DkhX2Cbs.d.ts → transport-Czht_irp.d.ts} +41259 -39835
  71. package/dist/{wallet-DTO7SXj7.d.ts → wallet-B7e06v4m.d.ts} +14 -4
  72. package/package.json +1 -1
  73. package/dist/chunk-UPQPUJOU.js +0 -457
  74. package/dist/runtime/chunks/Y4OAVXFR.js +0 -1
package/dist/testing.js CHANGED
@@ -1,26 +1,26 @@
1
1
  import {
2
2
  attemptCaptureSchema
3
- } from "./chunk-XNKSSE32.js";
3
+ } from "./chunk-VWQGWGCH.js";
4
4
  import {
5
5
  CapabilityError
6
- } from "./chunk-4OC7REYX.js";
6
+ } from "./chunk-MWMCQLCG.js";
7
7
  import {
8
8
  parseImageResult
9
- } from "./chunk-E6IKQHTX.js";
9
+ } from "./chunk-N4LNEGQX.js";
10
10
  import {
11
11
  imageRequestSchema,
12
12
  xConnectionSchema,
13
13
  xPostSchema,
14
14
  xProfileSchema,
15
15
  xRequestSchema
16
- } from "./chunk-QYPMPWVX.js";
16
+ } from "./chunk-7X67QLPB.js";
17
17
  import {
18
18
  isParticipantRoute
19
- } from "./chunk-CZFXGGEK.js";
19
+ } from "./chunk-U66GUVSG.js";
20
20
  import {
21
21
  participantActivitySchema,
22
22
  questExperienceSchema
23
- } from "./chunk-D26YNACF.js";
23
+ } from "./chunk-4NOFSGAL.js";
24
24
  import {
25
25
  badgeCatalogSchema,
26
26
  badgeSchema,
@@ -30,11 +30,11 @@ import {
30
30
  pointHistoryPageSchema,
31
31
  pointLedgerReferenceSchema,
32
32
  profileReferralSchema
33
- } from "./chunk-WSBYWVTZ.js";
33
+ } from "./chunk-W7YSMSGC.js";
34
34
  import {
35
35
  exchangeResultSchema,
36
36
  participantSessionSchema
37
- } from "./chunk-XJFYAXET.js";
37
+ } from "./chunk-N4BDKS6Y.js";
38
38
  import {
39
39
  contentPerformanceSnapshotSchema,
40
40
  cosmosAddressSchema,
@@ -50,9 +50,8 @@ import {
50
50
  isNftCollection,
51
51
  isSolanaProgram,
52
52
  knownResponse,
53
+ limits,
53
54
  linkedWalletSchema,
54
- maxMemberCompletions,
55
- maxWalletEventLogs,
56
55
  memberCompletionSchema,
57
56
  memberIdentitySchema,
58
57
  photoResultSchema,
@@ -82,10 +81,10 @@ import {
82
81
  walletEventsSchema,
83
82
  walletNftsSchema,
84
83
  walletTransactionsSchema
85
- } from "./chunk-MK425RXJ.js";
84
+ } from "./chunk-ID3BZXFZ.js";
86
85
  import {
87
86
  RelayErrorCode
88
- } from "./chunk-K2KS3JLY.js";
87
+ } from "./chunk-GLH6MEI2.js";
89
88
 
90
89
  // src/testing/run.ts
91
90
  import * as z3 from "zod";
@@ -175,12 +174,12 @@ function evaluationCalendar(snapshot, eligibleAt) {
175
174
 
176
175
  // src/testing/capabilities.ts
177
176
  import * as z from "zod";
178
- var trackerInput = {
177
+ var trackerInput = /* @__PURE__ */ (() => ({
179
178
  reference: identifier,
180
179
  query: trackerQuerySchema,
181
180
  asOf: z.number().int().nonnegative().safe()
182
- };
183
- var capabilityRequestSchemas = {
181
+ }))();
182
+ var capabilityRequestSchemas = /* @__PURE__ */ (() => ({
184
183
  "wallet-balance": z.strictObject({
185
184
  kind: z.literal("wallet-balance"),
186
185
  chain: z.union([
@@ -223,22 +222,22 @@ var capabilityRequestSchemas = {
223
222
  "member-identities": z.strictObject({
224
223
  kind: z.literal("member-identities")
225
224
  })
226
- };
227
- var telegramRequestSchema = z.strictObject({
225
+ }))();
226
+ var telegramRequestSchema = /* @__PURE__ */ (() => z.strictObject({
228
227
  kind: z.literal("telegram"),
229
228
  input: z.union([telegramMemberInputSchema, telegramConnectionInputSchema])
230
- });
231
- var walletNftsRequestSchema = z.strictObject({
229
+ }))();
230
+ var walletNftsRequestSchema = /* @__PURE__ */ (() => z.strictObject({
232
231
  kind: z.literal("wallet-nfts"),
233
232
  collection: z.string().max(200).refine(isNftCollection),
234
233
  address: z.string().min(1).max(100).nullable()
235
- });
236
- var walletEventConditionSchema = z.union([
234
+ }))();
235
+ var walletEventConditionSchema = /* @__PURE__ */ (() => z.union([
237
236
  z.string().min(1).max(200),
238
237
  z.boolean(),
239
238
  z.strictObject({ gte: z.string().regex(/^-?(0|[1-9][0-9]{0,77})$/) })
240
- ]);
241
- var walletEventsRequestSchema = z.strictObject({
239
+ ]))();
240
+ var walletEventsRequestSchema = /* @__PURE__ */ (() => z.strictObject({
242
241
  kind: z.literal("wallet-events"),
243
242
  event: z.string().max(1e3).refine(isContractEvent),
244
243
  account: z.string().min(1).max(100),
@@ -246,17 +245,17 @@ var walletEventsRequestSchema = z.strictObject({
246
245
  afterActivation: z.boolean(),
247
246
  where: z.record(z.string().min(1).max(100), walletEventConditionSchema).refine((where) => Object.keys(where).length <= 10).nullable(),
248
247
  address: z.string().min(1).max(100).nullable(),
249
- newest: z.number().int().min(1).max(maxWalletEventLogs).optional()
250
- });
251
- var walletTransactionsRequestSchema = z.strictObject({
248
+ newest: z.number().int().min(1).max(limits.walletEventLogs).optional()
249
+ }))();
250
+ var walletTransactionsRequestSchema = /* @__PURE__ */ (() => z.strictObject({
252
251
  kind: z.literal("wallet-transactions"),
253
252
  program: z.string().max(44).refine(isSolanaProgram),
254
253
  since: z.number().int().nonnegative().safe(),
255
254
  afterActivation: z.boolean(),
256
255
  mint: solanaAddressSchema.nullable(),
257
256
  address: z.string().min(1).max(100).nullable()
258
- });
259
- var walletCallRequestSchema = z.strictObject({
257
+ }))();
258
+ var walletCallRequestSchema = /* @__PURE__ */ (() => z.strictObject({
260
259
  kind: z.literal("wallet-call"),
261
260
  call: z.string().max(400).refine(isContractCall),
262
261
  args: z.array(
@@ -271,14 +270,14 @@ var walletCallRequestSchema = z.strictObject({
271
270
  "Pass the member's wallet ({ wallet: true }) at most once"
272
271
  ),
273
272
  address: z.string().min(1).max(100).nullable()
274
- });
275
- var walletDelegationsRequestSchema = z.strictObject({
273
+ }))();
274
+ var walletDelegationsRequestSchema = /* @__PURE__ */ (() => z.strictObject({
276
275
  kind: z.literal("wallet-delegations"),
277
276
  chain: cosmosNetworkSchema,
278
277
  validator: cosmosAddressSchema.nullable(),
279
278
  address: z.string().min(1).max(100).nullable()
280
- });
281
- var memberStateRequestSchemas = {
279
+ }))();
280
+ var memberStateRequestSchemas = /* @__PURE__ */ (() => ({
282
281
  "member-balance": z.strictObject({
283
282
  kind: z.literal("member-balance"),
284
283
  ledger: identifier
@@ -287,7 +286,7 @@ var memberStateRequestSchemas = {
287
286
  kind: z.literal("member-completions"),
288
287
  quest: identifier.nullable(),
289
288
  since: z.number().int().nonnegative().safe().nullable(),
290
- limit: z.number().int().min(1).max(maxMemberCompletions)
289
+ limit: z.number().int().min(1).max(limits.memberCompletions)
291
290
  }),
292
291
  "member-groups": z.strictObject({ kind: z.literal("member-groups") }),
293
292
  "member-enrolled": z.strictObject({
@@ -298,11 +297,11 @@ var memberStateRequestSchemas = {
298
297
  kind: z.literal("member-referrals"),
299
298
  program: identifier
300
299
  })
301
- };
300
+ }))();
302
301
  function unlistedRequest(request) {
303
302
  return request.kind === "telegram" || request.kind === "wallet-nfts" || request.kind === "wallet-call" || request.kind === "wallet-delegations" || request.kind === "wallet-events" || request.kind === "wallet-transactions" || request.kind === "member-balance" || request.kind === "member-completions" || request.kind === "member-groups" || request.kind === "member-enrolled" || request.kind === "member-referrals";
304
303
  }
305
- var capabilityRequestSchema = z.discriminatedUnion("kind", [
304
+ var capabilityRequestSchema = /* @__PURE__ */ (() => z.discriminatedUnion("kind", [
306
305
  capabilityRequestSchemas["wallet-balance"],
307
306
  capabilityRequestSchemas["tracker-content"],
308
307
  capabilityRequestSchemas.x,
@@ -325,7 +324,7 @@ var capabilityRequestSchema = z.discriminatedUnion("kind", [
325
324
  memberStateRequestSchemas["member-groups"],
326
325
  memberStateRequestSchemas["member-enrolled"],
327
326
  memberStateRequestSchemas["member-referrals"]
328
- ]);
327
+ ]))();
329
328
  function parseCapabilityRequest(raw) {
330
329
  return capabilityRequestSchema.safeParse(raw);
331
330
  }
@@ -390,6 +389,24 @@ function parseCapabilityResult(request, value) {
390
389
  return profileReferralSchema.parse(value);
391
390
  }
392
391
  }
392
+ function newerResultIssue(issue) {
393
+ if (issue.code === "unrecognized_keys" || issue.code === "invalid_value") {
394
+ return true;
395
+ }
396
+ return issue.code === "invalid_union" && issue.errors.some(
397
+ (branch) => branch.length > 0 && branch.every(newerResultIssue)
398
+ );
399
+ }
400
+ function parseCapturedResult(request, value) {
401
+ try {
402
+ return parseCapabilityResult(request, value);
403
+ } catch (error) {
404
+ if (error instanceof z.ZodError && error.issues.every(newerResultIssue)) {
405
+ return value;
406
+ }
407
+ throw error;
408
+ }
409
+ }
393
410
  function imageReferences(input) {
394
411
  return input.operation === "compare" || input.operation === "review" ? input.images : [input.image];
395
412
  }
@@ -703,10 +720,10 @@ function install(now, seed, restores) {
703
720
 
704
721
  // src/testing/facts.ts
705
722
  import * as z2 from "zod";
706
- var campaignFactSchema = z2.strictObject({
723
+ var campaignFactSchema = /* @__PURE__ */ (() => z2.strictObject({
707
724
  key: identifier,
708
725
  enrolled: z2.boolean()
709
- });
726
+ }))();
710
727
  var TestSetupError = class extends Error {
711
728
  constructor(message) {
712
729
  super(message);
@@ -1193,7 +1210,7 @@ function rewardSelectionIssue(selected, published) {
1193
1210
  }
1194
1211
 
1195
1212
  // src/testing/run.ts
1196
- var defaultNow = Date.UTC(2026, 0, 1);
1213
+ var defaultNow = /* @__PURE__ */ (() => Date.UTC(2026, 0, 1))();
1197
1214
  var defaultMember = "member_test";
1198
1215
  var defaultSeed = "attempt_test";
1199
1216
  var maxCapabilityCalls = 8;
@@ -1301,6 +1318,7 @@ function hostContext(run, answer) {
1301
1318
  const evidence = typeof input.evidence === "string" ? input.evidence : void 0;
1302
1319
  const calendar = evaluationCalendar({ segments: run.segments }, eligibleAt);
1303
1320
  const calls = [];
1321
+ const capabilityCalls = [];
1304
1322
  const diagnostics = [];
1305
1323
  const problems = [];
1306
1324
  const delivered = /* @__PURE__ */ new WeakSet();
@@ -1321,12 +1339,17 @@ function hostContext(run, answer) {
1321
1339
  request.kind === "photo" ? "Photo capability cannot access another attempt\u2019s evidence" : "Image capability cannot access another attempt\u2019s evidence"
1322
1340
  );
1323
1341
  }
1324
- const outcome = await answer(request, sequence2);
1342
+ const { captured, ...outcome } = await answer(request, sequence2);
1325
1343
  if ("error" in outcome) {
1326
1344
  return outcome;
1327
1345
  }
1328
1346
  try {
1329
- const value = z3.json().parse(parseCapabilityResult(request, outcome.value));
1347
+ const value = z3.json().parse(
1348
+ (captured ? parseCapturedResult : parseCapabilityResult)(
1349
+ request,
1350
+ outcome.value
1351
+ )
1352
+ );
1330
1353
  return { value: JSON.parse(JSON.stringify(value)) };
1331
1354
  } catch (error) {
1332
1355
  throw new TestSetupError(
@@ -1336,7 +1359,7 @@ function hostContext(run, answer) {
1336
1359
  }
1337
1360
  const call = async (raw) => {
1338
1361
  const current = sequence++;
1339
- if (current >= maxCapabilityCalls) {
1362
+ if (current >= limits.capabilityCalls) {
1340
1363
  throw capabilityLimitError();
1341
1364
  }
1342
1365
  const parsed = parseCapabilityRequest(raw);
@@ -1356,6 +1379,8 @@ function hostContext(run, answer) {
1356
1379
  problems.push(error instanceof Error ? error : new Error(String(error)));
1357
1380
  throw error;
1358
1381
  }
1382
+ capabilityCalls.push({ sequence: current, request: parsed.data, outcome });
1383
+ capabilityCalls.sort((a, b) => a.sequence - b.sequence);
1359
1384
  if (!unlistedRequest(parsed.data)) {
1360
1385
  calls.push({ sequence: current, request: parsed.data, outcome });
1361
1386
  calls.sort((a, b) => a.sequence - b.sequence);
@@ -1397,6 +1422,7 @@ function hostContext(run, answer) {
1397
1422
  return {
1398
1423
  context,
1399
1424
  calls,
1425
+ capabilityCalls,
1400
1426
  diagnostics,
1401
1427
  problems,
1402
1428
  delivered,
@@ -1430,7 +1456,7 @@ function thrownMessage(error) {
1430
1456
  function capabilityLimitError() {
1431
1457
  return new CapabilityError(
1432
1458
  "capability-limit",
1433
- `An evaluation run makes at most ${maxCapabilityCalls} capability calls, shared by all capabilities`,
1459
+ `An evaluation run makes at most ${limits.capabilityCalls} capability calls, shared by all capabilities`,
1434
1460
  { retryable: false }
1435
1461
  );
1436
1462
  }
@@ -1538,6 +1564,7 @@ function evaluateHosted(quest, host) {
1538
1564
  return {
1539
1565
  decision,
1540
1566
  calls: host.calls,
1567
+ capabilityCalls: host.capabilityCalls,
1541
1568
  release: host.release,
1542
1569
  diagnostics: host.diagnostics
1543
1570
  };
@@ -1580,6 +1607,41 @@ function fakeEvaluationMember(member = {}) {
1580
1607
  };
1581
1608
  }
1582
1609
 
1610
+ // src/testing/readers.ts
1611
+ import * as z4 from "zod";
1612
+ function factsCall(facts) {
1613
+ const answer = factsAnswerer(facts);
1614
+ return async (raw) => {
1615
+ const request = parseCapabilityRequest(raw);
1616
+ if (!request.success) {
1617
+ throw new CapabilityError(
1618
+ "author-error",
1619
+ z4.prettifyError(request.error),
1620
+ { retryable: false }
1621
+ );
1622
+ }
1623
+ const outcome = await answer(request.data);
1624
+ if ("error" in outcome) {
1625
+ throw CapabilityError.from(outcome.error);
1626
+ }
1627
+ try {
1628
+ return JSON.parse(
1629
+ JSON.stringify(parseCapabilityResult(request.data, outcome.value))
1630
+ );
1631
+ } catch (error) {
1632
+ throw new TestSetupError(
1633
+ `The answer to ${request.data.kind} is not a result Relay delivers: ${error instanceof z4.ZodError ? z4.prettifyError(error) : String(error)}`
1634
+ );
1635
+ }
1636
+ };
1637
+ }
1638
+ function fakeWalletReader(facts = {}) {
1639
+ return readerFactories.wallet(factsCall(facts));
1640
+ }
1641
+ function fakeTelegramReader(facts = {}) {
1642
+ return readerFactories.telegram(factsCall(facts));
1643
+ }
1644
+
1583
1645
  // src/testing/assertions.ts
1584
1646
  var DecisionAssertionError = class extends Error {
1585
1647
  decision;
@@ -1706,7 +1768,7 @@ function trackerPage(tracker, records, options = {}) {
1706
1768
  }
1707
1769
 
1708
1770
  // src/testing/replay.ts
1709
- import * as z4 from "zod";
1771
+ import * as z5 from "zod";
1710
1772
  var ReplayStopped = class extends Error {
1711
1773
  constructor(divergence) {
1712
1774
  super(
@@ -1742,43 +1804,7 @@ function captureAnswerer(facts, fallback, diverged) {
1742
1804
  const fact = facts.find((candidate) => candidate.sequence === sequence);
1743
1805
  const reason = !fact ? "new" : !sameJson(fact.request, request) ? "changed" : !fact.captured || !fact.outcome ? "uncaptured" : null;
1744
1806
  if (fact?.outcome && !reason) {
1745
- return fact.outcome;
1746
- }
1747
- if (unlistedRequest(request)) {
1748
- if (!answerFallback) {
1749
- const [reader, fact2] = {
1750
- telegram: request.kind === "telegram" && !("chat" in request.input) ? ["ctx.telegram.connection()", "facts.telegram.connection"] : ["ctx.telegram.member()", "facts.telegram"],
1751
- "wallet-nfts": ["ctx.wallet.nfts()", "facts.wallet.nfts"],
1752
- "wallet-call": ["ctx.wallet.call()", "facts.wallet.call"],
1753
- "wallet-delegations": [
1754
- "ctx.wallet.delegations()",
1755
- "facts.wallet.delegations"
1756
- ],
1757
- "wallet-events": ["ctx.wallet.events()", "facts.wallet.events"],
1758
- "wallet-transactions": [
1759
- "ctx.wallet.transactions()",
1760
- "facts.wallet.transactions"
1761
- ],
1762
- "member-balance": ["ctx.member.balance()", "facts.member.balances"],
1763
- "member-completions": [
1764
- "ctx.member.completions()",
1765
- "facts.member.completions"
1766
- ],
1767
- "member-groups": ["ctx.member.groups()", "facts.member.groups"],
1768
- "member-enrolled": [
1769
- "ctx.member.enrolled()",
1770
- "facts.member.campaigns"
1771
- ],
1772
- "member-referrals": [
1773
- "ctx.member.referrals()",
1774
- "facts.member.referrals"
1775
- ]
1776
- }[request.kind];
1777
- throw new TestSetupError(
1778
- `Capability call ${sequence}, ${reader}, is not in the capture (${reason ?? "new"}): pass ${fact2} to answer it`
1779
- );
1780
- }
1781
- return answerFallback(request);
1807
+ return { ...fact.outcome, captured: true };
1782
1808
  }
1783
1809
  const divergence = {
1784
1810
  sequence,
@@ -1786,7 +1812,7 @@ function captureAnswerer(facts, fallback, diverged) {
1786
1812
  recorded: fact?.request ?? null,
1787
1813
  replayed: request
1788
1814
  };
1789
- diverged(divergence);
1815
+ diverged(divergence, !unlistedRequest(request));
1790
1816
  if (!answerFallback) {
1791
1817
  throw new ReplayStopped(divergence);
1792
1818
  }
@@ -1797,7 +1823,7 @@ async function replayAttempt(quest, capture, options = {}) {
1797
1823
  const parsed = attemptCaptureSchema.safeParse(capture);
1798
1824
  if (!parsed.success) {
1799
1825
  throw new TestSetupError(
1800
- `Not an attempt capture: ${z4.prettifyError(parsed.error)}`
1826
+ `Not an attempt capture: ${z5.prettifyError(parsed.error)}`
1801
1827
  );
1802
1828
  }
1803
1829
  const { quest: captured, context, facts, recorded } = parsed.data;
@@ -1807,6 +1833,7 @@ async function replayAttempt(quest, capture, options = {}) {
1807
1833
  );
1808
1834
  }
1809
1835
  let divergence = null;
1836
+ let capabilityDivergence = null;
1810
1837
  const host = hostContext(
1811
1838
  {
1812
1839
  release: {
@@ -1824,8 +1851,17 @@ async function replayAttempt(quest, capture, options = {}) {
1824
1851
  now: parsed.data.now,
1825
1852
  seed: parsed.data.seed
1826
1853
  },
1827
- captureAnswerer(facts, options.facts, (found) => {
1828
- divergence ??= found;
1854
+ captureAnswerer(facts, options.facts, (found, listed) => {
1855
+ if (capabilityDivergence) {
1856
+ return;
1857
+ }
1858
+ capabilityDivergence = found;
1859
+ divergence = listed ? {
1860
+ sequence: found.sequence,
1861
+ reason: found.reason,
1862
+ recorded: found.recorded,
1863
+ replayed: found.replayed
1864
+ } : null;
1829
1865
  })
1830
1866
  );
1831
1867
  let decision = null;
@@ -1841,12 +1877,14 @@ async function replayAttempt(quest, capture, options = {}) {
1841
1877
  recorded,
1842
1878
  changed: decision && recorded ? !sameJson(decision, recorded) : null,
1843
1879
  divergence,
1844
- calls: host.calls
1880
+ capabilityDivergence,
1881
+ calls: host.calls,
1882
+ capabilityCalls: host.capabilityCalls
1845
1883
  };
1846
1884
  }
1847
1885
 
1848
1886
  // src/testing/participant-api.ts
1849
- import * as z5 from "zod";
1887
+ import * as z6 from "zod";
1850
1888
  var defaultScope = {
1851
1889
  organization: "org_test",
1852
1890
  project: "project_test",
@@ -1914,7 +1952,11 @@ function createFakeRelay(options = {}) {
1914
1952
  }
1915
1953
  const start = query.get("start") === "latest" ? activity.length : cursor === null ? 0 : Number(cursor.replace(/^fake-/, ""));
1916
1954
  if (!Number.isInteger(start) || start < 0 || start > activity.length) {
1917
- return refuse(400, "invalid-request", "Invalid activity cursor");
1955
+ return refuse(
1956
+ 400,
1957
+ "invalid-cursor",
1958
+ "Invalid cursor. Start from the first page."
1959
+ );
1918
1960
  }
1919
1961
  const items = activity.slice(start, start + limit);
1920
1962
  return answer("GET /v1/me/activity", participantActivitySchema, {
@@ -1978,7 +2020,7 @@ function createFakeRelay(options = {}) {
1978
2020
  }
1979
2021
  if (method === "POST" && path === "/v1/auth/logout") {
1980
2022
  member = null;
1981
- return answer("POST /v1/auth/logout", z5.object({ ok: z5.boolean() }), {
2023
+ return answer("POST /v1/auth/logout", z6.object({ ok: z6.boolean() }), {
1982
2024
  ok: true
1983
2025
  });
1984
2026
  }
@@ -1988,7 +2030,7 @@ function createFakeRelay(options = {}) {
1988
2030
  if (method === "GET" && path === "/v1/point-ledgers") {
1989
2031
  return answer(
1990
2032
  "GET /v1/point-ledgers",
1991
- z5.array(pointLedgerReferenceSchema),
2033
+ z6.array(pointLedgerReferenceSchema),
1992
2034
  ledgers
1993
2035
  );
1994
2036
  }
@@ -1998,7 +2040,7 @@ function createFakeRelay(options = {}) {
1998
2040
  });
1999
2041
  }
2000
2042
  if (method === "GET" && path === "/v1/badges") {
2001
- return answer("GET /v1/badges", z5.array(badgeSchema), badges);
2043
+ return answer("GET /v1/badges", z6.array(badgeSchema), badges);
2002
2044
  }
2003
2045
  const board = method === "GET" && /^\/v1\/leaderboards\/([\w-]+)$/.exec(path);
2004
2046
  if (board) {
@@ -2055,7 +2097,7 @@ function createFakeRelay(options = {}) {
2055
2097
  };
2056
2098
  experience(member ?? "member_test");
2057
2099
  answer("GET /v1/me/points", pointBalancesSchema, { items: balances });
2058
- answer("GET /v1/point-ledgers", z5.array(pointLedgerReferenceSchema), ledgers);
2100
+ answer("GET /v1/point-ledgers", z6.array(pointLedgerReferenceSchema), ledgers);
2059
2101
  answer("GET /v1/badges/catalog", badgeCatalogSchema, { items: badges });
2060
2102
  answer("GET /v1/me/activity", participantActivitySchema, {
2061
2103
  member: member ?? "member_test",
@@ -2101,6 +2143,9 @@ export {
2101
2143
  expectReject,
2102
2144
  expectReview,
2103
2145
  fakeEvaluationMember,
2146
+ fakeTelegramReader,
2147
+ fakeWalletReader,
2148
+ limits,
2104
2149
  maxCapabilityCalls,
2105
2150
  replayAttempt,
2106
2151
  runQuest,
@@ -141,7 +141,7 @@ declare const knownIdentityKinds: readonly ["wallet", "x", "discord", "member"];
141
141
  type KnownIdentityKind = (typeof knownIdentityKinds)[number];
142
142
  /**
143
143
  * An identity kind your app owns: `app:` and a name of lowercase letters, digits, `_` or `-`
144
- * (at most 40), such as `app:telegram` or `app:acme`. The identity integration created with this
144
+ * (at most 40), such as `app:game` or `app:acme`. The identity integration created with this
145
145
  * kind is the only one that can link it: each member it signs in gets the app's subject as an
146
146
  * identity of this kind in the project.
147
147
  */
@@ -897,6 +897,15 @@ declare const trackerSkipCodes: readonly ["quest-paused", "before-activation", "
897
897
  type KnownTrackerSkipCode = (typeof trackerSkipCodes)[number];
898
898
  /** A known skip code, or one a newer Relay sends. */
899
899
  type TrackerSkipCode = KnownTrackerSkipCode | (string & {});
900
+ /**
901
+ * Which enrollment a `not-enrolled` skip lacks: `"quest"`, the quest's own (`enrollment:
902
+ * "required"` on its trigger), or `"campaign"`, the campaign the quest belongs to.
903
+ *
904
+ * @compat open
905
+ */
906
+ type KnownSkipEnrollment = "quest" | "campaign";
907
+ /** A known enrollment, or one a newer Relay sends. */
908
+ type SkipEnrollment = KnownSkipEnrollment | (string & {});
900
909
  /**
901
910
  * One tracker-trigger decision: a quest admitted an attempt for a record observation, or skipped
902
911
  * it with a code and reason. Operators read these to see why a quest did or did not run.
@@ -924,6 +933,7 @@ declare const trackerOutcomeSchema: z.ZodDiscriminatedUnion<[z.ZodObject<{
924
933
  quest: "quest";
925
934
  tracker: "tracker";
926
935
  }>>;
936
+ enrollment: z.ZodOptional<z.ZodType<SkipEnrollment, unknown, z.core.$ZodTypeInternals<SkipEnrollment, unknown>>>;
927
937
  member: z.ZodNullable<z.ZodString>;
928
938
  attempt: z.ZodNullable<z.ZodString>;
929
939
  quest: z.ZodString;
@@ -976,6 +986,7 @@ declare const trackerTriggerOutcomePageSchema: z.ZodObject<{
976
986
  quest: "quest";
977
987
  tracker: "tracker";
978
988
  }>>;
989
+ enrollment: z.ZodOptional<z.ZodType<SkipEnrollment, unknown, z.core.$ZodTypeInternals<SkipEnrollment, unknown>>>;
979
990
  member: z.ZodNullable<z.ZodString>;
980
991
  attempt: z.ZodNullable<z.ZodString>;
981
992
  quest: z.ZodString;
@@ -1032,6 +1043,7 @@ declare const trackerOutcomePageSchema: z.ZodObject<{
1032
1043
  quest: "quest";
1033
1044
  tracker: "tracker";
1034
1045
  }>>;
1046
+ enrollment: z.ZodOptional<z.ZodType<SkipEnrollment, unknown, z.core.$ZodTypeInternals<SkipEnrollment, unknown>>>;
1035
1047
  member: z.ZodNullable<z.ZodString>;
1036
1048
  attempt: z.ZodNullable<z.ZodString>;
1037
1049
  quest: z.ZodString;
@@ -1267,7 +1279,11 @@ type TrackerPage<D = unknown> = Omit<z.infer<typeof trackerPageSchema>, "items">
1267
1279
  items: TypedTrackerRecord<D>[];
1268
1280
  excluded: number;
1269
1281
  });
1270
- /** Preview bounds: one sample, never stored, never a tracker. */
1282
+ /**
1283
+ * Preview bounds: one sample, never stored, never a tracker.
1284
+ *
1285
+ * @deprecated Use `limits.trackerPreview`, which a 1.x release can raise.
1286
+ */
1271
1287
  declare const trackerPreviewLimits: {
1272
1288
  readonly pages: 3;
1273
1289
  readonly posts: 100;
@@ -1348,10 +1364,12 @@ declare const trackerTriggerModeSchema: z.ZodEnum<{
1348
1364
  }>;
1349
1365
  type TrackerTriggerMode = z.infer<typeof trackerTriggerModeSchema>;
1350
1366
  /**
1351
- * Custom trackers fire on every new sample; X and Discord trackers on each record they collect,
1352
- * since a post, message or reaction is one event.
1367
+ * Custom trackers fire on every new sample; X, Discord and Telegram trackers on each record they
1368
+ * collect, since a post, message or reaction is one event. Telegram's sources are custom sources
1369
+ * on reserved namespaces in SDK 1.x, so `namespace` names them. A published policy keeps the mode
1370
+ * it was published with.
1353
1371
  */
1354
- declare function defaultTriggerMode(source: string): TrackerTriggerMode;
1372
+ declare function defaultTriggerMode(source: string, namespace?: string): TrackerTriggerMode;
1355
1373
  /**
1356
1374
  * A bound in a tracker trigger filter: a number, or the quest's integer or amount setting of that
1357
1375
  * name. An amount setting (`settings.amount()`) holds a base-unit integer string, compared exactly.
@@ -1783,9 +1801,17 @@ type TrackerDataSchema = {
1783
1801
  oneOf?: TrackerDataSchema[];
1784
1802
  allOf?: TrackerDataSchema[];
1785
1803
  };
1786
- /** The most branches one union may list. */
1804
+ /**
1805
+ * The most branches one union may list.
1806
+ *
1807
+ * @deprecated Use `limits.trackerData.branches`, which a 1.x release can raise.
1808
+ */
1787
1809
  declare const trackerDataMaxBranches = 16;
1788
- /** The most properties, `required` keys, enum values or allowed key names one schema node lists. */
1810
+ /**
1811
+ * The most properties, `required` keys, enum values or allowed key names one schema node lists.
1812
+ *
1813
+ * @deprecated Use `limits.trackerData.entries`, which a 1.x release can raise.
1814
+ */
1789
1815
  declare const trackerDataMaxEntries = 256;
1790
1816
  /**
1791
1817
  * A stored tracker data schema: an object schema in the supported subset, at most 32 KB and
@@ -1852,4 +1878,4 @@ declare function schemaCheckedReader(reader: TrackerReader): TrackerReader;
1852
1878
  */
1853
1879
  declare function whereSchemaIssue(schema: TrackerDataSchema, where: TrackerWhere | undefined): string | null;
1854
1880
 
1855
- export { type KnownIdentityKind as $, type RoleOf as A, type WhereSetting as B, type ContentBody as C, type BadgeHandle as D, type ContentMetricName as E, type LedgerSetting as F, type GroupHandle as G, type TrackerPage as H, type IdentityKind as I, type TrackerReadQuery as J, type KnownTrackerSkipCode as K, type LedgerReference as L, type MemberIdentity as M, trackerDataSchema as N, type OpenIdentityKind as O, trackerTriggerContextSchema as P, type QuestHandle as Q, type ResourceHandle as R, type SourceRoles as S, type TrackerSkipCode as T, type AccountRole as U, type AppIdentityKind as V, type WithRecordData as W, type XTweet as X, type Bound as Y, type Condition as Z, type DataLeaves as _, type TrackerDataBudget as a, trackerDefinitionResponseSchema as a$, type ManagedTrackerCreateInput as a0, type ManagedTrackerSource as a1, type ManagedTrackerSourceKind as a2, type TrackerAccount as a3, type TrackerAttribution as a4, type TrackerBound as a5, type TrackerCondition as a6, type TrackerContent as a7, type TrackerContentQuery as a8, type TrackerCreateInput as a9, identityKindSchema as aA, isAppIdentityKind as aB, isKnownTrackerSource as aC, knownIdentityKinds as aD, managedTrackerCreateSchema as aE, managedTrackerSource as aF, managedTrackerSourceKinds as aG, managedTrackerSourceSchema as aH, memberIdentitySchema as aI, openIdentityKindSchema as aJ, publishedTrackerSchema as aK, sourceContent as aL, sourceIdentities as aM, trackerAccountSchema as aN, trackerArtifactSchema as aO, trackerAttributionSchema as aP, trackerBoundSchema as aQ, trackerConditionSchema as aR, trackerContentQuerySchema as aS, trackerContentReadSchema as aT, trackerContentSchema as aU, trackerContentStageSchema as aV, trackerControlSchema as aW, trackerCreateSchema as aX, trackerDataMaxBranches as aY, trackerDataMaxEntries as aZ, trackerDataSchemaSchema as a_, type TrackerDataIssue as aa, type TrackerDefinition as ab, type TrackerDefinitionResponse as ac, type TrackerOutcome as ad, type TrackerOutcomeQuery as ae, type TrackerPreview as af, type TrackerPreviewInput as ag, type TrackerQuery as ah, type TrackerRecord as ai, type TrackerSourceKind as aj, type TrackerSourceResponse as ak, type TrackerStatus as al, type TrackerTriggerOutcomePage as am, type TrackerTriggerOutcomeQuery as an, type TrackerUpdateInput as ao, type TrackerWhere as ap, type TriggerEnrollment as aq, type TriggerHistorical as ar, type TriggerSince as as, type TypedTrackerRecord as at, accountRoleSchema as au, appIdentityKindSchema as av, beneficiaryRole as aw, contentMetricNameSchema as ax, customContentSchema as ay, defaultTriggerMode as az, trackerDataIssue as b, trackerEvidenceSchema as b0, trackerIngestResultSchema as b1, trackerIngestSchema as b2, trackerOutcomePageSchema as b3, trackerOutcomeQuerySchema as b4, trackerOutcomeRetrySchema as b5, trackerOutcomeSchema as b6, trackerPageSchema as b7, trackerPreviewInputSchema as b8, trackerPreviewLimits as b9, whereSettings as bA, xAccountRoles as bB, xContentMetrics as bC, xTweetSchema as bD, trackerPreviewSchema as ba, trackerPropertiesSchema as bb, trackerQuerySchema as bc, trackerRecordAccountSchema as bd, trackerRecordInputSchema as be, trackerRecordSchema as bf, trackerSkipCodes as bg, trackerSourceKinds as bh, trackerSourceResponseSchema as bi, trackerSourceSchema as bj, trackerStatusSchema as bk, trackerSummarySchema as bl, trackerTriggerModeSchema as bm, trackerTriggerOutcomePageSchema as bn, trackerTriggerOutcomeQuerySchema as bo, trackerTriggerPolicySchema as bp, trackerTriggerRecordSchema as bq, trackerUpdateSchema as br, trackerWhereSchema as bs, triggerAdmission as bt, triggerEnrollmentSchema as bu, triggerHistoricalSchema as bv, triggerMode as bw, triggerSinceSchema as bx, walletBalanceSourceSchema as by, whereConditions as bz, trackerDataIssues as c, trackerDataPathTypes as d, trackerDataRecordSteps as e, type TrackerDataSchema as f, customSourceSchema as g, type WithContent as h, type WithAccountRoles as i, type TrackerSource as j, trackerDefinitionSchema as k, type Tracker as l, type TrackerData as m, type LedgerHandle as n, xSearchSourceSchema as o, type XContentMetric as p, type TrackerTriggerPolicy as q, type Where as r, schemaCheckedReader as s, trackerDataBatchSteps as t, type ReferralHandle as u, type TrackerTriggerContext as v, whereSchemaIssue as w, xContentBodySchema as x, type TrackerReader as y, type TrackerTriggerMode as z };
1881
+ export { type AppIdentityKind as $, type ReferralHandle as A, type TrackerTriggerContext as B, type TrackerReader as C, type TrackerTriggerMode as D, type RoleOf as E, type WhereSetting as F, type GroupHandle as G, type ContentBody as H, type IdentityKind as I, type BadgeHandle as J, type KnownSkipEnrollment as K, type LedgerReference as L, type MemberIdentity as M, type ContentMetricName as N, type OpenIdentityKind as O, type LedgerSetting as P, type QuestHandle as Q, type ResourceHandle as R, type SkipEnrollment as S, type TrackerSkipCode as T, type TrackerPage as U, type TrackerReadQuery as V, type WithRecordData as W, type XTweet as X, trackerDataSchema as Y, trackerTriggerContextSchema as Z, type AccountRole as _, type KnownTrackerSkipCode as a, trackerDataMaxBranches as a$, type Bound as a0, type Condition as a1, type DataLeaves as a2, type KnownIdentityKind as a3, type ManagedTrackerCreateInput as a4, type ManagedTrackerSource as a5, type ManagedTrackerSourceKind as a6, type TrackerAccount as a7, type TrackerAttribution as a8, type TrackerBound as a9, beneficiaryRole as aA, contentMetricNameSchema as aB, customContentSchema as aC, defaultTriggerMode as aD, identityKindSchema as aE, isAppIdentityKind as aF, isKnownTrackerSource as aG, knownIdentityKinds as aH, managedTrackerCreateSchema as aI, managedTrackerSource as aJ, managedTrackerSourceKinds as aK, managedTrackerSourceSchema as aL, memberIdentitySchema as aM, openIdentityKindSchema as aN, publishedTrackerSchema as aO, sourceIdentities as aP, trackerAccountSchema as aQ, trackerArtifactSchema as aR, trackerAttributionSchema as aS, trackerBoundSchema as aT, trackerConditionSchema as aU, trackerContentQuerySchema as aV, trackerContentReadSchema as aW, trackerContentSchema as aX, trackerContentStageSchema as aY, trackerControlSchema as aZ, trackerCreateSchema as a_, type TrackerCondition as aa, type TrackerContent as ab, type TrackerContentQuery as ac, type TrackerCreateInput as ad, type TrackerDataIssue as ae, type TrackerDefinition as af, type TrackerDefinitionResponse as ag, type TrackerOutcome as ah, type TrackerOutcomeQuery as ai, type TrackerPreview as aj, type TrackerPreviewInput as ak, type TrackerQuery as al, type TrackerRecord as am, type TrackerSourceKind as an, type TrackerSourceResponse as ao, type TrackerStatus as ap, type TrackerTriggerOutcomePage as aq, type TrackerTriggerOutcomeQuery as ar, type TrackerUpdateInput as as, type TrackerWhere as at, type TriggerEnrollment as au, type TriggerHistorical as av, type TriggerSince as aw, type TypedTrackerRecord as ax, accountRoleSchema as ay, appIdentityKindSchema as az, type TrackerDataBudget as b, trackerDataMaxEntries as b0, trackerDataSchemaSchema as b1, trackerDefinitionResponseSchema as b2, trackerEvidenceSchema as b3, trackerIngestResultSchema as b4, trackerIngestSchema as b5, trackerOutcomePageSchema as b6, trackerOutcomeQuerySchema as b7, trackerOutcomeRetrySchema as b8, trackerOutcomeSchema as b9, triggerSinceSchema as bA, walletBalanceSourceSchema as bB, whereConditions as bC, xAccountRoles as bD, xContentMetrics as bE, xTweetSchema as bF, trackerPageSchema as ba, trackerPreviewInputSchema as bb, trackerPreviewLimits as bc, trackerPreviewSchema as bd, trackerPropertiesSchema as be, trackerQuerySchema as bf, trackerRecordAccountSchema as bg, trackerRecordInputSchema as bh, trackerRecordSchema as bi, trackerSkipCodes as bj, trackerSourceKinds as bk, trackerSourceResponseSchema as bl, trackerSourceSchema as bm, trackerStatusSchema as bn, trackerSummarySchema as bo, trackerTriggerModeSchema as bp, trackerTriggerOutcomePageSchema as bq, trackerTriggerOutcomeQuerySchema as br, trackerTriggerPolicySchema as bs, trackerTriggerRecordSchema as bt, trackerUpdateSchema as bu, trackerWhereSchema as bv, triggerAdmission as bw, triggerEnrollmentSchema as bx, triggerHistoricalSchema as by, triggerMode as bz, sourceContent as c, trackerDataIssue as d, trackerDataIssues as e, trackerDataPathTypes as f, trackerDataRecordSteps as g, whereSettings as h, type TrackerDataSchema as i, customSourceSchema as j, type WithContent as k, type WithAccountRoles as l, type TrackerSource as m, trackerDefinitionSchema as n, type Tracker as o, type TrackerData as p, type SourceRoles as q, type LedgerHandle as r, schemaCheckedReader as s, trackerDataBatchSteps as t, xSearchSourceSchema as u, type XContentMetric as v, whereSchemaIssue as w, xContentBodySchema as x, type TrackerTriggerPolicy as y, type Where as z };