samva 0.17.0 → 0.19.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (143) hide show
  1. package/AGENTS.md +5 -0
  2. package/README.md +18 -3
  3. package/dist/{rolldown-runtime-D7D4PA-g.js → _virtual/_rolldown/runtime.js} +1 -1
  4. package/dist/client/client/client.gen.js +174 -0
  5. package/dist/client/client/utils.gen.js +177 -0
  6. package/dist/client/client.gen.js +8 -0
  7. package/dist/client/core/auth.gen.js +12 -0
  8. package/dist/client/core/bodySerializer.gen.js +6 -0
  9. package/dist/client/core/params.gen.js +77 -0
  10. package/dist/client/core/pathSerializer.gen.js +82 -0
  11. package/dist/client/core/serverSentEvents.gen.js +96 -0
  12. package/dist/client/core/utils.gen.js +78 -0
  13. package/dist/client/sdk.gen.d.ts +39 -23
  14. package/dist/{promises---Kbh-7z.js → client/sdk.gen.js} +87 -2314
  15. package/dist/client/types.gen.d.ts +175 -44
  16. package/dist/client-attribution.js +9 -0
  17. package/dist/effect/analytics.d.ts +6 -6
  18. package/dist/effect/analytics.js +23 -2
  19. package/dist/effect/api-keys.d.ts +12 -12
  20. package/dist/effect/api-keys.js +29 -2
  21. package/dist/effect/attachments.d.ts +4 -4
  22. package/dist/effect/attachments.js +19 -2
  23. package/dist/effect/brands.d.ts +6 -6
  24. package/dist/effect/brands.js +26 -3
  25. package/dist/effect/campaigns.d.ts +18 -18
  26. package/dist/effect/campaigns.js +35 -2
  27. package/dist/effect/categories.d.ts +2 -2
  28. package/dist/effect/categories.js +95 -1
  29. package/dist/effect/client.js +3 -3
  30. package/dist/effect/contact-groups.d.ts +53 -17
  31. package/dist/effect/contact-groups.js +31 -2
  32. package/dist/effect/contacts.d.ts +244 -41
  33. package/dist/effect/contacts.js +54 -2
  34. package/dist/effect/conversations.d.ts +28 -28
  35. package/dist/effect/conversations.js +37 -2
  36. package/dist/effect/custom-fields.d.ts +4 -4
  37. package/dist/effect/custom-fields.js +19 -2
  38. package/dist/effect/email.d.ts +75 -75
  39. package/dist/effect/email.js +140 -2
  40. package/dist/effect/errors.d.ts +2 -0
  41. package/dist/effect/errors.js +3 -0
  42. package/dist/effect/events.d.ts +2 -2
  43. package/dist/effect/events.js +17 -3
  44. package/dist/effect/extension-installations.d.ts +23 -23
  45. package/dist/effect/extension-installations.js +29 -2
  46. package/dist/effect/extensions.d.ts +12 -12
  47. package/dist/effect/extensions.js +21 -2
  48. package/dist/effect/feedback.d.ts +1 -1
  49. package/dist/effect/feedback.js +14 -3
  50. package/dist/{analytics-CaqPRsry.js → effect/generated/analytics.js} +4 -23
  51. package/dist/{api-keys-Ce1Y4_Ip.js → effect/generated/api-keys.js} +4 -29
  52. package/dist/{attachments-DYqVIraC.js → effect/generated/attachments.js} +3 -18
  53. package/dist/{brands-ZwuOGIWO.js → effect/generated/brands.js} +5 -25
  54. package/dist/{campaigns-DZlz1E9E.js → effect/generated/campaigns.js} +4 -35
  55. package/dist/effect/generated/contact-events.js +37 -0
  56. package/dist/effect/generated/contact-groups.d.ts +33 -3
  57. package/dist/{contact-groups-BLbFXnjq.js → effect/generated/contact-groups.js} +3 -30
  58. package/dist/effect/generated/contacts.d.ts +477 -54
  59. package/dist/{contacts-BbsoXXB4.js → effect/generated/contacts.js} +41 -89
  60. package/dist/effect/generated/conversations.d.ts +25 -25
  61. package/dist/{conversations-_sRHueML.js → effect/generated/conversations.js} +4 -37
  62. package/dist/{custom-fields-BHWbwlKn.js → effect/generated/custom-fields.js} +5 -19
  63. package/dist/{email-R0NAA9PW.js → effect/generated/email.js} +995 -1146
  64. package/dist/{events-CxbTUHYT.js → effect/generated/events.js} +3 -15
  65. package/dist/effect/generated/extension-installations.d.ts +44 -44
  66. package/dist/{extension-installations-CD94LPmk.js → effect/generated/extension-installations.js} +10 -29
  67. package/dist/effect/generated/extensions.d.ts +10 -10
  68. package/dist/{extensions-BKyNQLvu.js → effect/generated/extensions.js} +5 -20
  69. package/dist/{feedback-Bpa09JOS.js → effect/generated/feedback.js} +3 -12
  70. package/dist/{journeys-CARo_BJT.js → effect/generated/journeys.js} +3 -38
  71. package/dist/effect/generated/mailboxes.d.ts +310 -0
  72. package/dist/{mailboxes-BRDn7BIK.js → effect/generated/mailboxes.js} +829 -954
  73. package/dist/{media-VrrtNnft.js → effect/generated/media.js} +3 -3
  74. package/dist/effect/generated/messages.d.ts +31 -0
  75. package/dist/effect/generated/messages.js +677 -0
  76. package/dist/{namespaces-CcvEbG-y.js → effect/generated/namespaces.js} +3 -20
  77. package/dist/{operations-CmB3FHwf.js → effect/generated/operations.js} +3 -16
  78. package/dist/effect/generated/organizations.d.ts +13 -11
  79. package/dist/{organizations-A-plufWc.js → effect/generated/organizations.js} +9 -26
  80. package/dist/{scheduled-messages-DkKZRRaN.js → effect/generated/scheduled-messages.js} +4 -21
  81. package/dist/effect/generated/shared.d.ts +70 -20
  82. package/dist/effect/generated/shared.js +1073 -0
  83. package/dist/{subscriptions-DEXYtMXg.js → effect/generated/subscriptions.js} +3 -9
  84. package/dist/{templates-DZomxsG7.js → effect/generated/templates.js} +3 -78
  85. package/dist/effect/generated/unsubscribe-groups.d.ts +173 -78
  86. package/dist/{unsubscribe-groups-Iqk4Isf9.js → effect/generated/unsubscribe-groups.js} +77 -84
  87. package/dist/effect/generated/webhooks.d.ts +19 -19
  88. package/dist/{webhooks-CPXuu8Xf.js → effect/generated/webhooks.js} +12 -34
  89. package/dist/{whoami-Ccz0jwlt.js → effect/generated/whoami.js} +5 -10
  90. package/dist/effect/generated-metadata.d.ts +7 -2
  91. package/dist/effect/generated-metadata.js +925 -0
  92. package/dist/effect/index.d.ts +1 -2
  93. package/dist/effect/index.js +32 -32
  94. package/dist/effect/internal/client.js +69 -0
  95. package/dist/effect/internal/email-sender.js +21 -0
  96. package/dist/effect/internal/mailbox-events.js +33 -0
  97. package/dist/effect/internal/operation.js +116 -0
  98. package/dist/effect/internal/send.js +56 -0
  99. package/dist/effect/journeys.d.ts +18 -18
  100. package/dist/effect/journeys.js +39 -2
  101. package/dist/effect/mailboxes.d.ts +314 -182
  102. package/dist/effect/mailboxes.js +135 -3
  103. package/dist/effect/media.d.ts +5 -5
  104. package/dist/effect/media.js +10 -10
  105. package/dist/effect/messages.d.ts +19 -14
  106. package/dist/effect/messages.js +15 -14
  107. package/dist/effect/namespaces.d.ts +7 -7
  108. package/dist/effect/namespaces.js +21 -2
  109. package/dist/effect/operations.d.ts +5 -5
  110. package/dist/effect/operations.js +17 -2
  111. package/dist/effect/organizations.d.ts +11 -11
  112. package/dist/effect/organizations.js +25 -2
  113. package/dist/effect/pagination.js +39 -0
  114. package/dist/effect/retry.js +3 -3
  115. package/dist/{runtime-P0l1_2-C.js → effect/runtime.js} +2 -2
  116. package/dist/effect/scheduled-messages.d.ts +7 -7
  117. package/dist/effect/scheduled-messages.js +21 -2
  118. package/dist/effect/subscriptions.d.ts +1 -1
  119. package/dist/effect/subscriptions.js +10 -2
  120. package/dist/effect/templates.d.ts +39 -39
  121. package/dist/effect/templates.js +80 -3
  122. package/dist/effect/unsubscribe-groups.d.ts +39 -28
  123. package/dist/effect/unsubscribe-groups.js +29 -2
  124. package/dist/effect/webhooks.d.ts +22 -22
  125. package/dist/effect/webhooks.js +35 -3
  126. package/dist/effect/whoami.d.ts +9 -9
  127. package/dist/effect/whoami.js +10 -2
  128. package/dist/index.js +4 -3
  129. package/dist/{inline-attachments-Bi1hDltp.js → inline-attachments.js} +13 -7
  130. package/dist/mailbox-events.d.ts +31 -4
  131. package/dist/{mailbox-events-VKR4f3qq.js → mailbox-events.js} +41 -13
  132. package/dist/{normalize-B79uJIeb.js → normalize.js} +2 -2
  133. package/dist/package.js +6 -0
  134. package/dist/promises/errors.gen.js +1340 -0
  135. package/dist/promises/index.d.ts +1 -1
  136. package/dist/promises/index.js +288 -3
  137. package/dist/promises/types.gen.d.ts +1 -1
  138. package/dist/service-map.d.ts +9 -4
  139. package/dist/{operation-n_IYgNVK.js → service-map.js} +12 -150
  140. package/package.json +6 -2
  141. package/dist/categories-CA4XIQAb.js +0 -1011
  142. package/dist/client-DOzUrdTE.js +0 -1115
  143. package/dist/send-Bxc0XfGE.js +0 -722
@@ -5,7 +5,8 @@
5
5
  * {@link MailboxEventStream} is an async iterable. The loop body handling an event is the
6
6
  * acknowledgement: asking for the next event marks the previous one handled, and the stream
7
7
  * resumes from the last handled event whenever it reconnects. Transient closes reconnect by
8
- * themselves; a close the caller has to act on ends the loop with a {@link MailboxEventStreamError}.
8
+ * themselves, and a normal close (1000) from the host ends the loop after the events already
9
+ * received; a close the caller has to act on ends the loop with a {@link MailboxEventStreamError}.
9
10
  *
10
11
  * This module has no runtime dependencies so the Promise and Effect clients share it.
11
12
  */
@@ -29,7 +30,7 @@ export declare const MailboxEventStreamCloseCode: {
29
30
  readonly accessUnavailable: 4503;
30
31
  };
31
32
  /** The event types the stream carries: the `mailbox.*` webhook events. */
32
- export type MailboxEventType = "mailbox.message.received" | "mailbox.message.sent" | "mailbox.action.pending_approval" | "mailbox.message.quarantined" | "mailbox.message.released" | "mailbox.message.discarded";
33
+ export type MailboxEventType = "mailbox.message.received" | "mailbox.message.sent" | "mailbox.action.pending_approval" | "mailbox.action.resolved" | "mailbox.message.quarantined" | "mailbox.message.released" | "mailbox.message.discarded";
33
34
  /** One event, as a webhook delivery of it would carry it, plus its stream position. */
34
35
  export interface MailboxEvent {
35
36
  /** The stream position of this event. Persist it after handling to resume from here. */
@@ -44,12 +45,19 @@ export interface MailboxEvent {
44
45
  /**
45
46
  * Why a stream ended, as the `_tag` of its {@link MailboxEventStreamError}. The first nine are the
46
47
  * API error tags the events host refuses with, or that a close code stands for. The rest are the
47
- * client's own: `StreamDisconnectedError` is a close or an unreachable host that was not retried
48
- * because `reconnect` is `false`, `StreamClientError` is a request this client could not make,
48
+ * client's own: `StreamDisconnectedError` is a close, an idle timeout, or an unreachable host that
49
+ * was not retried because `reconnect` is `false`, `StreamClientError` is a request this client could not make,
49
50
  * `StreamProtocolError` is a frame from the host it could not read, and `StreamRefusedError` is a refusal whose tag and status this client
50
51
  * does not know (`serverTag` carries the tag the host sent).
51
52
  */
52
53
  export type MailboxEventStreamErrorTag = "UnauthorizedError" | "ForbiddenError" | "ResourceNotFoundError" | "CursorExpiredError" | "ValidationError" | "UpgradeRequiredError" | "RateLimitedError" | "ServiceUnavailableError" | "MethodNotAllowedError" | "StreamDisconnectedError" | "StreamClientError" | "StreamProtocolError" | "StreamRefusedError";
54
+ /**
55
+ * Why a {@link MailboxEventStreamError} ended a stream, when `_tag` alone does not say.
56
+ * `idleTimeout`: the client heard no frame, not even a pong, for
57
+ * {@link MAILBOX_EVENT_STREAM_IDLE_MILLIS}, so it closed the connection itself. No close code
58
+ * accompanies it; a `closeCode` of `1006` is a close the client observed without a status.
59
+ */
60
+ export type MailboxEventStreamErrorReason = "idleTimeout";
53
61
  /** Field-level validation messages, keyed by dotted path, as a `ValidationError` carries them. */
54
62
  export type MailboxEventStreamErrorFields = Readonly<Record<string, ReadonlyArray<string>>>;
55
63
  /**
@@ -76,6 +84,8 @@ export declare class MailboxEventStreamError<Tag extends MailboxEventStreamError
76
84
  readonly retryAfterSeconds: number | undefined;
77
85
  /** The tag the host sent, when it is not one this client maps. */
78
86
  readonly serverTag: string | undefined;
87
+ /** Set when the client ended the connection itself; see {@link MailboxEventStreamErrorReason}. */
88
+ readonly reason: MailboxEventStreamErrorReason | undefined;
79
89
  constructor(input: {
80
90
  readonly _tag: Tag;
81
91
  readonly message: string;
@@ -85,6 +95,7 @@ export declare class MailboxEventStreamError<Tag extends MailboxEventStreamError
85
95
  readonly fields?: MailboxEventStreamErrorFields | undefined;
86
96
  readonly retryAfterSeconds?: number | undefined;
87
97
  readonly serverTag?: string | undefined;
98
+ readonly reason?: MailboxEventStreamErrorReason | undefined;
88
99
  });
89
100
  }
90
101
  /** Every stream error as a union over `_tag`, so `Effect.catchTag` can narrow it. */
@@ -113,6 +124,17 @@ export interface MailboxEventStreamSocket {
113
124
  export type MailboxEventStreamWebSocket = new (url: string, options: {
114
125
  readonly headers: Readonly<Record<string, string>>;
115
126
  }) => MailboxEventStreamSocket;
127
+ /** A reconnect the stream is about to make. */
128
+ export interface MailboxEventStreamReconnect {
129
+ /** Why the connection ended: the error the stream would have ended with had it not retried. */
130
+ readonly error: MailboxEventStreamError;
131
+ /** The cursor the next connection resumes from; undefined when the stream started live and has none yet. */
132
+ readonly cursor: string | undefined;
133
+ /** Failed attempts in a row, starting at 1; a connection that went live resets it. */
134
+ readonly attempt: number;
135
+ /** How long the stream waits before connecting again. */
136
+ readonly delayMillis: number;
137
+ }
116
138
  export interface MailboxEventStreamOptions {
117
139
  /** Resume after this cursor: every retained event after it, then live. Omit to start live. */
118
140
  readonly cursor?: string | undefined;
@@ -124,6 +146,11 @@ export interface MailboxEventStreamOptions {
124
146
  readonly onLive?: (() => void) | undefined;
125
147
  /** Reconnect after transient closes. Defaults to `true`. */
126
148
  readonly reconnect?: boolean | undefined;
149
+ /**
150
+ * Called when a transient failure ends a connection and the stream is about to reconnect from
151
+ * its last handled cursor, before the backoff wait. Never called when `reconnect` is `false`.
152
+ */
153
+ readonly onReconnect?: ((reconnect: MailboxEventStreamReconnect) => void) | undefined;
127
154
  /**
128
155
  * The events origin, such as `wss://events.samva.dev`. Defaults to the API origin with its
129
156
  * `api` host label replaced by `events`.
@@ -6,7 +6,8 @@
6
6
  * {@link MailboxEventStream} is an async iterable. The loop body handling an event is the
7
7
  * acknowledgement: asking for the next event marks the previous one handled, and the stream
8
8
  * resumes from the last handled event whenever it reconnects. Transient closes reconnect by
9
- * themselves; a close the caller has to act on ends the loop with a {@link MailboxEventStreamError}.
9
+ * themselves, and a normal close (1000) from the host ends the loop after the events already
10
+ * received; a close the caller has to act on ends the loop with a {@link MailboxEventStreamError}.
10
11
  *
11
12
  * This module has no runtime dependencies so the Promise and Effect clients share it.
12
13
  */
@@ -66,6 +67,8 @@ var MailboxEventStreamError = class extends Error {
66
67
  retryAfterSeconds;
67
68
  /** The tag the host sent, when it is not one this client maps. */
68
69
  serverTag;
70
+ /** Set when the client ended the connection itself; see {@link MailboxEventStreamErrorReason}. */
71
+ reason;
69
72
  constructor(input) {
70
73
  super(input.message);
71
74
  this._tag = input._tag;
@@ -75,9 +78,12 @@ var MailboxEventStreamError = class extends Error {
75
78
  this.fields = input.fields;
76
79
  this.retryAfterSeconds = input.retryAfterSeconds;
77
80
  this.serverTag = input.serverTag;
81
+ this.reason = input.reason;
78
82
  }
79
83
  };
80
84
  const OPEN = 1;
85
+ /** The close code a host ends a finished stream with. */
86
+ const NORMAL_CLOSE = 1e3;
81
87
  /** Acknowledge after this many handled events, well inside the server's window of 256. */
82
88
  const ACK_EVERY = 32;
83
89
  const RETRY_BASE_MILLIS = 500;
@@ -300,7 +306,7 @@ var MailboxEventStream = class {
300
306
  * {@link markHandled} was called, so a resume repeats it. A pending iteration finishes.
301
307
  */
302
308
  close() {
303
- if (this.#ended) return;
309
+ if (this.#closed) return;
304
310
  this.#ack();
305
311
  this.#ended = true;
306
312
  this.#closed = true;
@@ -349,10 +355,13 @@ var MailboxEventStream = class {
349
355
  draining?.resolve();
350
356
  this.#ack();
351
357
  if (this.#error !== void 0) throw this.#errorAtCursor(this.#error);
352
- if (this.#ended) return {
353
- done: true,
354
- value: void 0
355
- };
358
+ if (this.#ended) {
359
+ this.#callerSignal?.removeEventListener("abort", this.#onCallerAbort);
360
+ return {
361
+ done: true,
362
+ value: void 0
363
+ };
364
+ }
356
365
  await new Promise((resolve) => {
357
366
  this.#waiting = { resolve };
358
367
  });
@@ -418,8 +427,16 @@ var MailboxEventStream = class {
418
427
  attempt = 0;
419
428
  });
420
429
  if (this.#ended || outcome.kind === "stopped") return;
430
+ if (outcome.kind === "closed" && outcome.code === NORMAL_CLOSE) {
431
+ this.#finish();
432
+ return;
433
+ }
421
434
  let result;
422
435
  if (outcome.kind === "closed") result = closeOutcome(outcome.code);
436
+ else if (outcome.kind === "idle") result = outcomeOf("StreamDisconnectedError", true, {
437
+ reason: "idleTimeout",
438
+ message: `No frame from the events host in ${MAILBOX_EVENT_STREAM_IDLE_MILLIS / 1e3} seconds, so the stream closed the connection.`
439
+ });
423
440
  else {
424
441
  const refusal = await this.#diagnose();
425
442
  result = refusal === void 0 ? outcomeOf("StreamDisconnectedError", true) : refusalOutcome(refusal);
@@ -430,9 +447,23 @@ var MailboxEventStream = class {
430
447
  }
431
448
  const backoff = Math.min(RETRY_MAX_MILLIS, RETRY_BASE_MILLIS * 2 ** attempt);
432
449
  attempt += 1;
433
- await sleep(result.retryAfterMillis ?? backoff / 2 + Math.random() * (backoff / 2), this.#stop.signal);
450
+ const delayMillis = result.retryAfterMillis ?? backoff / 2 + Math.random() * (backoff / 2);
451
+ this.#options.onReconnect?.({
452
+ error: this.#withCursor(result.error),
453
+ cursor: this.#resumeCursor(),
454
+ attempt,
455
+ delayMillis
456
+ });
457
+ await sleep(delayMillis, this.#stop.signal);
434
458
  }
435
459
  }
460
+ /** End the iteration after the buffered events, with no error. */
461
+ #finish() {
462
+ if (this.#ended) return;
463
+ this.#ended = true;
464
+ this.#stop.abort();
465
+ this.#wake();
466
+ }
436
467
  #withCursor(error) {
437
468
  return new MailboxEventStreamError({
438
469
  ...error,
@@ -464,10 +495,7 @@ var MailboxEventStream = class {
464
495
  const armIdle = () => {
465
496
  clearTimeout(idleTimer);
466
497
  idleTimer = setTimeout(() => {
467
- settle(opened ? {
468
- kind: "closed",
469
- code: 1006
470
- } : { kind: "refused" });
498
+ settle(opened ? { kind: "idle" } : { kind: "refused" });
471
499
  socket.close(1e3);
472
500
  }, MAILBOX_EVENT_STREAM_IDLE_MILLIS);
473
501
  };
@@ -626,6 +654,6 @@ const readRefusalBody = async (response) => {
626
654
  }
627
655
  };
628
656
  //#endregion
629
- export { MailboxEventStreamError as n, MailboxEventStream as t };
657
+ export { MAILBOX_EVENT_STREAM_IDLE_MILLIS, MAILBOX_EVENT_STREAM_PATH, MAILBOX_EVENT_STREAM_PING_FRAME, MAILBOX_EVENT_STREAM_PING_MILLIS, MailboxEventStream, MailboxEventStreamCloseCode, MailboxEventStreamError, mailboxEventsUrl };
630
658
 
631
- //# sourceMappingURL=mailbox-events-VKR4f3qq.js.map
659
+ //# sourceMappingURL=mailbox-events.js.map
@@ -67,6 +67,6 @@ function buildMessagesSendPayload(input) {
67
67
  };
68
68
  }
69
69
  //#endregion
70
- export { buildMessagesSendPayload as n, replyToEmailsPayload as r, buildEmailSendPayload as t };
70
+ export { buildEmailSendPayload, buildMessagesSendPayload, replyToEmailsPayload };
71
71
 
72
- //# sourceMappingURL=normalize-B79uJIeb.js.map
72
+ //# sourceMappingURL=normalize.js.map
@@ -0,0 +1,6 @@
1
+ //#region package.json
2
+ var version = "0.19.0";
3
+ //#endregion
4
+ export { version };
5
+
6
+ //# sourceMappingURL=package.js.map