@primitivedotdev/sdk 0.9.0 → 0.10.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/README.md +22 -0
- package/dist/api/generated/index.js +1 -1
- package/dist/api/generated/sdk.gen.js +26 -0
- package/dist/api/index.d.ts +2 -2
- package/dist/api/index.js +72 -33
- package/dist/{api-COSr-Fqm.js → api-CLLpjjWy.js} +87 -31
- package/dist/{index-DVow4Fjd.d.ts → index-K4KbjppU.d.ts} +220 -5
- package/dist/index.d.ts +1 -1
- package/dist/index.js +1 -1
- package/dist/openapi/openapi.generated.js +190 -3
- package/dist/openapi/operations.generated.js +49 -0
- package/oclif.manifest.json +55 -1
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -103,6 +103,28 @@ await client.reply(email, {
|
|
|
103
103
|
});
|
|
104
104
|
```
|
|
105
105
|
|
|
106
|
+
### HTML replies and waiting on the delivery outcome
|
|
107
|
+
|
|
108
|
+
`reply()` accepts `html` as a sibling of `text`, plus the same `wait` flag the
|
|
109
|
+
top-level `send()` takes:
|
|
110
|
+
|
|
111
|
+
```ts
|
|
112
|
+
await client.reply(email, {
|
|
113
|
+
text: "Thanks for your email.",
|
|
114
|
+
html: "<p>Thanks for your email.</p>",
|
|
115
|
+
wait: true,
|
|
116
|
+
});
|
|
117
|
+
```
|
|
118
|
+
|
|
119
|
+
`subject` is intentionally not accepted on `reply()`. Gmail's Conversation View
|
|
120
|
+
needs both a References match and a normalized-subject match to thread, so a
|
|
121
|
+
custom subject silently breaks the thread for half the recipient population.
|
|
122
|
+
Use `client.send(...)` if you need full subject control.
|
|
123
|
+
|
|
124
|
+
If the inbound row is not in a state we can reply to (no `Message-Id` recorded,
|
|
125
|
+
or content was discarded), the API returns `inbound_not_repliable` (HTTP 422)
|
|
126
|
+
and the SDK throws.
|
|
127
|
+
|
|
106
128
|
### Forward an inbound email
|
|
107
129
|
|
|
108
130
|
```ts
|
|
@@ -1,2 +1,2 @@
|
|
|
1
1
|
// This file is auto-generated by @hey-api/openapi-ts
|
|
2
|
-
export { addDomain, createEndpoint, createFilter, deleteDomain, deleteEmail, deleteEndpoint, deleteFilter, downloadAttachments, downloadRawEmail, getAccount, getEmail, getStorageStats, getWebhookSecret, listDeliveries, listDomains, listEmails, listEndpoints, listFilters, replayDelivery, replayEmailWebhooks, rotateWebhookSecret, sendEmail, testEndpoint, updateAccount, updateDomain, updateEndpoint, updateFilter, verifyDomain } from './sdk.gen.js';
|
|
2
|
+
export { addDomain, createEndpoint, createFilter, deleteDomain, deleteEmail, deleteEndpoint, deleteFilter, downloadAttachments, downloadRawEmail, getAccount, getEmail, getStorageStats, getWebhookSecret, listDeliveries, listDomains, listEmails, listEndpoints, listFilters, replayDelivery, replayEmailWebhooks, replyToEmail, rotateWebhookSecret, sendEmail, testEndpoint, updateAccount, updateDomain, updateEndpoint, updateFilter, verifyDomain } from './sdk.gen.js';
|
|
@@ -184,6 +184,32 @@ export const downloadAttachments = (options) => (options.client ?? client).get({
|
|
|
184
184
|
url: '/emails/{id}/attachments.tar.gz',
|
|
185
185
|
...options
|
|
186
186
|
});
|
|
187
|
+
/**
|
|
188
|
+
* Reply to an inbound email
|
|
189
|
+
*
|
|
190
|
+
* Sends an outbound reply to the inbound email identified by `id`.
|
|
191
|
+
* Threading headers (`In-Reply-To`, `References`), recipient
|
|
192
|
+
* derivation (Reply-To, then From, then bare sender), and the
|
|
193
|
+
* `Re:` subject prefix are all derived server-side from the
|
|
194
|
+
* stored inbound row. The request body carries only the message
|
|
195
|
+
* body and optional `wait` flag; passing any header or recipient
|
|
196
|
+
* override is rejected by the schema (`additionalProperties:
|
|
197
|
+
* false`).
|
|
198
|
+
*
|
|
199
|
+
* Forwards through the same gates as `/send-mail`: the response
|
|
200
|
+
* status, error envelope, and `idempotent_replay` flag mirror
|
|
201
|
+
* the send-mail contract verbatim.
|
|
202
|
+
*
|
|
203
|
+
*/
|
|
204
|
+
export const replyToEmail = (options) => (options.client ?? client).post({
|
|
205
|
+
security: [{ scheme: 'bearer', type: 'http' }],
|
|
206
|
+
url: '/emails/{id}/reply',
|
|
207
|
+
...options,
|
|
208
|
+
headers: {
|
|
209
|
+
'Content-Type': 'application/json',
|
|
210
|
+
...options.headers
|
|
211
|
+
}
|
|
212
|
+
});
|
|
187
213
|
/**
|
|
188
214
|
* Replay email webhooks
|
|
189
215
|
*
|
package/dist/api/index.d.ts
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { $ as
|
|
2
|
-
export { Account, AccountUpdated, AddDomainData, AddDomainError, AddDomainErrors, AddDomainInput, AddDomainResponse, AddDomainResponses, Auth, ClientOptions, CreateClientConfig, CreateEndpointData, CreateEndpointError, CreateEndpointErrors, CreateEndpointInput, CreateEndpointResponse, CreateEndpointResponses, CreateFilterData, CreateFilterError, CreateFilterErrors, CreateFilterInput, CreateFilterResponse, CreateFilterResponses, Cursor, DEFAULT_BASE_URL, DeleteDomainData, DeleteDomainError, DeleteDomainErrors, DeleteDomainResponse, DeleteDomainResponses, DeleteEmailData, DeleteEmailError, DeleteEmailErrors, DeleteEmailResponse, DeleteEmailResponses, DeleteEndpointData, DeleteEndpointError, DeleteEndpointErrors, DeleteEndpointResponse, DeleteEndpointResponses, DeleteFilterData, DeleteFilterError, DeleteFilterErrors, DeleteFilterResponse, DeleteFilterResponses, DeliveryStatus, DeliverySummary, Domain, DomainVerifyResult, DownloadAttachmentsData, DownloadAttachmentsError, DownloadAttachmentsErrors, DownloadAttachmentsResponse, DownloadAttachmentsResponses, DownloadRawEmailData, DownloadRawEmailError, DownloadRawEmailErrors, DownloadRawEmailResponse, DownloadRawEmailResponses, EmailDetail, EmailSummary, Endpoint, ErrorResponse, Filter, ForwardInput, GateDenial, GateFix, GetAccountData, GetAccountError, GetAccountErrors, GetAccountResponse, GetAccountResponses, GetEmailData, GetEmailError, GetEmailErrors, GetEmailResponse, GetEmailResponses, GetStorageStatsData, GetStorageStatsError, GetStorageStatsErrors, GetStorageStatsResponse, GetStorageStatsResponses, GetWebhookSecretData, GetWebhookSecretError, GetWebhookSecretErrors, GetWebhookSecretResponse, GetWebhookSecretResponses, Limit, ListDeliveriesData, ListDeliveriesError, ListDeliveriesErrors, ListDeliveriesResponse, ListDeliveriesResponses, ListDomainsData, ListDomainsError, ListDomainsErrors, ListDomainsResponse, ListDomainsResponses, ListEmailsData, ListEmailsError, ListEmailsErrors, ListEmailsResponse, ListEmailsResponses, ListEndpointsData, ListEndpointsError, ListEndpointsErrors, ListEndpointsResponse, ListEndpointsResponses, ListEnvelope, ListFiltersData, ListFiltersError, ListFiltersErrors, ListFiltersResponse, ListFiltersResponses, Options, PaginationMeta, PrimitiveApiClient, PrimitiveApiClientOptions, PrimitiveApiError, PrimitiveApiErrorDetails, PrimitiveClient, PrimitiveClientOptions, Client as PrimitiveGeneratedApiClient, ClientOptions$1 as PrimitiveGeneratedApiClientOptions, Config as PrimitiveGeneratedApiConfig, Options$1 as PrimitiveGeneratedApiOptions, RequestOptions as PrimitiveGeneratedApiRequestOptions, RequestResult as PrimitiveGeneratedApiRequestResult, ReplayDeliveryData, ReplayDeliveryError, ReplayDeliveryErrors, ReplayDeliveryResponse, ReplayDeliveryResponses, ReplayEmailWebhooksData, ReplayEmailWebhooksError, ReplayEmailWebhooksErrors, ReplayEmailWebhooksResponse, ReplayEmailWebhooksResponses, ReplayResult, ReplyInput, ResourceId, ResponseStyle, RotateWebhookSecretData, RotateWebhookSecretError, RotateWebhookSecretErrors, RotateWebhookSecretResponse, RotateWebhookSecretResponses, SendEmailData, SendEmailError, SendEmailErrors, SendEmailResponse, SendEmailResponses, SendInput, SendMailInput, SendMailResult, SendResult, SendThreadInput, SentEmailStatus, StorageStats, SuccessEnvelope, TestEndpointData, TestEndpointError, TestEndpointErrors, TestEndpointResponse, TestEndpointResponses, TestResult, UnverifiedDomain, UpdateAccountData, UpdateAccountError, UpdateAccountErrors, UpdateAccountInput, UpdateAccountResponse, UpdateAccountResponses, UpdateDomainData, UpdateDomainError, UpdateDomainErrors, UpdateDomainInput, UpdateDomainResponse, UpdateDomainResponses, UpdateEndpointData, UpdateEndpointError, UpdateEndpointErrors, UpdateEndpointInput, UpdateEndpointResponse, UpdateEndpointResponses, UpdateFilterData, UpdateFilterError, UpdateFilterErrors, UpdateFilterInput, UpdateFilterResponse, UpdateFilterResponses, VerifiedDomain, VerifyDomainData, VerifyDomainError, VerifyDomainErrors, VerifyDomainResponse, VerifyDomainResponses, WebhookSecret, addDomain, client, createEndpoint, createFilter, createPrimitiveApiClient, createPrimitiveClient, deleteDomain, deleteEmail, deleteEndpoint, deleteFilter, downloadAttachments, downloadRawEmail, getAccount, getEmail, getStorageStats, getWebhookSecret, listDeliveries, listDomains, listEmails, listEndpoints, listFilters, operations, replayDelivery, replayEmailWebhooks, rotateWebhookSecret, sendEmail, testEndpoint, updateAccount, updateDomain, updateEndpoint, updateFilter, verifyDomain };
|
|
1
|
+
import { $ as AddDomainResponse, $n as ReplayDeliveryErrors, $r as UpdateEndpointResponses, $t as ErrorResponse, A as getWebhookSecret, An as ListDomainsError, Ar as TestEndpointError, At as DeleteFilterData, B as sendEmail, Bn as ListEndpointsError, Br as UpdateAccountResponse, Bt as DownloadAttachmentsError, C as deleteEndpoint, Cn as Limit, Cr as SendEmailResponses, Ct as DeleteEmailResponse, D as getAccount, Dn as ListDeliveriesResponse, Dr as StorageStats, Dt as DeleteEndpointErrors, E as downloadRawEmail, En as ListDeliveriesErrors, Er as SentEmailStatus, Et as DeleteEndpointError, F as listFilters, Fn as ListEmailsError, Fr as UnverifiedDomain, Ft as DeliveryStatus, G as updateFilter, Gn as ListFiltersData, Gr as UpdateDomainInput, Gt as DownloadRawEmailError, H as updateAccount, Hn as ListEndpointsResponse, Hr as UpdateDomainData, Ht as DownloadAttachmentsResponse, I as replayDelivery, In as ListEmailsErrors, Ir as UpdateAccountData, It as DeliverySummary, J as AccountUpdated, Jn as ListFiltersResponse, Jr as UpdateEndpointData, Jt as DownloadRawEmailResponses, K as verifyDomain, Kn as ListFiltersError, Kr as UpdateDomainResponse, Kt as DownloadRawEmailErrors, L as replayEmailWebhooks, Ln as ListEmailsResponse, Lr as UpdateAccountError, Lt as Domain, M as listDomains, Mn as ListDomainsResponse, Mr as TestEndpointResponse, Mt as DeleteFilterErrors, N as listEmails, Nn as ListDomainsResponses, Nr as TestEndpointResponses, Nt as DeleteFilterResponse, O as getEmail, On as ListDeliveriesResponses, Or as SuccessEnvelope, Ot as DeleteEndpointResponse, P as listEndpoints, Pn as ListEmailsData, Pr as TestResult, Pt as DeleteFilterResponses, Q as AddDomainInput, Qn as ReplayDeliveryError, Qr as UpdateEndpointResponse, Qt as Endpoint, R as replyToEmail, Rn as ListEmailsResponses, Rr as UpdateAccountErrors, Rt as DomainVerifyResult, S as deleteEmail, Sn as GetWebhookSecretResponses, Sr as SendEmailResponse, St as DeleteEmailErrors, T as downloadAttachments, Tn as ListDeliveriesError, Tr as SendMailResult, Tt as DeleteEndpointData, U as updateDomain, Un as ListEndpointsResponses, Ur as UpdateDomainError, Ut as DownloadAttachmentsResponses, V as testEndpoint, Vn as ListEndpointsErrors, Vr as UpdateAccountResponses, Vt as DownloadAttachmentsErrors, W as updateEndpoint, Wn as ListEnvelope, Wr as UpdateDomainErrors, Wt as DownloadRawEmailData, X as AddDomainError, Xn as PaginationMeta, Xr as UpdateEndpointErrors, Xt as EmailDetailReply, Y as AddDomainData, Yn as ListFiltersResponses, Yr as UpdateEndpointError, Yt as EmailDetail, Z as AddDomainErrors, Zn as ReplayDeliveryData, Zr as UpdateEndpointInput, Zt as EmailSummary, _ as Options, _i as Options$1, _n as GetStorageStatsResponses, _r as RotateWebhookSecretResponse, _t as DeleteDomainErrors, a as PrimitiveApiError, ai as UpdateFilterResponses, an as GetAccountErrors, ar as ReplayEmailWebhooksResponse, at as CreateEndpointInput, b as createFilter, bi as ResponseStyle, bn as GetWebhookSecretErrors, br as SendEmailError, bt as DeleteEmailData, c as PrimitiveClientOptions, ci as VerifyDomainError, cn as GetEmailData, cr as ReplyToEmailData, ct as CreateFilterData, d as SendResult, di as VerifyDomainResponses, dn as GetEmailResponse, dr as ReplyToEmailResponse, dt as CreateFilterInput, ei as UpdateFilterData, en as Filter, er as ReplayDeliveryResponse, et as AddDomainResponses, f as SendThreadInput, fi as WebhookSecret, fn as GetEmailResponses, fr as ReplyToEmailResponses, ft as CreateFilterResponse, g as operations, gi as CreateClientConfig, gn as GetStorageStatsResponse, gr as RotateWebhookSecretErrors, gt as DeleteDomainError, h as createPrimitiveClient, hi as Config, hn as GetStorageStatsErrors, hr as RotateWebhookSecretError, ht as DeleteDomainData, i as PrimitiveApiClientOptions, ii as UpdateFilterResponse, in as GetAccountError, ir as ReplayEmailWebhooksErrors, it as CreateEndpointErrors, j as listDeliveries, jn as ListDomainsErrors, jr as TestEndpointErrors, jt as DeleteFilterError, k as getStorageStats, kn as ListDomainsData, kr as TestEndpointData, kt as DeleteEndpointResponses, l as ReplyInput, li as VerifyDomainErrors, ln as GetEmailError, lr as ReplyToEmailError, lt as CreateFilterError, m as createPrimitiveApiClient, mi as ClientOptions$1, mn as GetStorageStatsError, mr as RotateWebhookSecretData, mt as Cursor, n as ForwardInput, ni as UpdateFilterErrors, nn as GateFix, nr as ReplayEmailWebhooksData, nt as CreateEndpointData, o as PrimitiveApiErrorDetails, oi as VerifiedDomain, on as GetAccountResponse, or as ReplayEmailWebhooksResponses, ot as CreateEndpointResponse, p as client, pi as Client, pn as GetStorageStatsData, pr as ResourceId, pt as CreateFilterResponses, q as Account, qn as ListFiltersErrors, qr as UpdateDomainResponses, qt as DownloadRawEmailResponse, r as PrimitiveApiClient, ri as UpdateFilterInput, rn as GetAccountData, rr as ReplayEmailWebhooksError, rt as CreateEndpointError, s as PrimitiveClient, si as VerifyDomainData, sn as GetAccountResponses, sr as ReplayResult, st as CreateEndpointResponses, t as DEFAULT_BASE_URL, ti as UpdateFilterError, tn as GateDenial, tr as ReplayDeliveryResponses, tt as ClientOptions, u as SendInput, ui as VerifyDomainResponse, un as GetEmailErrors, ur as ReplyToEmailErrors, ut as CreateFilterErrors, v as addDomain, vi as RequestOptions, vn as GetWebhookSecretData, vr as RotateWebhookSecretResponses, vt as DeleteDomainResponse, w as deleteFilter, wn as ListDeliveriesData, wr as SendMailInput, wt as DeleteEmailResponses, x as deleteDomain, xi as Auth, xn as GetWebhookSecretResponse, xr as SendEmailErrors, xt as DeleteEmailError, y as createEndpoint, yi as RequestResult, yn as GetWebhookSecretError, yr as SendEmailData, yt as DeleteDomainResponses, z as rotateWebhookSecret, zn as ListEndpointsData, zr as UpdateAccountInput, zt as DownloadAttachmentsData } from "../index-K4KbjppU.js";
|
|
2
|
+
export { Account, AccountUpdated, AddDomainData, AddDomainError, AddDomainErrors, AddDomainInput, AddDomainResponse, AddDomainResponses, Auth, ClientOptions, CreateClientConfig, CreateEndpointData, CreateEndpointError, CreateEndpointErrors, CreateEndpointInput, CreateEndpointResponse, CreateEndpointResponses, CreateFilterData, CreateFilterError, CreateFilterErrors, CreateFilterInput, CreateFilterResponse, CreateFilterResponses, Cursor, DEFAULT_BASE_URL, DeleteDomainData, DeleteDomainError, DeleteDomainErrors, DeleteDomainResponse, DeleteDomainResponses, DeleteEmailData, DeleteEmailError, DeleteEmailErrors, DeleteEmailResponse, DeleteEmailResponses, DeleteEndpointData, DeleteEndpointError, DeleteEndpointErrors, DeleteEndpointResponse, DeleteEndpointResponses, DeleteFilterData, DeleteFilterError, DeleteFilterErrors, DeleteFilterResponse, DeleteFilterResponses, DeliveryStatus, DeliverySummary, Domain, DomainVerifyResult, DownloadAttachmentsData, DownloadAttachmentsError, DownloadAttachmentsErrors, DownloadAttachmentsResponse, DownloadAttachmentsResponses, DownloadRawEmailData, DownloadRawEmailError, DownloadRawEmailErrors, DownloadRawEmailResponse, DownloadRawEmailResponses, EmailDetail, EmailDetailReply, EmailSummary, Endpoint, ErrorResponse, Filter, ForwardInput, GateDenial, GateFix, GetAccountData, GetAccountError, GetAccountErrors, GetAccountResponse, GetAccountResponses, GetEmailData, GetEmailError, GetEmailErrors, GetEmailResponse, GetEmailResponses, GetStorageStatsData, GetStorageStatsError, GetStorageStatsErrors, GetStorageStatsResponse, GetStorageStatsResponses, GetWebhookSecretData, GetWebhookSecretError, GetWebhookSecretErrors, GetWebhookSecretResponse, GetWebhookSecretResponses, Limit, ListDeliveriesData, ListDeliveriesError, ListDeliveriesErrors, ListDeliveriesResponse, ListDeliveriesResponses, ListDomainsData, ListDomainsError, ListDomainsErrors, ListDomainsResponse, ListDomainsResponses, ListEmailsData, ListEmailsError, ListEmailsErrors, ListEmailsResponse, ListEmailsResponses, ListEndpointsData, ListEndpointsError, ListEndpointsErrors, ListEndpointsResponse, ListEndpointsResponses, ListEnvelope, ListFiltersData, ListFiltersError, ListFiltersErrors, ListFiltersResponse, ListFiltersResponses, Options, PaginationMeta, PrimitiveApiClient, PrimitiveApiClientOptions, PrimitiveApiError, PrimitiveApiErrorDetails, PrimitiveClient, PrimitiveClientOptions, Client as PrimitiveGeneratedApiClient, ClientOptions$1 as PrimitiveGeneratedApiClientOptions, Config as PrimitiveGeneratedApiConfig, Options$1 as PrimitiveGeneratedApiOptions, RequestOptions as PrimitiveGeneratedApiRequestOptions, RequestResult as PrimitiveGeneratedApiRequestResult, ReplayDeliveryData, ReplayDeliveryError, ReplayDeliveryErrors, ReplayDeliveryResponse, ReplayDeliveryResponses, ReplayEmailWebhooksData, ReplayEmailWebhooksError, ReplayEmailWebhooksErrors, ReplayEmailWebhooksResponse, ReplayEmailWebhooksResponses, ReplayResult, ReplyInput, ReplyToEmailData, ReplyToEmailError, ReplyToEmailErrors, ReplyToEmailResponse, ReplyToEmailResponses, ResourceId, ResponseStyle, RotateWebhookSecretData, RotateWebhookSecretError, RotateWebhookSecretErrors, RotateWebhookSecretResponse, RotateWebhookSecretResponses, SendEmailData, SendEmailError, SendEmailErrors, SendEmailResponse, SendEmailResponses, SendInput, SendMailInput, SendMailResult, SendResult, SendThreadInput, SentEmailStatus, StorageStats, SuccessEnvelope, TestEndpointData, TestEndpointError, TestEndpointErrors, TestEndpointResponse, TestEndpointResponses, TestResult, UnverifiedDomain, UpdateAccountData, UpdateAccountError, UpdateAccountErrors, UpdateAccountInput, UpdateAccountResponse, UpdateAccountResponses, UpdateDomainData, UpdateDomainError, UpdateDomainErrors, UpdateDomainInput, UpdateDomainResponse, UpdateDomainResponses, UpdateEndpointData, UpdateEndpointError, UpdateEndpointErrors, UpdateEndpointInput, UpdateEndpointResponse, UpdateEndpointResponses, UpdateFilterData, UpdateFilterError, UpdateFilterErrors, UpdateFilterInput, UpdateFilterResponse, UpdateFilterResponses, VerifiedDomain, VerifyDomainData, VerifyDomainError, VerifyDomainErrors, VerifyDomainResponse, VerifyDomainResponses, WebhookSecret, addDomain, client, createEndpoint, createFilter, createPrimitiveApiClient, createPrimitiveClient, deleteDomain, deleteEmail, deleteEndpoint, deleteFilter, downloadAttachments, downloadRawEmail, getAccount, getEmail, getStorageStats, getWebhookSecret, listDeliveries, listDomains, listEmails, listEndpoints, listFilters, operations, replayDelivery, replayEmailWebhooks, replyToEmail, rotateWebhookSecret, sendEmail, testEndpoint, updateAccount, updateDomain, updateEndpoint, updateFilter, verifyDomain };
|
package/dist/api/index.js
CHANGED
|
@@ -194,43 +194,50 @@ export class PrimitiveClient extends PrimitiveApiClient {
|
|
|
194
194
|
client: this.client,
|
|
195
195
|
responseStyle: "fields",
|
|
196
196
|
});
|
|
197
|
-
|
|
198
|
-
if (result.error) {
|
|
199
|
-
const parsed = parseApiErrorPayload(result.error);
|
|
200
|
-
throw new PrimitiveApiError(parsed.message, {
|
|
201
|
-
payload: result.error,
|
|
202
|
-
status: response?.status,
|
|
203
|
-
code: parsed.code,
|
|
204
|
-
gates: parsed.gates,
|
|
205
|
-
requestId: parsed.requestId,
|
|
206
|
-
retryAfter: parseRetryAfterHeader(response),
|
|
207
|
-
details: parsed.details,
|
|
208
|
-
});
|
|
209
|
-
}
|
|
210
|
-
if (!result.data?.data) {
|
|
211
|
-
throw new PrimitiveApiError("Primitive API returned no send result", {
|
|
212
|
-
payload: result,
|
|
213
|
-
status: response?.status,
|
|
214
|
-
});
|
|
215
|
-
}
|
|
216
|
-
return mapSendResult(result.data.data);
|
|
197
|
+
return unwrapSendResult(result);
|
|
217
198
|
}
|
|
199
|
+
/**
|
|
200
|
+
* Reply to an inbound email.
|
|
201
|
+
*
|
|
202
|
+
* Calls `POST /emails/{id}/reply`. The server derives recipients
|
|
203
|
+
* (Reply-To, then From, then sender), subject (`Re: <parent>` with
|
|
204
|
+
* idempotent prefix), and threading headers (`In-Reply-To`,
|
|
205
|
+
* `References`) from the stored inbound row. The customer controls
|
|
206
|
+
* only the body, an optional `from` override, and the `wait` flag.
|
|
207
|
+
*
|
|
208
|
+
* Subject overrides are intentionally not supported: Gmail's
|
|
209
|
+
* Conversation View needs both a References match and a normalized-
|
|
210
|
+
* subject match to thread, so a custom subject silently breaks the
|
|
211
|
+
* thread for half the recipient population.
|
|
212
|
+
*/
|
|
218
213
|
async reply(email, input) {
|
|
219
214
|
const resolved = typeof input === "string" ? { text: input } : input;
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
215
|
+
// Reject the subject override at runtime so a JS caller (no TS
|
|
216
|
+
// types) gets the same loud error as a TS caller. Without this,
|
|
217
|
+
// `client.reply(email, { text, subject: "Custom" })` silently
|
|
218
|
+
// dropped subject and sent a "Re:" reply, breaking Gmail
|
|
219
|
+
// threading without telling the caller. Mirrors Python's
|
|
220
|
+
// ValueError. Checked before the empty-body check so passing
|
|
221
|
+
// ONLY a subject surfaces the more informative error.
|
|
222
|
+
if ("subject" in resolved) {
|
|
223
|
+
throw new TypeError("reply does not support a subject override; the server prepends 'Re:' to the parent's subject for thread continuity");
|
|
224
|
+
}
|
|
225
|
+
if (!resolved.text && !resolved.html) {
|
|
226
|
+
throw new TypeError("reply requires text or html");
|
|
227
|
+
}
|
|
228
|
+
const body = {
|
|
229
|
+
...(resolved.text !== undefined ? { body_text: resolved.text } : {}),
|
|
230
|
+
...(resolved.html !== undefined ? { body_html: resolved.html } : {}),
|
|
231
|
+
...(resolved.from !== undefined ? { from: resolved.from } : {}),
|
|
232
|
+
...(resolved.wait !== undefined ? { wait: resolved.wait } : {}),
|
|
233
|
+
};
|
|
234
|
+
const result = await generatedOperations.replyToEmail({
|
|
235
|
+
body,
|
|
236
|
+
path: { id: email.id },
|
|
237
|
+
client: this.client,
|
|
238
|
+
responseStyle: "fields",
|
|
233
239
|
});
|
|
240
|
+
return unwrapSendResult(result);
|
|
234
241
|
}
|
|
235
242
|
async forward(email, input) {
|
|
236
243
|
validateForwardInput(input);
|
|
@@ -260,6 +267,34 @@ function buildForwardText(email, intro) {
|
|
|
260
267
|
];
|
|
261
268
|
return lines.join("\n").trimEnd();
|
|
262
269
|
}
|
|
270
|
+
/**
|
|
271
|
+
* Shared response handler for `send`, `reply`, and any future
|
|
272
|
+
* operation that returns a SendMailResult envelope. Unifies the
|
|
273
|
+
* error-mapping path so the network call sites only have to invoke
|
|
274
|
+
* the generated operation.
|
|
275
|
+
*/
|
|
276
|
+
function unwrapSendResult(result) {
|
|
277
|
+
const response = result.response;
|
|
278
|
+
if (result.error) {
|
|
279
|
+
const parsed = parseApiErrorPayload(result.error);
|
|
280
|
+
throw new PrimitiveApiError(parsed.message, {
|
|
281
|
+
payload: result.error,
|
|
282
|
+
status: response?.status,
|
|
283
|
+
code: parsed.code,
|
|
284
|
+
gates: parsed.gates,
|
|
285
|
+
requestId: parsed.requestId,
|
|
286
|
+
retryAfter: parseRetryAfterHeader(response),
|
|
287
|
+
details: parsed.details,
|
|
288
|
+
});
|
|
289
|
+
}
|
|
290
|
+
if (!result.data?.data) {
|
|
291
|
+
throw new PrimitiveApiError("Primitive API returned no send result", {
|
|
292
|
+
payload: result,
|
|
293
|
+
status: response?.status,
|
|
294
|
+
});
|
|
295
|
+
}
|
|
296
|
+
return mapSendResult(result.data.data);
|
|
297
|
+
}
|
|
263
298
|
function mapSendResult(result) {
|
|
264
299
|
return {
|
|
265
300
|
id: result.id,
|
|
@@ -270,6 +305,10 @@ function mapSendResult(result) {
|
|
|
270
305
|
clientIdempotencyKey: result.client_idempotency_key,
|
|
271
306
|
requestId: result.request_id,
|
|
272
307
|
contentHash: result.content_hash,
|
|
308
|
+
// Default to false if the server omits the field (old-format
|
|
309
|
+
// response, mocked partial response in a customer's tests). The
|
|
310
|
+
// type signature claims `boolean`, so undefined would be a lie.
|
|
311
|
+
idempotentReplay: result.idempotent_replay ?? false,
|
|
273
312
|
...(result.delivery_status !== undefined
|
|
274
313
|
? { deliveryStatus: result.delivery_status }
|
|
275
314
|
: {}),
|
|
@@ -633,6 +633,7 @@ var sdk_gen_exports = /* @__PURE__ */ __exportAll({
|
|
|
633
633
|
listFilters: () => listFilters,
|
|
634
634
|
replayDelivery: () => replayDelivery,
|
|
635
635
|
replayEmailWebhooks: () => replayEmailWebhooks,
|
|
636
|
+
replyToEmail: () => replyToEmail,
|
|
636
637
|
rotateWebhookSecret: () => rotateWebhookSecret,
|
|
637
638
|
sendEmail: () => sendEmail,
|
|
638
639
|
testEndpoint: () => testEndpoint,
|
|
@@ -872,6 +873,35 @@ const downloadAttachments = (options) => (options.client ?? client$1).get({
|
|
|
872
873
|
...options
|
|
873
874
|
});
|
|
874
875
|
/**
|
|
876
|
+
* Reply to an inbound email
|
|
877
|
+
*
|
|
878
|
+
* Sends an outbound reply to the inbound email identified by `id`.
|
|
879
|
+
* Threading headers (`In-Reply-To`, `References`), recipient
|
|
880
|
+
* derivation (Reply-To, then From, then bare sender), and the
|
|
881
|
+
* `Re:` subject prefix are all derived server-side from the
|
|
882
|
+
* stored inbound row. The request body carries only the message
|
|
883
|
+
* body and optional `wait` flag; passing any header or recipient
|
|
884
|
+
* override is rejected by the schema (`additionalProperties:
|
|
885
|
+
* false`).
|
|
886
|
+
*
|
|
887
|
+
* Forwards through the same gates as `/send-mail`: the response
|
|
888
|
+
* status, error envelope, and `idempotent_replay` flag mirror
|
|
889
|
+
* the send-mail contract verbatim.
|
|
890
|
+
*
|
|
891
|
+
*/
|
|
892
|
+
const replyToEmail = (options) => (options.client ?? client$1).post({
|
|
893
|
+
security: [{
|
|
894
|
+
scheme: "bearer",
|
|
895
|
+
type: "http"
|
|
896
|
+
}],
|
|
897
|
+
url: "/emails/{id}/reply",
|
|
898
|
+
...options,
|
|
899
|
+
headers: {
|
|
900
|
+
"Content-Type": "application/json",
|
|
901
|
+
...options.headers
|
|
902
|
+
}
|
|
903
|
+
});
|
|
904
|
+
/**
|
|
875
905
|
* Replay email webhooks
|
|
876
906
|
*
|
|
877
907
|
* Re-delivers the webhook payload for this email to all active
|
|
@@ -1211,7 +1241,7 @@ var PrimitiveApiClient = class {
|
|
|
1211
1241
|
var PrimitiveClient = class extends PrimitiveApiClient {
|
|
1212
1242
|
async send(input) {
|
|
1213
1243
|
validateSendInput(input);
|
|
1214
|
-
|
|
1244
|
+
return unwrapSendResult(await sendEmail({
|
|
1215
1245
|
body: {
|
|
1216
1246
|
from: input.from,
|
|
1217
1247
|
to: input.to,
|
|
@@ -1226,38 +1256,37 @@ var PrimitiveClient = class extends PrimitiveApiClient {
|
|
|
1226
1256
|
...input.idempotencyKey ? { headers: { "Idempotency-Key": input.idempotencyKey } } : {},
|
|
1227
1257
|
client: this.client,
|
|
1228
1258
|
responseStyle: "fields"
|
|
1229
|
-
});
|
|
1230
|
-
const response = result.response;
|
|
1231
|
-
if (result.error) {
|
|
1232
|
-
const parsed = parseApiErrorPayload(result.error);
|
|
1233
|
-
throw new PrimitiveApiError(parsed.message, {
|
|
1234
|
-
payload: result.error,
|
|
1235
|
-
status: response?.status,
|
|
1236
|
-
code: parsed.code,
|
|
1237
|
-
gates: parsed.gates,
|
|
1238
|
-
requestId: parsed.requestId,
|
|
1239
|
-
retryAfter: parseRetryAfterHeader(response),
|
|
1240
|
-
details: parsed.details
|
|
1241
|
-
});
|
|
1242
|
-
}
|
|
1243
|
-
if (!result.data?.data) throw new PrimitiveApiError("Primitive API returned no send result", {
|
|
1244
|
-
payload: result,
|
|
1245
|
-
status: response?.status
|
|
1246
|
-
});
|
|
1247
|
-
return mapSendResult(result.data.data);
|
|
1259
|
+
}));
|
|
1248
1260
|
}
|
|
1261
|
+
/**
|
|
1262
|
+
* Reply to an inbound email.
|
|
1263
|
+
*
|
|
1264
|
+
* Calls `POST /emails/{id}/reply`. The server derives recipients
|
|
1265
|
+
* (Reply-To, then From, then sender), subject (`Re: <parent>` with
|
|
1266
|
+
* idempotent prefix), and threading headers (`In-Reply-To`,
|
|
1267
|
+
* `References`) from the stored inbound row. The customer controls
|
|
1268
|
+
* only the body, an optional `from` override, and the `wait` flag.
|
|
1269
|
+
*
|
|
1270
|
+
* Subject overrides are intentionally not supported: Gmail's
|
|
1271
|
+
* Conversation View needs both a References match and a normalized-
|
|
1272
|
+
* subject match to thread, so a custom subject silently breaks the
|
|
1273
|
+
* thread for half the recipient population.
|
|
1274
|
+
*/
|
|
1249
1275
|
async reply(email, input) {
|
|
1250
1276
|
const resolved = typeof input === "string" ? { text: input } : input;
|
|
1251
|
-
|
|
1252
|
-
|
|
1253
|
-
|
|
1254
|
-
|
|
1255
|
-
|
|
1256
|
-
|
|
1257
|
-
...
|
|
1258
|
-
|
|
1259
|
-
}
|
|
1260
|
-
|
|
1277
|
+
if ("subject" in resolved) throw new TypeError("reply does not support a subject override; the server prepends 'Re:' to the parent's subject for thread continuity");
|
|
1278
|
+
if (!resolved.text && !resolved.html) throw new TypeError("reply requires text or html");
|
|
1279
|
+
return unwrapSendResult(await replyToEmail({
|
|
1280
|
+
body: {
|
|
1281
|
+
...resolved.text !== void 0 ? { body_text: resolved.text } : {},
|
|
1282
|
+
...resolved.html !== void 0 ? { body_html: resolved.html } : {},
|
|
1283
|
+
...resolved.from !== void 0 ? { from: resolved.from } : {},
|
|
1284
|
+
...resolved.wait !== void 0 ? { wait: resolved.wait } : {}
|
|
1285
|
+
},
|
|
1286
|
+
path: { id: email.id },
|
|
1287
|
+
client: this.client,
|
|
1288
|
+
responseStyle: "fields"
|
|
1289
|
+
}));
|
|
1261
1290
|
}
|
|
1262
1291
|
async forward(email, input) {
|
|
1263
1292
|
validateForwardInput(input);
|
|
@@ -1282,6 +1311,32 @@ function buildForwardText(email, intro) {
|
|
|
1282
1311
|
email.text ?? ""
|
|
1283
1312
|
].join("\n").trimEnd();
|
|
1284
1313
|
}
|
|
1314
|
+
/**
|
|
1315
|
+
* Shared response handler for `send`, `reply`, and any future
|
|
1316
|
+
* operation that returns a SendMailResult envelope. Unifies the
|
|
1317
|
+
* error-mapping path so the network call sites only have to invoke
|
|
1318
|
+
* the generated operation.
|
|
1319
|
+
*/
|
|
1320
|
+
function unwrapSendResult(result) {
|
|
1321
|
+
const response = result.response;
|
|
1322
|
+
if (result.error) {
|
|
1323
|
+
const parsed = parseApiErrorPayload(result.error);
|
|
1324
|
+
throw new PrimitiveApiError(parsed.message, {
|
|
1325
|
+
payload: result.error,
|
|
1326
|
+
status: response?.status,
|
|
1327
|
+
code: parsed.code,
|
|
1328
|
+
gates: parsed.gates,
|
|
1329
|
+
requestId: parsed.requestId,
|
|
1330
|
+
retryAfter: parseRetryAfterHeader(response),
|
|
1331
|
+
details: parsed.details
|
|
1332
|
+
});
|
|
1333
|
+
}
|
|
1334
|
+
if (!result.data?.data) throw new PrimitiveApiError("Primitive API returned no send result", {
|
|
1335
|
+
payload: result,
|
|
1336
|
+
status: response?.status
|
|
1337
|
+
});
|
|
1338
|
+
return mapSendResult(result.data.data);
|
|
1339
|
+
}
|
|
1285
1340
|
function mapSendResult(result) {
|
|
1286
1341
|
return {
|
|
1287
1342
|
id: result.id,
|
|
@@ -1292,6 +1347,7 @@ function mapSendResult(result) {
|
|
|
1292
1347
|
clientIdempotencyKey: result.client_idempotency_key,
|
|
1293
1348
|
requestId: result.request_id,
|
|
1294
1349
|
contentHash: result.content_hash,
|
|
1350
|
+
idempotentReplay: result.idempotent_replay ?? false,
|
|
1295
1351
|
...result.delivery_status !== void 0 ? { deliveryStatus: result.delivery_status } : {},
|
|
1296
1352
|
...result.smtp_response_code !== void 0 ? { smtpResponseCode: result.smtp_response_code } : {},
|
|
1297
1353
|
...result.smtp_response_text !== void 0 ? { smtpResponseText: result.smtp_response_text } : {}
|
|
@@ -1308,4 +1364,4 @@ function client(options = {}) {
|
|
|
1308
1364
|
}
|
|
1309
1365
|
const operations = sdk_gen_exports;
|
|
1310
1366
|
//#endregion
|
|
1311
|
-
export {
|
|
1367
|
+
export { rotateWebhookSecret as A, listDomains as C, replayDelivery as D, listFilters as E, updateEndpoint as F, updateFilter as I, verifyDomain as L, testEndpoint as M, updateAccount as N, replayEmailWebhooks as O, updateDomain as P, listDeliveries as S, listEndpoints as T, downloadRawEmail as _, client as a, getStorageStats as b, operations as c, createFilter as d, deleteDomain as f, downloadAttachments as g, deleteFilter as h, PrimitiveClient as i, sendEmail as j, replyToEmail as k, addDomain as l, deleteEndpoint as m, PrimitiveApiClient as n, createPrimitiveApiClient as o, deleteEmail as p, PrimitiveApiError as r, createPrimitiveClient as s, DEFAULT_BASE_URL as t, createEndpoint as u, getAccount as v, listEmails as w, getWebhookSecret as x, getEmail as y };
|
|
@@ -347,7 +347,7 @@ type PaginationMeta = {
|
|
|
347
347
|
type ErrorResponse = {
|
|
348
348
|
success: boolean;
|
|
349
349
|
error: {
|
|
350
|
-
code: 'unauthorized' | 'forbidden' | 'not_found' | 'validation_error' | 'rate_limit_exceeded' | 'internal_error' | 'conflict' | 'mx_conflict' | 'outbound_disabled' | 'cannot_send_from_domain' | 'recipient_not_allowed' | 'outbound_key_missing' | 'outbound_unreachable' | 'outbound_key_invalid' | 'outbound_capacity_exhausted' | 'outbound_response_malformed' | 'outbound_relay_failed';
|
|
350
|
+
code: 'unauthorized' | 'forbidden' | 'not_found' | 'validation_error' | 'rate_limit_exceeded' | 'internal_error' | 'conflict' | 'mx_conflict' | 'outbound_disabled' | 'cannot_send_from_domain' | 'recipient_not_allowed' | 'outbound_key_missing' | 'outbound_unreachable' | 'outbound_key_invalid' | 'outbound_capacity_exhausted' | 'outbound_response_malformed' | 'outbound_relay_failed' | 'inbound_not_repliable';
|
|
351
351
|
message: string;
|
|
352
352
|
/**
|
|
353
353
|
* Optional structured data that callers can inspect to recover
|
|
@@ -579,6 +579,14 @@ type EmailDetail = {
|
|
|
579
579
|
sender: string;
|
|
580
580
|
recipient: string;
|
|
581
581
|
subject?: string | null;
|
|
582
|
+
/**
|
|
583
|
+
* Plain-text body parsed from the inbound MIME, matching the `email.parsed.body_text` field on the webhook payload. Null when the message had no text part or parsing failed.
|
|
584
|
+
*/
|
|
585
|
+
body_text?: string | null;
|
|
586
|
+
/**
|
|
587
|
+
* HTML body parsed from the inbound MIME, matching the `email.parsed.body_html` field on the webhook payload. Null when the message had no HTML part or parsing failed.
|
|
588
|
+
*/
|
|
589
|
+
body_html?: string | null;
|
|
582
590
|
status: 'pending' | 'accepted' | 'completed' | 'rejected';
|
|
583
591
|
domain: string;
|
|
584
592
|
spam_score?: number | null;
|
|
@@ -607,6 +615,42 @@ type EmailDetail = {
|
|
|
607
615
|
* Parsed to address (same as recipient)
|
|
608
616
|
*/
|
|
609
617
|
to_email: string;
|
|
618
|
+
/**
|
|
619
|
+
* True when the inbound's sender address has a matching grant
|
|
620
|
+
* in the org's known-send-addresses list. Advisory: a true
|
|
621
|
+
* value does not by itself guarantee that a reply will be
|
|
622
|
+
* accepted by send-mail's gates; the per-send check at send
|
|
623
|
+
* time remains authoritative.
|
|
624
|
+
*
|
|
625
|
+
*/
|
|
626
|
+
from_known_address?: boolean;
|
|
627
|
+
/**
|
|
628
|
+
* Sent emails recorded as replies to this inbound, in send
|
|
629
|
+
* order (ascending). Populated when a customer's send-mail
|
|
630
|
+
* request carries an `in_reply_to` Message-ID that matches
|
|
631
|
+
* this inbound's `message_id` in the same org. Includes
|
|
632
|
+
* attempts that were gate-denied, so the array reflects every
|
|
633
|
+
* recorded reply attempt regardless of outcome.
|
|
634
|
+
*
|
|
635
|
+
*/
|
|
636
|
+
replies: Array<EmailDetailReply>;
|
|
637
|
+
};
|
|
638
|
+
type EmailDetailReply = {
|
|
639
|
+
/**
|
|
640
|
+
* Sent-email row id.
|
|
641
|
+
*/
|
|
642
|
+
id: string;
|
|
643
|
+
status: SentEmailStatus;
|
|
644
|
+
/**
|
|
645
|
+
* Recipient address as recorded on the sent_emails row.
|
|
646
|
+
*/
|
|
647
|
+
to_address: string;
|
|
648
|
+
subject?: string | null;
|
|
649
|
+
created_at: string;
|
|
650
|
+
/**
|
|
651
|
+
* Outbound relay queue identifier when available.
|
|
652
|
+
*/
|
|
653
|
+
queue_id?: string | null;
|
|
610
654
|
};
|
|
611
655
|
type SendMailInput = {
|
|
612
656
|
/**
|
|
@@ -648,6 +692,44 @@ type SendMailInput = {
|
|
|
648
692
|
};
|
|
649
693
|
type SentEmailStatus = 'queued' | 'submitted_to_agent' | 'agent_failed' | 'unknown' | 'delivered' | 'bounced' | 'deferred' | 'wait_timeout';
|
|
650
694
|
type DeliveryStatus = 'delivered' | 'bounced' | 'deferred' | 'wait_timeout';
|
|
695
|
+
/**
|
|
696
|
+
* Body shape for `/emails/{id}/reply`. Intentionally narrow:
|
|
697
|
+
* recipients (`to`), subject, and threading headers
|
|
698
|
+
* (`in_reply_to`, `references`) are derived server-side from
|
|
699
|
+
* the inbound row referenced by the path id and are rejected by
|
|
700
|
+
* `additionalProperties` if passed (returns 400).
|
|
701
|
+
*
|
|
702
|
+
* `from` IS allowed because of legitimate use cases (display-name
|
|
703
|
+
* addition, replying from a different verified outbound address,
|
|
704
|
+
* multi-team triage). Send-mail's per-send `canSendFrom` gate
|
|
705
|
+
* validates the from-domain regardless, so the override carries
|
|
706
|
+
* no extra privilege.
|
|
707
|
+
*
|
|
708
|
+
*/
|
|
709
|
+
type ReplyInput$1 = {
|
|
710
|
+
/**
|
|
711
|
+
* Plain-text reply body. At least one of body_text or body_html is required. The combined UTF-8 byte length of body_text and body_html must be at most 262144 bytes (same cap as send-mail).
|
|
712
|
+
*/
|
|
713
|
+
body_text?: string;
|
|
714
|
+
/**
|
|
715
|
+
* HTML reply body. At least one of body_text or body_html is required.
|
|
716
|
+
*/
|
|
717
|
+
body_html?: string;
|
|
718
|
+
/**
|
|
719
|
+
* Optional override for the reply's From header. Defaults to
|
|
720
|
+
* the inbound's recipient. Use to add a display name (`"Acme
|
|
721
|
+
* Support" <agent@company.com>`) or to reply from a different
|
|
722
|
+
* verified outbound address (e.g. multi-team routing where
|
|
723
|
+
* support@ triages to billing@). The from-domain must be a
|
|
724
|
+
* verified outbound domain for your org, same as send-mail.
|
|
725
|
+
*
|
|
726
|
+
*/
|
|
727
|
+
from?: string;
|
|
728
|
+
/**
|
|
729
|
+
* When true, wait for the first downstream SMTP delivery outcome before returning, mirroring the send-mail `wait` semantics.
|
|
730
|
+
*/
|
|
731
|
+
wait?: boolean;
|
|
732
|
+
};
|
|
651
733
|
type SendMailResult = {
|
|
652
734
|
/**
|
|
653
735
|
* Persisted sent-email attempt ID.
|
|
@@ -687,6 +769,15 @@ type SendMailResult = {
|
|
|
687
769
|
* SMTP response text from the first downstream delivery outcome when wait is true.
|
|
688
770
|
*/
|
|
689
771
|
smtp_response_text?: string;
|
|
772
|
+
/**
|
|
773
|
+
* True when the response replays a previously-recorded send
|
|
774
|
+
* keyed by `client_idempotency_key` (same key, same canonical
|
|
775
|
+
* payload). False on a fresh send and on gate-denied
|
|
776
|
+
* responses. Lets callers branch on cache state without
|
|
777
|
+
* diffing fields.
|
|
778
|
+
*
|
|
779
|
+
*/
|
|
780
|
+
idempotent_replay: boolean;
|
|
690
781
|
};
|
|
691
782
|
type Endpoint = {
|
|
692
783
|
id: string;
|
|
@@ -1359,6 +1450,68 @@ type DownloadAttachmentsResponses = {
|
|
|
1359
1450
|
200: Blob | File;
|
|
1360
1451
|
};
|
|
1361
1452
|
type DownloadAttachmentsResponse = DownloadAttachmentsResponses[keyof DownloadAttachmentsResponses];
|
|
1453
|
+
type ReplyToEmailData = {
|
|
1454
|
+
body: ReplyInput$1;
|
|
1455
|
+
path: {
|
|
1456
|
+
/**
|
|
1457
|
+
* Resource UUID
|
|
1458
|
+
*/
|
|
1459
|
+
id: string;
|
|
1460
|
+
};
|
|
1461
|
+
query?: never;
|
|
1462
|
+
url: '/emails/{id}/reply';
|
|
1463
|
+
};
|
|
1464
|
+
type ReplyToEmailErrors = {
|
|
1465
|
+
/**
|
|
1466
|
+
* Invalid request parameters
|
|
1467
|
+
*/
|
|
1468
|
+
400: ErrorResponse;
|
|
1469
|
+
/**
|
|
1470
|
+
* Invalid or missing API key
|
|
1471
|
+
*/
|
|
1472
|
+
401: ErrorResponse;
|
|
1473
|
+
/**
|
|
1474
|
+
* Authenticated caller lacks permission for the operation
|
|
1475
|
+
*/
|
|
1476
|
+
403: ErrorResponse;
|
|
1477
|
+
/**
|
|
1478
|
+
* Resource not found
|
|
1479
|
+
*/
|
|
1480
|
+
404: ErrorResponse;
|
|
1481
|
+
/**
|
|
1482
|
+
* Inbound is not repliable: the row exists but lacks a
|
|
1483
|
+
* `message_id` (no thread anchor) or a `recipient` (cannot
|
|
1484
|
+
* derive the From address).
|
|
1485
|
+
*
|
|
1486
|
+
*/
|
|
1487
|
+
422: ErrorResponse;
|
|
1488
|
+
/**
|
|
1489
|
+
* Rate limit exceeded
|
|
1490
|
+
*/
|
|
1491
|
+
429: ErrorResponse;
|
|
1492
|
+
/**
|
|
1493
|
+
* Primitive encountered an internal error
|
|
1494
|
+
*/
|
|
1495
|
+
500: ErrorResponse;
|
|
1496
|
+
/**
|
|
1497
|
+
* Primitive could not complete the downstream SMTP request
|
|
1498
|
+
*/
|
|
1499
|
+
502: ErrorResponse;
|
|
1500
|
+
/**
|
|
1501
|
+
* Primitive is temporarily unable to process the request
|
|
1502
|
+
*/
|
|
1503
|
+
503: ErrorResponse;
|
|
1504
|
+
};
|
|
1505
|
+
type ReplyToEmailError = ReplyToEmailErrors[keyof ReplyToEmailErrors];
|
|
1506
|
+
type ReplyToEmailResponses = {
|
|
1507
|
+
/**
|
|
1508
|
+
* Outbound relay result
|
|
1509
|
+
*/
|
|
1510
|
+
200: SuccessEnvelope & {
|
|
1511
|
+
data?: SendMailResult;
|
|
1512
|
+
};
|
|
1513
|
+
};
|
|
1514
|
+
type ReplyToEmailResponse = ReplyToEmailResponses[keyof ReplyToEmailResponses];
|
|
1362
1515
|
type ReplayEmailWebhooksData = {
|
|
1363
1516
|
body?: never;
|
|
1364
1517
|
path: {
|
|
@@ -1829,7 +1982,7 @@ type SendEmailResponses = {
|
|
|
1829
1982
|
};
|
|
1830
1983
|
type SendEmailResponse = SendEmailResponses[keyof SendEmailResponses];
|
|
1831
1984
|
declare namespace sdk_gen_d_exports {
|
|
1832
|
-
export { Options, addDomain, createEndpoint, createFilter, deleteDomain, deleteEmail, deleteEndpoint, deleteFilter, downloadAttachments, downloadRawEmail, getAccount, getEmail, getStorageStats, getWebhookSecret, listDeliveries, listDomains, listEmails, listEndpoints, listFilters, replayDelivery, replayEmailWebhooks, rotateWebhookSecret, sendEmail, testEndpoint, updateAccount, updateDomain, updateEndpoint, updateFilter, verifyDomain };
|
|
1985
|
+
export { Options, addDomain, createEndpoint, createFilter, deleteDomain, deleteEmail, deleteEndpoint, deleteFilter, downloadAttachments, downloadRawEmail, getAccount, getEmail, getStorageStats, getWebhookSecret, listDeliveries, listDomains, listEmails, listEndpoints, listFilters, replayDelivery, replayEmailWebhooks, replyToEmail, rotateWebhookSecret, sendEmail, testEndpoint, updateAccount, updateDomain, updateEndpoint, updateFilter, verifyDomain };
|
|
1833
1986
|
}
|
|
1834
1987
|
type Options<TData extends TDataShape = TDataShape, ThrowOnError extends boolean = boolean, TResponse = unknown> = Options$1<TData, ThrowOnError, TResponse> & {
|
|
1835
1988
|
/**
|
|
@@ -1948,6 +2101,24 @@ declare const downloadRawEmail: <ThrowOnError extends boolean = false>(options:
|
|
|
1948
2101
|
*
|
|
1949
2102
|
*/
|
|
1950
2103
|
declare const downloadAttachments: <ThrowOnError extends boolean = false>(options: Options<DownloadAttachmentsData, ThrowOnError>) => RequestResult<DownloadAttachmentsResponses, DownloadAttachmentsErrors, ThrowOnError, "fields">;
|
|
2104
|
+
/**
|
|
2105
|
+
* Reply to an inbound email
|
|
2106
|
+
*
|
|
2107
|
+
* Sends an outbound reply to the inbound email identified by `id`.
|
|
2108
|
+
* Threading headers (`In-Reply-To`, `References`), recipient
|
|
2109
|
+
* derivation (Reply-To, then From, then bare sender), and the
|
|
2110
|
+
* `Re:` subject prefix are all derived server-side from the
|
|
2111
|
+
* stored inbound row. The request body carries only the message
|
|
2112
|
+
* body and optional `wait` flag; passing any header or recipient
|
|
2113
|
+
* override is rejected by the schema (`additionalProperties:
|
|
2114
|
+
* false`).
|
|
2115
|
+
*
|
|
2116
|
+
* Forwards through the same gates as `/send-mail`: the response
|
|
2117
|
+
* status, error envelope, and `idempotent_replay` flag mirror
|
|
2118
|
+
* the send-mail contract verbatim.
|
|
2119
|
+
*
|
|
2120
|
+
*/
|
|
2121
|
+
declare const replyToEmail: <ThrowOnError extends boolean = false>(options: Options<ReplyToEmailData, ThrowOnError>) => RequestResult<ReplyToEmailResponses, ReplyToEmailErrors, ThrowOnError, "fields">;
|
|
1951
2122
|
/**
|
|
1952
2123
|
* Replay email webhooks
|
|
1953
2124
|
*
|
|
@@ -2077,10 +2248,34 @@ interface SendInput {
|
|
|
2077
2248
|
waitTimeoutMs?: number;
|
|
2078
2249
|
idempotencyKey?: string;
|
|
2079
2250
|
}
|
|
2251
|
+
/**
|
|
2252
|
+
* Input shape for `client.reply(email, input)`.
|
|
2253
|
+
*
|
|
2254
|
+
* Can be a bare string (treated as `text`) or an object. The reply
|
|
2255
|
+
* operation calls the server's `/emails/{id}/reply` endpoint, which
|
|
2256
|
+
* derives recipients, subject (`Re: <parent>`), and threading headers
|
|
2257
|
+
* from the inbound row. The shape here is the small subset of fields
|
|
2258
|
+
* the customer can still control:
|
|
2259
|
+
*
|
|
2260
|
+
* - `text` / `html`: the reply body. At least one is required.
|
|
2261
|
+
* - `from`: optional override for the From header. Defaults server-
|
|
2262
|
+
* side to the address that received the inbound. Use to add a
|
|
2263
|
+
* display name (`"Acme Support" <agent@company.com>`) or to reply
|
|
2264
|
+
* from a different verified outbound address. The from-domain must
|
|
2265
|
+
* be a verified outbound domain for your org.
|
|
2266
|
+
* - `wait`: when true, wait for the first downstream SMTP delivery
|
|
2267
|
+
* outcome before resolving. Mirrors send-mail's `wait` semantics.
|
|
2268
|
+
*
|
|
2269
|
+
* `subject` is intentionally not accepted: a custom subject silently
|
|
2270
|
+
* breaks Gmail's threading because Gmail's Conversation View requires
|
|
2271
|
+
* both a References match and a normalized-subject match. Always
|
|
2272
|
+
* sends `Re: <parent>` with idempotent prefixing.
|
|
2273
|
+
*/
|
|
2080
2274
|
type ReplyInput = string | {
|
|
2081
|
-
text
|
|
2082
|
-
|
|
2275
|
+
text?: string;
|
|
2276
|
+
html?: string;
|
|
2083
2277
|
from?: string;
|
|
2278
|
+
wait?: boolean;
|
|
2084
2279
|
};
|
|
2085
2280
|
interface ForwardInput {
|
|
2086
2281
|
to: string;
|
|
@@ -2097,6 +2292,12 @@ interface SendResult {
|
|
|
2097
2292
|
clientIdempotencyKey: string;
|
|
2098
2293
|
requestId: string;
|
|
2099
2294
|
contentHash: string;
|
|
2295
|
+
/**
|
|
2296
|
+
* True when the response replays a previously-recorded send keyed by
|
|
2297
|
+
* `clientIdempotencyKey` (same key, same canonical payload). False on
|
|
2298
|
+
* a fresh send and on gate-denied responses.
|
|
2299
|
+
*/
|
|
2300
|
+
idempotentReplay: boolean;
|
|
2100
2301
|
deliveryStatus?: SendMailResult["delivery_status"];
|
|
2101
2302
|
smtpResponseCode?: number | null;
|
|
2102
2303
|
smtpResponseText?: string;
|
|
@@ -2129,6 +2330,20 @@ declare class PrimitiveApiClient {
|
|
|
2129
2330
|
type PrimitiveClientOptions = PrimitiveApiClientOptions;
|
|
2130
2331
|
declare class PrimitiveClient extends PrimitiveApiClient {
|
|
2131
2332
|
send(input: SendInput): Promise<SendResult>;
|
|
2333
|
+
/**
|
|
2334
|
+
* Reply to an inbound email.
|
|
2335
|
+
*
|
|
2336
|
+
* Calls `POST /emails/{id}/reply`. The server derives recipients
|
|
2337
|
+
* (Reply-To, then From, then sender), subject (`Re: <parent>` with
|
|
2338
|
+
* idempotent prefix), and threading headers (`In-Reply-To`,
|
|
2339
|
+
* `References`) from the stored inbound row. The customer controls
|
|
2340
|
+
* only the body, an optional `from` override, and the `wait` flag.
|
|
2341
|
+
*
|
|
2342
|
+
* Subject overrides are intentionally not supported: Gmail's
|
|
2343
|
+
* Conversation View needs both a References match and a normalized-
|
|
2344
|
+
* subject match to thread, so a custom subject silently breaks the
|
|
2345
|
+
* thread for half the recipient population.
|
|
2346
|
+
*/
|
|
2132
2347
|
reply(email: ReceivedEmail, input: ReplyInput): Promise<SendResult>;
|
|
2133
2348
|
forward(email: ReceivedEmail, input: ForwardInput): Promise<SendResult>;
|
|
2134
2349
|
}
|
|
@@ -2137,4 +2352,4 @@ declare function createPrimitiveClient(options?: PrimitiveClientOptions): Primit
|
|
|
2137
2352
|
declare function client(options?: PrimitiveClientOptions): PrimitiveClient;
|
|
2138
2353
|
declare const operations: typeof sdk_gen_d_exports;
|
|
2139
2354
|
//#endregion
|
|
2140
|
-
export {
|
|
2355
|
+
export { AddDomainResponse as $, ReplayDeliveryErrors as $n, UpdateEndpointResponses as $r, ErrorResponse as $t, getWebhookSecret as A, ListDomainsError as An, TestEndpointError as Ar, DeleteFilterData as At, sendEmail as B, ListEndpointsError as Bn, UpdateAccountResponse as Br, DownloadAttachmentsError as Bt, deleteEndpoint as C, Limit as Cn, SendEmailResponses as Cr, DeleteEmailResponse as Ct, getAccount as D, ListDeliveriesResponse as Dn, StorageStats as Dr, DeleteEndpointErrors as Dt, downloadRawEmail as E, ListDeliveriesErrors as En, SentEmailStatus as Er, DeleteEndpointError as Et, listFilters as F, ListEmailsError as Fn, UnverifiedDomain as Fr, DeliveryStatus as Ft, updateFilter as G, ListFiltersData as Gn, UpdateDomainInput as Gr, DownloadRawEmailError as Gt, updateAccount as H, ListEndpointsResponse as Hn, UpdateDomainData as Hr, DownloadAttachmentsResponse as Ht, replayDelivery as I, ListEmailsErrors as In, UpdateAccountData as Ir, DeliverySummary as It, AccountUpdated as J, ListFiltersResponse as Jn, UpdateEndpointData as Jr, DownloadRawEmailResponses as Jt, verifyDomain as K, ListFiltersError as Kn, UpdateDomainResponse as Kr, DownloadRawEmailErrors as Kt, replayEmailWebhooks as L, ListEmailsResponse as Ln, UpdateAccountError as Lr, Domain as Lt, listDomains as M, ListDomainsResponse as Mn, TestEndpointResponse as Mr, DeleteFilterErrors as Mt, listEmails as N, ListDomainsResponses as Nn, TestEndpointResponses as Nr, DeleteFilterResponse as Nt, getEmail as O, ListDeliveriesResponses as On, SuccessEnvelope as Or, DeleteEndpointResponse as Ot, listEndpoints as P, ListEmailsData as Pn, TestResult as Pr, DeleteFilterResponses as Pt, AddDomainInput as Q, ReplayDeliveryError as Qn, UpdateEndpointResponse as Qr, Endpoint as Qt, replyToEmail as R, ListEmailsResponses as Rn, UpdateAccountErrors as Rr, DomainVerifyResult as Rt, deleteEmail as S, GetWebhookSecretResponses as Sn, SendEmailResponse as Sr, DeleteEmailErrors as St, downloadAttachments as T, ListDeliveriesError as Tn, SendMailResult as Tr, DeleteEndpointData as Tt, updateDomain as U, ListEndpointsResponses as Un, UpdateDomainError as Ur, DownloadAttachmentsResponses as Ut, testEndpoint as V, ListEndpointsErrors as Vn, UpdateAccountResponses as Vr, DownloadAttachmentsErrors as Vt, updateEndpoint as W, ListEnvelope as Wn, UpdateDomainErrors as Wr, DownloadRawEmailData as Wt, AddDomainError as X, PaginationMeta as Xn, UpdateEndpointErrors as Xr, EmailDetailReply as Xt, AddDomainData as Y, ListFiltersResponses as Yn, UpdateEndpointError as Yr, EmailDetail as Yt, AddDomainErrors as Z, ReplayDeliveryData as Zn, UpdateEndpointInput as Zr, EmailSummary as Zt, Options as _, Options$1 as _i, GetStorageStatsResponses as _n, RotateWebhookSecretResponse as _r, DeleteDomainErrors as _t, PrimitiveApiError as a, UpdateFilterResponses as ai, GetAccountErrors as an, ReplayEmailWebhooksResponse as ar, CreateEndpointInput as at, createFilter as b, ResponseStyle as bi, GetWebhookSecretErrors as bn, SendEmailError as br, DeleteEmailData as bt, PrimitiveClientOptions as c, VerifyDomainError as ci, GetEmailData as cn, ReplyToEmailData as cr, CreateFilterData as ct, SendResult as d, VerifyDomainResponses as di, GetEmailResponse as dn, ReplyToEmailResponse as dr, CreateFilterInput as dt, UpdateFilterData as ei, Filter as en, ReplayDeliveryResponse as er, AddDomainResponses as et, SendThreadInput as f, WebhookSecret as fi, GetEmailResponses as fn, ReplyToEmailResponses as fr, CreateFilterResponse as ft, operations as g, CreateClientConfig as gi, GetStorageStatsResponse as gn, RotateWebhookSecretErrors as gr, DeleteDomainError as gt, createPrimitiveClient as h, Config as hi, GetStorageStatsErrors as hn, RotateWebhookSecretError as hr, DeleteDomainData as ht, PrimitiveApiClientOptions as i, UpdateFilterResponse as ii, GetAccountError as in, ReplayEmailWebhooksErrors as ir, CreateEndpointErrors as it, listDeliveries as j, ListDomainsErrors as jn, TestEndpointErrors as jr, DeleteFilterError as jt, getStorageStats as k, ListDomainsData as kn, TestEndpointData as kr, DeleteEndpointResponses as kt, ReplyInput as l, VerifyDomainErrors as li, GetEmailError as ln, ReplyToEmailError as lr, CreateFilterError as lt, createPrimitiveApiClient as m, ClientOptions$1 as mi, GetStorageStatsError as mn, RotateWebhookSecretData as mr, Cursor as mt, ForwardInput as n, UpdateFilterErrors as ni, GateFix as nn, ReplayEmailWebhooksData as nr, CreateEndpointData as nt, PrimitiveApiErrorDetails as o, VerifiedDomain as oi, GetAccountResponse as on, ReplayEmailWebhooksResponses as or, CreateEndpointResponse as ot, client as p, Client as pi, GetStorageStatsData as pn, ResourceId as pr, CreateFilterResponses as pt, Account as q, ListFiltersErrors as qn, UpdateDomainResponses as qr, DownloadRawEmailResponse as qt, PrimitiveApiClient as r, UpdateFilterInput as ri, GetAccountData as rn, ReplayEmailWebhooksError as rr, CreateEndpointError as rt, PrimitiveClient as s, VerifyDomainData as si, GetAccountResponses as sn, ReplayResult as sr, CreateEndpointResponses as st, DEFAULT_BASE_URL as t, UpdateFilterError as ti, GateDenial as tn, ReplayDeliveryResponses as tr, ClientOptions as tt, SendInput as u, VerifyDomainResponse as ui, GetEmailErrors as un, ReplyToEmailErrors as ur, CreateFilterErrors as ut, addDomain as v, RequestOptions as vi, GetWebhookSecretData as vn, RotateWebhookSecretResponses as vr, DeleteDomainResponse as vt, deleteFilter as w, ListDeliveriesData as wn, SendMailInput as wr, DeleteEmailResponses as wt, deleteDomain as x, Auth as xi, GetWebhookSecretResponse as xn, SendEmailErrors as xr, DeleteEmailError as xt, createEndpoint as y, RequestResult as yi, GetWebhookSecretError as yn, SendEmailData as yr, DeleteDomainResponses as yt, rotateWebhookSecret as z, ListEndpointsData as zn, UpdateAccountInput as zr, DownloadAttachmentsData as zt };
|
package/dist/index.d.ts
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import { A as UnknownEvent, C as ParsedDataFailed, D as RawContentDownloadOnly, E as RawContent, M as WebhookAttachment, N as WebhookEvent, O as RawContentInline, S as ParsedDataComplete, T as ParsedStatus, _ as ForwardResultInline, a as DmarcPolicy, b as KnownWebhookEvent, c as EmailAnalysis, d as EventType, f as ForwardAnalysis, g as ForwardResultAttachmentSkipped, h as ForwardResultAttachmentAnalyzed, i as DkimSignature, j as ValidateEmailAuthResult, k as SpfResult, l as EmailAuth, m as ForwardResult, n as AuthVerdict, o as DmarcResult, p as ForwardOriginalSender, r as DkimResult, s as EmailAddress, t as AuthConfidence, u as EmailReceivedEvent, v as ForwardVerdict, w as ParsedError, x as ParsedData, y as ForwardVerification } from "./types-9vXGZjPd.js";
|
|
2
2
|
import { a as buildReplySubject, c as parseHeaderAddress, i as buildForwardSubject, n as ReceivedEmailAddress, o as formatAddress, r as ReceivedEmailThread, s as normalizeReceivedEmail, t as ReceivedEmail } from "./received-email-DNjpq_Wt.js";
|
|
3
|
-
import { a as PrimitiveApiError, c as PrimitiveClientOptions, d as SendResult, f as SendThreadInput, h as createPrimitiveClient, l as ReplyInput, n as ForwardInput, p as client, s as PrimitiveClient, u as SendInput } from "./index-
|
|
3
|
+
import { a as PrimitiveApiError, c as PrimitiveClientOptions, d as SendResult, f as SendThreadInput, h as createPrimitiveClient, l as ReplyInput, n as ForwardInput, p as client, s as PrimitiveClient, u as SendInput } from "./index-K4KbjppU.js";
|
|
4
4
|
import { A as VerifyOptions, B as PAYLOAD_ERRORS, C as signStandardWebhooksPayload, D as PRIMITIVE_CONFIRMED_HEADER, E as LEGACY_SIGNATURE_HEADER, F as VerifyDownloadTokenResult, G as VERIFICATION_ERRORS, H as RAW_EMAIL_ERRORS, I as generateDownloadToken, J as WebhookPayloadErrorCode, K as WebhookErrorCode, L as verifyDownloadToken, M as verifyWebhookSignature, N as GenerateDownloadTokenOptions, O as PRIMITIVE_SIGNATURE_HEADER, P as VerifyDownloadTokenOptions, Q as WebhookVerificationErrorCode, R as safeValidateEmailReceivedEvent, S as StandardWebhooksVerifyOptions, T as LEGACY_CONFIRMED_HEADER, U as RawEmailDecodeError, V as PrimitiveWebhookError, W as RawEmailDecodeErrorCode, X as WebhookValidationErrorCode, Y as WebhookValidationError, Z as WebhookVerificationError, _ as emailReceivedEventJsonSchema, a as confirmedHeaders, b as STANDARD_WEBHOOK_TIMESTAMP_HEADER, c as handleWebhook, d as isRawIncluded, f as parseWebhookEvent, g as validateEmailAuth, h as WEBHOOK_VERSION, i as WebhookHeaders, j as signWebhookPayload, k as SignResult, l as isDownloadExpired, m as verifyRawEmailDownload, n as HandleWebhookOptions, o as decodeRawEmail, p as receive, q as WebhookPayloadError, r as ReceiveRequestOptions, s as getDownloadTimeRemaining, t as DecodeRawEmailOptions, u as isEmailReceivedEvent, v as STANDARD_WEBHOOK_ID_HEADER, w as verifyStandardWebhooksSignature, x as StandardWebhooksSignResult, y as STANDARD_WEBHOOK_SIGNATURE_HEADER, z as validateEmailReceivedEvent } from "./index-CbEivn3S.js";
|
|
5
5
|
|
|
6
6
|
//#region src/index.d.ts
|
package/dist/index.js
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { a as parseHeaderAddress, i as normalizeReceivedEmail, n as buildReplySubject, r as formatAddress, t as buildForwardSubject } from "./received-email-D6tKtWwW.js";
|
|
2
|
-
import { a as client, i as PrimitiveClient, r as PrimitiveApiError, s as createPrimitiveClient } from "./api-
|
|
2
|
+
import { a as client, i as PrimitiveClient, r as PrimitiveApiError, s as createPrimitiveClient } from "./api-CLLpjjWy.js";
|
|
3
3
|
import { A as PRIMITIVE_CONFIRMED_HEADER, B as RAW_EMAIL_ERRORS, C as STANDARD_WEBHOOK_ID_HEADER, D as verifyStandardWebhooksSignature, E as signStandardWebhooksPayload, F as verifyDownloadToken, G as WebhookVerificationError, H as VERIFICATION_ERRORS, I as safeValidateEmailReceivedEvent, L as validateEmailReceivedEvent, M as signWebhookPayload, N as verifyWebhookSignature, O as LEGACY_CONFIRMED_HEADER, P as generateDownloadToken, R as PAYLOAD_ERRORS, S as emailReceivedEventJsonSchema, T as STANDARD_WEBHOOK_TIMESTAMP_HEADER, U as WebhookPayloadError, V as RawEmailDecodeError, W as WebhookValidationError, _ as DmarcResult, a as isDownloadExpired, b as ParsedStatus, c as parseWebhookEvent, d as WEBHOOK_VERSION, f as validateEmailAuth, g as DmarcPolicy, h as DkimResult, i as handleWebhook, j as PRIMITIVE_SIGNATURE_HEADER, k as LEGACY_SIGNATURE_HEADER, l as receive, m as AuthVerdict, n as decodeRawEmail, o as isEmailReceivedEvent, p as AuthConfidence, r as getDownloadTimeRemaining, s as isRawIncluded, t as confirmedHeaders, u as verifyRawEmailDownload, v as EventType, w as STANDARD_WEBHOOK_SIGNATURE_HEADER, x as SpfResult, y as ForwardVerdict, z as PrimitiveWebhookError } from "./webhook-zkN4wUTs.js";
|
|
4
4
|
//#region src/index.ts
|
|
5
5
|
const primitive = {
|
|
@@ -842,6 +842,96 @@ export const openapiDocument = {
|
|
|
842
842
|
}
|
|
843
843
|
}
|
|
844
844
|
},
|
|
845
|
+
"/emails/{id}/reply": {
|
|
846
|
+
"parameters": [
|
|
847
|
+
{
|
|
848
|
+
"$ref": "#/components/parameters/ResourceId"
|
|
849
|
+
}
|
|
850
|
+
],
|
|
851
|
+
"post": {
|
|
852
|
+
"operationId": "replyToEmail",
|
|
853
|
+
"summary": "Reply to an inbound email",
|
|
854
|
+
"description": "Sends an outbound reply to the inbound email identified by `id`.\nThreading headers (`In-Reply-To`, `References`), recipient\nderivation (Reply-To, then From, then bare sender), and the\n`Re:` subject prefix are all derived server-side from the\nstored inbound row. The request body carries only the message\nbody and optional `wait` flag; passing any header or recipient\noverride is rejected by the schema (`additionalProperties:\nfalse`).\n\nForwards through the same gates as `/send-mail`: the response\nstatus, error envelope, and `idempotent_replay` flag mirror\nthe send-mail contract verbatim.\n",
|
|
855
|
+
"tags": [
|
|
856
|
+
"Sending"
|
|
857
|
+
],
|
|
858
|
+
"requestBody": {
|
|
859
|
+
"required": true,
|
|
860
|
+
"content": {
|
|
861
|
+
"application/json": {
|
|
862
|
+
"schema": {
|
|
863
|
+
"$ref": "#/components/schemas/ReplyInput"
|
|
864
|
+
}
|
|
865
|
+
}
|
|
866
|
+
}
|
|
867
|
+
},
|
|
868
|
+
"responses": {
|
|
869
|
+
"200": {
|
|
870
|
+
"description": "Outbound relay result",
|
|
871
|
+
"content": {
|
|
872
|
+
"application/json": {
|
|
873
|
+
"schema": {
|
|
874
|
+
"allOf": [
|
|
875
|
+
{
|
|
876
|
+
"$ref": "#/components/schemas/SuccessEnvelope"
|
|
877
|
+
},
|
|
878
|
+
{
|
|
879
|
+
"type": "object",
|
|
880
|
+
"properties": {
|
|
881
|
+
"data": {
|
|
882
|
+
"$ref": "#/components/schemas/SendMailResult"
|
|
883
|
+
}
|
|
884
|
+
}
|
|
885
|
+
}
|
|
886
|
+
]
|
|
887
|
+
}
|
|
888
|
+
}
|
|
889
|
+
}
|
|
890
|
+
},
|
|
891
|
+
"400": {
|
|
892
|
+
"$ref": "#/components/responses/ValidationError"
|
|
893
|
+
},
|
|
894
|
+
"401": {
|
|
895
|
+
"$ref": "#/components/responses/Unauthorized"
|
|
896
|
+
},
|
|
897
|
+
"403": {
|
|
898
|
+
"$ref": "#/components/responses/Forbidden"
|
|
899
|
+
},
|
|
900
|
+
"404": {
|
|
901
|
+
"$ref": "#/components/responses/NotFound"
|
|
902
|
+
},
|
|
903
|
+
"422": {
|
|
904
|
+
"description": "Inbound is not repliable: the row exists but lacks a\n`message_id` (no thread anchor) or a `recipient` (cannot\nderive the From address).\n",
|
|
905
|
+
"content": {
|
|
906
|
+
"application/json": {
|
|
907
|
+
"schema": {
|
|
908
|
+
"$ref": "#/components/schemas/ErrorResponse"
|
|
909
|
+
},
|
|
910
|
+
"example": {
|
|
911
|
+
"success": false,
|
|
912
|
+
"error": {
|
|
913
|
+
"code": "inbound_not_repliable",
|
|
914
|
+
"message": "inbound has no Message-ID; cannot anchor a reply thread"
|
|
915
|
+
}
|
|
916
|
+
}
|
|
917
|
+
}
|
|
918
|
+
}
|
|
919
|
+
},
|
|
920
|
+
"429": {
|
|
921
|
+
"$ref": "#/components/responses/RateLimited"
|
|
922
|
+
},
|
|
923
|
+
"500": {
|
|
924
|
+
"$ref": "#/components/responses/InternalError"
|
|
925
|
+
},
|
|
926
|
+
"502": {
|
|
927
|
+
"$ref": "#/components/responses/BadGateway"
|
|
928
|
+
},
|
|
929
|
+
"503": {
|
|
930
|
+
"$ref": "#/components/responses/ServiceUnavailable"
|
|
931
|
+
}
|
|
932
|
+
}
|
|
933
|
+
}
|
|
934
|
+
},
|
|
845
935
|
"/emails/{id}/replay": {
|
|
846
936
|
"parameters": [
|
|
847
937
|
{
|
|
@@ -1819,7 +1909,8 @@ export const openapiDocument = {
|
|
|
1819
1909
|
"outbound_key_invalid",
|
|
1820
1910
|
"outbound_capacity_exhausted",
|
|
1821
1911
|
"outbound_response_malformed",
|
|
1822
|
-
"outbound_relay_failed"
|
|
1912
|
+
"outbound_relay_failed",
|
|
1913
|
+
"inbound_not_repliable"
|
|
1823
1914
|
]
|
|
1824
1915
|
},
|
|
1825
1916
|
"message": {
|
|
@@ -2443,6 +2534,20 @@ export const openapiDocument = {
|
|
|
2443
2534
|
"null"
|
|
2444
2535
|
]
|
|
2445
2536
|
},
|
|
2537
|
+
"body_text": {
|
|
2538
|
+
"type": [
|
|
2539
|
+
"string",
|
|
2540
|
+
"null"
|
|
2541
|
+
],
|
|
2542
|
+
"description": "Plain-text body parsed from the inbound MIME, matching the `email.parsed.body_text` field on the webhook payload. Null when the message had no text part or parsing failed."
|
|
2543
|
+
},
|
|
2544
|
+
"body_html": {
|
|
2545
|
+
"type": [
|
|
2546
|
+
"string",
|
|
2547
|
+
"null"
|
|
2548
|
+
],
|
|
2549
|
+
"description": "HTML body parsed from the inbound MIME, matching the `email.parsed.body_html` field on the webhook payload. Null when the message had no HTML part or parsing failed."
|
|
2550
|
+
},
|
|
2446
2551
|
"status": {
|
|
2447
2552
|
"type": "string",
|
|
2448
2553
|
"enum": [
|
|
@@ -2577,6 +2682,17 @@ export const openapiDocument = {
|
|
|
2577
2682
|
"to_email": {
|
|
2578
2683
|
"type": "string",
|
|
2579
2684
|
"description": "Parsed to address (same as recipient)"
|
|
2685
|
+
},
|
|
2686
|
+
"from_known_address": {
|
|
2687
|
+
"type": "boolean",
|
|
2688
|
+
"description": "True when the inbound's sender address has a matching grant\nin the org's known-send-addresses list. Advisory: a true\nvalue does not by itself guarantee that a reply will be\naccepted by send-mail's gates; the per-send check at send\ntime remains authoritative.\n"
|
|
2689
|
+
},
|
|
2690
|
+
"replies": {
|
|
2691
|
+
"type": "array",
|
|
2692
|
+
"description": "Sent emails recorded as replies to this inbound, in send\norder (ascending). Populated when a customer's send-mail\nrequest carries an `in_reply_to` Message-ID that matches\nthis inbound's `message_id` in the same org. Includes\nattempts that were gate-denied, so the array reflects every\nrecorded reply attempt regardless of outcome.\n",
|
|
2693
|
+
"items": {
|
|
2694
|
+
"$ref": "#/components/schemas/EmailDetailReply"
|
|
2695
|
+
}
|
|
2580
2696
|
}
|
|
2581
2697
|
},
|
|
2582
2698
|
"required": [
|
|
@@ -2589,7 +2705,48 @@ export const openapiDocument = {
|
|
|
2589
2705
|
"received_at",
|
|
2590
2706
|
"webhook_attempt_count",
|
|
2591
2707
|
"from_email",
|
|
2592
|
-
"to_email"
|
|
2708
|
+
"to_email",
|
|
2709
|
+
"replies"
|
|
2710
|
+
]
|
|
2711
|
+
},
|
|
2712
|
+
"EmailDetailReply": {
|
|
2713
|
+
"type": "object",
|
|
2714
|
+
"properties": {
|
|
2715
|
+
"id": {
|
|
2716
|
+
"type": "string",
|
|
2717
|
+
"format": "uuid",
|
|
2718
|
+
"description": "Sent-email row id."
|
|
2719
|
+
},
|
|
2720
|
+
"status": {
|
|
2721
|
+
"$ref": "#/components/schemas/SentEmailStatus"
|
|
2722
|
+
},
|
|
2723
|
+
"to_address": {
|
|
2724
|
+
"type": "string",
|
|
2725
|
+
"description": "Recipient address as recorded on the sent_emails row."
|
|
2726
|
+
},
|
|
2727
|
+
"subject": {
|
|
2728
|
+
"type": [
|
|
2729
|
+
"string",
|
|
2730
|
+
"null"
|
|
2731
|
+
]
|
|
2732
|
+
},
|
|
2733
|
+
"created_at": {
|
|
2734
|
+
"type": "string",
|
|
2735
|
+
"format": "date-time"
|
|
2736
|
+
},
|
|
2737
|
+
"queue_id": {
|
|
2738
|
+
"type": [
|
|
2739
|
+
"string",
|
|
2740
|
+
"null"
|
|
2741
|
+
],
|
|
2742
|
+
"description": "Outbound relay queue identifier when available."
|
|
2743
|
+
}
|
|
2744
|
+
},
|
|
2745
|
+
"required": [
|
|
2746
|
+
"id",
|
|
2747
|
+
"status",
|
|
2748
|
+
"to_address",
|
|
2749
|
+
"created_at"
|
|
2593
2750
|
]
|
|
2594
2751
|
},
|
|
2595
2752
|
"SendMailInput": {
|
|
@@ -2679,6 +2836,31 @@ export const openapiDocument = {
|
|
|
2679
2836
|
"wait_timeout"
|
|
2680
2837
|
]
|
|
2681
2838
|
},
|
|
2839
|
+
"ReplyInput": {
|
|
2840
|
+
"type": "object",
|
|
2841
|
+
"additionalProperties": false,
|
|
2842
|
+
"description": "Body shape for `/emails/{id}/reply`. Intentionally narrow:\nrecipients (`to`), subject, and threading headers\n(`in_reply_to`, `references`) are derived server-side from\nthe inbound row referenced by the path id and are rejected by\n`additionalProperties` if passed (returns 400).\n\n`from` IS allowed because of legitimate use cases (display-name\naddition, replying from a different verified outbound address,\nmulti-team triage). Send-mail's per-send `canSendFrom` gate\nvalidates the from-domain regardless, so the override carries\nno extra privilege.\n",
|
|
2843
|
+
"properties": {
|
|
2844
|
+
"body_text": {
|
|
2845
|
+
"type": "string",
|
|
2846
|
+
"description": "Plain-text reply body. At least one of body_text or body_html is required. The combined UTF-8 byte length of body_text and body_html must be at most 262144 bytes (same cap as send-mail)."
|
|
2847
|
+
},
|
|
2848
|
+
"body_html": {
|
|
2849
|
+
"type": "string",
|
|
2850
|
+
"description": "HTML reply body. At least one of body_text or body_html is required."
|
|
2851
|
+
},
|
|
2852
|
+
"from": {
|
|
2853
|
+
"type": "string",
|
|
2854
|
+
"minLength": 3,
|
|
2855
|
+
"maxLength": 998,
|
|
2856
|
+
"description": "Optional override for the reply's From header. Defaults to\nthe inbound's recipient. Use to add a display name (`\"Acme\nSupport\" <agent@company.com>`) or to reply from a different\nverified outbound address (e.g. multi-team routing where\nsupport@ triages to billing@). The from-domain must be a\nverified outbound domain for your org, same as send-mail.\n"
|
|
2857
|
+
},
|
|
2858
|
+
"wait": {
|
|
2859
|
+
"type": "boolean",
|
|
2860
|
+
"description": "When true, wait for the first downstream SMTP delivery outcome before returning, mirroring the send-mail `wait` semantics."
|
|
2861
|
+
}
|
|
2862
|
+
}
|
|
2863
|
+
},
|
|
2682
2864
|
"SendMailResult": {
|
|
2683
2865
|
"type": "object",
|
|
2684
2866
|
"properties": {
|
|
@@ -2735,6 +2917,10 @@ export const openapiDocument = {
|
|
|
2735
2917
|
"smtp_response_text": {
|
|
2736
2918
|
"type": "string",
|
|
2737
2919
|
"description": "SMTP response text from the first downstream delivery outcome when wait is true."
|
|
2920
|
+
},
|
|
2921
|
+
"idempotent_replay": {
|
|
2922
|
+
"type": "boolean",
|
|
2923
|
+
"description": "True when the response replays a previously-recorded send\nkeyed by `client_idempotency_key` (same key, same canonical\npayload). False on a fresh send and on gate-denied\nresponses. Lets callers branch on cache state without\ndiffing fields.\n"
|
|
2738
2924
|
}
|
|
2739
2925
|
},
|
|
2740
2926
|
"required": [
|
|
@@ -2745,7 +2931,8 @@ export const openapiDocument = {
|
|
|
2745
2931
|
"rejected",
|
|
2746
2932
|
"client_idempotency_key",
|
|
2747
2933
|
"request_id",
|
|
2748
|
-
"content_hash"
|
|
2934
|
+
"content_hash",
|
|
2935
|
+
"idempotent_replay"
|
|
2749
2936
|
]
|
|
2750
2937
|
},
|
|
2751
2938
|
"Endpoint": {
|
|
@@ -752,6 +752,55 @@ export const operationManifest = [
|
|
|
752
752
|
"tag": "Filters",
|
|
753
753
|
"tagCommand": "filters"
|
|
754
754
|
},
|
|
755
|
+
{
|
|
756
|
+
"binaryResponse": false,
|
|
757
|
+
"bodyRequired": true,
|
|
758
|
+
"command": "reply-to-email",
|
|
759
|
+
"description": "Sends an outbound reply to the inbound email identified by `id`.\nThreading headers (`In-Reply-To`, `References`), recipient\nderivation (Reply-To, then From, then bare sender), and the\n`Re:` subject prefix are all derived server-side from the\nstored inbound row. The request body carries only the message\nbody and optional `wait` flag; passing any header or recipient\noverride is rejected by the schema (`additionalProperties:\nfalse`).\n\nForwards through the same gates as `/send-mail`: the response\nstatus, error envelope, and `idempotent_replay` flag mirror\nthe send-mail contract verbatim.\n",
|
|
760
|
+
"hasJsonBody": true,
|
|
761
|
+
"method": "POST",
|
|
762
|
+
"operationId": "replyToEmail",
|
|
763
|
+
"path": "/emails/{id}/reply",
|
|
764
|
+
"pathParams": [
|
|
765
|
+
{
|
|
766
|
+
"description": "Resource UUID",
|
|
767
|
+
"enum": null,
|
|
768
|
+
"name": "id",
|
|
769
|
+
"required": true,
|
|
770
|
+
"type": "string"
|
|
771
|
+
}
|
|
772
|
+
],
|
|
773
|
+
"queryParams": [],
|
|
774
|
+
"requestSchema": {
|
|
775
|
+
"type": "object",
|
|
776
|
+
"additionalProperties": false,
|
|
777
|
+
"description": "Body shape for `/emails/{id}/reply`. Intentionally narrow:\nrecipients (`to`), subject, and threading headers\n(`in_reply_to`, `references`) are derived server-side from\nthe inbound row referenced by the path id and are rejected by\n`additionalProperties` if passed (returns 400).\n\n`from` IS allowed because of legitimate use cases (display-name\naddition, replying from a different verified outbound address,\nmulti-team triage). Send-mail's per-send `canSendFrom` gate\nvalidates the from-domain regardless, so the override carries\nno extra privilege.\n",
|
|
778
|
+
"properties": {
|
|
779
|
+
"body_text": {
|
|
780
|
+
"type": "string",
|
|
781
|
+
"description": "Plain-text reply body. At least one of body_text or body_html is required. The combined UTF-8 byte length of body_text and body_html must be at most 262144 bytes (same cap as send-mail)."
|
|
782
|
+
},
|
|
783
|
+
"body_html": {
|
|
784
|
+
"type": "string",
|
|
785
|
+
"description": "HTML reply body. At least one of body_text or body_html is required."
|
|
786
|
+
},
|
|
787
|
+
"from": {
|
|
788
|
+
"type": "string",
|
|
789
|
+
"minLength": 3,
|
|
790
|
+
"maxLength": 998,
|
|
791
|
+
"description": "Optional override for the reply's From header. Defaults to\nthe inbound's recipient. Use to add a display name (`\"Acme\nSupport\" <agent@company.com>`) or to reply from a different\nverified outbound address (e.g. multi-team routing where\nsupport@ triages to billing@). The from-domain must be a\nverified outbound domain for your org, same as send-mail.\n"
|
|
792
|
+
},
|
|
793
|
+
"wait": {
|
|
794
|
+
"type": "boolean",
|
|
795
|
+
"description": "When true, wait for the first downstream SMTP delivery outcome before returning, mirroring the send-mail `wait` semantics."
|
|
796
|
+
}
|
|
797
|
+
}
|
|
798
|
+
},
|
|
799
|
+
"sdkName": "replyToEmail",
|
|
800
|
+
"summary": "Reply to an inbound email",
|
|
801
|
+
"tag": "Sending",
|
|
802
|
+
"tagCommand": "sending"
|
|
803
|
+
},
|
|
755
804
|
{
|
|
756
805
|
"binaryResponse": false,
|
|
757
806
|
"bodyRequired": true,
|
package/oclif.manifest.json
CHANGED
|
@@ -1136,6 +1136,60 @@
|
|
|
1136
1136
|
"summary": "Update a filter rule",
|
|
1137
1137
|
"enableJsonFlag": false
|
|
1138
1138
|
},
|
|
1139
|
+
"sending:reply-to-email": {
|
|
1140
|
+
"aliases": [],
|
|
1141
|
+
"args": {},
|
|
1142
|
+
"description": "Sends an outbound reply to the inbound email identified by `id`.\nThreading headers (`In-Reply-To`, `References`), recipient\nderivation (Reply-To, then From, then bare sender), and the\n`Re:` subject prefix are all derived server-side from the\nstored inbound row. The request body carries only the message\nbody and optional `wait` flag; passing any header or recipient\noverride is rejected by the schema (`additionalProperties:\nfalse`).\n\nForwards through the same gates as `/send-mail`: the response\nstatus, error envelope, and `idempotent_replay` flag mirror\nthe send-mail contract verbatim.\n\n\nBody fields (JSON --body):\n body_html string HTML reply body. At least one of body_text or body_html is required.\n body_text string Plain-text reply body. At least one of body_text or body_html is required. ...\n from string Optional override for the reply's From header. Defaults to\n wait boolean When true, wait for the first downstream SMTP delivery outcome before retur...\n(* = required)",
|
|
1143
|
+
"flags": {
|
|
1144
|
+
"api-key": {
|
|
1145
|
+
"description": "Primitive API key (defaults to PRIMITIVE_API_KEY)",
|
|
1146
|
+
"env": "PRIMITIVE_API_KEY",
|
|
1147
|
+
"name": "api-key",
|
|
1148
|
+
"hasDynamicHelp": false,
|
|
1149
|
+
"multiple": false,
|
|
1150
|
+
"type": "option"
|
|
1151
|
+
},
|
|
1152
|
+
"base-url": {
|
|
1153
|
+
"description": "API base URL (defaults to PRIMITIVE_API_URL or production)",
|
|
1154
|
+
"env": "PRIMITIVE_API_URL",
|
|
1155
|
+
"name": "base-url",
|
|
1156
|
+
"hasDynamicHelp": false,
|
|
1157
|
+
"multiple": false,
|
|
1158
|
+
"type": "option"
|
|
1159
|
+
},
|
|
1160
|
+
"id": {
|
|
1161
|
+
"description": "Resource UUID",
|
|
1162
|
+
"name": "id",
|
|
1163
|
+
"required": true,
|
|
1164
|
+
"hasDynamicHelp": false,
|
|
1165
|
+
"multiple": false,
|
|
1166
|
+
"type": "option"
|
|
1167
|
+
},
|
|
1168
|
+
"body": {
|
|
1169
|
+
"description": "JSON request body",
|
|
1170
|
+
"name": "body",
|
|
1171
|
+
"hasDynamicHelp": false,
|
|
1172
|
+
"multiple": false,
|
|
1173
|
+
"type": "option"
|
|
1174
|
+
},
|
|
1175
|
+
"body-file": {
|
|
1176
|
+
"description": "Path to a JSON file used as the request body",
|
|
1177
|
+
"name": "body-file",
|
|
1178
|
+
"hasDynamicHelp": false,
|
|
1179
|
+
"multiple": false,
|
|
1180
|
+
"type": "option"
|
|
1181
|
+
}
|
|
1182
|
+
},
|
|
1183
|
+
"hasDynamicHelp": false,
|
|
1184
|
+
"hiddenAliases": [],
|
|
1185
|
+
"id": "sending:reply-to-email",
|
|
1186
|
+
"pluginAlias": "@primitivedotdev/sdk",
|
|
1187
|
+
"pluginName": "@primitivedotdev/sdk",
|
|
1188
|
+
"pluginType": "core",
|
|
1189
|
+
"strict": true,
|
|
1190
|
+
"summary": "Reply to an inbound email",
|
|
1191
|
+
"enableJsonFlag": false
|
|
1192
|
+
},
|
|
1139
1193
|
"sending:send-email": {
|
|
1140
1194
|
"aliases": [],
|
|
1141
1195
|
"args": {},
|
|
@@ -1309,5 +1363,5 @@
|
|
|
1309
1363
|
"enableJsonFlag": false
|
|
1310
1364
|
}
|
|
1311
1365
|
},
|
|
1312
|
-
"version": "0.
|
|
1366
|
+
"version": "0.10.0"
|
|
1313
1367
|
}
|