@marlinjai/mail-contract 0.9.0 → 0.11.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js CHANGED
@@ -209,6 +209,7 @@ __export(index_exports, {
209
209
  InviteListQuery: () => InviteListQuery,
210
210
  InviteStatus: () => InviteStatus,
211
211
  JsonValue: () => JsonValue,
212
+ LETTER_ONLY_MERGE_FIELDS: () => LETTER_ONLY_MERGE_FIELDS,
212
213
  LETTER_RECIPIENT_REFUSAL: () => LETTER_RECIPIENT_REFUSAL,
213
214
  LIST_UNSUBSCRIBE_POST_VALUE: () => LIST_UNSUBSCRIBE_POST_VALUE,
214
215
  LOCALE_TAG_PATTERN: () => LOCALE_TAG_PATTERN,
@@ -277,7 +278,10 @@ __export(index_exports, {
277
278
  MailingLanguageReport: () => MailingLanguageReport,
278
279
  MailingLanguageStatus: () => MailingLanguageStatus,
279
280
  MailingListQuery: () => MailingListQuery,
281
+ MailingMerge: () => MailingMerge,
280
282
  MailingMetadata: () => MailingMetadata,
283
+ MailingResolveRequest: () => MailingResolveRequest,
284
+ MailingResolveResult: () => MailingResolveResult,
281
285
  MailingRetryFailedRequest: () => MailingRetryFailedRequest,
282
286
  MailingScheduleFailedData: () => MailingScheduleFailedData,
283
287
  MailingScheduleRequest: () => MailingScheduleRequest,
@@ -302,6 +306,8 @@ __export(index_exports, {
302
306
  MessageOutcome: () => MessageOutcome,
303
307
  MessageSentData: () => MessageSentData,
304
308
  MessageSummary: () => MessageSummary,
309
+ MessageValues: () => MessageValues,
310
+ NAME_ON_BROADCAST_REFUSAL: () => NAME_ON_BROADCAST_REFUSAL,
305
311
  NotifyRecipients: () => NotifyRecipients,
306
312
  NotifyStep: () => NotifyStep,
307
313
  ON_BEHALF_OF_HEADER: () => ON_BEHALF_OF_HEADER,
@@ -337,6 +343,8 @@ __export(index_exports, {
337
343
  REQUEST_ID_HEADER: () => REQUEST_ID_HEADER,
338
344
  RESEND_EVENT_TYPES: () => RESEND_EVENT_TYPES,
339
345
  RESERVED_MERGE_FIELDS: () => RESERVED_MERGE_FIELDS,
346
+ RESOLVE_PROBLEMS: () => RESOLVE_PROBLEMS,
347
+ RESOLVE_REJECTIONS: () => RESOLVE_REJECTIONS,
340
348
  RETRYABLE_ERRORS: () => RETRYABLE_ERRORS,
341
349
  RETRY_AFTER_HEADER: () => RETRY_AFTER_HEADER,
342
350
  RE_ENTRY_MODES: () => RE_ENTRY_MODES,
@@ -349,6 +357,9 @@ __export(index_exports, {
349
357
  RecipientStatus: () => RecipientStatus,
350
358
  RemoteImage: () => RemoteImage,
351
359
  ResendSigningSecret: () => ResendSigningSecret,
360
+ ResolveProblem: () => ResolveProblem,
361
+ ResolvedRecipient: () => ResolvedRecipient,
362
+ ResolvedValue: () => ResolvedValue,
352
363
  SERVICE_FILLED_MERGE_FIELDS: () => SERVICE_FILLED_MERGE_FIELDS,
353
364
  SIGNUP_FORM_FIELDS: () => SIGNUP_FORM_FIELDS,
354
365
  SKIP_REASONS: () => SKIP_REASONS,
@@ -435,10 +446,13 @@ __export(index_exports, {
435
446
  USAGE_METRICS: () => USAGE_METRICS,
436
447
  USAGE_WARNING_HEADER: () => USAGE_WARNING_HEADER,
437
448
  USAGE_WARNING_RATIO: () => USAGE_WARNING_RATIO,
449
+ UnfilledLink: () => UnfilledLink,
438
450
  Usage: () => Usage,
439
451
  UsageMetric: () => UsageMetric,
440
452
  UsageWarning: () => UsageWarning,
453
+ VALUE_LAYERS: () => VALUE_LAYERS,
441
454
  ValidationIssue: () => ValidationIssue,
455
+ ValueLayer: () => ValueLayer,
442
456
  VariantAnalytics: () => VariantAnalytics,
443
457
  WEBHOOK_DELIVERY_STATUSES: () => WEBHOOK_DELIVERY_STATUSES,
444
458
  WEBHOOK_EVENT_ID_HEADER: () => WEBHOOK_EVENT_ID_HEADER,
@@ -502,6 +516,7 @@ __export(index_exports, {
502
516
  editMainInsertions: () => editMainInsertions,
503
517
  effectivePreviewPicks: () => effectivePreviewPicks,
504
518
  emptyFlow: () => emptyFlow,
519
+ emptyLinkValues: () => emptyLinkValues,
505
520
  errorBody: () => errorBody,
506
521
  escapeMergeHtml: () => escapeMergeHtml,
507
522
  exportFilename: () => exportFilename,
@@ -532,6 +547,8 @@ __export(index_exports, {
532
547
  languageInsertions: () => languageInsertions,
533
548
  languageName: () => languageName,
534
549
  languageTabs: () => languageTabs,
550
+ letterOnlyValues: () => letterOnlyValues,
551
+ linkTokens: () => linkTokens,
535
552
  mainInsertionText: () => mainInsertionText,
536
553
  matchLocale: () => matchLocale,
537
554
  matchRoute: () => matchRoute,
@@ -552,6 +569,8 @@ __export(index_exports, {
552
569
  previewInsertions: () => previewInsertions,
553
570
  previewPersonalization: () => previewPersonalization,
554
571
  primaryLanguage: () => primaryLanguage,
572
+ printedFields: () => printedFields,
573
+ rawMergeValue: () => rawMergeValue,
555
574
  reachable: () => reachable,
556
575
  readyWithoutInsertions: () => readyWithoutInsertions,
557
576
  readyWithoutSubject: () => readyWithoutSubject,
@@ -568,6 +587,7 @@ __export(index_exports, {
568
587
  renameTokenInDocument: () => renameTokenInDocument,
569
588
  renameTokenInText: () => renameTokenInText,
570
589
  resolveInsertions: () => resolveInsertions,
590
+ resolveValue: () => resolveValue,
571
591
  restorePatch: () => restorePatch,
572
592
  routes: () => routes,
573
593
  sameJson: () => sameJson,
@@ -594,6 +614,8 @@ __export(index_exports, {
594
614
  unknownRefusedInsertions: () => unknownRefusedInsertions,
595
615
  unplacedInsertions: () => unplacedInsertions,
596
616
  validateAutomation: () => validateAutomation,
617
+ valueNames: () => valueNames,
618
+ valuesRead: () => valuesRead,
597
619
  verifyWebhook: () => verifyWebhook
598
620
  });
599
621
  module.exports = __toCommonJS(index_exports);
@@ -677,6 +699,12 @@ var ERROR_STATUS = {
677
699
  invalid_mjml: 422,
678
700
  missing_unsubscribe_url: 422,
679
701
  mailing_not_ready: 422,
702
+ /**
703
+ * A value placed inside a link's address comes out empty for at least one
704
+ * recipient, so the mailing does not start; `details.values` lists each such
705
+ * value with how many recipients it is empty for.
706
+ */
707
+ unfilled_link: 422,
680
708
  unknown_topic: 422,
681
709
  unknown_provider: 422,
682
710
  /**
@@ -745,10 +773,10 @@ var API_VERSION_PREFIX = "/v1";
745
773
  var HEALTH_PATH = "/healthz";
746
774
 
747
775
  // src/workspace.ts
748
- var import_zod10 = require("zod");
776
+ var import_zod11 = require("zod");
749
777
 
750
778
  // src/automations.ts
751
- var import_zod9 = require("zod");
779
+ var import_zod10 = require("zod");
752
780
 
753
781
  // src/templates.ts
754
782
  var import_zod5 = require("zod");
@@ -769,11 +797,11 @@ var RESERVED_MERGE_FIELDS = {
769
797
  };
770
798
  var MERGE_FIELD_PATTERN = /\{\{\s*([a-z][a-z0-9_]*)\s*(?:\|([^}]*))?\}\}/g;
771
799
  function findMergeFields(html) {
772
- const uses = [];
800
+ const uses2 = [];
773
801
  for (const match of html.matchAll(MERGE_FIELD_PATTERN)) {
774
- uses.push({ name: match[1], fallback: match[2] === void 0 ? null : match[2].trim() });
802
+ uses2.push({ name: match[1], fallback: match[2] === void 0 ? null : match[2].trim() });
775
803
  }
776
- return uses;
804
+ return uses2;
777
805
  }
778
806
  function missingRequiredMergeFields(html) {
779
807
  const used = new Set(findMergeFields(html).map((u) => u.name));
@@ -1456,10 +1484,10 @@ function exportFilename(name, format) {
1456
1484
  }
1457
1485
 
1458
1486
  // src/platform.ts
1459
- var import_zod8 = require("zod");
1487
+ var import_zod9 = require("zod");
1460
1488
 
1461
1489
  // src/mailings.ts
1462
- var import_zod7 = require("zod");
1490
+ var import_zod8 = require("zod");
1463
1491
 
1464
1492
  // src/ab-test.ts
1465
1493
  var import_zod6 = require("zod");
@@ -1510,6 +1538,167 @@ function testGroupSize(total, fraction, variants) {
1510
1538
  return Math.min(total, Math.max(variants, Math.ceil(total * fraction)));
1511
1539
  }
1512
1540
 
1541
+ // src/values.ts
1542
+ var import_zod7 = require("zod");
1543
+ var MAX_MERGE_DEFAULTS = 50;
1544
+ var MAX_MERGE_DEFAULT_LENGTH = 2e3;
1545
+ var MergeFieldName = import_zod7.z.string().regex(/^[a-z][a-z0-9_]*$/, "a merge-field name: lowercase letters, digits and underscores, starting with a letter").max(64);
1546
+ var MergeDefaultValue = import_zod7.z.union([import_zod7.z.string().max(MAX_MERGE_DEFAULT_LENGTH), import_zod7.z.number().finite(), import_zod7.z.boolean()]);
1547
+ var MailingMerge = import_zod7.z.record(MergeFieldName, MergeDefaultValue).refine((m) => Object.keys(m).length <= MAX_MERGE_DEFAULTS, `at most ${MAX_MERGE_DEFAULTS} values on a mailing`).refine((m) => !Object.keys(m).some((k) => SERVICE_FILLED_MERGE_FIELDS.includes(k)), {
1548
+ message: `the service fills ${SERVICE_FILLED_MERGE_FIELDS.join(" and ")}; a mailing cannot set them`
1549
+ });
1550
+ var LETTER_ONLY_MERGE_FIELDS = ["first_name", "last_name"];
1551
+ var NAME_ON_BROADCAST_REFUSAL = "name_on_broadcast";
1552
+ function letterOnlyValues(merge) {
1553
+ return LETTER_ONLY_MERGE_FIELDS.filter((name) => ownEntry(merge, name) !== void 0);
1554
+ }
1555
+ var VALUE_LAYERS = ["recipient", "mailing", "contact", "workspace", "fallback", "empty"];
1556
+ var ValueLayer = import_zod7.z.enum(VALUE_LAYERS);
1557
+ var ResolvedValue = import_zod7.z.object({ text: import_zod7.z.string(), layer: ValueLayer });
1558
+ var MessageValues = import_zod7.z.record(ResolvedValue);
1559
+ function scalarText(value) {
1560
+ if (typeof value === "string") return value;
1561
+ if (typeof value === "number" && Number.isFinite(value)) return String(value);
1562
+ if (typeof value === "boolean") return String(value);
1563
+ return null;
1564
+ }
1565
+ function isNameField(name) {
1566
+ return name === "first_name" || name === "last_name";
1567
+ }
1568
+ function rawMergeValue(name, sources) {
1569
+ const own = ownEntry(sources.recipient, name);
1570
+ if (scalarText(own) !== null) return { value: own, layer: "recipient" };
1571
+ const held = ownEntry(sources.mailing, name);
1572
+ if (scalarText(held) !== null) return { value: held, layer: "mailing" };
1573
+ if (isNameField(name)) {
1574
+ const stored = sources.contact?.[name];
1575
+ return typeof stored === "string" ? { value: stored, layer: "contact" } : null;
1576
+ }
1577
+ const property = ownEntry(sources.contact?.properties, name);
1578
+ if (scalarText(property) !== null) return { value: property, layer: "contact" };
1579
+ const byDefault = ownEntry(sources.workspace, name);
1580
+ return scalarText(byDefault) !== null ? { value: byDefault, layer: "workspace" } : null;
1581
+ }
1582
+ function resolveValue(name, fallback, sources) {
1583
+ const found = rawMergeValue(name, sources);
1584
+ const text = found === null ? null : scalarText(found.value);
1585
+ if (found !== null && text !== null && text.trim() !== "") return { text, layer: found.layer };
1586
+ const instead = fallback?.trim() ?? "";
1587
+ return instead === "" ? { text: "", layer: "empty" } : { text: instead, layer: "fallback" };
1588
+ }
1589
+ function pattern2() {
1590
+ return new RegExp(MERGE_FIELD_PATTERN.source, "g");
1591
+ }
1592
+ function isServiceFilled(name) {
1593
+ return SERVICE_FILLED_MERGE_FIELDS.includes(name);
1594
+ }
1595
+ function uses(text) {
1596
+ return [...text.matchAll(pattern2())].map((m) => ({ name: m[1], fallback: m[2] === void 0 ? null : m[2].trim() }));
1597
+ }
1598
+ function valueNames(texts, insertions) {
1599
+ const names = [];
1600
+ const add = (name) => {
1601
+ if (!isServiceFilled(name) && !names.includes(name)) names.push(name);
1602
+ };
1603
+ for (const text of texts) {
1604
+ for (const use of uses(text ?? "")) {
1605
+ const def = ownEntry(insertions, use.name);
1606
+ if (!def) {
1607
+ add(use.name);
1608
+ continue;
1609
+ }
1610
+ add(def.by);
1611
+ for (const inner of [...Object.values(def.choices), def.filled ?? "", def.otherwise]) for (const u of uses(inner)) add(u.name);
1612
+ }
1613
+ }
1614
+ return names;
1615
+ }
1616
+ function printedFields(texts, insertions, chosen2) {
1617
+ const out = [];
1618
+ const add = (use) => {
1619
+ if (isServiceFilled(use.name)) return;
1620
+ if (!out.some((o) => o.name === use.name && o.fallback === use.fallback)) out.push(use);
1621
+ };
1622
+ for (const text of texts) {
1623
+ for (const use of uses(text ?? "")) {
1624
+ if (!ownEntry(insertions, use.name)) add(use);
1625
+ else for (const inner of uses(ownEntry(chosen2, use.name)?.text ?? "")) add(inner);
1626
+ }
1627
+ }
1628
+ return out;
1629
+ }
1630
+ function valuesRead(texts, insertions, chosen2, resolve) {
1631
+ const out = {};
1632
+ const read = (use) => {
1633
+ if (isServiceFilled(use.name)) return;
1634
+ const value = resolve(use.name, use.fallback);
1635
+ const seen = ownEntry(out, use.name);
1636
+ if (seen === void 0 || value.layer === "empty" && seen.layer !== "empty") out[use.name] = value;
1637
+ };
1638
+ for (const text of texts) {
1639
+ for (const use of uses(text ?? "")) {
1640
+ const def = ownEntry(insertions, use.name);
1641
+ if (!def) {
1642
+ read(use);
1643
+ continue;
1644
+ }
1645
+ read({ name: def.by, fallback: null });
1646
+ for (const inner of uses(ownEntry(chosen2, use.name)?.text ?? "")) read(inner);
1647
+ }
1648
+ }
1649
+ return out;
1650
+ }
1651
+ var HREF = /\bhref\s*=\s*(?:"([^"]*)"|'([^']*)')/gi;
1652
+ function linkTokens(html) {
1653
+ const out = [];
1654
+ for (const match of html.matchAll(HREF)) {
1655
+ for (const use of uses(match[1] ?? match[2] ?? "")) {
1656
+ if (isServiceFilled(use.name)) continue;
1657
+ if (!out.some((o) => o.name === use.name && o.fallback === use.fallback)) out.push(use);
1658
+ }
1659
+ }
1660
+ return out;
1661
+ }
1662
+ function emptyLinkValues(tokens, p) {
1663
+ const empty = [];
1664
+ for (const token of tokens) {
1665
+ const ins = ownEntry(p.insertions, token.name);
1666
+ const text = ins ? ins.text.replace(pattern2(), (_m, name, fallback) => p.value(name, fallback)) : p.value(token.name, token.fallback ?? void 0);
1667
+ if (text.trim() === "" && !empty.includes(token.name)) empty.push(token.name);
1668
+ }
1669
+ return empty;
1670
+ }
1671
+ var UnfilledLink = import_zod7.z.object({
1672
+ /** The value, or the insertion, that comes out empty. */
1673
+ value: import_zod7.z.string(),
1674
+ /** How many recipients it is empty for. */
1675
+ recipients: import_zod7.z.number().int().min(1)
1676
+ });
1677
+ var RESOLVE_PROBLEMS = ["unfilled_link", "empty_value", "insertion_miss"];
1678
+ var ResolveProblem = import_zod7.z.object({
1679
+ kind: import_zod7.z.enum(RESOLVE_PROBLEMS),
1680
+ severity: import_zod7.z.enum(["blocking", "note"]),
1681
+ value: import_zod7.z.string(),
1682
+ message: import_zod7.z.string()
1683
+ });
1684
+ var ResolvedRecipient = import_zod7.z.object({
1685
+ /** The recipient's index in the request; null for the reader with nothing of their own. */
1686
+ index: import_zod7.z.number().int().min(0).nullable(),
1687
+ /** The address the message would go to; null for the reader with nothing of their own. */
1688
+ email: Email.nullable(),
1689
+ /** The contact found for the recipient; null when the address has none yet (a send creates it, empty). */
1690
+ contact_id: Id.nullable(),
1691
+ /** The language version this recipient would get. */
1692
+ locale: LocaleTag,
1693
+ /** The subject line as they would read it. */
1694
+ subject: import_zod7.z.string(),
1695
+ values: MessageValues,
1696
+ /** The choice each insertion would make; null when the content has none. */
1697
+ insertions: InsertionChoices.nullable(),
1698
+ problems: import_zod7.z.array(ResolveProblem)
1699
+ });
1700
+ var RESOLVE_REJECTIONS = ["unknown_contact", "duplicate_in_batch"];
1701
+
1513
1702
  // src/mailings.ts
1514
1703
  var MAILING_STATUSES = [
1515
1704
  "draft",
@@ -1520,9 +1709,9 @@ var MAILING_STATUSES = [
1520
1709
  "partially_failed",
1521
1710
  "cancelled"
1522
1711
  ];
1523
- var MailingStatus = import_zod7.z.enum(MAILING_STATUSES);
1712
+ var MailingStatus = import_zod8.z.enum(MAILING_STATUSES);
1524
1713
  var MAILING_ACTIONS = ["send", "schedule", "unschedule", "pause", "resume", "cancel", "retry-failed"];
1525
- var MailingAction = import_zod7.z.enum(MAILING_ACTIONS);
1714
+ var MailingAction = import_zod8.z.enum(MAILING_ACTIONS);
1526
1715
  var MAILING_TRANSITIONS = {
1527
1716
  draft: ["send", "schedule", "cancel"],
1528
1717
  scheduled: ["send", "schedule", "unschedule", "cancel"],
@@ -1537,23 +1726,23 @@ function canTransition(status, action) {
1537
1726
  }
1538
1727
  var EDITABLE_MAILING_STATUSES = ["draft", "scheduled"];
1539
1728
  var TERMINAL_MAILING_STATUSES = ["sent", "cancelled"];
1540
- var MailingMetadata = import_zod7.z.record(import_zod7.z.string().max(500)).refine((v) => Object.keys(v).length <= 20, "at most 20 keys").refine((v) => Object.keys(v).every((k) => k.length >= 1 && k.length <= 64), "keys are 1 to 64 characters");
1541
- var MailingCounts = import_zod7.z.object({
1542
- total: import_zod7.z.number().int().min(0),
1543
- queued: import_zod7.z.number().int().min(0),
1544
- sending: import_zod7.z.number().int().min(0),
1545
- sent: import_zod7.z.number().int().min(0),
1546
- failed: import_zod7.z.number().int().min(0),
1547
- skipped: import_zod7.z.number().int().min(0)
1729
+ var MailingMetadata = import_zod8.z.record(import_zod8.z.string().max(500)).refine((v) => Object.keys(v).length <= 20, "at most 20 keys").refine((v) => Object.keys(v).every((k) => k.length >= 1 && k.length <= 64), "keys are 1 to 64 characters");
1730
+ var MailingCounts = import_zod8.z.object({
1731
+ total: import_zod8.z.number().int().min(0),
1732
+ queued: import_zod8.z.number().int().min(0),
1733
+ sending: import_zod8.z.number().int().min(0),
1734
+ sent: import_zod8.z.number().int().min(0),
1735
+ failed: import_zod8.z.number().int().min(0),
1736
+ skipped: import_zod8.z.number().int().min(0)
1548
1737
  });
1549
1738
  var MAILING_KINDS = ["broadcast", "automation", "notification"];
1550
- var MailingKind = import_zod7.z.enum(MAILING_KINDS);
1551
- var Mailing = import_zod7.z.object({
1739
+ var MailingKind = import_zod8.z.enum(MAILING_KINDS);
1740
+ var Mailing = import_zod8.z.object({
1552
1741
  id: Id,
1553
1742
  kind: MailingKind,
1554
- name: import_zod7.z.string().max(200).nullable(),
1555
- subject: import_zod7.z.string().min(1).max(998),
1556
- preheader: import_zod7.z.string().max(500).nullable(),
1743
+ name: import_zod8.z.string().max(200).nullable(),
1744
+ subject: import_zod8.z.string().min(1).max(998),
1745
+ preheader: import_zod8.z.string().max(500).nullable(),
1557
1746
  /**
1558
1747
  * The template the document was taken from, if any. The snapshot is what is
1559
1748
  * sent in the main language; the template's other language versions are
@@ -1577,6 +1766,14 @@ var Mailing = import_zod7.z.object({
1577
1766
  * language: without a ready version in it, the main language goes out.
1578
1767
  */
1579
1768
  send_locale: LocaleTag.nullable(),
1769
+ /**
1770
+ * The template's language version the mailing was written from
1771
+ * (`MailingCreate.template_locale`), or null. When set, it equals `locale`
1772
+ * and `send_locale`: the mailing is one letter in that language, and the
1773
+ * template's other versions never go out with it (see "Writing from one
1774
+ * language version" in the contract's documentation).
1775
+ */
1776
+ template_locale: LocaleTag.nullable().default(null),
1580
1777
  /**
1581
1778
  * The topic the mailing is sent under. Null for a letter (a one-to-one
1582
1779
  * mailing with at most one recipient, which belongs to no topic and whose
@@ -1587,6 +1784,12 @@ var Mailing = import_zod7.z.object({
1587
1784
  status: MailingStatus,
1588
1785
  counts: MailingCounts,
1589
1786
  metadata: MailingMetadata,
1787
+ /**
1788
+ * The values held on this mailing (see `MailingMerge`): the same for
1789
+ * everyone who gets it, above the contact's stored name and properties and
1790
+ * the workspace's defaults, below the recipient's own. Empty by default.
1791
+ */
1792
+ merge: MailingMerge.default({}),
1590
1793
  scheduled_at: Timestamp.nullable(),
1591
1794
  /** The A/B test on subject or content (S4), null when there is none. */
1592
1795
  ab_test: AbTestState.nullable(),
@@ -1598,15 +1801,15 @@ var Mailing = import_zod7.z.object({
1598
1801
  * recipients refused as dead addresses in one run (see the provider's
1599
1802
  * `rejections.anomaly`). Resuming clears it and starts a new run.
1600
1803
  */
1601
- pause_reason: import_zod7.z.string().nullable().default(null),
1804
+ pause_reason: import_zod8.z.string().nullable().default(null),
1602
1805
  created_at: Timestamp,
1603
1806
  updated_at: Timestamp
1604
1807
  });
1605
1808
  var MailingSummary = Mailing.omit({ document: true });
1606
1809
  var MailingContent = {
1607
- name: import_zod7.z.string().max(200).optional(),
1608
- subject: import_zod7.z.string().min(1).max(998),
1609
- preheader: import_zod7.z.string().max(500).optional(),
1810
+ name: import_zod8.z.string().max(200).optional(),
1811
+ subject: import_zod8.z.string().min(1).max(998),
1812
+ preheader: import_zod8.z.string().max(500).optional(),
1610
1813
  /** See `Mailing.send_locale`. */
1611
1814
  send_locale: LocaleTag.nullable().optional(),
1612
1815
  /**
@@ -1617,29 +1820,42 @@ var MailingContent = {
1617
1820
  */
1618
1821
  topic: Slug.nullable().optional(),
1619
1822
  provider_id: Id,
1620
- metadata: MailingMetadata.optional()
1823
+ metadata: MailingMetadata.optional(),
1824
+ /** See `Mailing.merge`. `first_name` and `last_name` only on a letter (no topic). */
1825
+ merge: MailingMerge.optional()
1621
1826
  };
1622
- var MailingCreate = import_zod7.z.object({
1827
+ var MailingCreate = import_zod8.z.object({
1623
1828
  ...MailingContent,
1624
1829
  subject: MailingContent.subject.optional(),
1625
1830
  document: TemplateDocument.optional(),
1626
- template_id: Id.optional()
1831
+ template_id: Id.optional(),
1832
+ template_locale: LocaleTag.optional()
1627
1833
  }).refine((v) => v.document === void 0 !== (v.template_id === void 0), {
1628
1834
  message: "exactly one of document or template_id",
1629
1835
  path: ["document"]
1836
+ }).refine((v) => v.template_locale === void 0 || v.template_id !== void 0, {
1837
+ message: "template_locale names a version of template_id",
1838
+ path: ["template_locale"]
1630
1839
  }).refine((v) => v.template_id !== void 0 || v.subject !== void 0, {
1631
1840
  message: "a mailing made from a document needs a subject",
1632
1841
  path: ["subject"]
1633
1842
  });
1634
- var MailingUpdate = import_zod7.z.object({
1635
- name: import_zod7.z.string().max(200).nullable().optional(),
1843
+ var MailingUpdate = import_zod8.z.object({
1844
+ name: import_zod8.z.string().max(200).nullable().optional(),
1636
1845
  subject: MailingContent.subject.optional(),
1637
- preheader: import_zod7.z.string().max(500).nullable().optional(),
1846
+ preheader: import_zod8.z.string().max(500).nullable().optional(),
1638
1847
  /** Null turns a draft into a letter, which it can only be with at most one recipient. */
1639
1848
  topic: Slug.nullable().optional(),
1640
1849
  send_locale: LocaleTag.nullable().optional(),
1641
1850
  provider_id: Id.optional(),
1642
1851
  metadata: MailingMetadata.optional(),
1852
+ /**
1853
+ * Replaces the mailing's values whole (see `Mailing.merge`). Giving a
1854
+ * mailing that holds `first_name` or `last_name` a topic is refused
1855
+ * (`name_on_broadcast`) unless the same call replaces its values without
1856
+ * them.
1857
+ */
1858
+ merge: MailingMerge.optional(),
1643
1859
  document: TemplateDocument.optional()
1644
1860
  }).refine((v) => Object.keys(v).length > 0, "at least one field");
1645
1861
  var MailingListQuery = PageQuery.extend({
@@ -1648,30 +1864,30 @@ var MailingListQuery = PageQuery.extend({
1648
1864
  kind: MailingKind.optional(),
1649
1865
  automation_id: Id.optional()
1650
1866
  });
1651
- var MailingSendRequest = import_zod7.z.object({}).strict();
1652
- var MailingRetryFailedRequest = import_zod7.z.object({
1867
+ var MailingSendRequest = import_zod8.z.object({}).strict();
1868
+ var MailingRetryFailedRequest = import_zod8.z.object({
1653
1869
  /**
1654
1870
  * Also requeue recipients whose outcome is unknown after a crash. They may
1655
1871
  * already have received the message, so this is a human's decision, never a
1656
1872
  * default.
1657
1873
  */
1658
- include_outcome_unknown: import_zod7.z.boolean().optional()
1874
+ include_outcome_unknown: import_zod8.z.boolean().optional()
1659
1875
  }).strict();
1660
- var MailingActionRequest = import_zod7.z.object({}).strict();
1661
- var MailingTestRequest = import_zod7.z.object({
1876
+ var MailingActionRequest = import_zod8.z.object({}).strict();
1877
+ var MailingTestRequest = import_zod8.z.object({
1662
1878
  to: Email,
1663
1879
  merge: Properties.optional(),
1664
1880
  locale: LocaleTag.optional()
1665
1881
  });
1666
- var MailingTestResult = import_zod7.z.object({
1882
+ var MailingTestResult = import_zod8.z.object({
1667
1883
  message_id: Id,
1668
- provider_message_id: import_zod7.z.string().nullable()
1884
+ provider_message_id: import_zod8.z.string().nullable()
1669
1885
  });
1670
1886
  var RECIPIENT_STATUSES = ["queued", "sending", "sent", "failed", "skipped"];
1671
- var RecipientStatus = import_zod7.z.enum(RECIPIENT_STATUSES);
1887
+ var RecipientStatus = import_zod8.z.enum(RECIPIENT_STATUSES);
1672
1888
  var SKIP_REASONS = ["suppressed", "not_subscribed", "contact_erased", "cancelled", "outcome_unknown"];
1673
- var SkipReason = import_zod7.z.enum(SKIP_REASONS);
1674
- var Recipient = import_zod7.z.object({
1889
+ var SkipReason = import_zod8.z.enum(SKIP_REASONS);
1890
+ var Recipient = import_zod8.z.object({
1675
1891
  id: Id,
1676
1892
  mailing_id: Id,
1677
1893
  contact_id: Id.nullable(),
@@ -1679,55 +1895,55 @@ var Recipient = import_zod7.z.object({
1679
1895
  merge: Properties,
1680
1896
  status: RecipientStatus,
1681
1897
  skip_reason: SkipReason.nullable(),
1682
- attempts: import_zod7.z.number().int().min(0),
1898
+ attempts: import_zod8.z.number().int().min(0),
1683
1899
  message_id: Id.nullable(),
1684
- last_error: import_zod7.z.string().nullable(),
1900
+ last_error: import_zod8.z.string().nullable(),
1685
1901
  created_at: Timestamp,
1686
1902
  updated_at: Timestamp
1687
1903
  });
1688
1904
  var MAX_RECIPIENTS_PER_BATCH = 1e3;
1689
1905
  var MAX_LETTER_RECIPIENTS = 1;
1690
1906
  var LETTER_RECIPIENT_REFUSAL = "letter_has_one_recipient";
1691
- var RecipientInput = import_zod7.z.object({
1907
+ var RecipientInput = import_zod8.z.object({
1692
1908
  contact_id: Id.optional(),
1693
- external_id: import_zod7.z.string().min(1).max(255).optional(),
1909
+ external_id: import_zod8.z.string().min(1).max(255).optional(),
1694
1910
  email: Email.optional(),
1695
1911
  merge: Properties.optional()
1696
1912
  }).refine((v) => v.contact_id !== void 0 || v.external_id !== void 0 || v.email !== void 0, {
1697
1913
  message: "contact_id, external_id or email is required",
1698
1914
  path: ["email"]
1699
1915
  });
1700
- var RecipientBatch = import_zod7.z.object({
1701
- recipients: import_zod7.z.array(RecipientInput).min(1).max(MAX_RECIPIENTS_PER_BATCH)
1916
+ var RecipientBatch = import_zod8.z.object({
1917
+ recipients: import_zod8.z.array(RecipientInput).min(1).max(MAX_RECIPIENTS_PER_BATCH)
1702
1918
  });
1703
1919
  var RECIPIENT_REJECTIONS = ["unknown_contact", "duplicate_in_batch"];
1704
- var RecipientBatchResult = import_zod7.z.object({
1920
+ var RecipientBatchResult = import_zod8.z.object({
1705
1921
  /** Newly queued. */
1706
- added: import_zod7.z.number().int().min(0),
1922
+ added: import_zod8.z.number().int().min(0),
1707
1923
  /** Already on the mailing from an earlier batch: left unchanged. */
1708
- already_present: import_zod7.z.number().int().min(0),
1924
+ already_present: import_zod8.z.number().int().min(0),
1709
1925
  /** Items not added, by their index in the request. */
1710
- rejected: import_zod7.z.array(import_zod7.z.object({ index: import_zod7.z.number().int().min(0), reason: import_zod7.z.enum(RECIPIENT_REJECTIONS) }))
1926
+ rejected: import_zod8.z.array(import_zod8.z.object({ index: import_zod8.z.number().int().min(0), reason: import_zod8.z.enum(RECIPIENT_REJECTIONS) }))
1711
1927
  });
1712
1928
  var RecipientListQuery = PageQuery.extend({
1713
1929
  status: RecipientStatus.optional(),
1714
1930
  skip_reason: SkipReason.optional()
1715
1931
  });
1716
1932
  var MESSAGE_OUTCOMES = ["sent", "failed"];
1717
- var MessageOutcome = import_zod7.z.enum(MESSAGE_OUTCOMES);
1718
- var MessageSummary = import_zod7.z.object({
1933
+ var MessageOutcome = import_zod8.z.enum(MESSAGE_OUTCOMES);
1934
+ var MessageSummary = import_zod8.z.object({
1719
1935
  id: Id,
1720
1936
  mailing_id: Id.nullable(),
1721
1937
  recipient_id: Id.nullable(),
1722
1938
  contact_id: Id.nullable(),
1723
1939
  to: Email,
1724
- subject: import_zod7.z.string(),
1940
+ subject: import_zod8.z.string(),
1725
1941
  provider_id: Id,
1726
- provider_message_id: import_zod7.z.string().nullable(),
1942
+ provider_message_id: import_zod8.z.string().nullable(),
1727
1943
  outcome: MessageOutcome,
1728
- error: import_zod7.z.string().nullable(),
1729
- is_test: import_zod7.z.boolean(),
1730
- recipient_count: import_zod7.z.number().int().min(1),
1944
+ error: import_zod8.z.string().nullable(),
1945
+ is_test: import_zod8.z.boolean(),
1946
+ recipient_count: import_zod8.z.number().int().min(1),
1731
1947
  /** The language version the message was sent in; null for messages archived before languages existed. */
1732
1948
  locale: LocaleTag.nullable(),
1733
1949
  /**
@@ -1737,24 +1953,32 @@ var MessageSummary = import_zod7.z.object({
1737
1953
  * "otherwise" text. Null when the message had no insertions.
1738
1954
  */
1739
1955
  insertions: InsertionChoices.nullable(),
1956
+ /**
1957
+ * The values the message was written with, by name: the text each one
1958
+ * printed and the layer it came from (see `MessageValues`), recorded when it
1959
+ * was sent, so a later change to a default never rewrites what a reader got.
1960
+ * Null for a message archived before values were recorded, and for a signup
1961
+ * form's confirmation, which belongs to no mailing.
1962
+ */
1963
+ values: MessageValues.nullable().default(null),
1740
1964
  created_at: Timestamp
1741
1965
  });
1742
- var Message = MessageSummary.extend({ html: import_zod7.z.string() });
1743
- var MailingLanguageStatus = import_zod7.z.enum(["main", "ready", "draft", "not_a_workspace_language"]);
1744
- var MailingLanguage = import_zod7.z.object({
1966
+ var Message = MessageSummary.extend({ html: import_zod8.z.string() });
1967
+ var MailingLanguageStatus = import_zod8.z.enum(["main", "ready", "draft", "not_a_workspace_language"]);
1968
+ var MailingLanguage = import_zod8.z.object({
1745
1969
  locale: LocaleTag,
1746
1970
  status: MailingLanguageStatus,
1747
1971
  /** Queued recipients who will get this version. */
1748
- planned: import_zod7.z.number().int().min(0),
1972
+ planned: import_zod8.z.number().int().min(0),
1749
1973
  /** Messages already sent in this language (tests excluded). */
1750
- sent: import_zod7.z.number().int().min(0)
1974
+ sent: import_zod8.z.number().int().min(0)
1751
1975
  });
1752
- var MailingLanguageReport = import_zod7.z.object({
1976
+ var MailingLanguageReport = import_zod8.z.object({
1753
1977
  main_locale: LocaleTag,
1754
1978
  send_locale: LocaleTag.nullable(),
1755
- languages: import_zod7.z.array(MailingLanguage),
1756
- fallback: import_zod7.z.array(import_zod7.z.object({ wanted: import_zod7.z.string(), planned: import_zod7.z.number().int().min(1) })),
1757
- no_language: import_zod7.z.number().int().min(0),
1979
+ languages: import_zod8.z.array(MailingLanguage),
1980
+ fallback: import_zod8.z.array(import_zod8.z.object({ wanted: import_zod8.z.string(), planned: import_zod8.z.number().int().min(1) })),
1981
+ no_language: import_zod8.z.number().int().min(0),
1758
1982
  /**
1759
1983
  * Values that no choice of an insertion takes, so the "otherwise" text goes
1760
1984
  * out (docs/plans/2026-09-25-translated-insertions.md, decision 3): per
@@ -1763,41 +1987,56 @@ var MailingLanguageReport = import_zod7.z.object({
1763
1987
  * template's keys never produces one; a non-empty list means the client and
1764
1988
  * the template have drifted apart.
1765
1989
  */
1766
- insertion_misses: import_zod7.z.array(
1767
- import_zod7.z.object({
1768
- insertion: import_zod7.z.string(),
1769
- value: import_zod7.z.string(),
1770
- planned: import_zod7.z.number().int().min(0),
1771
- sent: import_zod7.z.number().int().min(0)
1990
+ insertion_misses: import_zod8.z.array(
1991
+ import_zod8.z.object({
1992
+ insertion: import_zod8.z.string(),
1993
+ value: import_zod8.z.string(),
1994
+ planned: import_zod8.z.number().int().min(0),
1995
+ sent: import_zod8.z.number().int().min(0)
1772
1996
  })
1773
1997
  )
1774
1998
  });
1999
+ var MailingResolveRequest = import_zod8.z.object({
2000
+ recipients: import_zod8.z.array(RecipientInput).max(MAX_RECIPIENTS_PER_BATCH).optional()
2001
+ });
2002
+ var MailingResolveResult = import_zod8.z.object({
2003
+ /** Every value the mailing's content can read, in order of first appearance, without `email` and `unsubscribe_url`. */
2004
+ names: import_zod8.z.array(import_zod8.z.string()),
2005
+ /** The values and insertions placed inside a link's address: one of them empty for anybody refuses the send. */
2006
+ link_values: import_zod8.z.array(import_zod8.z.string()),
2007
+ /** One entry per resolved recipient, in the request's order; a single entry with `index: null` when none were given. */
2008
+ recipients: import_zod8.z.array(ResolvedRecipient),
2009
+ /** Items not resolved, by their index in the request, for the reasons `mailings.addRecipients` rejects one. */
2010
+ rejected: import_zod8.z.array(import_zod8.z.object({ index: import_zod8.z.number().int().min(0), reason: import_zod8.z.enum(RESOLVE_REJECTIONS) })),
2011
+ /** What would refuse `mailings.send` for these recipients, as its `unfilled_link` refusal lists it; empty means none. */
2012
+ blocking: import_zod8.z.array(UnfilledLink)
2013
+ });
1775
2014
  var MessageListQuery = PageQuery.extend({
1776
2015
  mailing_id: Id.optional(),
1777
2016
  outcome: MessageOutcome.optional()
1778
2017
  });
1779
2018
 
1780
2019
  // src/platform.ts
1781
- var Tag = import_zod8.z.object({
2020
+ var Tag = import_zod9.z.object({
1782
2021
  id: Id,
1783
2022
  slug: Slug,
1784
- name: import_zod8.z.string().min(1).max(120),
1785
- contact_count: import_zod8.z.number().int().min(0),
2023
+ name: import_zod9.z.string().min(1).max(120),
2024
+ contact_count: import_zod9.z.number().int().min(0),
1786
2025
  created_at: Timestamp
1787
2026
  });
1788
- var TagCreate = import_zod8.z.object({ slug: Slug, name: import_zod8.z.string().min(1).max(120) });
1789
- var TagAssignment = import_zod8.z.object({
1790
- contact_ids: import_zod8.z.array(Id).min(1).max(1e3)
2027
+ var TagCreate = import_zod9.z.object({ slug: Slug, name: import_zod9.z.string().min(1).max(120) });
2028
+ var TagAssignment = import_zod9.z.object({
2029
+ contact_ids: import_zod9.z.array(Id).min(1).max(1e3)
1791
2030
  });
1792
2031
  var CONTACT_PROPERTY_TYPES = ["string", "number", "boolean", "date"];
1793
- var ContactPropertyType = import_zod8.z.enum(CONTACT_PROPERTY_TYPES);
1794
- var ContactPropertyKey = import_zod8.z.string().regex(/^[A-Za-z0-9_.-]{1,64}$/, "letters, digits, dot, underscore and hyphen, 1 to 64");
1795
- var ContactPropertyDefinition = import_zod8.z.object({
2032
+ var ContactPropertyType = import_zod9.z.enum(CONTACT_PROPERTY_TYPES);
2033
+ var ContactPropertyKey = import_zod9.z.string().regex(/^[A-Za-z0-9_.-]{1,64}$/, "letters, digits, dot, underscore and hyphen, 1 to 64");
2034
+ var ContactPropertyDefinition = import_zod9.z.object({
1796
2035
  key: ContactPropertyKey,
1797
- label: import_zod8.z.string().min(1).max(120),
2036
+ label: import_zod9.z.string().min(1).max(120),
1798
2037
  type: ContactPropertyType
1799
2038
  });
1800
- var ContactPropertyParams = import_zod8.z.object({ key: ContactPropertyKey });
2039
+ var ContactPropertyParams = import_zod9.z.object({ key: ContactPropertyKey });
1801
2040
  var FILTER_OPERATORS = [
1802
2041
  "eq",
1803
2042
  "neq",
@@ -1813,8 +2052,8 @@ var FILTER_OPERATORS = [
1813
2052
  "in",
1814
2053
  "not_in"
1815
2054
  ];
1816
- var FilterOperator = import_zod8.z.enum(FILTER_OPERATORS);
1817
- var FilterField = import_zod8.z.string().regex(
2055
+ var FilterOperator = import_zod9.z.enum(FILTER_OPERATORS);
2056
+ var FilterField = import_zod9.z.string().regex(
1818
2057
  /^(email|first_name|last_name|locale|created_at|tag|topic|engagement:(opened|clicked)|property:[A-Za-z0-9_.-]{1,64})$/,
1819
2058
  "unknown filter field"
1820
2059
  );
@@ -1830,18 +2069,18 @@ var FILTER_FIELD_OPERATORS = {
1830
2069
  property: FILTER_OPERATORS
1831
2070
  };
1832
2071
  var MAX_FILTER_DEPTH = 5;
1833
- var FilterCondition = import_zod8.z.object({ field: FilterField, op: FilterOperator, value: JsonValue.optional() }).strict().refine((c) => (c.op === "exists" || c.op === "not_exists") === (c.value === void 0), {
2072
+ var FilterCondition = import_zod9.z.object({ field: FilterField, op: FilterOperator, value: JsonValue.optional() }).strict().refine((c) => (c.op === "exists" || c.op === "not_exists") === (c.value === void 0), {
1834
2073
  message: "exists and not_exists take no value; every other operator needs one",
1835
2074
  path: ["value"]
1836
2075
  }).refine((c) => c.op !== "in" && c.op !== "not_in" || Array.isArray(c.value), {
1837
2076
  message: "in and not_in take an array",
1838
2077
  path: ["value"]
1839
2078
  });
1840
- var SegmentFilter = import_zod8.z.lazy(
1841
- () => import_zod8.z.union([
1842
- import_zod8.z.object({ and: import_zod8.z.array(SegmentFilter).min(1).max(50) }).strict(),
1843
- import_zod8.z.object({ or: import_zod8.z.array(SegmentFilter).min(1).max(50) }).strict(),
1844
- import_zod8.z.object({ not: SegmentFilter }).strict(),
2079
+ var SegmentFilter = import_zod9.z.lazy(
2080
+ () => import_zod9.z.union([
2081
+ import_zod9.z.object({ and: import_zod9.z.array(SegmentFilter).min(1).max(50) }).strict(),
2082
+ import_zod9.z.object({ or: import_zod9.z.array(SegmentFilter).min(1).max(50) }).strict(),
2083
+ import_zod9.z.object({ not: SegmentFilter }).strict(),
1845
2084
  FilterCondition
1846
2085
  ])
1847
2086
  );
@@ -1929,42 +2168,42 @@ function untypedValueProblem(c, every) {
1929
2168
  if (orderOp) return every(isFilterNumber, "numbers (define the property to compare dates)");
1930
2169
  return every((v) => isScalar(v) || v === null, "strings, numbers, booleans or null");
1931
2170
  }
1932
- var Segment = import_zod8.z.object({
2171
+ var Segment = import_zod9.z.object({
1933
2172
  id: Id,
1934
- name: import_zod8.z.string().min(1).max(120),
2173
+ name: import_zod9.z.string().min(1).max(120),
1935
2174
  filter: SegmentFilter,
1936
2175
  /** Computed on read. */
1937
- contact_count: import_zod8.z.number().int().min(0),
2176
+ contact_count: import_zod9.z.number().int().min(0),
1938
2177
  created_at: Timestamp,
1939
2178
  updated_at: Timestamp
1940
2179
  });
1941
- var SegmentCreate = import_zod8.z.object({ name: import_zod8.z.string().min(1).max(120), filter: BoundedSegmentFilter });
1942
- var SegmentPreviewRequest = import_zod8.z.object({ filter: BoundedSegmentFilter });
1943
- var SegmentPreview = import_zod8.z.object({
1944
- contact_count: import_zod8.z.number().int().min(0),
2180
+ var SegmentCreate = import_zod9.z.object({ name: import_zod9.z.string().min(1).max(120), filter: BoundedSegmentFilter });
2181
+ var SegmentPreviewRequest = import_zod9.z.object({ filter: BoundedSegmentFilter });
2182
+ var SegmentPreview = import_zod9.z.object({
2183
+ contact_count: import_zod9.z.number().int().min(0),
1945
2184
  /** Up to five matching contacts, for a human to sanity-check the filter. */
1946
- sample: import_zod8.z.array(import_zod8.z.object({ id: Id, email: Email })).max(5)
2185
+ sample: import_zod9.z.array(import_zod9.z.object({ id: Id, email: Email })).max(5)
1947
2186
  });
1948
- var MailingAudienceFromSegment = import_zod8.z.object({ segment_id: Id });
2187
+ var MailingAudienceFromSegment = import_zod9.z.object({ segment_id: Id });
1949
2188
  var SIGNUP_FORM_FIELDS = ["first_name", "last_name"];
1950
2189
  var HOSTED_PAGE_LOCALES = ["en", "de", "it", "fr", "es"];
1951
- var SignupFormTranslation = import_zod8.z.object({
1952
- title: import_zod8.z.string().min(1).max(120),
1953
- consent_text: import_zod8.z.string().min(1).max(2e3)
2190
+ var SignupFormTranslation = import_zod9.z.object({
2191
+ title: import_zod9.z.string().min(1).max(120),
2192
+ consent_text: import_zod9.z.string().min(1).max(2e3)
1954
2193
  });
1955
- var SignupForm = import_zod8.z.object({
2194
+ var SignupForm = import_zod9.z.object({
1956
2195
  id: Id,
1957
- name: import_zod8.z.string().min(1).max(120),
2196
+ name: import_zod9.z.string().min(1).max(120),
1958
2197
  /** The heading of the hosted page. */
1959
- title: import_zod8.z.string().min(1).max(120),
2198
+ title: import_zod9.z.string().min(1).max(120),
1960
2199
  /** What the person agrees to, shown above the button and recorded with the confirmation. */
1961
- consent_text: import_zod8.z.string().min(1).max(2e3),
1962
- translations: import_zod8.z.record(SignupFormTranslation),
1963
- topics: import_zod8.z.array(Slug).min(1),
1964
- tags: import_zod8.z.array(Slug),
2200
+ consent_text: import_zod9.z.string().min(1).max(2e3),
2201
+ translations: import_zod9.z.record(SignupFormTranslation),
2202
+ topics: import_zod9.z.array(Slug).min(1),
2203
+ tags: import_zod9.z.array(Slug),
1965
2204
  /** Fields shown besides email. */
1966
- fields: import_zod8.z.array(import_zod8.z.enum(SIGNUP_FORM_FIELDS)),
1967
- double_opt_in: import_zod8.z.literal(true),
2205
+ fields: import_zod9.z.array(import_zod9.z.enum(SIGNUP_FORM_FIELDS)),
2206
+ double_opt_in: import_zod9.z.literal(true),
1968
2207
  /** The provider the confirmation mail is sent through. */
1969
2208
  provider_id: Id,
1970
2209
  /**
@@ -1973,11 +2212,11 @@ var SignupForm = import_zod8.z.object({
1973
2212
  */
1974
2213
  confirmation_template_id: Id.nullable(),
1975
2214
  /** Where the person lands after confirming. Null shows the hosted confirmation page. */
1976
- redirect_url: import_zod8.z.string().url().nullable(),
2215
+ redirect_url: import_zod9.z.string().url().nullable(),
1977
2216
  /** Origins allowed to embed the form and call the submission route from a browser. */
1978
- allowed_origins: import_zod8.z.array(import_zod8.z.string().url()).max(20),
2217
+ allowed_origins: import_zod9.z.array(import_zod9.z.string().url()).max(20),
1979
2218
  /** Bumped on every change; recorded with each confirmation. */
1980
- version: import_zod8.z.number().int().min(1),
2219
+ version: import_zod9.z.number().int().min(1),
1981
2220
  created_at: Timestamp,
1982
2221
  updated_at: Timestamp
1983
2222
  });
@@ -1992,56 +2231,56 @@ var SignupFormCreate = SignupForm.omit({
1992
2231
  tags: SignupForm.shape.tags.optional(),
1993
2232
  fields: SignupForm.shape.fields.optional(),
1994
2233
  confirmation_template_id: Id.nullable().optional(),
1995
- redirect_url: import_zod8.z.string().url().nullable().optional(),
2234
+ redirect_url: import_zod9.z.string().url().nullable().optional(),
1996
2235
  allowed_origins: SignupForm.shape.allowed_origins.optional()
1997
2236
  });
1998
- var SignupFormEmbed = import_zod8.z.object({
1999
- hosted_url: import_zod8.z.string().url(),
2237
+ var SignupFormEmbed = import_zod9.z.object({
2238
+ hosted_url: import_zod9.z.string().url(),
2000
2239
  /** A plain HTML form posting to the hosted page; works without JavaScript. */
2001
- html: import_zod8.z.string(),
2240
+ html: import_zod9.z.string(),
2002
2241
  /** A small optional script that adds the time check and submits in place. */
2003
- script_url: import_zod8.z.string().url(),
2242
+ script_url: import_zod9.z.string().url(),
2004
2243
  /** Where a browser fetches a fresh `form_token` from (GET, public, CORS for `allowed_origins`). */
2005
- token_url: import_zod8.z.string().url()
2244
+ token_url: import_zod9.z.string().url()
2006
2245
  });
2007
- var SignupSubmission = import_zod8.z.object({
2246
+ var SignupSubmission = import_zod9.z.object({
2008
2247
  email: Email,
2009
- first_name: import_zod8.z.string().max(200).optional(),
2010
- last_name: import_zod8.z.string().max(200).optional(),
2011
- locale: import_zod8.z.string().min(2).max(35).optional(),
2248
+ first_name: import_zod9.z.string().max(200).optional(),
2249
+ last_name: import_zod9.z.string().max(200).optional(),
2250
+ locale: import_zod9.z.string().min(2).max(35).optional(),
2012
2251
  /** Honeypot: must be empty. */
2013
- website: import_zod8.z.string().max(0).optional(),
2252
+ website: import_zod9.z.string().max(0).optional(),
2014
2253
  /**
2015
2254
  * The signed render time from the form's token URL: a submission sooner than a
2016
2255
  * human could fill the form, or long after, is refused.
2017
2256
  */
2018
- form_token: import_zod8.z.string().min(1).max(512)
2257
+ form_token: import_zod9.z.string().min(1).max(512)
2019
2258
  });
2020
2259
  var IMPORT_STATUSES = ["uploaded", "validating", "validated", "committing", "completed", "failed", "cancelled"];
2021
- var ImportStatus = import_zod8.z.enum(IMPORT_STATUSES);
2260
+ var ImportStatus = import_zod9.z.enum(IMPORT_STATUSES);
2022
2261
  var IMPORT_TERMINAL_STATUSES = ["completed", "failed", "cancelled"];
2023
- var ImportColumnMapping = import_zod8.z.record(
2024
- import_zod8.z.string().regex(/^(email|external_id|first_name|last_name|locale|property:[A-Za-z0-9_.-]{1,64}|ignore)$/)
2262
+ var ImportColumnMapping = import_zod9.z.record(
2263
+ import_zod9.z.string().regex(/^(email|external_id|first_name|last_name|locale|property:[A-Za-z0-9_.-]{1,64}|ignore)$/)
2025
2264
  );
2026
2265
  var IMPORT_FILE_FIELD = "file";
2027
2266
  var MAX_IMPORT_BYTES = 50 * 1024 * 1024;
2028
2267
  var MAX_IMPORT_ROWS = 2e5;
2029
- var ImportMappingRequest = import_zod8.z.object({
2268
+ var ImportMappingRequest = import_zod9.z.object({
2030
2269
  /** CSV header -> contact field. Exactly one column maps to `email`. */
2031
2270
  mapping: ImportColumnMapping.refine(
2032
2271
  (m) => Object.values(m).filter((v) => v === "email").length === 1,
2033
2272
  "exactly one column maps to email"
2034
2273
  ),
2035
- topics: import_zod8.z.array(Slug).max(100),
2036
- tags: import_zod8.z.array(Slug).max(100),
2274
+ topics: import_zod9.z.array(Slug).max(100),
2275
+ tags: import_zod9.z.array(Slug).max(100),
2037
2276
  /** Existing contacts get the mapped fields overwritten; false only adds topics, tags and missing fields. */
2038
- update_existing: import_zod8.z.boolean().optional(),
2277
+ update_existing: import_zod9.z.boolean().optional(),
2039
2278
  /** The importer states the people consented; the service records who said so and when. */
2040
- consent_confirmed: import_zod8.z.literal(true)
2279
+ consent_confirmed: import_zod9.z.literal(true)
2041
2280
  });
2042
- var ImportCommitRequest = import_zod8.z.object({ mapping_version: import_zod8.z.number().int().min(1) });
2281
+ var ImportCommitRequest = import_zod9.z.object({ mapping_version: import_zod9.z.number().int().min(1) });
2043
2282
  var IMPORT_ROW_OUTCOMES = ["created", "updated", "unchanged", "suppressed", "skipped"];
2044
- var ImportRowOutcome = import_zod8.z.enum(IMPORT_ROW_OUTCOMES);
2283
+ var ImportRowOutcome = import_zod9.z.enum(IMPORT_ROW_OUTCOMES);
2045
2284
  var IMPORT_SKIP_REASONS = [
2046
2285
  "missing_email",
2047
2286
  "invalid_email",
@@ -2050,90 +2289,90 @@ var IMPORT_SKIP_REASONS = [
2050
2289
  "external_id_conflict",
2051
2290
  "wrong_column_count"
2052
2291
  ];
2053
- var ImportSkipReason = import_zod8.z.enum(IMPORT_SKIP_REASONS);
2054
- var ImportReport = import_zod8.z.object({
2055
- created: import_zod8.z.number().int().min(0),
2056
- updated: import_zod8.z.number().int().min(0),
2057
- unchanged: import_zod8.z.number().int().min(0),
2058
- suppressed: import_zod8.z.number().int().min(0),
2059
- skipped: import_zod8.z.number().int().min(0),
2060
- skipped_by_reason: import_zod8.z.record(ImportSkipReason, import_zod8.z.number().int().min(0)),
2292
+ var ImportSkipReason = import_zod9.z.enum(IMPORT_SKIP_REASONS);
2293
+ var ImportReport = import_zod9.z.object({
2294
+ created: import_zod9.z.number().int().min(0),
2295
+ updated: import_zod9.z.number().int().min(0),
2296
+ unchanged: import_zod9.z.number().int().min(0),
2297
+ suppressed: import_zod9.z.number().int().min(0),
2298
+ skipped: import_zod9.z.number().int().min(0),
2299
+ skipped_by_reason: import_zod9.z.record(ImportSkipReason, import_zod9.z.number().int().min(0)),
2061
2300
  /** Rows whose contact was subscribed without some topic, because the address is blocked for it. */
2062
- topics_withheld: import_zod8.z.number().int().min(0)
2301
+ topics_withheld: import_zod9.z.number().int().min(0)
2063
2302
  });
2064
- var ImportJob = import_zod8.z.object({
2303
+ var ImportJob = import_zod9.z.object({
2065
2304
  id: Id,
2066
2305
  status: ImportStatus,
2067
- file_name: import_zod8.z.string().max(255).nullable(),
2068
- file_bytes: import_zod8.z.number().int().min(0),
2069
- total_rows: import_zod8.z.number().int().min(0),
2306
+ file_name: import_zod9.z.string().max(255).nullable(),
2307
+ file_bytes: import_zod9.z.number().int().min(0),
2308
+ total_rows: import_zod9.z.number().int().min(0),
2070
2309
  /** The header row, as in the file. */
2071
- columns: import_zod8.z.array(import_zod8.z.string()),
2310
+ columns: import_zod9.z.array(import_zod9.z.string()),
2072
2311
  /** The first rows, for the mapping screen. */
2073
- sample: import_zod8.z.array(import_zod8.z.array(import_zod8.z.string())).max(5),
2312
+ sample: import_zod9.z.array(import_zod9.z.array(import_zod9.z.string())).max(5),
2074
2313
  /** A mapping guessed from the headers, for the mapping screen to start from. */
2075
2314
  suggested_mapping: ImportColumnMapping,
2076
2315
  mapping: ImportColumnMapping.nullable(),
2077
- mapping_version: import_zod8.z.number().int().min(0),
2078
- topics: import_zod8.z.array(Slug),
2079
- tags: import_zod8.z.array(Slug),
2080
- update_existing: import_zod8.z.boolean(),
2316
+ mapping_version: import_zod9.z.number().int().min(0),
2317
+ topics: import_zod9.z.array(Slug),
2318
+ tags: import_zod9.z.array(Slug),
2319
+ update_existing: import_zod9.z.boolean(),
2081
2320
  /** The dry run of the current mapping; null before one finished. */
2082
2321
  dry_run: ImportReport.nullable(),
2083
2322
  /** What the commit has written so far; null before it started. */
2084
2323
  result: ImportReport.nullable(),
2085
2324
  /** Rows the current phase (dry run or commit) has processed. */
2086
- processed_rows: import_zod8.z.number().int().min(0),
2325
+ processed_rows: import_zod9.z.number().int().min(0),
2087
2326
  /** Why a `failed` import failed. */
2088
- error: import_zod8.z.string().nullable(),
2327
+ error: import_zod9.z.string().nullable(),
2089
2328
  created_at: Timestamp,
2090
2329
  updated_at: Timestamp,
2091
2330
  finished_at: Timestamp.nullable()
2092
2331
  });
2093
- var ImportRow = import_zod8.z.object({
2332
+ var ImportRow = import_zod9.z.object({
2094
2333
  /** The line in the file, 1 being the first line after the header. */
2095
- row: import_zod8.z.number().int().min(1),
2096
- email: import_zod8.z.string().nullable(),
2334
+ row: import_zod9.z.number().int().min(1),
2335
+ email: import_zod9.z.string().nullable(),
2097
2336
  outcome: ImportRowOutcome,
2098
2337
  reason: ImportSkipReason.nullable(),
2099
2338
  /** A human explanation for a skipped row (which value, which column). */
2100
- message: import_zod8.z.string().nullable(),
2339
+ message: import_zod9.z.string().nullable(),
2101
2340
  contact_id: Id.nullable()
2102
2341
  });
2103
2342
  var ImportRowListQuery = PageQuery.extend({ outcome: ImportRowOutcome.optional() });
2104
- var MailingScheduleRequest = import_zod8.z.object({ send_at: Timestamp });
2105
- var TrackingSettings = import_zod8.z.object({ opens: import_zod8.z.boolean(), clicks: import_zod8.z.boolean() });
2106
- var VariantAnalytics = import_zod8.z.object({
2107
- key: import_zod8.z.string(),
2108
- sent: import_zod8.z.number().int().min(0),
2109
- unique_opens: import_zod8.z.number().int().min(0).nullable(),
2110
- unique_clicks: import_zod8.z.number().int().min(0).nullable()
2111
- });
2112
- var MailingAnalytics = import_zod8.z.object({
2343
+ var MailingScheduleRequest = import_zod9.z.object({ send_at: Timestamp });
2344
+ var TrackingSettings = import_zod9.z.object({ opens: import_zod9.z.boolean(), clicks: import_zod9.z.boolean() });
2345
+ var VariantAnalytics = import_zod9.z.object({
2346
+ key: import_zod9.z.string(),
2347
+ sent: import_zod9.z.number().int().min(0),
2348
+ unique_opens: import_zod9.z.number().int().min(0).nullable(),
2349
+ unique_clicks: import_zod9.z.number().int().min(0).nullable()
2350
+ });
2351
+ var MailingAnalytics = import_zod9.z.object({
2113
2352
  mailing_id: Id,
2114
2353
  counts: MailingCounts,
2115
2354
  /** What was tracked for this mailing, fixed when it started; null before it started. */
2116
2355
  tracking: TrackingSettings.nullable(),
2117
2356
  /** Unique recipients with a human open. Null when opens were not tracked. */
2118
- unique_opens: import_zod8.z.number().int().min(0).nullable(),
2357
+ unique_opens: import_zod9.z.number().int().min(0).nullable(),
2119
2358
  /**
2120
2359
  * Recipients whose only opens came from Apple Mail Privacy Protection, which
2121
2360
  * loads every image on delivery: counted apart, never as human opens.
2122
2361
  */
2123
- apple_mpp_opens: import_zod8.z.number().int().min(0).nullable(),
2362
+ apple_mpp_opens: import_zod9.z.number().int().min(0).nullable(),
2124
2363
  /** Opens and clicks from security scanners and prefetchers, filtered out of the unique counts. */
2125
- machine_events: import_zod8.z.number().int().min(0).nullable(),
2126
- unique_clicks: import_zod8.z.number().int().min(0).nullable(),
2127
- unsubscribes: import_zod8.z.number().int().min(0),
2128
- bounces: import_zod8.z.number().int().min(0),
2129
- complaints: import_zod8.z.number().int().min(0),
2130
- links: import_zod8.z.array(import_zod8.z.object({ url: import_zod8.z.string(), unique_clicks: import_zod8.z.number().int().min(0) })).nullable(),
2131
- variants: import_zod8.z.array(VariantAnalytics).nullable()
2364
+ machine_events: import_zod9.z.number().int().min(0).nullable(),
2365
+ unique_clicks: import_zod9.z.number().int().min(0).nullable(),
2366
+ unsubscribes: import_zod9.z.number().int().min(0),
2367
+ bounces: import_zod9.z.number().int().min(0),
2368
+ complaints: import_zod9.z.number().int().min(0),
2369
+ links: import_zod9.z.array(import_zod9.z.object({ url: import_zod9.z.string(), unique_clicks: import_zod9.z.number().int().min(0) })).nullable(),
2370
+ variants: import_zod9.z.array(VariantAnalytics).nullable()
2132
2371
  });
2133
2372
 
2134
2373
  // src/automations.ts
2135
2374
  var AUTOMATION_FILTER_FIELD_PATTERN = /^(email|first_name|last_name|locale|created_at|tag|topic|segment|engagement:(opened|clicked)|step:(opened|clicked)|property:[A-Za-z0-9_.-]{1,64}|event:[A-Za-z0-9_.-]{1,64})$/;
2136
- var AutomationFilterField = import_zod9.z.string().regex(AUTOMATION_FILTER_FIELD_PATTERN, "unknown filter field");
2375
+ var AutomationFilterField = import_zod10.z.string().regex(AUTOMATION_FILTER_FIELD_PATTERN, "unknown filter field");
2137
2376
  var AUTOMATION_FILTER_FIELD_OPERATORS = {
2138
2377
  ...FILTER_FIELD_OPERATORS,
2139
2378
  segment: ["eq", "neq", "in", "not_in"],
@@ -2143,18 +2382,18 @@ var AUTOMATION_FILTER_FIELD_OPERATORS = {
2143
2382
  step: ["eq", "neq"]
2144
2383
  };
2145
2384
  var automationFilterFamily = filterFieldFamily;
2146
- var AutomationFilterCondition = import_zod9.z.object({ field: AutomationFilterField, op: FilterOperator, value: JsonValue.optional() }).strict().refine((c) => (c.op === "exists" || c.op === "not_exists") === (c.value === void 0), {
2385
+ var AutomationFilterCondition = import_zod10.z.object({ field: AutomationFilterField, op: FilterOperator, value: JsonValue.optional() }).strict().refine((c) => (c.op === "exists" || c.op === "not_exists") === (c.value === void 0), {
2147
2386
  message: "exists and not_exists take no value; every other operator needs one",
2148
2387
  path: ["value"]
2149
2388
  }).refine((c) => c.op !== "in" && c.op !== "not_in" || Array.isArray(c.value), {
2150
2389
  message: "in and not_in take an array",
2151
2390
  path: ["value"]
2152
2391
  });
2153
- var AutomationFilter = import_zod9.z.lazy(
2154
- () => import_zod9.z.union([
2155
- import_zod9.z.object({ and: import_zod9.z.array(AutomationFilter).min(1).max(50) }).strict(),
2156
- import_zod9.z.object({ or: import_zod9.z.array(AutomationFilter).min(1).max(50) }).strict(),
2157
- import_zod9.z.object({ not: AutomationFilter }).strict(),
2392
+ var AutomationFilter = import_zod10.z.lazy(
2393
+ () => import_zod10.z.union([
2394
+ import_zod10.z.object({ and: import_zod10.z.array(AutomationFilter).min(1).max(50) }).strict(),
2395
+ import_zod10.z.object({ or: import_zod10.z.array(AutomationFilter).min(1).max(50) }).strict(),
2396
+ import_zod10.z.object({ not: AutomationFilter }).strict(),
2158
2397
  AutomationFilterCondition
2159
2398
  ])
2160
2399
  );
@@ -2167,20 +2406,20 @@ function filterConditions(filter) {
2167
2406
  if ("not" in filter) return filterConditions(filter.not);
2168
2407
  return [filter];
2169
2408
  }
2170
- var StepId = import_zod9.z.string().regex(/^[A-Za-z0-9_-]{1,64}$/, "letters, digits, underscore and hyphen, 1 to 64");
2171
- var TimeOfDay = import_zod9.z.string().regex(/^([01]\d|2[0-3]):[0-5]\d$/, "HH:MM in 24 hours");
2172
- var Weekday = import_zod9.z.number().int().min(0).max(6);
2173
- var TimezoneName = import_zod9.z.string().min(1).max(64).regex(/^(UTC|[A-Za-z][A-Za-z0-9_+-]*(?:\/[A-Za-z0-9_+-]+)+)$/, "an IANA time zone name such as Europe/Berlin");
2409
+ var StepId = import_zod10.z.string().regex(/^[A-Za-z0-9_-]{1,64}$/, "letters, digits, underscore and hyphen, 1 to 64");
2410
+ var TimeOfDay = import_zod10.z.string().regex(/^([01]\d|2[0-3]):[0-5]\d$/, "HH:MM in 24 hours");
2411
+ var Weekday = import_zod10.z.number().int().min(0).max(6);
2412
+ var TimezoneName = import_zod10.z.string().min(1).max(64).regex(/^(UTC|[A-Za-z][A-Za-z0-9_+-]*(?:\/[A-Za-z0-9_+-]+)+)$/, "an IANA time zone name such as Europe/Berlin");
2174
2413
  var MAX_DELAY_SECONDS = 365 * 24 * 60 * 60;
2175
- var DateOnly = import_zod9.z.string().regex(/^\d{4}-\d{2}-\d{2}$/, "a calendar date such as 2026-09-20").refine((v) => {
2414
+ var DateOnly = import_zod10.z.string().regex(/^\d{4}-\d{2}-\d{2}$/, "a calendar date such as 2026-09-20").refine((v) => {
2176
2415
  const [y, m, d] = v.split("-").map(Number);
2177
2416
  const t = new Date(Date.UTC(y, m - 1, d));
2178
2417
  return t.getUTCFullYear() === y && t.getUTCMonth() + 1 === m && t.getUTCDate() === d;
2179
2418
  }, "a real calendar date");
2180
- var OffsetDays = import_zod9.z.number().int().min(-365).max(365);
2419
+ var OffsetDays = import_zod10.z.number().int().min(-365).max(365);
2181
2420
  var DATE_PASSED_ANSWERS = ["skip", "stop", "continue"];
2182
- var DatePassedAnswer = import_zod9.z.enum(DATE_PASSED_ANSWERS);
2183
- var EventName = import_zod9.z.string().regex(/^[A-Za-z0-9][A-Za-z0-9_.:-]{0,79}$/, "letters, digits, dot, colon, underscore and hyphen, 1 to 80");
2421
+ var DatePassedAnswer = import_zod10.z.enum(DATE_PASSED_ANSWERS);
2422
+ var EventName = import_zod10.z.string().regex(/^[A-Za-z0-9][A-Za-z0-9_.:-]{0,79}$/, "letters, digits, dot, colon, underscore and hyphen, 1 to 80");
2184
2423
  var AUTOMATION_TRIGGER_KINDS = [
2185
2424
  "topic_subscribed",
2186
2425
  "form_confirmed",
@@ -2193,17 +2432,17 @@ var AUTOMATION_TRIGGER_KINDS = [
2193
2432
  "segment_entered",
2194
2433
  "link_clicked"
2195
2434
  ];
2196
- var AutomationTriggerKind = import_zod9.z.enum(AUTOMATION_TRIGGER_KINDS);
2435
+ var AutomationTriggerKind = import_zod10.z.enum(AUTOMATION_TRIGGER_KINDS);
2197
2436
  var exclude = { exclude: BoundedAutomationFilter.nullish() };
2198
- var AutomationTrigger = import_zod9.z.discriminatedUnion("kind", [
2199
- import_zod9.z.object({ kind: import_zod9.z.literal("topic_subscribed"), topic: Slug, ...exclude }).strict(),
2200
- import_zod9.z.object({ kind: import_zod9.z.literal("form_confirmed"), form_id: Id, ...exclude }).strict(),
2201
- import_zod9.z.object({ kind: import_zod9.z.literal("tag_added"), tag: Slug, ...exclude }).strict(),
2437
+ var AutomationTrigger = import_zod10.z.discriminatedUnion("kind", [
2438
+ import_zod10.z.object({ kind: import_zod10.z.literal("topic_subscribed"), topic: Slug, ...exclude }).strict(),
2439
+ import_zod10.z.object({ kind: import_zod10.z.literal("form_confirmed"), form_id: Id, ...exclude }).strict(),
2440
+ import_zod10.z.object({ kind: import_zod10.z.literal("tag_added"), tag: Slug, ...exclude }).strict(),
2202
2441
  /** `to` given: only a change that lands on this value fires. Absent: any change of the key. */
2203
- import_zod9.z.object({ kind: import_zod9.z.literal("property_changed"), key: ContactPropertyKey, to: JsonValue.optional(), ...exclude }).strict(),
2442
+ import_zod10.z.object({ kind: import_zod10.z.literal("property_changed"), key: ContactPropertyKey, to: JsonValue.optional(), ...exclude }).strict(),
2204
2443
  /** `where` filters the event's own data, so only `event:<key>` leaves belong in it. */
2205
- import_zod9.z.object({ kind: import_zod9.z.literal("event"), name: EventName, where: BoundedAutomationFilter.nullish(), ...exclude }).strict(),
2206
- import_zod9.z.object({ kind: import_zod9.z.literal("manual"), ...exclude }).strict(),
2444
+ import_zod10.z.object({ kind: import_zod10.z.literal("event"), name: EventName, where: BoundedAutomationFilter.nullish(), ...exclude }).strict(),
2445
+ import_zod10.z.object({ kind: import_zod10.z.literal("manual"), ...exclude }).strict(),
2207
2446
  /**
2208
2447
  * Every year on a date the contact carries: a birthday, a joining date, a
2209
2448
  * renewal. `offset_days` moves it ("three days before"), `at` is the wall
@@ -2213,8 +2452,8 @@ var AutomationTrigger = import_zod9.z.discriminatedUnion("kind", [
2213
2452
  * A 29 February date fires on 1 March in a year that has no 29 February, so
2214
2453
  * nobody is skipped every fourth year.
2215
2454
  */
2216
- import_zod9.z.object({
2217
- kind: import_zod9.z.literal("date_anniversary"),
2455
+ import_zod10.z.object({
2456
+ kind: import_zod10.z.literal("date_anniversary"),
2218
2457
  key: ContactPropertyKey,
2219
2458
  offset_days: OffsetDays,
2220
2459
  at: TimeOfDay,
@@ -2226,8 +2465,8 @@ var AutomationTrigger = import_zod9.z.discriminatedUnion("kind", [
2226
2465
  * not ask about a segment or about an event's data: there is no event, and a
2227
2466
  * segment is its own trigger kind.
2228
2467
  */
2229
- import_zod9.z.object({
2230
- kind: import_zod9.z.literal("exact_date"),
2468
+ import_zod10.z.object({
2469
+ kind: import_zod10.z.literal("exact_date"),
2231
2470
  on: DateOnly,
2232
2471
  at: TimeOfDay,
2233
2472
  where: BoundedAutomationFilter.nullish(),
@@ -2246,7 +2485,7 @@ var AutomationTrigger = import_zod9.z.discriminatedUnion("kind", [
2246
2485
  * already exists. Entering those people as well is the publish dialog's
2247
2486
  * backfill question, answered by a person rather than by the sweep.
2248
2487
  */
2249
- import_zod9.z.object({ kind: import_zod9.z.literal("segment_entered"), segment_id: Id, ...exclude }).strict(),
2488
+ import_zod10.z.object({ kind: import_zod10.z.literal("segment_entered"), segment_id: Id, ...exclude }).strict(),
2250
2489
  /**
2251
2490
  * S4. When somebody clicks a link in a mailing that has already gone out.
2252
2491
  *
@@ -2256,7 +2495,7 @@ var AutomationTrigger = import_zod9.z.discriminatedUnion("kind", [
2256
2495
  * tracking off there is no click to hear about, so the validator refuses it
2257
2496
  * rather than leaving an automation that can never fire.
2258
2497
  */
2259
- import_zod9.z.object({ kind: import_zod9.z.literal("link_clicked"), mailing_id: Id, url: import_zod9.z.string().min(1).max(2048).optional(), ...exclude }).strict()
2498
+ import_zod10.z.object({ kind: import_zod10.z.literal("link_clicked"), mailing_id: Id, url: import_zod10.z.string().min(1).max(2048).optional(), ...exclude }).strict()
2260
2499
  ]);
2261
2500
  var AUTOMATION_DATE_TRIGGER_KINDS = ["date_anniversary", "exact_date"];
2262
2501
  var MAX_TRIGGERS = 10;
@@ -2275,45 +2514,45 @@ var AUTOMATION_STEP_KINDS = [
2275
2514
  "webhook",
2276
2515
  "notify"
2277
2516
  ];
2278
- var AutomationStepKind = import_zod9.z.enum(AUTOMATION_STEP_KINDS);
2517
+ var AutomationStepKind = import_zod10.z.enum(AUTOMATION_STEP_KINDS);
2279
2518
  var next = { next: StepId.nullable() };
2280
- var Unchosen = import_zod9.z.literal("");
2281
- var DraftSlug = import_zod9.z.union([Slug, Unchosen]);
2282
- var DraftPropertyKey = import_zod9.z.union([ContactPropertyKey, Unchosen]);
2283
- var label2 = { label: import_zod9.z.string().max(120).nullish() };
2284
- var EmailStepLanguage = import_zod9.z.object({
2285
- subject: import_zod9.z.string().min(1).max(998),
2286
- preheader: import_zod9.z.string().max(500).nullable(),
2519
+ var Unchosen = import_zod10.z.literal("");
2520
+ var DraftSlug = import_zod10.z.union([Slug, Unchosen]);
2521
+ var DraftPropertyKey = import_zod10.z.union([ContactPropertyKey, Unchosen]);
2522
+ var label2 = { label: import_zod10.z.string().max(120).nullish() };
2523
+ var EmailStepLanguage = import_zod10.z.object({
2524
+ subject: import_zod10.z.string().min(1).max(998),
2525
+ preheader: import_zod10.z.string().max(500).nullable(),
2287
2526
  document: TemplateDocument,
2288
2527
  /** This language's insertions, its texts over the template's structure (every text present). */
2289
2528
  insertions: Insertions.nullish()
2290
2529
  }).strict();
2291
- var EmailStep = import_zod9.z.object({
2292
- kind: import_zod9.z.literal("email"),
2530
+ var EmailStep = import_zod10.z.object({
2531
+ kind: import_zod10.z.literal("email"),
2293
2532
  ...label2,
2294
2533
  ...next,
2295
2534
  template_id: Id.nullish(),
2296
2535
  document: TemplateDocument.nullish(),
2297
2536
  /** Empty while the step is being written, or when its template has a subject; else `not_chosen` refuses to publish it. */
2298
- subject: import_zod9.z.string().max(998),
2299
- preheader: import_zod9.z.string().max(500).nullish(),
2537
+ subject: import_zod10.z.string().max(998),
2538
+ preheader: import_zod10.z.string().max(500).nullish(),
2300
2539
  locale: LocaleTag.nullish(),
2301
- languages: import_zod9.z.record(LocaleTag, EmailStepLanguage).nullish(),
2540
+ languages: import_zod10.z.record(LocaleTag, EmailStepLanguage).nullish(),
2302
2541
  /** The main language's insertions, snapshot from the template when the automation is published. */
2303
2542
  insertions: Insertions.nullish()
2304
2543
  }).strict();
2305
- var DelayStep = import_zod9.z.object({
2306
- kind: import_zod9.z.literal("delay"),
2544
+ var DelayStep = import_zod10.z.object({
2545
+ kind: import_zod10.z.literal("delay"),
2307
2546
  ...label2,
2308
2547
  ...next,
2309
- wait: import_zod9.z.discriminatedUnion("mode", [
2310
- import_zod9.z.object({ mode: import_zod9.z.literal("duration"), seconds: import_zod9.z.number().int().min(1).max(MAX_DELAY_SECONDS) }).strict(),
2311
- import_zod9.z.object({ mode: import_zod9.z.literal("time_of_day"), at: TimeOfDay }).strict(),
2312
- import_zod9.z.object({ mode: import_zod9.z.literal("weekday"), weekday: Weekday, at: TimeOfDay }).strict(),
2548
+ wait: import_zod10.z.discriminatedUnion("mode", [
2549
+ import_zod10.z.object({ mode: import_zod10.z.literal("duration"), seconds: import_zod10.z.number().int().min(1).max(MAX_DELAY_SECONDS) }).strict(),
2550
+ import_zod10.z.object({ mode: import_zod10.z.literal("time_of_day"), at: TimeOfDay }).strict(),
2551
+ import_zod10.z.object({ mode: import_zod10.z.literal("weekday"), weekday: Weekday, at: TimeOfDay }).strict(),
2313
2552
  /** A fixed day has no next occurrence, so `continue` is not one of its answers. */
2314
- import_zod9.z.object({ mode: import_zod9.z.literal("date"), on: DateOnly, at: TimeOfDay, passed: import_zod9.z.enum(["skip", "stop"]) }).strict(),
2315
- import_zod9.z.object({
2316
- mode: import_zod9.z.literal("date_property"),
2553
+ import_zod10.z.object({ mode: import_zod10.z.literal("date"), on: DateOnly, at: TimeOfDay, passed: import_zod10.z.enum(["skip", "stop"]) }).strict(),
2554
+ import_zod10.z.object({
2555
+ mode: import_zod10.z.literal("date_property"),
2317
2556
  key: ContactPropertyKey,
2318
2557
  offset_days: OffsetDays,
2319
2558
  at: TimeOfDay,
@@ -2321,8 +2560,8 @@ var DelayStep = import_zod9.z.object({
2321
2560
  }).strict()
2322
2561
  ])
2323
2562
  }).strict();
2324
- var ConditionStep = import_zod9.z.object({
2325
- kind: import_zod9.z.literal("condition"),
2563
+ var ConditionStep = import_zod10.z.object({
2564
+ kind: import_zod10.z.literal("condition"),
2326
2565
  ...label2,
2327
2566
  filter: BoundedAutomationFilter,
2328
2567
  yes: StepId.nullable(),
@@ -2333,49 +2572,49 @@ var ConditionStep = import_zod9.z.object({
2333
2572
  * neither half means anything without the other: a window with no answer
2334
2573
  * for the end of it would be a silent decision.
2335
2574
  */
2336
- wait_for: import_zod9.z.object({ up_to_s: import_zod9.z.number().int().min(1).max(MAX_DELAY_SECONDS), on_timeout: import_zod9.z.enum(["yes", "no"]) }).strict().nullish()
2575
+ wait_for: import_zod10.z.object({ up_to_s: import_zod10.z.number().int().min(1).max(MAX_DELAY_SECONDS), on_timeout: import_zod10.z.enum(["yes", "no"]) }).strict().nullish()
2337
2576
  }).strict();
2338
- var SplitBranchKey = import_zod9.z.string().regex(/^[A-Za-z0-9_-]{1,32}$/, "letters, digits, underscore and hyphen, 1 to 32");
2577
+ var SplitBranchKey = import_zod10.z.string().regex(/^[A-Za-z0-9_-]{1,32}$/, "letters, digits, underscore and hyphen, 1 to 32");
2339
2578
  var MIN_SPLIT_BRANCHES = 2;
2340
2579
  var MAX_SPLIT_BRANCHES = 4;
2341
- var SplitStep = import_zod9.z.object({
2342
- kind: import_zod9.z.literal("split"),
2580
+ var SplitStep = import_zod10.z.object({
2581
+ kind: import_zod10.z.literal("split"),
2343
2582
  ...label2,
2344
- branches: import_zod9.z.array(
2345
- import_zod9.z.object({
2583
+ branches: import_zod10.z.array(
2584
+ import_zod10.z.object({
2346
2585
  key: SplitBranchKey,
2347
2586
  /** A whole percentage. Zero is allowed: a branch kept in the flow but switched off. */
2348
- weight: import_zod9.z.number().int().min(0).max(100),
2587
+ weight: import_zod10.z.number().int().min(0).max(100),
2349
2588
  next: StepId.nullable()
2350
2589
  }).strict()
2351
2590
  ).min(MIN_SPLIT_BRANCHES).max(MAX_SPLIT_BRANCHES).refine((bs) => new Set(bs.map((b) => b.key)).size === bs.length, "each branch needs its own key").refine((bs) => bs.reduce((sum, b) => sum + b.weight, 0) === 100, "the weights have to come to 100")
2352
2591
  }).strict();
2353
- var GotoStep = import_zod9.z.object({ kind: import_zod9.z.literal("goto"), ...label2, target: StepId.nullable() }).strict();
2592
+ var GotoStep = import_zod10.z.object({ kind: import_zod10.z.literal("goto"), ...label2, target: StepId.nullable() }).strict();
2354
2593
  var MAX_STEP_VISITS = 20;
2355
- var WebhookStep = import_zod9.z.object({ kind: import_zod9.z.literal("webhook"), ...label2, ...next, endpoint_id: Id.nullable(), payload: JsonValue.nullish() }).strict();
2356
- var NotifyRecipients = import_zod9.z.union([import_zod9.z.literal("owner"), import_zod9.z.literal("admins"), import_zod9.z.object({ member_id: Id }).strict()]);
2357
- var NotifyStep = import_zod9.z.object({
2358
- kind: import_zod9.z.literal("notify"),
2594
+ var WebhookStep = import_zod10.z.object({ kind: import_zod10.z.literal("webhook"), ...label2, ...next, endpoint_id: Id.nullable(), payload: JsonValue.nullish() }).strict();
2595
+ var NotifyRecipients = import_zod10.z.union([import_zod10.z.literal("owner"), import_zod10.z.literal("admins"), import_zod10.z.object({ member_id: Id }).strict()]);
2596
+ var NotifyStep = import_zod10.z.object({
2597
+ kind: import_zod10.z.literal("notify"),
2359
2598
  ...label2,
2360
2599
  ...next,
2361
2600
  to: NotifyRecipients,
2362
2601
  /** Empty while the step is being written; `not_chosen` refuses to publish it. */
2363
- subject: import_zod9.z.string().max(998),
2364
- body: import_zod9.z.string().max(1e4)
2602
+ subject: import_zod10.z.string().max(998),
2603
+ body: import_zod10.z.string().max(1e4)
2365
2604
  }).strict();
2366
- var AutomationStep = import_zod9.z.discriminatedUnion("kind", [
2605
+ var AutomationStep = import_zod10.z.discriminatedUnion("kind", [
2367
2606
  EmailStep,
2368
2607
  DelayStep,
2369
2608
  ConditionStep,
2370
- import_zod9.z.object({ kind: import_zod9.z.literal("add_tag"), ...label2, ...next, tag: DraftSlug }).strict(),
2371
- import_zod9.z.object({ kind: import_zod9.z.literal("remove_tag"), ...label2, ...next, tag: DraftSlug }).strict(),
2609
+ import_zod10.z.object({ kind: import_zod10.z.literal("add_tag"), ...label2, ...next, tag: DraftSlug }).strict(),
2610
+ import_zod10.z.object({ kind: import_zod10.z.literal("remove_tag"), ...label2, ...next, tag: DraftSlug }).strict(),
2372
2611
  /** `value` null clears the property, as a contact upsert does. */
2373
- import_zod9.z.object({ kind: import_zod9.z.literal("set_property"), ...label2, ...next, key: DraftPropertyKey, value: JsonValue }).strict(),
2612
+ import_zod10.z.object({ kind: import_zod10.z.literal("set_property"), ...label2, ...next, key: DraftPropertyKey, value: JsonValue }).strict(),
2374
2613
  /** Subscribing never lifts a suppression: the service checks that, not the flow. */
2375
- import_zod9.z.object({ kind: import_zod9.z.literal("subscribe_topic"), ...label2, ...next, topic: DraftSlug }).strict(),
2614
+ import_zod10.z.object({ kind: import_zod10.z.literal("subscribe_topic"), ...label2, ...next, topic: DraftSlug }).strict(),
2376
2615
  /** `topic` unsubscribes from the automation's own topic, `all` from every topic. */
2377
- import_zod9.z.object({ kind: import_zod9.z.literal("unsubscribe"), ...label2, ...next, scope: import_zod9.z.enum(["topic", "all"]) }).strict(),
2378
- import_zod9.z.object({ kind: import_zod9.z.literal("exit"), ...label2 }).strict(),
2616
+ import_zod10.z.object({ kind: import_zod10.z.literal("unsubscribe"), ...label2, ...next, scope: import_zod10.z.enum(["topic", "all"]) }).strict(),
2617
+ import_zod10.z.object({ kind: import_zod10.z.literal("exit"), ...label2 }).strict(),
2379
2618
  SplitStep,
2380
2619
  GotoStep,
2381
2620
  WebhookStep,
@@ -2399,25 +2638,25 @@ function stepTargets(step) {
2399
2638
  }
2400
2639
  }
2401
2640
  var MAX_STEPS = 200;
2402
- var AutomationFlow = import_zod9.z.object({
2403
- triggers: import_zod9.z.array(AutomationTrigger).max(MAX_TRIGGERS),
2641
+ var AutomationFlow = import_zod10.z.object({
2642
+ triggers: import_zod10.z.array(AutomationTrigger).max(MAX_TRIGGERS),
2404
2643
  /** The first step. `null` is an empty flow. */
2405
2644
  entry: StepId.nullable(),
2406
- steps: import_zod9.z.record(StepId, AutomationStep)
2645
+ steps: import_zod10.z.record(StepId, AutomationStep)
2407
2646
  }).strict();
2408
2647
  var emptyFlow = () => ({ triggers: [], entry: null, steps: {} });
2409
- var QuietHours = import_zod9.z.object({
2648
+ var QuietHours = import_zod10.z.object({
2410
2649
  start: TimeOfDay,
2411
2650
  end: TimeOfDay,
2412
- weekdays: import_zod9.z.array(Weekday).min(1).max(7).nullish()
2651
+ weekdays: import_zod10.z.array(Weekday).min(1).max(7).nullish()
2413
2652
  }).strict();
2414
2653
  var RE_ENTRY_MODES = ["off", "after_exit"];
2415
- var ReEntryMode = import_zod9.z.enum(RE_ENTRY_MODES);
2654
+ var ReEntryMode = import_zod10.z.enum(RE_ENTRY_MODES);
2416
2655
  var MAX_RE_ENTRY_COOLDOWN_SECONDS = 365 * 24 * 60 * 60;
2417
- var AutomationSettings = import_zod9.z.object({
2656
+ var AutomationSettings = import_zod10.z.object({
2418
2657
  re_entry: ReEntryMode,
2419
2658
  /** Seconds a person must wait after leaving before entering again. Only with `after_exit`. */
2420
- re_entry_cooldown_s: import_zod9.z.number().int().min(0).max(MAX_RE_ENTRY_COOLDOWN_SECONDS).nullish(),
2659
+ re_entry_cooldown_s: import_zod10.z.number().int().min(0).max(MAX_RE_ENTRY_COOLDOWN_SECONDS).nullish(),
2421
2660
  quiet_hours: QuietHours.nullish(),
2422
2661
  /** Checked before every step; when it matches, the run ends. */
2423
2662
  exit_filter: BoundedAutomationFilter.nullish()
@@ -2475,18 +2714,18 @@ var AUTOMATION_ISSUE_CODES = [
2475
2714
  /** A one-off date that is already over everywhere on earth, so it would fire for nobody. */
2476
2715
  "date_in_the_past"
2477
2716
  ];
2478
- var AutomationIssueCode = import_zod9.z.enum(AUTOMATION_ISSUE_CODES);
2479
- var AutomationIssue = import_zod9.z.object({
2717
+ var AutomationIssueCode = import_zod10.z.enum(AUTOMATION_ISSUE_CODES);
2718
+ var AutomationIssue = import_zod10.z.object({
2480
2719
  code: AutomationIssueCode,
2481
2720
  /** The step the issue is about, when it is about one. */
2482
2721
  step_id: StepId.nullable(),
2483
2722
  /** Where inside the document, for the canvas to point at a field. */
2484
- path: import_zod9.z.array(import_zod9.z.union([import_zod9.z.string(), import_zod9.z.number()])),
2485
- message: import_zod9.z.string()
2723
+ path: import_zod10.z.array(import_zod10.z.union([import_zod10.z.string(), import_zod10.z.number()])),
2724
+ message: import_zod10.z.string()
2486
2725
  });
2487
- var AutomationValidation = import_zod9.z.object({
2488
- ok: import_zod9.z.boolean(),
2489
- issues: import_zod9.z.array(AutomationIssue)
2726
+ var AutomationValidation = import_zod10.z.object({
2727
+ ok: import_zod10.z.boolean(),
2728
+ issues: import_zod10.z.array(AutomationIssue)
2490
2729
  });
2491
2730
  function validateAutomation(flow, settings, ctx) {
2492
2731
  const issues = [];
@@ -2877,7 +3116,7 @@ function cycles(flow) {
2877
3116
  return out.sort();
2878
3117
  }
2879
3118
  var AUTOMATION_STATUSES = ["draft", "active", "paused", "archived"];
2880
- var AutomationStatus = import_zod9.z.enum(AUTOMATION_STATUSES);
3119
+ var AutomationStatus = import_zod10.z.enum(AUTOMATION_STATUSES);
2881
3120
  var AUTOMATION_END_REASONS = [
2882
3121
  "completed",
2883
3122
  "exit_filter",
@@ -2896,9 +3135,9 @@ var AUTOMATION_END_REASONS = [
2896
3135
  "ended_by_hand",
2897
3136
  "failed"
2898
3137
  ];
2899
- var AutomationEndReason = import_zod9.z.enum(AUTOMATION_END_REASONS);
3138
+ var AutomationEndReason = import_zod10.z.enum(AUTOMATION_END_REASONS);
2900
3139
  var AUTOMATION_WAIT_REASONS = ["delay", "quiet_hours", "plan_limit", "sending", "condition"];
2901
- var AutomationWaitReason = import_zod9.z.enum(AUTOMATION_WAIT_REASONS);
3140
+ var AutomationWaitReason = import_zod10.z.enum(AUTOMATION_WAIT_REASONS);
2902
3141
  var AUTOMATION_ENTRY_REFUSALS = [
2903
3142
  "already_inside",
2904
3143
  "re_entry_off",
@@ -2909,26 +3148,26 @@ var AUTOMATION_ENTRY_REFUSALS = [
2909
3148
  "not_active",
2910
3149
  "unknown_contact"
2911
3150
  ];
2912
- var AutomationEntryRefusal = import_zod9.z.enum(AUTOMATION_ENTRY_REFUSALS);
2913
- var AutomationCounts = import_zod9.z.object({
2914
- started: import_zod9.z.number().int().min(0),
2915
- in_progress: import_zod9.z.number().int().min(0),
2916
- completed: import_zod9.z.number().int().min(0),
2917
- exited: import_zod9.z.number().int().min(0),
2918
- failed: import_zod9.z.number().int().min(0)
2919
- });
2920
- var Automation = import_zod9.z.object({
3151
+ var AutomationEntryRefusal = import_zod10.z.enum(AUTOMATION_ENTRY_REFUSALS);
3152
+ var AutomationCounts = import_zod10.z.object({
3153
+ started: import_zod10.z.number().int().min(0),
3154
+ in_progress: import_zod10.z.number().int().min(0),
3155
+ completed: import_zod10.z.number().int().min(0),
3156
+ exited: import_zod10.z.number().int().min(0),
3157
+ failed: import_zod10.z.number().int().min(0)
3158
+ });
3159
+ var Automation = import_zod10.z.object({
2921
3160
  id: Id,
2922
- name: import_zod9.z.string().min(1).max(200),
3161
+ name: import_zod10.z.string().min(1).max(200),
2923
3162
  status: AutomationStatus,
2924
3163
  /** Every automation sends under one topic; there are no transactional automations. */
2925
3164
  topic: Slug,
2926
3165
  provider_id: Id.nullable(),
2927
3166
  settings: AutomationSettings,
2928
3167
  /** The flow people are running through, null while the automation has never been published. */
2929
- published_version: import_zod9.z.number().int().min(1).nullable(),
3168
+ published_version: import_zod10.z.number().int().min(1).nullable(),
2930
3169
  /** The flow being edited. Increments on every save, like a template's version. */
2931
- draft_version: import_zod9.z.number().int().min(1),
3170
+ draft_version: import_zod10.z.number().int().min(1),
2932
3171
  counts: AutomationCounts,
2933
3172
  created_at: Timestamp,
2934
3173
  updated_at: Timestamp,
@@ -2941,16 +3180,16 @@ var AutomationWithFlow = Automation.extend({
2941
3180
  published_flow: AutomationFlow.nullable()
2942
3181
  });
2943
3182
  var AutomationSummary = Automation;
2944
- var AutomationCreate = import_zod9.z.object({
2945
- name: import_zod9.z.string().min(1).max(200),
3183
+ var AutomationCreate = import_zod10.z.object({
3184
+ name: import_zod10.z.string().min(1).max(200),
2946
3185
  topic: Slug,
2947
3186
  provider_id: Id.optional(),
2948
3187
  flow: AutomationFlow.optional(),
2949
3188
  settings: AutomationSettings.partial().optional()
2950
3189
  });
2951
- var AutomationUpdate = import_zod9.z.object({
2952
- base_version: import_zod9.z.number().int().min(1),
2953
- name: import_zod9.z.string().min(1).max(200).optional(),
3190
+ var AutomationUpdate = import_zod10.z.object({
3191
+ base_version: import_zod10.z.number().int().min(1),
3192
+ name: import_zod10.z.string().min(1).max(200).optional(),
2954
3193
  topic: Slug.optional(),
2955
3194
  provider_id: Id.optional(),
2956
3195
  flow: AutomationFlow.optional(),
@@ -2963,42 +3202,42 @@ var AutomationListQuery = PageQuery.extend({
2963
3202
  status: AutomationStatus.optional(),
2964
3203
  topic: Slug.optional()
2965
3204
  });
2966
- var AutomationPublishRequest = import_zod9.z.object({
3205
+ var AutomationPublishRequest = import_zod10.z.object({
2967
3206
  /**
2968
3207
  * Answer what this publish would do and change nothing, whatever the flow
2969
3208
  * looks like. Without it a publish that has no issues and moves nobody
2970
3209
  * simply goes ahead, which is right for an API caller and wrong for a
2971
3210
  * dialog that is only showing somebody what they are about to do.
2972
3211
  */
2973
- dry_run: import_zod9.z.boolean().optional(),
2974
- confirm: import_zod9.z.boolean().optional(),
3212
+ dry_run: import_zod10.z.boolean().optional(),
3213
+ confirm: import_zod10.z.boolean().optional(),
2975
3214
  /** Per removed step: the step its waiting runs move to, or null to end them. */
2976
- moves: import_zod9.z.record(StepId, StepId.nullable()).optional(),
3215
+ moves: import_zod10.z.record(StepId, StepId.nullable()).optional(),
2977
3216
  /** Also enter everyone who matches a trigger's condition right now. */
2978
- backfill: import_zod9.z.boolean().optional()
3217
+ backfill: import_zod10.z.boolean().optional()
2979
3218
  }).strict();
2980
- var AutomationPublishMove = import_zod9.z.object({
3219
+ var AutomationPublishMove = import_zod10.z.object({
2981
3220
  step_id: StepId,
2982
3221
  /** Why the step's people have to move: it is gone, or its delay changed. */
2983
- change: import_zod9.z.enum(["removed", "delay_changed", "kind_changed"]),
2984
- waiting: import_zod9.z.number().int().min(0),
3222
+ change: import_zod10.z.enum(["removed", "delay_changed", "kind_changed"]),
3223
+ waiting: import_zod10.z.number().int().min(0),
2985
3224
  /** Where they go: a step id, or null to end their runs with `step_removed`. */
2986
3225
  destination: StepId.nullable()
2987
3226
  });
2988
- var AutomationPublishResult = import_zod9.z.object({
2989
- published: import_zod9.z.boolean(),
3227
+ var AutomationPublishResult = import_zod10.z.object({
3228
+ published: import_zod10.z.boolean(),
2990
3229
  automation: Automation,
2991
3230
  /** Empty when nothing has to move; non-empty and `published` false asks for a confirmation. */
2992
- moves: import_zod9.z.array(AutomationPublishMove),
3231
+ moves: import_zod10.z.array(AutomationPublishMove),
2993
3232
  /** How many people the backfill entered, or would enter when it is not confirmed. */
2994
- backfill: import_zod9.z.number().int().min(0),
2995
- issues: import_zod9.z.array(AutomationIssue)
2996
- });
2997
- var AutomationDuplicateRequest = import_zod9.z.object({ name: import_zod9.z.string().min(1).max(200).optional() }).strict();
2998
- var AutomationEnrollRequest = import_zod9.z.object({
2999
- contact_ids: import_zod9.z.array(Id).min(1).max(1e3).optional(),
3000
- external_ids: import_zod9.z.array(import_zod9.z.string().min(1).max(255)).min(1).max(1e3).optional(),
3001
- emails: import_zod9.z.array(Email).min(1).max(1e3).optional(),
3233
+ backfill: import_zod10.z.number().int().min(0),
3234
+ issues: import_zod10.z.array(AutomationIssue)
3235
+ });
3236
+ var AutomationDuplicateRequest = import_zod10.z.object({ name: import_zod10.z.string().min(1).max(200).optional() }).strict();
3237
+ var AutomationEnrollRequest = import_zod10.z.object({
3238
+ contact_ids: import_zod10.z.array(Id).min(1).max(1e3).optional(),
3239
+ external_ids: import_zod10.z.array(import_zod10.z.string().min(1).max(255)).min(1).max(1e3).optional(),
3240
+ emails: import_zod10.z.array(Email).min(1).max(1e3).optional(),
3002
3241
  segment_id: Id.optional(),
3003
3242
  /** Where to start them; the flow's entry step by default. */
3004
3243
  step_id: StepId.optional()
@@ -3006,34 +3245,34 @@ var AutomationEnrollRequest = import_zod9.z.object({
3006
3245
  (v) => [v.contact_ids, v.external_ids, v.emails, v.segment_id].filter((x) => x !== void 0).length === 1,
3007
3246
  "name the people exactly one way: contact_ids, external_ids, emails or segment_id"
3008
3247
  );
3009
- var AutomationEnrollment = import_zod9.z.object({
3248
+ var AutomationEnrollment = import_zod10.z.object({
3010
3249
  contact_id: Id.nullable(),
3011
3250
  email: Email.nullable(),
3012
- external_id: import_zod9.z.string().nullable(),
3013
- entered: import_zod9.z.boolean(),
3251
+ external_id: import_zod10.z.string().nullable(),
3252
+ entered: import_zod10.z.boolean(),
3014
3253
  run_id: Id.nullable(),
3015
3254
  reason: AutomationEntryRefusal.nullable()
3016
3255
  });
3017
- var AutomationEnrollResult = import_zod9.z.object({
3018
- entered: import_zod9.z.number().int().min(0),
3019
- refused: import_zod9.z.number().int().min(0),
3020
- results: import_zod9.z.array(AutomationEnrollment)
3256
+ var AutomationEnrollResult = import_zod10.z.object({
3257
+ entered: import_zod10.z.number().int().min(0),
3258
+ refused: import_zod10.z.number().int().min(0),
3259
+ results: import_zod10.z.array(AutomationEnrollment)
3021
3260
  });
3022
- var AutomationRunStatus = import_zod9.z.enum(["active", "waiting", "completed", "exited", "failed"]);
3023
- var AutomationRun = import_zod9.z.object({
3261
+ var AutomationRunStatus = import_zod10.z.enum(["active", "waiting", "completed", "exited", "failed"]);
3262
+ var AutomationRun = import_zod10.z.object({
3024
3263
  id: Id,
3025
3264
  automation_id: Id,
3026
3265
  contact_id: Id,
3027
3266
  email: Email,
3028
- external_id: import_zod9.z.string().nullable(),
3029
- version: import_zod9.z.number().int().min(1),
3267
+ external_id: import_zod10.z.string().nullable(),
3268
+ version: import_zod10.z.number().int().min(1),
3030
3269
  status: AutomationRunStatus,
3031
3270
  current_step_id: StepId.nullable(),
3032
3271
  next_action_at: Timestamp.nullable(),
3033
3272
  wait_reason: AutomationWaitReason.nullable(),
3034
- end_reason: import_zod9.z.string().nullable(),
3273
+ end_reason: import_zod10.z.string().nullable(),
3035
3274
  /** What went wrong the last time this run tried to take its step, null otherwise. */
3036
- last_error: import_zod9.z.string().nullable(),
3275
+ last_error: import_zod10.z.string().nullable(),
3037
3276
  entered_at: Timestamp,
3038
3277
  ended_at: Timestamp.nullable()
3039
3278
  });
@@ -3043,13 +3282,13 @@ var AutomationRunListQuery = PageQuery.extend({
3043
3282
  contact_id: Id.optional()
3044
3283
  });
3045
3284
  var ContactAutomationRun = AutomationRun.extend({
3046
- automation: import_zod9.z.object({ id: Id, name: import_zod9.z.string(), status: AutomationStatus })
3285
+ automation: import_zod10.z.object({ id: Id, name: import_zod10.z.string(), status: AutomationStatus })
3047
3286
  });
3048
3287
  var ContactAutomationListQuery = PageQuery.extend({ status: AutomationRunStatus.optional() });
3049
- var AutomationStepExecution = import_zod9.z.object({
3288
+ var AutomationStepExecution = import_zod10.z.object({
3050
3289
  step_id: StepId,
3051
3290
  step_kind: AutomationStepKind,
3052
- visit: import_zod9.z.number().int().min(1),
3291
+ visit: import_zod10.z.number().int().min(1),
3053
3292
  started_at: Timestamp,
3054
3293
  finished_at: Timestamp.nullable(),
3055
3294
  /**
@@ -3061,48 +3300,48 @@ var AutomationStepExecution = import_zod9.z.object({
3061
3300
  */
3062
3301
  outcome: Properties
3063
3302
  });
3064
- var AutomationJourney = import_zod9.z.object({
3303
+ var AutomationJourney = import_zod10.z.object({
3065
3304
  run: AutomationRun,
3066
- steps: import_zod9.z.array(AutomationStepExecution)
3305
+ steps: import_zod10.z.array(AutomationStepExecution)
3067
3306
  });
3068
- var AutomationStepReport = import_zod9.z.object({
3307
+ var AutomationStepReport = import_zod10.z.object({
3069
3308
  step_id: StepId,
3070
3309
  step_kind: AutomationStepKind,
3071
- reached: import_zod9.z.number().int().min(0),
3072
- waiting: import_zod9.z.number().int().min(0),
3073
- passed: import_zod9.z.number().int().min(0),
3310
+ reached: import_zod10.z.number().int().min(0),
3311
+ waiting: import_zod10.z.number().int().min(0),
3312
+ passed: import_zod10.z.number().int().min(0),
3074
3313
  /** Per branch, for a condition: how many took `yes` and how many `no`. */
3075
- branches: import_zod9.z.record(import_zod9.z.number().int().min(0)),
3314
+ branches: import_zod10.z.record(import_zod10.z.number().int().min(0)),
3076
3315
  /** The step mailing's id, for an email step of the published version. */
3077
3316
  mailing_id: Id.nullable()
3078
3317
  });
3079
- var AutomationReport = import_zod9.z.object({
3318
+ var AutomationReport = import_zod10.z.object({
3080
3319
  counts: AutomationCounts,
3081
3320
  /** Why the people who left did: `AutomationEndReason` to a count. */
3082
- end_reasons: import_zod9.z.record(import_zod9.z.number().int().min(0)),
3321
+ end_reasons: import_zod10.z.record(import_zod10.z.number().int().min(0)),
3083
3322
  /**
3084
3323
  * Why people a trigger named did not enter: `AutomationEntryRefusal` to a
3085
3324
  * count. Without it a pause, an exclusion or a missing subscription would
3086
3325
  * turn people away invisibly.
3087
3326
  */
3088
- refusals: import_zod9.z.record(import_zod9.z.number().int().min(0)),
3089
- steps: import_zod9.z.array(AutomationStepReport)
3090
- });
3091
- var AutomationExitRunRequest = import_zod9.z.object({ reason: import_zod9.z.string().max(200).optional() }).strict();
3092
- var AutomationRunParams = import_zod9.z.object({ id: Id, run_id: Id });
3093
- var AutomationStepParams = import_zod9.z.object({ id: Id, step_id: StepId });
3094
- var AutomationTestEmailRequest = import_zod9.z.object({ to: Email, merge: Properties.optional(), locale: LocaleTag.optional() }).strict();
3095
- var AutomationValidateRequest = import_zod9.z.object({ flow: AutomationFlow.optional(), settings: AutomationSettings.partial().optional() }).strict();
3096
- var EventCreate = import_zod9.z.object({
3327
+ refusals: import_zod10.z.record(import_zod10.z.number().int().min(0)),
3328
+ steps: import_zod10.z.array(AutomationStepReport)
3329
+ });
3330
+ var AutomationExitRunRequest = import_zod10.z.object({ reason: import_zod10.z.string().max(200).optional() }).strict();
3331
+ var AutomationRunParams = import_zod10.z.object({ id: Id, run_id: Id });
3332
+ var AutomationStepParams = import_zod10.z.object({ id: Id, step_id: StepId });
3333
+ var AutomationTestEmailRequest = import_zod10.z.object({ to: Email, merge: Properties.optional(), locale: LocaleTag.optional() }).strict();
3334
+ var AutomationValidateRequest = import_zod10.z.object({ flow: AutomationFlow.optional(), settings: AutomationSettings.partial().optional() }).strict();
3335
+ var EventCreate = import_zod10.z.object({
3097
3336
  name: EventName,
3098
- contact: import_zod9.z.object({ external_id: import_zod9.z.string().min(1).max(255).optional(), email: Email.optional(), id: Id.optional() }).refine((c) => [c.external_id, c.email, c.id].filter((x) => x !== void 0).length === 1, "name the contact exactly one way"),
3337
+ contact: import_zod10.z.object({ external_id: import_zod10.z.string().min(1).max(255).optional(), email: Email.optional(), id: Id.optional() }).refine((c) => [c.external_id, c.email, c.id].filter((x) => x !== void 0).length === 1, "name the contact exactly one way"),
3099
3338
  data: Properties.optional(),
3100
3339
  occurred_at: Timestamp.optional(),
3101
- id: import_zod9.z.string().min(1).max(128).optional()
3340
+ id: import_zod10.z.string().min(1).max(128).optional()
3102
3341
  }).strict();
3103
- var Event = import_zod9.z.object({
3342
+ var Event = import_zod10.z.object({
3104
3343
  id: Id,
3105
- client_event_id: import_zod9.z.string().nullable(),
3344
+ client_event_id: import_zod10.z.string().nullable(),
3106
3345
  name: EventName,
3107
3346
  contact_id: Id,
3108
3347
  data: Properties,
@@ -3113,7 +3352,7 @@ var Event = import_zod9.z.object({
3113
3352
  * hand. Each is then admitted or refused by the runtime on its own rules
3114
3353
  * (consent, exclusions, re-entry), which `automations.report` counts.
3115
3354
  */
3116
- entered: import_zod9.z.number().int().min(0)
3355
+ entered: import_zod10.z.number().int().min(0)
3117
3356
  });
3118
3357
  var EventListQuery = PageQuery.extend({
3119
3358
  name: EventName.optional(),
@@ -3121,19 +3360,15 @@ var EventListQuery = PageQuery.extend({
3121
3360
  });
3122
3361
 
3123
3362
  // src/workspace.ts
3124
- var CompanyId = import_zod10.z.string().min(1).max(64);
3363
+ var CompanyId = import_zod11.z.string().min(1).max(64);
3125
3364
  var ASSET_POLICIES = ["any", "service_only"];
3126
- var AssetPolicy = import_zod10.z.enum(ASSET_POLICIES);
3365
+ var AssetPolicy = import_zod11.z.enum(ASSET_POLICIES);
3127
3366
  var MAX_ALLOWED_ASSET_HOSTS = 20;
3128
- var AssetHost = import_zod10.z.string().trim().toLowerCase().min(1).max(253).regex(/^(?=.{1,253}(?::\d{1,5})?$)[a-z0-9]([a-z0-9-]{0,61}[a-z0-9])?(\.[a-z0-9]([a-z0-9-]{0,61}[a-z0-9])?)+(:\d{1,5})?$/, "a host name such as example.com");
3129
- var MAX_MERGE_DEFAULTS = 50;
3130
- var MAX_MERGE_DEFAULT_LENGTH = 2e3;
3131
- var MergeFieldName = import_zod10.z.string().regex(/^[a-z][a-z0-9_]*$/, "a merge-field name: lowercase letters, digits and underscores, starting with a letter").max(64);
3132
- var MergeDefaultValue = import_zod10.z.union([import_zod10.z.string().max(MAX_MERGE_DEFAULT_LENGTH), import_zod10.z.number().finite(), import_zod10.z.boolean()]);
3133
- var MergeDefaults = import_zod10.z.record(MergeFieldName, MergeDefaultValue).refine((m) => Object.keys(m).length <= MAX_MERGE_DEFAULTS, `at most ${MAX_MERGE_DEFAULTS} merge defaults`).refine((m) => !Object.keys(m).some((k) => k in RESERVED_MERGE_FIELDS), {
3367
+ var AssetHost = import_zod11.z.string().trim().toLowerCase().min(1).max(253).regex(/^(?=.{1,253}(?::\d{1,5})?$)[a-z0-9]([a-z0-9-]{0,61}[a-z0-9])?(\.[a-z0-9]([a-z0-9-]{0,61}[a-z0-9])?)+(:\d{1,5})?$/, "a host name such as example.com");
3368
+ var MergeDefaults = import_zod11.z.record(MergeFieldName, MergeDefaultValue).refine((m) => Object.keys(m).length <= MAX_MERGE_DEFAULTS, `at most ${MAX_MERGE_DEFAULTS} merge defaults`).refine((m) => !Object.keys(m).some((k) => k in RESERVED_MERGE_FIELDS), {
3134
3369
  message: `a reserved merge field (${Object.keys(RESERVED_MERGE_FIELDS).join(", ")}) cannot have a workspace default`
3135
3370
  });
3136
- var WorkspaceSettings = import_zod10.z.object({
3371
+ var WorkspaceSettings = import_zod11.z.object({
3137
3372
  /**
3138
3373
  * The workspace's main language (a {@link LocaleTag}, e.g. "de"): the main
3139
3374
  * language of a new template, and of the hosted pages when nothing else
@@ -3146,9 +3381,9 @@ var WorkspaceSettings = import_zod10.z.object({
3146
3381
  * each; the hosted pages are offered in those of them they support (English,
3147
3382
  * German, French, Italian, Spanish). The service stores canonical casing.
3148
3383
  */
3149
- locales: import_zod10.z.array(LocaleTag).min(1).max(20).refine((l) => new Set(l.map((t) => t.toLowerCase())).size === l.length, "a language appears twice"),
3384
+ locales: import_zod11.z.array(LocaleTag).min(1).max(20).refine((l) => new Set(l.map((t) => t.toLowerCase())).size === l.length, "a language appears twice"),
3150
3385
  /** Open and click tracking. Off by default, opt-in per workspace. */
3151
- tracking_enabled: import_zod10.z.boolean(),
3386
+ tracking_enabled: import_zod11.z.boolean(),
3152
3387
  /** Where images, stylesheets and fonts in a mail may load from. `any` by default. */
3153
3388
  asset_policy: AssetPolicy,
3154
3389
  /**
@@ -3156,7 +3391,7 @@ var WorkspaceSettings = import_zod10.z.object({
3156
3391
  * the workspace's website, typically. Empty by default. Ignored under `any`,
3157
3392
  * which allows everything already.
3158
3393
  */
3159
- allowed_asset_hosts: import_zod10.z.array(AssetHost).max(MAX_ALLOWED_ASSET_HOSTS),
3394
+ allowed_asset_hosts: import_zod11.z.array(AssetHost).max(MAX_ALLOWED_ASSET_HOSTS),
3160
3395
  /** Merge values every mail of the workspace can use (see `MergeDefaults`). Empty by default. */
3161
3396
  merge_defaults: MergeDefaults,
3162
3397
  /**
@@ -3165,10 +3400,10 @@ var WorkspaceSettings = import_zod10.z.object({
3165
3400
  */
3166
3401
  default_timezone: TimezoneName.nullable()
3167
3402
  });
3168
- var Workspace = import_zod10.z.object({
3403
+ var Workspace = import_zod11.z.object({
3169
3404
  id: Id,
3170
3405
  slug: Slug,
3171
- name: import_zod10.z.string().min(1).max(120),
3406
+ name: import_zod11.z.string().min(1).max(120),
3172
3407
  settings: WorkspaceSettings,
3173
3408
  /**
3174
3409
  * The auth-brain company (tenant) the workspace was created for, or null for
@@ -3179,13 +3414,13 @@ var Workspace = import_zod10.z.object({
3179
3414
  created_at: Timestamp,
3180
3415
  updated_at: Timestamp
3181
3416
  });
3182
- var WorkspaceCreate = import_zod10.z.object({
3417
+ var WorkspaceCreate = import_zod11.z.object({
3183
3418
  slug: Slug,
3184
- name: import_zod10.z.string().min(1).max(120),
3419
+ name: import_zod11.z.string().min(1).max(120),
3185
3420
  settings: WorkspaceSettings.partial().optional(),
3186
- owner: import_zod10.z.object({
3421
+ owner: import_zod11.z.object({
3187
3422
  email: Email,
3188
- name: import_zod10.z.string().max(200).nullable().optional()
3423
+ name: import_zod11.z.string().max(200).nullable().optional()
3189
3424
  }),
3190
3425
  /**
3191
3426
  * The signed-in person's active auth-brain company. The dashboard always
@@ -3195,49 +3430,49 @@ var WorkspaceCreate = import_zod10.z.object({
3195
3430
  */
3196
3431
  company_id: CompanyId.optional()
3197
3432
  });
3198
- var WorkspaceUpdate = import_zod10.z.object({
3199
- name: import_zod10.z.string().min(1).max(120),
3433
+ var WorkspaceUpdate = import_zod11.z.object({
3434
+ name: import_zod11.z.string().min(1).max(120),
3200
3435
  settings: WorkspaceSettings.partial()
3201
3436
  }).partial().refine((v) => Object.keys(v).length > 0, "at least one field");
3202
- var WorkspaceMove = import_zod10.z.object({ company_id: CompanyId });
3437
+ var WorkspaceMove = import_zod11.z.object({ company_id: CompanyId });
3203
3438
  var MEMBER_ROLES = ["owner", "admin", "editor", "viewer"];
3204
- var MemberRole = import_zod10.z.enum(MEMBER_ROLES);
3439
+ var MemberRole = import_zod11.z.enum(MEMBER_ROLES);
3205
3440
  var WorkspaceMembership = Workspace.extend({ role: MemberRole });
3206
- var Member = import_zod10.z.object({
3441
+ var Member = import_zod11.z.object({
3207
3442
  id: Id,
3208
3443
  /** The person's auth-brain subject. */
3209
- subject: import_zod10.z.string().min(1).max(255),
3444
+ subject: import_zod11.z.string().min(1).max(255),
3210
3445
  email: Email,
3211
- name: import_zod10.z.string().max(200).nullable(),
3446
+ name: import_zod11.z.string().max(200).nullable(),
3212
3447
  role: MemberRole,
3213
3448
  created_at: Timestamp
3214
3449
  });
3215
- var MemberCreate = import_zod10.z.object({
3216
- subject: import_zod10.z.string().min(1).max(255),
3450
+ var MemberCreate = import_zod11.z.object({
3451
+ subject: import_zod11.z.string().min(1).max(255),
3217
3452
  email: Email,
3218
- name: import_zod10.z.string().max(200).nullable().optional(),
3453
+ name: import_zod11.z.string().max(200).nullable().optional(),
3219
3454
  role: MemberRole
3220
3455
  });
3221
- var MemberUpdate = import_zod10.z.object({ role: MemberRole });
3456
+ var MemberUpdate = import_zod11.z.object({ role: MemberRole });
3222
3457
  var API_KEY_SCOPES = ["full", "read", "send"];
3223
- var ApiKeyScope = import_zod10.z.enum(API_KEY_SCOPES);
3224
- var ApiKey = import_zod10.z.object({
3458
+ var ApiKeyScope = import_zod11.z.enum(API_KEY_SCOPES);
3459
+ var ApiKey = import_zod11.z.object({
3225
3460
  id: Id,
3226
- name: import_zod10.z.string().min(1).max(120),
3461
+ name: import_zod11.z.string().min(1).max(120),
3227
3462
  /** The first characters of the key, for recognising it in a list. */
3228
- prefix: import_zod10.z.string().min(4).max(32),
3463
+ prefix: import_zod11.z.string().min(4).max(32),
3229
3464
  scope: ApiKeyScope,
3230
3465
  last_used_at: Timestamp.nullable(),
3231
3466
  revoked_at: Timestamp.nullable(),
3232
3467
  created_at: Timestamp
3233
3468
  });
3234
- var ApiKeyCreate = import_zod10.z.object({
3235
- name: import_zod10.z.string().min(1).max(120),
3469
+ var ApiKeyCreate = import_zod11.z.object({
3470
+ name: import_zod11.z.string().min(1).max(120),
3236
3471
  /** Omitted means `full`. */
3237
3472
  scope: ApiKeyScope.optional()
3238
3473
  });
3239
- var ApiKeyCreated = import_zod10.z.object({
3240
- key: import_zod10.z.string().min(20),
3474
+ var ApiKeyCreated = import_zod11.z.object({
3475
+ key: import_zod11.z.string().min(20),
3241
3476
  api_key: ApiKey
3242
3477
  });
3243
3478
  var AUDIT_ACTIONS = [
@@ -3326,29 +3561,29 @@ var AUDIT_ACTIONS = [
3326
3561
  "automation.run_ended",
3327
3562
  "event.recorded"
3328
3563
  ];
3329
- var AuditAction = import_zod10.z.enum(AUDIT_ACTIONS);
3330
- var AuditActor = import_zod10.z.discriminatedUnion("type", [
3331
- import_zod10.z.object({ type: import_zod10.z.literal("member"), member_id: Id, subject: import_zod10.z.string().min(1) }),
3332
- import_zod10.z.object({
3333
- type: import_zod10.z.literal("api_key"),
3564
+ var AuditAction = import_zod11.z.enum(AUDIT_ACTIONS);
3565
+ var AuditActor = import_zod11.z.discriminatedUnion("type", [
3566
+ import_zod11.z.object({ type: import_zod11.z.literal("member"), member_id: Id, subject: import_zod11.z.string().min(1) }),
3567
+ import_zod11.z.object({
3568
+ type: import_zod11.z.literal("api_key"),
3334
3569
  api_key_id: Id,
3335
3570
  /**
3336
3571
  * Who the client's application said it was acting for, from
3337
3572
  * `ON_BEHALF_OF_HEADER`: reported by that application, never verified.
3338
3573
  * Absent when the call carried no label.
3339
3574
  */
3340
- on_behalf_of: import_zod10.z.string().min(1).max(ON_BEHALF_OF_MAX_LENGTH).optional()
3575
+ on_behalf_of: import_zod11.z.string().min(1).max(ON_BEHALF_OF_MAX_LENGTH).optional()
3341
3576
  }),
3342
3577
  /** The service itself (the worker, a bounce, the hosted unsubscribe page). */
3343
- import_zod10.z.object({ type: import_zod10.z.literal("system"), reason: import_zod10.z.string().min(1).max(200) })
3578
+ import_zod11.z.object({ type: import_zod11.z.literal("system"), reason: import_zod11.z.string().min(1).max(200) })
3344
3579
  ]);
3345
- var AuditEntry = import_zod10.z.object({
3580
+ var AuditEntry = import_zod11.z.object({
3346
3581
  id: Id,
3347
3582
  action: AuditAction,
3348
3583
  actor: AuditActor,
3349
- target_type: import_zod10.z.string().min(1).max(64),
3584
+ target_type: import_zod11.z.string().min(1).max(64),
3350
3585
  target_id: Id.nullable(),
3351
- details: import_zod10.z.record(import_zod10.z.unknown()),
3586
+ details: import_zod11.z.record(import_zod11.z.unknown()),
3352
3587
  created_at: Timestamp
3353
3588
  });
3354
3589
  var AuditQuery = PageQuery.extend({
@@ -3357,12 +3592,12 @@ var AuditQuery = PageQuery.extend({
3357
3592
  });
3358
3593
 
3359
3594
  // src/invites.ts
3360
- var import_zod11 = require("zod");
3595
+ var import_zod12 = require("zod");
3361
3596
  var INVITE_STATUSES = ["pending", "accepted", "revoked", "expired"];
3362
- var InviteStatus = import_zod11.z.enum(INVITE_STATUSES);
3597
+ var InviteStatus = import_zod12.z.enum(INVITE_STATUSES);
3363
3598
  var DEFAULT_INVITE_TTL_DAYS = 7;
3364
3599
  var MAX_INVITE_TTL_DAYS = 30;
3365
- var Invite = import_zod11.z.object({
3600
+ var Invite = import_zod12.z.object({
3366
3601
  id: Id,
3367
3602
  /** Stored lowercased; only a person signed in with this address can accept. */
3368
3603
  email: Email,
@@ -3370,32 +3605,32 @@ var Invite = import_zod11.z.object({
3370
3605
  /** Derived from the timestamps below, never stored. */
3371
3606
  status: InviteStatus,
3372
3607
  /** The member who invited, while they are still one (null after they left). */
3373
- invited_by: import_zod11.z.object({ member_id: Id.nullable(), email: Email.nullable() }),
3608
+ invited_by: import_zod12.z.object({ member_id: Id.nullable(), email: Email.nullable() }),
3374
3609
  expires_at: Timestamp,
3375
3610
  accepted_at: Timestamp.nullable(),
3376
3611
  revoked_at: Timestamp.nullable(),
3377
3612
  created_at: Timestamp
3378
3613
  });
3379
- var InviteCreate = import_zod11.z.object({
3614
+ var InviteCreate = import_zod12.z.object({
3380
3615
  email: Email,
3381
3616
  role: MemberRole,
3382
- expires_in_days: import_zod11.z.number().int().min(1).max(MAX_INVITE_TTL_DAYS).optional()
3617
+ expires_in_days: import_zod12.z.number().int().min(1).max(MAX_INVITE_TTL_DAYS).optional()
3383
3618
  });
3384
- var InviteCreated = import_zod11.z.object({
3619
+ var InviteCreated = import_zod12.z.object({
3385
3620
  invite: Invite,
3386
- token: import_zod11.z.string().min(32).max(128)
3621
+ token: import_zod12.z.string().min(32).max(128)
3387
3622
  });
3388
3623
  var InviteListQuery = PageQuery.extend({
3389
3624
  status: InviteStatus.optional()
3390
3625
  });
3391
- var InviteAccept = import_zod11.z.object({
3392
- token: import_zod11.z.string().min(32).max(128),
3626
+ var InviteAccept = import_zod12.z.object({
3627
+ token: import_zod12.z.string().min(32).max(128),
3393
3628
  email: Email,
3394
- name: import_zod11.z.string().max(200).nullable().optional()
3629
+ name: import_zod12.z.string().max(200).nullable().optional()
3395
3630
  });
3396
- var InviteAccepted = import_zod11.z.object({
3631
+ var InviteAccepted = import_zod12.z.object({
3397
3632
  workspace: WorkspaceMembership,
3398
- already_member: import_zod11.z.boolean()
3633
+ already_member: import_zod12.z.boolean()
3399
3634
  });
3400
3635
  var INVITE_REFUSAL_REASONS = ["email_mismatch", "inviter_lacks_role", "expired", "revoked", "accepted"];
3401
3636
 
@@ -4025,13 +4260,13 @@ function renameInsertionEverywhere(drafts, from, rawTo) {
4025
4260
  }
4026
4261
 
4027
4262
  // src/providers.ts
4028
- var import_zod12 = require("zod");
4263
+ var import_zod13 = require("zod");
4029
4264
  var PROVIDER_KINDS = ["smtp", "resend"];
4030
- var ProviderKind = import_zod12.z.enum(PROVIDER_KINDS);
4031
- var ProviderPolicy = import_zod12.z.object({
4032
- daily_recipient_budget: import_zod12.z.number().int().min(1).max(1e7),
4033
- min_interval_ms: import_zod12.z.number().int().min(0).max(36e5),
4034
- max_recipients_per_message: import_zod12.z.number().int().min(1).max(1e3)
4265
+ var ProviderKind = import_zod13.z.enum(PROVIDER_KINDS);
4266
+ var ProviderPolicy = import_zod13.z.object({
4267
+ daily_recipient_budget: import_zod13.z.number().int().min(1).max(1e7),
4268
+ min_interval_ms: import_zod13.z.number().int().min(0).max(36e5),
4269
+ max_recipients_per_message: import_zod13.z.number().int().min(1).max(1e3)
4035
4270
  });
4036
4271
  var ICLOUD_SMTP_POLICY = {
4037
4272
  daily_recipient_budget: 800,
@@ -4039,17 +4274,17 @@ var ICLOUD_SMTP_POLICY = {
4039
4274
  max_recipients_per_message: 1
4040
4275
  };
4041
4276
  var SMTP_SECURITY = ["tls", "starttls"];
4042
- var SmtpConfigBase = import_zod12.z.object({
4043
- host: import_zod12.z.string().min(1).max(255),
4044
- port: import_zod12.z.number().int().min(1).max(65535),
4277
+ var SmtpConfigBase = import_zod13.z.object({
4278
+ host: import_zod13.z.string().min(1).max(255),
4279
+ port: import_zod13.z.number().int().min(1).max(65535),
4045
4280
  /** `tls` connects encrypted (465), `starttls` upgrades (587). Never plaintext. */
4046
- security: import_zod12.z.enum(SMTP_SECURITY),
4047
- username: import_zod12.z.string().min(1).max(255)
4281
+ security: import_zod13.z.enum(SMTP_SECURITY),
4282
+ username: import_zod13.z.string().min(1).max(255)
4048
4283
  });
4049
- var ResendConfigBase = import_zod12.z.object({});
4050
- var ProviderRejections = import_zod12.z.object({
4051
- count: import_zod12.z.number().int().min(0),
4052
- last_error: import_zod12.z.string().nullable(),
4284
+ var ResendConfigBase = import_zod13.z.object({});
4285
+ var ProviderRejections = import_zod13.z.object({
4286
+ count: import_zod13.z.number().int().min(0),
4287
+ last_error: import_zod13.z.string().nullable(),
4053
4288
  last_at: Timestamp.nullable(),
4054
4289
  /**
4055
4290
  * The last time the bounce circuit breaker tripped on one of this provider's
@@ -4059,59 +4294,59 @@ var ProviderRejections = import_zod12.z.object({
4059
4294
  * run's bounce blocks were undone and the mailing paused. `sample` is the
4060
4295
  * reply that tripped it.
4061
4296
  */
4062
- anomaly: import_zod12.z.object({
4297
+ anomaly: import_zod13.z.object({
4063
4298
  at: Timestamp,
4064
4299
  /** `mailing`: one mailing was paused. `provider`: 5 refusals in a row with the same reply across the provider's sends (test sends and one-recipient mailings included) within 24 hours. */
4065
- scope: import_zod12.z.enum(["mailing", "provider"]),
4300
+ scope: import_zod13.z.enum(["mailing", "provider"]),
4066
4301
  /**
4067
4302
  * True while the provider-wide breaker is open: no bounce blocks through
4068
4303
  * this provider, test sends refused and mailings not started or resumed
4069
4304
  * (`provider_anomaly`), until an admin clears it (`providers.clearAnomaly`).
4070
4305
  */
4071
- blocking: import_zod12.z.boolean(),
4306
+ blocking: import_zod13.z.boolean(),
4072
4307
  mailing_id: Id.nullable(),
4073
- reason: import_zod12.z.string(),
4074
- sample: import_zod12.z.string()
4308
+ reason: import_zod13.z.string(),
4309
+ sample: import_zod13.z.string()
4075
4310
  }).nullable()
4076
4311
  });
4077
- var ProviderEvents = import_zod12.z.object({
4078
- status: import_zod12.z.enum(["active", "needs_secret"]),
4079
- source: import_zod12.z.enum(["automatic", "manual"]).nullable(),
4080
- url: import_zod12.z.string().url(),
4081
- error: import_zod12.z.string().nullable(),
4312
+ var ProviderEvents = import_zod13.z.object({
4313
+ status: import_zod13.z.enum(["active", "needs_secret"]),
4314
+ source: import_zod13.z.enum(["automatic", "manual"]).nullable(),
4315
+ url: import_zod13.z.string().url(),
4316
+ error: import_zod13.z.string().nullable(),
4082
4317
  /**
4083
4318
  * Events that named an email this provider never sent through the service
4084
4319
  * (another workspace or system sharing the Resend account): counted, never
4085
4320
  * acted on.
4086
4321
  */
4087
- unmatched: import_zod12.z.number().int().min(0)
4322
+ unmatched: import_zod13.z.number().int().min(0)
4088
4323
  });
4089
4324
  var RESEND_EVENT_TYPES = ["email.bounced", "email.complained", "email.delivery_delayed"];
4090
- var ResendSigningSecret = import_zod12.z.string().max(200).regex(/^whsec_[A-Za-z0-9+/]{16,}={0,2}$/, "must be the signing secret Resend shows, starting with whsec_");
4091
- var ProviderEventsSecret = import_zod12.z.object({ signing_secret: ResendSigningSecret });
4325
+ var ResendSigningSecret = import_zod13.z.string().max(200).regex(/^whsec_[A-Za-z0-9+/]{16,}={0,2}$/, "must be the signing secret Resend shows, starting with whsec_");
4326
+ var ProviderEventsSecret = import_zod13.z.object({ signing_secret: ResendSigningSecret });
4092
4327
  var ProviderFields = {
4093
- name: import_zod12.z.string().min(1).max(120),
4094
- from_name: import_zod12.z.string().min(1).max(120),
4328
+ name: import_zod13.z.string().min(1).max(120),
4329
+ from_name: import_zod13.z.string().min(1).max(120),
4095
4330
  from_email: Email,
4096
4331
  reply_to: Email.nullable(),
4097
4332
  policy: ProviderPolicy
4098
4333
  };
4099
- var Provider = import_zod12.z.discriminatedUnion("kind", [
4100
- import_zod12.z.object({
4334
+ var Provider = import_zod13.z.discriminatedUnion("kind", [
4335
+ import_zod13.z.object({
4101
4336
  id: Id,
4102
- kind: import_zod12.z.literal("smtp"),
4337
+ kind: import_zod13.z.literal("smtp"),
4103
4338
  config: SmtpConfigBase,
4104
- has_secret: import_zod12.z.boolean(),
4339
+ has_secret: import_zod13.z.boolean(),
4105
4340
  ...ProviderFields,
4106
4341
  rejections: ProviderRejections,
4107
4342
  created_at: Timestamp,
4108
4343
  updated_at: Timestamp
4109
4344
  }),
4110
- import_zod12.z.object({
4345
+ import_zod13.z.object({
4111
4346
  id: Id,
4112
- kind: import_zod12.z.literal("resend"),
4347
+ kind: import_zod13.z.literal("resend"),
4113
4348
  config: ResendConfigBase,
4114
- has_secret: import_zod12.z.boolean(),
4349
+ has_secret: import_zod13.z.boolean(),
4115
4350
  ...ProviderFields,
4116
4351
  rejections: ProviderRejections,
4117
4352
  events: ProviderEvents,
@@ -4119,31 +4354,31 @@ var Provider = import_zod12.z.discriminatedUnion("kind", [
4119
4354
  updated_at: Timestamp
4120
4355
  })
4121
4356
  ]);
4122
- var ProviderCreate = import_zod12.z.discriminatedUnion("kind", [
4123
- import_zod12.z.object({
4124
- kind: import_zod12.z.literal("smtp"),
4125
- config: SmtpConfigBase.extend({ password: import_zod12.z.string().min(1).max(1024) }),
4357
+ var ProviderCreate = import_zod13.z.discriminatedUnion("kind", [
4358
+ import_zod13.z.object({
4359
+ kind: import_zod13.z.literal("smtp"),
4360
+ config: SmtpConfigBase.extend({ password: import_zod13.z.string().min(1).max(1024) }),
4126
4361
  ...ProviderFields
4127
4362
  }),
4128
- import_zod12.z.object({
4129
- kind: import_zod12.z.literal("resend"),
4130
- config: ResendConfigBase.extend({ api_key: import_zod12.z.string().min(1).max(1024) }),
4363
+ import_zod13.z.object({
4364
+ kind: import_zod13.z.literal("resend"),
4365
+ config: ResendConfigBase.extend({ api_key: import_zod13.z.string().min(1).max(1024) }),
4131
4366
  ...ProviderFields
4132
4367
  })
4133
4368
  ]);
4134
- var ProviderUpdate = import_zod12.z.discriminatedUnion("kind", [
4135
- import_zod12.z.object({
4136
- kind: import_zod12.z.literal("smtp"),
4137
- config: SmtpConfigBase.extend({ password: import_zod12.z.string().min(1).max(1024).optional() }).partial().optional(),
4369
+ var ProviderUpdate = import_zod13.z.discriminatedUnion("kind", [
4370
+ import_zod13.z.object({
4371
+ kind: import_zod13.z.literal("smtp"),
4372
+ config: SmtpConfigBase.extend({ password: import_zod13.z.string().min(1).max(1024).optional() }).partial().optional(),
4138
4373
  name: ProviderFields.name.optional(),
4139
4374
  from_name: ProviderFields.from_name.optional(),
4140
4375
  from_email: ProviderFields.from_email.optional(),
4141
4376
  reply_to: ProviderFields.reply_to.optional(),
4142
4377
  policy: ProviderPolicy.partial().optional()
4143
4378
  }),
4144
- import_zod12.z.object({
4145
- kind: import_zod12.z.literal("resend"),
4146
- config: ResendConfigBase.extend({ api_key: import_zod12.z.string().min(1).max(1024).optional() }).optional(),
4379
+ import_zod13.z.object({
4380
+ kind: import_zod13.z.literal("resend"),
4381
+ config: ResendConfigBase.extend({ api_key: import_zod13.z.string().min(1).max(1024).optional() }).optional(),
4147
4382
  name: ProviderFields.name.optional(),
4148
4383
  from_name: ProviderFields.from_name.optional(),
4149
4384
  from_email: ProviderFields.from_email.optional(),
@@ -4151,48 +4386,48 @@ var ProviderUpdate = import_zod12.z.discriminatedUnion("kind", [
4151
4386
  policy: ProviderPolicy.partial().optional()
4152
4387
  })
4153
4388
  ]);
4154
- var ProviderUsage = import_zod12.z.object({
4389
+ var ProviderUsage = import_zod13.z.object({
4155
4390
  provider_id: Id,
4156
- recipients_last_24h: import_zod12.z.number().int().min(0),
4157
- remaining_budget: import_zod12.z.number().int().min(0),
4391
+ recipients_last_24h: import_zod13.z.number().int().min(0),
4392
+ remaining_budget: import_zod13.z.number().int().min(0),
4158
4393
  /** When enough of the rolling window frees up to send again, if exhausted. */
4159
4394
  next_capacity_at: Timestamp.nullable()
4160
4395
  });
4161
- var ProviderVerifyResult = import_zod12.z.object({
4162
- ok: import_zod12.z.boolean(),
4163
- error: import_zod12.z.string().nullable()
4396
+ var ProviderVerifyResult = import_zod13.z.object({
4397
+ ok: import_zod13.z.boolean(),
4398
+ error: import_zod13.z.string().nullable()
4164
4399
  });
4165
4400
 
4166
4401
  // src/contacts.ts
4167
- var import_zod13 = require("zod");
4168
- var Topic = import_zod13.z.object({
4402
+ var import_zod14 = require("zod");
4403
+ var Topic = import_zod14.z.object({
4169
4404
  id: Id,
4170
4405
  slug: Slug,
4171
- name: import_zod13.z.string().min(1).max(120),
4406
+ name: import_zod14.z.string().min(1).max(120),
4172
4407
  /** Shown on the hosted preference page. */
4173
- description: import_zod13.z.string().max(1e3).nullable(),
4408
+ description: import_zod14.z.string().max(1e3).nullable(),
4174
4409
  /** Translations of `name` and `description` per locale, for the hosted page. */
4175
- translations: import_zod13.z.record(
4176
- import_zod13.z.object({ name: import_zod13.z.string().min(1).max(120), description: import_zod13.z.string().max(1e3).nullable() })
4410
+ translations: import_zod14.z.record(
4411
+ import_zod14.z.object({ name: import_zod14.z.string().min(1).max(120), description: import_zod14.z.string().max(1e3).nullable() })
4177
4412
  ),
4178
4413
  created_at: Timestamp,
4179
4414
  updated_at: Timestamp
4180
4415
  });
4181
- var TopicCreate = import_zod13.z.object({
4416
+ var TopicCreate = import_zod14.z.object({
4182
4417
  slug: Slug,
4183
- name: import_zod13.z.string().min(1).max(120),
4184
- description: import_zod13.z.string().max(1e3).optional(),
4418
+ name: import_zod14.z.string().min(1).max(120),
4419
+ description: import_zod14.z.string().max(1e3).optional(),
4185
4420
  translations: Topic.shape.translations.optional()
4186
4421
  });
4187
4422
  var TopicUpdate = TopicCreate.omit({ slug: true }).partial().refine((v) => Object.keys(v).length > 0, "at least one field");
4188
- var Contact = import_zod13.z.object({
4423
+ var Contact = import_zod14.z.object({
4189
4424
  id: Id,
4190
- external_id: import_zod13.z.string().min(1).max(255).nullable(),
4425
+ external_id: import_zod14.z.string().min(1).max(255).nullable(),
4191
4426
  /** Stored lowercased, unique per workspace. */
4192
4427
  email: Email,
4193
- first_name: import_zod13.z.string().max(200).nullable(),
4194
- last_name: import_zod13.z.string().max(200).nullable(),
4195
- locale: import_zod13.z.string().min(2).max(35).nullable(),
4428
+ first_name: import_zod14.z.string().max(200).nullable(),
4429
+ last_name: import_zod14.z.string().max(200).nullable(),
4430
+ locale: import_zod14.z.string().min(2).max(35).nullable(),
4196
4431
  /**
4197
4432
  * The person's own time zone, an IANA name such as `Europe/Berlin` (A1).
4198
4433
  * Every wall clock an automation waits for is read in it, falling back to the
@@ -4200,65 +4435,65 @@ var Contact = import_zod13.z.object({
4200
4435
  */
4201
4436
  timezone: TimezoneName.nullable(),
4202
4437
  properties: Properties,
4203
- topics: import_zod13.z.array(Slug),
4438
+ topics: import_zod14.z.array(Slug),
4204
4439
  /** The slugs of the contact's tags (S4). */
4205
- tags: import_zod13.z.array(Slug),
4440
+ tags: import_zod14.z.array(Slug),
4206
4441
  created_at: Timestamp,
4207
4442
  updated_at: Timestamp
4208
4443
  });
4209
- var ContactUpsert = import_zod13.z.object({
4210
- external_id: import_zod13.z.string().min(1).max(255).optional(),
4444
+ var ContactUpsert = import_zod14.z.object({
4445
+ external_id: import_zod14.z.string().min(1).max(255).optional(),
4211
4446
  email: Email.optional(),
4212
- first_name: import_zod13.z.string().max(200).nullable().optional(),
4213
- last_name: import_zod13.z.string().max(200).nullable().optional(),
4214
- locale: import_zod13.z.string().min(2).max(35).nullable().optional(),
4447
+ first_name: import_zod14.z.string().max(200).nullable().optional(),
4448
+ last_name: import_zod14.z.string().max(200).nullable().optional(),
4449
+ locale: import_zod14.z.string().min(2).max(35).nullable().optional(),
4215
4450
  timezone: TimezoneName.nullable().optional(),
4216
4451
  properties: Properties.optional(),
4217
- topics: import_zod13.z.array(Slug).max(100).optional()
4452
+ topics: import_zod14.z.array(Slug).max(100).optional()
4218
4453
  }).refine((v) => v.external_id !== void 0 || v.email !== void 0, {
4219
4454
  message: "external_id or email is required",
4220
4455
  path: ["email"]
4221
4456
  });
4222
- var ContactUpsertResult = import_zod13.z.object({
4457
+ var ContactUpsertResult = import_zod14.z.object({
4223
4458
  contact: Contact,
4224
- created: import_zod13.z.boolean()
4459
+ created: import_zod14.z.boolean()
4225
4460
  });
4226
4461
  var ContactListQuery = PageQuery.extend({
4227
- email: import_zod13.z.string().min(1).max(254).optional(),
4228
- external_id: import_zod13.z.string().min(1).max(255).optional(),
4462
+ email: import_zod14.z.string().min(1).max(254).optional(),
4463
+ external_id: import_zod14.z.string().min(1).max(255).optional(),
4229
4464
  topic: Slug.optional()
4230
4465
  });
4231
- var ContactErased = import_zod13.z.object({
4232
- ok: import_zod13.z.literal(true),
4233
- erased_messages: import_zod13.z.number().int().min(0),
4234
- erased_recipients: import_zod13.z.number().int().min(0),
4235
- suppressions_kept: import_zod13.z.number().int().min(0)
4466
+ var ContactErased = import_zod14.z.object({
4467
+ ok: import_zod14.z.literal(true),
4468
+ erased_messages: import_zod14.z.number().int().min(0),
4469
+ erased_recipients: import_zod14.z.number().int().min(0),
4470
+ suppressions_kept: import_zod14.z.number().int().min(0)
4236
4471
  });
4237
4472
  var SUPPRESSION_REASONS = ["unsubscribed", "bounced", "complained", "manual"];
4238
- var SuppressionReason = import_zod13.z.enum(SUPPRESSION_REASONS);
4239
- var Suppression = import_zod13.z.object({
4473
+ var SuppressionReason = import_zod14.z.enum(SUPPRESSION_REASONS);
4474
+ var Suppression = import_zod14.z.object({
4240
4475
  id: Id,
4241
4476
  email: Email,
4242
4477
  reason: SuppressionReason,
4243
4478
  topic: Slug.nullable(),
4244
4479
  source_message_id: Id.nullable(),
4245
- note: import_zod13.z.string().max(1e3).nullable(),
4480
+ note: import_zod14.z.string().max(1e3).nullable(),
4246
4481
  created_at: Timestamp
4247
4482
  });
4248
- var SuppressionCreate = import_zod13.z.object({
4483
+ var SuppressionCreate = import_zod14.z.object({
4249
4484
  email: Email,
4250
- reason: import_zod13.z.enum(["manual", "unsubscribed"]),
4485
+ reason: import_zod14.z.enum(["manual", "unsubscribed"]),
4251
4486
  topic: Slug.nullable().optional(),
4252
- note: import_zod13.z.string().max(1e3).optional()
4487
+ note: import_zod14.z.string().max(1e3).optional()
4253
4488
  });
4254
4489
  var SuppressionListQuery = PageQuery.extend({
4255
- email: import_zod13.z.string().min(1).max(254).optional(),
4490
+ email: import_zod14.z.string().min(1).max(254).optional(),
4256
4491
  reason: SuppressionReason.optional(),
4257
4492
  topic: Slug.optional()
4258
4493
  });
4259
4494
 
4260
4495
  // src/webhooks.ts
4261
- var import_zod14 = require("zod");
4496
+ var import_zod15 = require("zod");
4262
4497
  var WEBHOOK_EVENT_TYPES = [
4263
4498
  "message.sent",
4264
4499
  "message.failed",
@@ -4302,23 +4537,23 @@ var WEBHOOK_EVENT_TYPES = [
4302
4537
  "template.updated",
4303
4538
  "template.deleted"
4304
4539
  ];
4305
- var WebhookEventType = import_zod14.z.enum(WEBHOOK_EVENT_TYPES);
4306
- var MessageEventBase = import_zod14.z.object({
4540
+ var WebhookEventType = import_zod15.z.enum(WEBHOOK_EVENT_TYPES);
4541
+ var MessageEventBase = import_zod15.z.object({
4307
4542
  message_id: Id,
4308
4543
  mailing_id: Id.nullable(),
4309
4544
  mailing_metadata: MailingMetadata.nullable(),
4310
4545
  recipient_id: Id.nullable(),
4311
4546
  contact_id: Id.nullable(),
4312
- external_id: import_zod14.z.string().nullable(),
4547
+ external_id: import_zod15.z.string().nullable(),
4313
4548
  email: Email,
4314
- subject: import_zod14.z.string(),
4549
+ subject: import_zod15.z.string(),
4315
4550
  topic: Slug.nullable(),
4316
- provider_message_id: import_zod14.z.string().nullable(),
4317
- is_test: import_zod14.z.boolean()
4551
+ provider_message_id: import_zod15.z.string().nullable(),
4552
+ is_test: import_zod15.z.boolean()
4318
4553
  });
4319
4554
  var MessageSentData = MessageEventBase.extend({
4320
4555
  /** The final HTML as sent, so the client can archive it beside its own records. */
4321
- html: import_zod14.z.string(),
4556
+ html: import_zod15.z.string(),
4322
4557
  sent_at: Timestamp,
4323
4558
  /**
4324
4559
  * The choice each insertion made (see `Message.insertions`); absent or null
@@ -4329,20 +4564,20 @@ var MessageSentData = MessageEventBase.extend({
4329
4564
  insertions: InsertionChoices.nullish()
4330
4565
  });
4331
4566
  var MessageFailedData = MessageEventBase.extend({
4332
- error: import_zod14.z.string(),
4567
+ error: import_zod15.z.string(),
4333
4568
  /** False when the provider rejected permanently; the recipient will not be retried. */
4334
- retryable: import_zod14.z.boolean(),
4569
+ retryable: import_zod15.z.boolean(),
4335
4570
  failed_at: Timestamp
4336
4571
  });
4337
4572
  var UNSUBSCRIBE_SOURCES = ["hosted_page", "one_click", "api", "dashboard", "signup_form"];
4338
- var ContactUnsubscribedData = import_zod14.z.object({
4573
+ var ContactUnsubscribedData = import_zod15.z.object({
4339
4574
  contact_id: Id.nullable(),
4340
- external_id: import_zod14.z.string().nullable(),
4575
+ external_id: import_zod15.z.string().nullable(),
4341
4576
  email: Email,
4342
4577
  /** The topic unsubscribed from; null means every topic. */
4343
4578
  topic: Slug.nullable(),
4344
4579
  mailing_id: Id.nullable(),
4345
- source: import_zod14.z.enum(UNSUBSCRIBE_SOURCES),
4580
+ source: import_zod15.z.enum(UNSUBSCRIBE_SOURCES),
4346
4581
  unsubscribed_at: Timestamp
4347
4582
  });
4348
4583
  var ContactResubscribedData = ContactUnsubscribedData.omit({ unsubscribed_at: true }).extend({
@@ -4351,142 +4586,142 @@ var ContactResubscribedData = ContactUnsubscribedData.omit({ unsubscribed_at: tr
4351
4586
  * breaker undid a `bounced` block it judged false (a `contact.bounced` for the
4352
4587
  * same address and mailing went out before); `topic` is null.
4353
4588
  */
4354
- source: import_zod14.z.enum([...UNSUBSCRIBE_SOURCES, "bounce_reverted"]),
4589
+ source: import_zod15.z.enum([...UNSUBSCRIBE_SOURCES, "bounce_reverted"]),
4355
4590
  resubscribed_at: Timestamp
4356
4591
  });
4357
- var ContactBouncedData = import_zod14.z.object({
4592
+ var ContactBouncedData = import_zod15.z.object({
4358
4593
  contact_id: Id.nullable(),
4359
- external_id: import_zod14.z.string().nullable(),
4594
+ external_id: import_zod15.z.string().nullable(),
4360
4595
  email: Email,
4361
4596
  /** `bounced` for a hard bounce, `complained` for a spam complaint. */
4362
- reason: import_zod14.z.enum(["bounced", "complained"]),
4597
+ reason: import_zod15.z.enum(["bounced", "complained"]),
4363
4598
  message_id: Id.nullable(),
4364
- diagnostic: import_zod14.z.string().nullable(),
4599
+ diagnostic: import_zod15.z.string().nullable(),
4365
4600
  bounced_at: Timestamp
4366
4601
  });
4367
- var MailingFinishedData = import_zod14.z.object({
4602
+ var MailingFinishedData = import_zod15.z.object({
4368
4603
  mailing_id: Id,
4369
4604
  mailing_metadata: MailingMetadata,
4370
- status: import_zod14.z.enum(["sent", "partially_failed", "cancelled"]),
4605
+ status: import_zod15.z.enum(["sent", "partially_failed", "cancelled"]),
4371
4606
  counts: MailingCounts,
4372
4607
  finished_at: Timestamp
4373
4608
  });
4374
- var ContactSubscribedData = import_zod14.z.object({
4609
+ var ContactSubscribedData = import_zod15.z.object({
4375
4610
  contact_id: Id,
4376
- external_id: import_zod14.z.string().nullable(),
4611
+ external_id: import_zod15.z.string().nullable(),
4377
4612
  email: Email,
4378
- topics: import_zod14.z.array(Slug),
4379
- source: import_zod14.z.enum(["signup_form", "api", "dashboard", "automation"]),
4613
+ topics: import_zod15.z.array(Slug),
4614
+ source: import_zod15.z.enum(["signup_form", "api", "dashboard", "automation"]),
4380
4615
  signup_form_id: Id.nullable(),
4381
- signup_form_version: import_zod14.z.number().int().min(1).nullable(),
4616
+ signup_form_version: import_zod15.z.number().int().min(1).nullable(),
4382
4617
  subscribed_at: Timestamp
4383
4618
  });
4384
- var ImportFinishedData = import_zod14.z.object({
4619
+ var ImportFinishedData = import_zod15.z.object({
4385
4620
  import_id: Id,
4386
- status: import_zod14.z.enum(["completed", "cancelled", "failed"]),
4621
+ status: import_zod15.z.enum(["completed", "cancelled", "failed"]),
4387
4622
  result: ImportReport.nullable(),
4388
- error: import_zod14.z.string().nullable(),
4623
+ error: import_zod15.z.string().nullable(),
4389
4624
  finished_at: Timestamp
4390
4625
  });
4391
- var MailingScheduledData = import_zod14.z.object({
4626
+ var MailingScheduledData = import_zod15.z.object({
4392
4627
  mailing_id: Id,
4393
4628
  mailing_metadata: MailingMetadata,
4394
4629
  scheduled_at: Timestamp.nullable()
4395
4630
  });
4396
- var MailingStartedData = import_zod14.z.object({
4631
+ var MailingStartedData = import_zod15.z.object({
4397
4632
  mailing_id: Id,
4398
4633
  mailing_metadata: MailingMetadata,
4399
- trigger: import_zod14.z.enum(["send", "schedule"]),
4400
- recipients: import_zod14.z.number().int().min(0),
4634
+ trigger: import_zod15.z.enum(["send", "schedule"]),
4635
+ recipients: import_zod15.z.number().int().min(0),
4401
4636
  started_at: Timestamp
4402
4637
  });
4403
- var MailingScheduleFailedData = import_zod14.z.object({
4638
+ var MailingScheduleFailedData = import_zod15.z.object({
4404
4639
  mailing_id: Id,
4405
4640
  mailing_metadata: MailingMetadata,
4406
- code: import_zod14.z.string(),
4407
- message: import_zod14.z.string(),
4641
+ code: import_zod15.z.string(),
4642
+ message: import_zod15.z.string(),
4408
4643
  failed_at: Timestamp
4409
4644
  });
4410
- var MailingAbWinnerSelectedData = import_zod14.z.object({
4645
+ var MailingAbWinnerSelectedData = import_zod15.z.object({
4411
4646
  mailing_id: Id,
4412
4647
  mailing_metadata: MailingMetadata,
4413
- winner: import_zod14.z.string(),
4414
- decided_by: import_zod14.z.enum(["metric", "manual"]),
4415
- variants: import_zod14.z.array(VariantAnalytics),
4648
+ winner: import_zod15.z.string(),
4649
+ decided_by: import_zod15.z.enum(["metric", "manual"]),
4650
+ variants: import_zod15.z.array(VariantAnalytics),
4416
4651
  decided_at: Timestamp
4417
4652
  });
4418
- var ContactTaggedData = import_zod14.z.object({
4653
+ var ContactTaggedData = import_zod15.z.object({
4419
4654
  contact_id: Id,
4420
- external_id: import_zod14.z.string().nullable(),
4655
+ external_id: import_zod15.z.string().nullable(),
4421
4656
  email: Email,
4422
4657
  /** Only the tags the contact did not already have. */
4423
- tags: import_zod14.z.array(Slug).min(1),
4424
- source: import_zod14.z.enum(["api", "dashboard", "signup_form", "import", "automation"]),
4658
+ tags: import_zod15.z.array(Slug).min(1),
4659
+ source: import_zod15.z.enum(["api", "dashboard", "signup_form", "import", "automation"]),
4425
4660
  tagged_at: Timestamp
4426
4661
  });
4427
- var ContactUpdatedData = import_zod14.z.object({
4662
+ var ContactUpdatedData = import_zod15.z.object({
4428
4663
  contact_id: Id,
4429
- external_id: import_zod14.z.string().nullable(),
4664
+ external_id: import_zod15.z.string().nullable(),
4430
4665
  email: Email,
4431
- changed: import_zod14.z.array(import_zod14.z.string()).min(1),
4666
+ changed: import_zod15.z.array(import_zod15.z.string()).min(1),
4432
4667
  properties: Properties,
4433
- source: import_zod14.z.enum(["api", "dashboard", "signup_form", "import", "automation"]),
4668
+ source: import_zod15.z.enum(["api", "dashboard", "signup_form", "import", "automation"]),
4434
4669
  updated_at: Timestamp
4435
4670
  });
4436
- var AutomationRunEventBase = import_zod14.z.object({
4671
+ var AutomationRunEventBase = import_zod15.z.object({
4437
4672
  automation_id: Id,
4438
- automation_name: import_zod14.z.string(),
4673
+ automation_name: import_zod15.z.string(),
4439
4674
  run_id: Id,
4440
- version: import_zod14.z.number().int().min(1),
4675
+ version: import_zod15.z.number().int().min(1),
4441
4676
  contact_id: Id,
4442
- external_id: import_zod14.z.string().nullable(),
4677
+ external_id: import_zod15.z.string().nullable(),
4443
4678
  email: Email
4444
4679
  });
4445
4680
  var AutomationRunStartedData = AutomationRunEventBase.extend({
4446
4681
  /** What let them in: a trigger kind, or `manual` for an explicit enrolment. */
4447
- trigger_kind: import_zod14.z.string(),
4682
+ trigger_kind: import_zod15.z.string(),
4448
4683
  entered_at: Timestamp
4449
4684
  });
4450
4685
  var AutomationRunCompletedData = AutomationRunEventBase.extend({
4451
- last_step_id: import_zod14.z.string().nullable(),
4686
+ last_step_id: import_zod15.z.string().nullable(),
4452
4687
  completed_at: Timestamp
4453
4688
  });
4454
4689
  var AutomationRunExitedData = AutomationRunEventBase.extend({
4455
4690
  reason: AutomationEndReason,
4456
- step_id: import_zod14.z.string().nullable(),
4691
+ step_id: import_zod15.z.string().nullable(),
4457
4692
  exited_at: Timestamp
4458
4693
  });
4459
4694
  var AutomationRunFailedData = AutomationRunEventBase.extend({
4460
- reason: import_zod14.z.string(),
4461
- step_id: import_zod14.z.string().nullable(),
4695
+ reason: import_zod15.z.string(),
4696
+ step_id: import_zod15.z.string().nullable(),
4462
4697
  failed_at: Timestamp
4463
4698
  });
4464
4699
  var AutomationWebhookData = AutomationRunEventBase.extend({
4465
- step_id: import_zod14.z.string(),
4700
+ step_id: import_zod15.z.string(),
4466
4701
  /** The step's own label, when it was given one, so a receiver can branch on a name. */
4467
- step_label: import_zod14.z.string().nullable(),
4702
+ step_label: import_zod15.z.string().nullable(),
4468
4703
  /** Whatever the step carries, verbatim. Null when it carries nothing. */
4469
4704
  payload: JsonValue.nullable(),
4470
4705
  fired_at: Timestamp
4471
4706
  });
4472
- var TemplateEventBase = import_zod14.z.object({
4707
+ var TemplateEventBase = import_zod15.z.object({
4473
4708
  template_id: Id,
4474
- name: import_zod14.z.string().min(1).max(200),
4475
- version: import_zod14.z.number().int().min(1),
4476
- source: import_zod14.z.enum(["api", "dashboard", "mjml_import"])
4709
+ name: import_zod15.z.string().min(1).max(200),
4710
+ version: import_zod15.z.number().int().min(1),
4711
+ source: import_zod15.z.enum(["api", "dashboard", "mjml_import"])
4477
4712
  });
4478
4713
  var TemplateCreatedData = TemplateEventBase.extend({ created_at: Timestamp });
4479
- var TemplateUpdatedData = TemplateEventBase.extend({ archived: import_zod14.z.boolean(), updated_at: Timestamp });
4714
+ var TemplateUpdatedData = TemplateEventBase.extend({ archived: import_zod15.z.boolean(), updated_at: Timestamp });
4480
4715
  var TemplateDeletedData = TemplateEventBase.extend({ deleted_at: Timestamp });
4481
- var envelope = (type, data) => import_zod14.z.object({
4716
+ var envelope = (type, data) => import_zod15.z.object({
4482
4717
  /** Unique per event: a receiver deduplicates on it (deliveries may repeat). */
4483
4718
  id: Id,
4484
- type: import_zod14.z.literal(type),
4719
+ type: import_zod15.z.literal(type),
4485
4720
  created_at: Timestamp,
4486
4721
  workspace_id: Id,
4487
4722
  data
4488
4723
  });
4489
- var WebhookEvent = import_zod14.z.discriminatedUnion("type", [
4724
+ var WebhookEvent = import_zod15.z.discriminatedUnion("type", [
4490
4725
  envelope("message.sent", MessageSentData),
4491
4726
  envelope("message.failed", MessageFailedData),
4492
4727
  envelope("contact.unsubscribed", ContactUnsubscribedData),
@@ -4510,16 +4745,16 @@ var WebhookEvent = import_zod14.z.discriminatedUnion("type", [
4510
4745
  envelope("template.updated", TemplateUpdatedData),
4511
4746
  envelope("template.deleted", TemplateDeletedData)
4512
4747
  ]);
4513
- var WebhookEndpoint = import_zod14.z.object({
4748
+ var WebhookEndpoint = import_zod15.z.object({
4514
4749
  id: Id,
4515
- url: import_zod14.z.string().url(),
4516
- description: import_zod14.z.string().max(500).nullable(),
4517
- events: import_zod14.z.array(WebhookEventType).min(1),
4518
- enabled: import_zod14.z.boolean(),
4750
+ url: import_zod15.z.string().url(),
4751
+ description: import_zod15.z.string().max(500).nullable(),
4752
+ events: import_zod15.z.array(WebhookEventType).min(1),
4753
+ enabled: import_zod15.z.boolean(),
4519
4754
  created_at: Timestamp,
4520
4755
  updated_at: Timestamp
4521
4756
  });
4522
- var WebhookUrl = import_zod14.z.string().url().refine((u) => {
4757
+ var WebhookUrl = import_zod15.z.string().url().refine((u) => {
4523
4758
  try {
4524
4759
  const url = new URL(u);
4525
4760
  if (url.protocol === "https:") return true;
@@ -4528,35 +4763,35 @@ var WebhookUrl = import_zod14.z.string().url().refine((u) => {
4528
4763
  return false;
4529
4764
  }
4530
4765
  }, "must be https (http only for localhost)");
4531
- var WebhookEndpointCreate = import_zod14.z.object({
4766
+ var WebhookEndpointCreate = import_zod15.z.object({
4532
4767
  url: WebhookUrl,
4533
- description: import_zod14.z.string().max(500).optional(),
4534
- events: import_zod14.z.array(WebhookEventType).min(1),
4535
- enabled: import_zod14.z.boolean().optional()
4768
+ description: import_zod15.z.string().max(500).optional(),
4769
+ events: import_zod15.z.array(WebhookEventType).min(1),
4770
+ enabled: import_zod15.z.boolean().optional()
4536
4771
  });
4537
- var WebhookEndpointUpdate = import_zod14.z.object({
4772
+ var WebhookEndpointUpdate = import_zod15.z.object({
4538
4773
  url: WebhookUrl,
4539
- description: import_zod14.z.string().max(500).nullable(),
4540
- events: import_zod14.z.array(WebhookEventType).min(1),
4541
- enabled: import_zod14.z.boolean()
4774
+ description: import_zod15.z.string().max(500).nullable(),
4775
+ events: import_zod15.z.array(WebhookEventType).min(1),
4776
+ enabled: import_zod15.z.boolean()
4542
4777
  }).partial().refine((v) => Object.keys(v).length > 0, "at least one field");
4543
- var WebhookEndpointWithSecret = import_zod14.z.object({
4778
+ var WebhookEndpointWithSecret = import_zod15.z.object({
4544
4779
  endpoint: WebhookEndpoint,
4545
- secret: import_zod14.z.string().min(32)
4780
+ secret: import_zod15.z.string().min(32)
4546
4781
  });
4547
4782
  var WEBHOOK_DELIVERY_STATUSES = ["pending", "succeeded", "failed"];
4548
- var WebhookDeliveryStatus = import_zod14.z.enum(WEBHOOK_DELIVERY_STATUSES);
4783
+ var WebhookDeliveryStatus = import_zod15.z.enum(WEBHOOK_DELIVERY_STATUSES);
4549
4784
  var WEBHOOK_MAX_ATTEMPTS = 8;
4550
4785
  var WEBHOOK_RETRY_DELAYS_SECONDS = [30, 120, 600, 1800, 3600, 7200, 21600];
4551
- var WebhookDelivery = import_zod14.z.object({
4786
+ var WebhookDelivery = import_zod15.z.object({
4552
4787
  id: Id,
4553
4788
  endpoint_id: Id,
4554
4789
  event_id: Id,
4555
4790
  event_type: WebhookEventType,
4556
4791
  status: WebhookDeliveryStatus,
4557
- attempts: import_zod14.z.number().int().min(0),
4558
- last_status_code: import_zod14.z.number().int().min(100).max(599).nullable(),
4559
- last_error: import_zod14.z.string().nullable(),
4792
+ attempts: import_zod15.z.number().int().min(0),
4793
+ last_status_code: import_zod15.z.number().int().min(100).max(599).nullable(),
4794
+ last_error: import_zod15.z.string().nullable(),
4560
4795
  next_attempt_at: Timestamp.nullable(),
4561
4796
  delivered_at: Timestamp.nullable(),
4562
4797
  created_at: Timestamp
@@ -4565,7 +4800,7 @@ var WebhookDeliveryListQuery = PageQuery.extend({
4565
4800
  status: WebhookDeliveryStatus.optional(),
4566
4801
  event_type: WebhookEventType.optional()
4567
4802
  });
4568
- var WebhookDeliveryParams = import_zod14.z.object({ id: Id, delivery_id: Id });
4803
+ var WebhookDeliveryParams = import_zod15.z.object({ id: Id, delivery_id: Id });
4569
4804
 
4570
4805
  // src/webhook-signing.ts
4571
4806
  var WEBHOOK_SIGNATURE_HEADER = "x-mail-signature";
@@ -4632,79 +4867,79 @@ async function verifyWebhook(input) {
4632
4867
  }
4633
4868
 
4634
4869
  // src/billing.ts
4635
- var import_zod15 = require("zod");
4870
+ var import_zod16 = require("zod");
4636
4871
  var PLAN_IDS = ["free", "starter", "growth", "design_partner"];
4637
- var PlanId = import_zod15.z.enum(PLAN_IDS);
4638
- var PlanLimits = import_zod15.z.object({
4639
- monthly_messages: import_zod15.z.number().int().min(0).nullable(),
4640
- contacts: import_zod15.z.number().int().min(0).nullable(),
4641
- members: import_zod15.z.number().int().min(1).nullable(),
4642
- providers: import_zod15.z.number().int().min(1).nullable(),
4643
- webhook_endpoints: import_zod15.z.number().int().min(0).nullable(),
4872
+ var PlanId = import_zod16.z.enum(PLAN_IDS);
4873
+ var PlanLimits = import_zod16.z.object({
4874
+ monthly_messages: import_zod16.z.number().int().min(0).nullable(),
4875
+ contacts: import_zod16.z.number().int().min(0).nullable(),
4876
+ members: import_zod16.z.number().int().min(1).nullable(),
4877
+ providers: import_zod16.z.number().int().min(1).nullable(),
4878
+ webhook_endpoints: import_zod16.z.number().int().min(0).nullable(),
4644
4879
  /** Automations that may be live (active or paused) at once (A1). */
4645
- active_automations: import_zod15.z.number().int().min(0).nullable(),
4880
+ active_automations: import_zod16.z.number().int().min(0).nullable(),
4646
4881
  /** Steps one automation may hold. Null is the flow's own cap, not unlimited. */
4647
- automation_steps: import_zod15.z.number().int().min(1).nullable()
4882
+ automation_steps: import_zod16.z.number().int().min(1).nullable()
4648
4883
  });
4649
- var PlanFeatures = import_zod15.z.object({
4884
+ var PlanFeatures = import_zod16.z.object({
4650
4885
  /** A/B tests of subject and content on a mailing (S4). */
4651
- ab_testing: import_zod15.z.boolean(),
4886
+ ab_testing: import_zod16.z.boolean(),
4652
4887
  /** Open and click tracking, still off until a workspace turns it on (`settings.tracking_enabled`). */
4653
- tracking: import_zod15.z.boolean(),
4888
+ tracking: import_zod16.z.boolean(),
4654
4889
  /** Sending and hosting pages on the workspace's own domain (a later phase). */
4655
- custom_domains: import_zod15.z.boolean(),
4890
+ custom_domains: import_zod16.z.boolean(),
4656
4891
  /** Automations: flows a person walks through step by step (A1). */
4657
- automations: import_zod15.z.boolean()
4892
+ automations: import_zod16.z.boolean()
4658
4893
  });
4659
4894
  var PLAN_FEATURES = ["ab_testing", "tracking", "custom_domains", "automations"];
4660
- var Plan = import_zod15.z.object({
4895
+ var Plan = import_zod16.z.object({
4661
4896
  id: PlanId,
4662
- name: import_zod15.z.string().min(1),
4897
+ name: import_zod16.z.string().min(1),
4663
4898
  /** Price in the smallest currency unit per month; null for plans not sold. */
4664
- monthly_price_cents: import_zod15.z.number().int().min(0).nullable(),
4665
- currency: import_zod15.z.string().length(3),
4899
+ monthly_price_cents: import_zod16.z.number().int().min(0).nullable(),
4900
+ currency: import_zod16.z.string().length(3),
4666
4901
  limits: PlanLimits,
4667
4902
  features: PlanFeatures
4668
4903
  });
4669
- var CatalogPlan = Plan.extend({ sellable: import_zod15.z.boolean() });
4670
- var Subscription = import_zod15.z.object({
4904
+ var CatalogPlan = Plan.extend({ sellable: import_zod16.z.boolean() });
4905
+ var Subscription = import_zod16.z.object({
4671
4906
  workspace_id: Id,
4672
4907
  plan: PlanId,
4673
- status: import_zod15.z.enum(["active", "trialing", "past_due", "cancelled"]),
4908
+ status: import_zod16.z.enum(["active", "trialing", "past_due", "cancelled"]),
4674
4909
  current_period_start: Timestamp,
4675
4910
  current_period_end: Timestamp,
4676
- cancel_at_period_end: import_zod15.z.boolean(),
4911
+ cancel_at_period_end: import_zod16.z.boolean(),
4677
4912
  /**
4678
4913
  * A design partner outside billing (plan `design_partner`, no limits, no
4679
4914
  * checkout). Set only by an operator, never through the API.
4680
4915
  */
4681
- billing_exempt: import_zod15.z.boolean()
4916
+ billing_exempt: import_zod16.z.boolean()
4682
4917
  });
4683
4918
  var USAGE_METRICS = ["messages", "contacts", "members", "providers", "webhook_endpoints", "active_automations"];
4684
- var UsageMetric = import_zod15.z.enum(USAGE_METRICS);
4919
+ var UsageMetric = import_zod16.z.enum(USAGE_METRICS);
4685
4920
  var USAGE_WARNING_RATIO = 0.8;
4686
- var UsageWarning = import_zod15.z.object({
4921
+ var UsageWarning = import_zod16.z.object({
4687
4922
  metric: UsageMetric,
4688
- used: import_zod15.z.number().int().min(0),
4689
- limit: import_zod15.z.number().int().min(0),
4923
+ used: import_zod16.z.number().int().min(0),
4924
+ limit: import_zod16.z.number().int().min(0),
4690
4925
  /** `approaching`: at or above USAGE_WARNING_RATIO of the limit; `reached`: at or above the limit. */
4691
- level: import_zod15.z.enum(["approaching", "reached"])
4926
+ level: import_zod16.z.enum(["approaching", "reached"])
4692
4927
  });
4693
- var Usage = import_zod15.z.object({
4928
+ var Usage = import_zod16.z.object({
4694
4929
  plan: PlanId,
4695
4930
  period_start: Timestamp,
4696
4931
  period_end: Timestamp,
4697
- metrics: import_zod15.z.record(UsageMetric, import_zod15.z.object({ used: import_zod15.z.number().int().min(0), limit: import_zod15.z.number().int().min(0).nullable() })),
4698
- warnings: import_zod15.z.array(UsageWarning)
4932
+ metrics: import_zod16.z.record(UsageMetric, import_zod16.z.object({ used: import_zod16.z.number().int().min(0), limit: import_zod16.z.number().int().min(0).nullable() })),
4933
+ warnings: import_zod16.z.array(UsageWarning)
4699
4934
  });
4700
- var CheckoutRequest = import_zod15.z.object({
4701
- plan: import_zod15.z.enum(["starter", "growth"]),
4702
- success_url: import_zod15.z.string().url(),
4703
- cancel_url: import_zod15.z.string().url()
4935
+ var CheckoutRequest = import_zod16.z.object({
4936
+ plan: import_zod16.z.enum(["starter", "growth"]),
4937
+ success_url: import_zod16.z.string().url(),
4938
+ cancel_url: import_zod16.z.string().url()
4704
4939
  });
4705
- var CheckoutSession = import_zod15.z.object({ url: import_zod15.z.string().url() });
4706
- var PortalRequest = import_zod15.z.object({ return_url: import_zod15.z.string().url() });
4707
- var PortalSession = import_zod15.z.object({ url: import_zod15.z.string().url() });
4940
+ var CheckoutSession = import_zod16.z.object({ url: import_zod16.z.string().url() });
4941
+ var PortalRequest = import_zod16.z.object({ return_url: import_zod16.z.string().url() });
4942
+ var PortalSession = import_zod16.z.object({ url: import_zod16.z.string().url() });
4708
4943
  var USAGE_WARNING_HEADER = "x-mail-usage-warning";
4709
4944
  function formatUsageWarningHeader(warnings) {
4710
4945
  if (warnings.length === 0) return null;
@@ -4724,7 +4959,7 @@ function parseUsageWarningHeader(value) {
4724
4959
  }
4725
4960
 
4726
4961
  // src/routes.ts
4727
- var import_zod16 = require("zod");
4962
+ var import_zod17 = require("zod");
4728
4963
  var list = (item) => page(item);
4729
4964
  var foundationRoutes = {
4730
4965
  "workspaces.create": {
@@ -4952,7 +5187,7 @@ var templateRoutes = {
4952
5187
  path: "/v1/templates/:id/export",
4953
5188
  params: IdParams,
4954
5189
  query: TemplateExportQuery,
4955
- response: import_zod16.z.string(),
5190
+ response: import_zod17.z.string(),
4956
5191
  responseType: "text",
4957
5192
  status: 200,
4958
5193
  access: "read",
@@ -5276,7 +5511,7 @@ var sendingRoutes = {
5276
5511
  path: "/v1/mailings/:id/export",
5277
5512
  params: IdParams,
5278
5513
  query: MailingExportQuery,
5279
- response: import_zod16.z.string(),
5514
+ response: import_zod17.z.string(),
5280
5515
  responseType: "text",
5281
5516
  status: 200,
5282
5517
  access: "read",
@@ -5322,6 +5557,21 @@ var sendingRoutes = {
5322
5557
  access: "write",
5323
5558
  phase: "S2"
5324
5559
  },
5560
+ /**
5561
+ * A dry run: what each given recipient would be sent (every value's text and
5562
+ * the layer it comes from, each insertion's choice, the problems found),
5563
+ * without adding anybody. Reads only, in any state of the mailing.
5564
+ */
5565
+ "mailings.resolve": {
5566
+ method: "POST",
5567
+ path: "/v1/mailings/:id/resolve",
5568
+ params: IdParams,
5569
+ body: MailingResolveRequest,
5570
+ response: MailingResolveResult,
5571
+ status: 200,
5572
+ access: "read",
5573
+ phase: "S2"
5574
+ },
5325
5575
  "mailings.send": {
5326
5576
  method: "POST",
5327
5577
  path: "/v1/mailings/:id/send",
@@ -5509,7 +5759,7 @@ var platformRoutes = {
5509
5759
  "contactProperties.list": {
5510
5760
  method: "GET",
5511
5761
  path: "/v1/contact-properties",
5512
- response: import_zod16.z.object({ data: import_zod16.z.array(ContactPropertyDefinition) }),
5762
+ response: import_zod17.z.object({ data: import_zod17.z.array(ContactPropertyDefinition) }),
5513
5763
  status: 200,
5514
5764
  access: "read",
5515
5765
  phase: "S4"
@@ -5808,7 +6058,7 @@ var billingRoutes = {
5808
6058
  "billing.plans": {
5809
6059
  method: "GET",
5810
6060
  path: "/v1/billing/plans",
5811
- response: import_zod16.z.object({ data: import_zod16.z.array(CatalogPlan) }),
6061
+ response: import_zod17.z.object({ data: import_zod17.z.array(CatalogPlan) }),
5812
6062
  status: 200,
5813
6063
  access: "read",
5814
6064
  phase: "S5"
@@ -5950,7 +6200,7 @@ var automationRoutes = {
5950
6200
  method: "POST",
5951
6201
  path: "/v1/automations/:id/pause",
5952
6202
  params: IdParams,
5953
- body: import_zod16.z.object({}).strict(),
6203
+ body: import_zod17.z.object({}).strict(),
5954
6204
  response: Automation,
5955
6205
  status: 200,
5956
6206
  access: "write",
@@ -5960,7 +6210,7 @@ var automationRoutes = {
5960
6210
  method: "POST",
5961
6211
  path: "/v1/automations/:id/resume",
5962
6212
  params: IdParams,
5963
- body: import_zod16.z.object({}).strict(),
6213
+ body: import_zod17.z.object({}).strict(),
5964
6214
  response: Automation,
5965
6215
  status: 200,
5966
6216
  access: "write",
@@ -5970,7 +6220,7 @@ var automationRoutes = {
5970
6220
  method: "POST",
5971
6221
  path: "/v1/automations/:id/archive",
5972
6222
  params: IdParams,
5973
- body: import_zod16.z.object({}).strict(),
6223
+ body: import_zod17.z.object({}).strict(),
5974
6224
  response: Automation,
5975
6225
  status: 200,
5976
6226
  access: "write",
@@ -6104,13 +6354,13 @@ function matchRoute(method, pathname) {
6104
6354
  for (const [id, route] of Object.entries(routes)) {
6105
6355
  if (route.method !== method) continue;
6106
6356
  const names = [];
6107
- const pattern2 = new RegExp(
6357
+ const pattern3 = new RegExp(
6108
6358
  "^" + route.path.replace(/[.*+?^${}()|[\]\\]/g, "\\$&").replace(/:([a-z_]+)/g, (_, name) => {
6109
6359
  names.push(name);
6110
6360
  return "([^/]+)";
6111
6361
  }) + "$"
6112
6362
  );
6113
- const match = pattern2.exec(pathname);
6363
+ const match = pattern3.exec(pathname);
6114
6364
  if (!match) continue;
6115
6365
  const params = {};
6116
6366
  names.forEach((name, i) => {
@@ -6311,6 +6561,7 @@ function matchRoute(method, pathname) {
6311
6561
  InviteListQuery,
6312
6562
  InviteStatus,
6313
6563
  JsonValue,
6564
+ LETTER_ONLY_MERGE_FIELDS,
6314
6565
  LETTER_RECIPIENT_REFUSAL,
6315
6566
  LIST_UNSUBSCRIBE_POST_VALUE,
6316
6567
  LOCALE_TAG_PATTERN,
@@ -6379,7 +6630,10 @@ function matchRoute(method, pathname) {
6379
6630
  MailingLanguageReport,
6380
6631
  MailingLanguageStatus,
6381
6632
  MailingListQuery,
6633
+ MailingMerge,
6382
6634
  MailingMetadata,
6635
+ MailingResolveRequest,
6636
+ MailingResolveResult,
6383
6637
  MailingRetryFailedRequest,
6384
6638
  MailingScheduleFailedData,
6385
6639
  MailingScheduleRequest,
@@ -6404,6 +6658,8 @@ function matchRoute(method, pathname) {
6404
6658
  MessageOutcome,
6405
6659
  MessageSentData,
6406
6660
  MessageSummary,
6661
+ MessageValues,
6662
+ NAME_ON_BROADCAST_REFUSAL,
6407
6663
  NotifyRecipients,
6408
6664
  NotifyStep,
6409
6665
  ON_BEHALF_OF_HEADER,
@@ -6439,6 +6695,8 @@ function matchRoute(method, pathname) {
6439
6695
  REQUEST_ID_HEADER,
6440
6696
  RESEND_EVENT_TYPES,
6441
6697
  RESERVED_MERGE_FIELDS,
6698
+ RESOLVE_PROBLEMS,
6699
+ RESOLVE_REJECTIONS,
6442
6700
  RETRYABLE_ERRORS,
6443
6701
  RETRY_AFTER_HEADER,
6444
6702
  RE_ENTRY_MODES,
@@ -6451,6 +6709,9 @@ function matchRoute(method, pathname) {
6451
6709
  RecipientStatus,
6452
6710
  RemoteImage,
6453
6711
  ResendSigningSecret,
6712
+ ResolveProblem,
6713
+ ResolvedRecipient,
6714
+ ResolvedValue,
6454
6715
  SERVICE_FILLED_MERGE_FIELDS,
6455
6716
  SIGNUP_FORM_FIELDS,
6456
6717
  SKIP_REASONS,
@@ -6537,10 +6798,13 @@ function matchRoute(method, pathname) {
6537
6798
  USAGE_METRICS,
6538
6799
  USAGE_WARNING_HEADER,
6539
6800
  USAGE_WARNING_RATIO,
6801
+ UnfilledLink,
6540
6802
  Usage,
6541
6803
  UsageMetric,
6542
6804
  UsageWarning,
6805
+ VALUE_LAYERS,
6543
6806
  ValidationIssue,
6807
+ ValueLayer,
6544
6808
  VariantAnalytics,
6545
6809
  WEBHOOK_DELIVERY_STATUSES,
6546
6810
  WEBHOOK_EVENT_ID_HEADER,
@@ -6604,6 +6868,7 @@ function matchRoute(method, pathname) {
6604
6868
  editMainInsertions,
6605
6869
  effectivePreviewPicks,
6606
6870
  emptyFlow,
6871
+ emptyLinkValues,
6607
6872
  errorBody,
6608
6873
  escapeMergeHtml,
6609
6874
  exportFilename,
@@ -6634,6 +6899,8 @@ function matchRoute(method, pathname) {
6634
6899
  languageInsertions,
6635
6900
  languageName,
6636
6901
  languageTabs,
6902
+ letterOnlyValues,
6903
+ linkTokens,
6637
6904
  mainInsertionText,
6638
6905
  matchLocale,
6639
6906
  matchRoute,
@@ -6654,6 +6921,8 @@ function matchRoute(method, pathname) {
6654
6921
  previewInsertions,
6655
6922
  previewPersonalization,
6656
6923
  primaryLanguage,
6924
+ printedFields,
6925
+ rawMergeValue,
6657
6926
  reachable,
6658
6927
  readyWithoutInsertions,
6659
6928
  readyWithoutSubject,
@@ -6670,6 +6939,7 @@ function matchRoute(method, pathname) {
6670
6939
  renameTokenInDocument,
6671
6940
  renameTokenInText,
6672
6941
  resolveInsertions,
6942
+ resolveValue,
6673
6943
  restorePatch,
6674
6944
  routes,
6675
6945
  sameJson,
@@ -6696,5 +6966,7 @@ function matchRoute(method, pathname) {
6696
6966
  unknownRefusedInsertions,
6697
6967
  unplacedInsertions,
6698
6968
  validateAutomation,
6969
+ valueNames,
6970
+ valuesRead,
6699
6971
  verifyWebhook
6700
6972
  });