@softure-ai/mailing 0.2.4 → 0.2.5
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/CHANGELOG.md +16 -0
- package/README.md +16 -4
- package/dist/cli/run.d.ts.map +1 -1
- package/dist/cli/run.js +74 -19
- package/dist/cli/run.js.map +1 -1
- package/dist/contract.d.ts +9 -1
- package/dist/contract.d.ts.map +1 -1
- package/dist/index.d.ts +1 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +1 -1
- package/dist/options.d.ts +3 -0
- package/dist/options.d.ts.map +1 -1
- package/dist/options.js +10 -0
- package/dist/options.js.map +1 -1
- package/dist/server/deliveries.d.ts.map +1 -1
- package/dist/server/deliveries.js +3 -2
- package/dist/server/deliveries.js.map +1 -1
- package/dist/server/send-mail.d.ts +6 -0
- package/dist/server/send-mail.d.ts.map +1 -1
- package/dist/server/send-mail.js +30 -5
- package/dist/server/send-mail.js.map +1 -1
- package/dist/server/validate-mail.d.ts +3 -1
- package/dist/server/validate-mail.d.ts.map +1 -1
- package/dist/server/validate-mail.js +5 -2
- package/dist/server/validate-mail.js.map +1 -1
- package/module.json +1 -1
- package/package.json +1 -1
- package/src/cli/run.ts +84 -20
- package/src/contract.ts +9 -1
- package/src/index.ts +1 -1
- package/src/options.ts +12 -0
- package/src/server/deliveries.ts +3 -2
- package/src/server/send-mail.ts +27 -5
- package/src/server/validate-mail.ts +7 -2
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"deliveries.js","sourceRoot":"","sources":["../../src/server/deliveries.ts"],"names":[],"mappings":"AAAA,kGAAkG;AAClG,mGAAmG;AACnG,mGAAmG;AACnG,kGAAkG;AAClG,iGAAiG;AACjG,8FAA8F;AAC9F,8FAA8F;AAC9F,OAAO,EAAsB,MAAM,kBAAkB,CAAC;AAEtD,OAAO,EAAE,GAAG,EAAE,EAAE,EAAE,GAAG,EAAE,EAAE,EAAE,EAAE,EAAE,GAAG,EAAY,MAAM,aAAa,CAAC;AAClE,OAAO,EAAE,UAAU,EAAE,MAAM,eAAe,CAAC;AAC3C,OAAO,EAAE,mBAAmB,EAAE,kBAAkB,EAA4C,MAAM,gBAAgB,CAAC;AACnH,OAAO,EAAE,oBAAoB,EAAE,sBAAsB,EAAE,0BAA0B,EAAE,MAAM,eAAe,CAAC;AACzG,OAAO,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAC1C,OAAO,EAAE,iBAAiB,EAAE,MAAM,cAAc,CAAC;AACjD,OAAO,EAAE,QAAQ,EAAE,MAAM,gBAAgB,CAAC;
|
|
1
|
+
{"version":3,"file":"deliveries.js","sourceRoot":"","sources":["../../src/server/deliveries.ts"],"names":[],"mappings":"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"}
|
|
@@ -2,6 +2,7 @@ import { type Err, type Ok, type SoftureConfig } from "@softure-ai/core";
|
|
|
2
2
|
import type { Queryable } from "@softure-ai/db";
|
|
3
3
|
import { type OutgoingMail, type ProviderMessage, type SendMailOptions, type SendMailResult } from "../contract.js";
|
|
4
4
|
import { type Env } from "./unsubscribe-link.js";
|
|
5
|
+
import { type ValidMail } from "./validate-mail.js";
|
|
5
6
|
/**
|
|
6
7
|
* What `sendMail` needs: the app's configuration and, for list mail, the database handle (the
|
|
7
8
|
* suppression check reads it). Transactional mail needs no `db`.
|
|
@@ -26,6 +27,11 @@ export declare function sendMail(context: MailContext, mail: OutgoingMail, optio
|
|
|
26
27
|
* code can send list mail to a real recipient past the suppression list.
|
|
27
28
|
*/
|
|
28
29
|
export declare function sendMailUnchecked(config: SoftureConfig, mail: OutgoingMail, options?: SendMailOptions): Promise<SendMailResult>;
|
|
30
|
+
/**
|
|
31
|
+
* The sender of `mail`: its named sender of `mailing({ senders })`, `from` when it names none, or `null` when the name
|
|
32
|
+
* is not configured (the mail must not go out: a request cannot pick a sender the app does not have).
|
|
33
|
+
*/
|
|
34
|
+
export declare function resolveSender(config: SoftureConfig, mail: Pick<ValidMail, "sender">): string | null;
|
|
29
35
|
/** Why `previewMail` cannot render a mail: invalid input (with the fields), or list mail without the secret. */
|
|
30
36
|
export type MailPreviewFailure = (Err<"mailing.invalid_input"> & {
|
|
31
37
|
readonly fields: readonly string[];
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"send-mail.d.ts","sourceRoot":"","sources":["../../src/server/send-mail.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"send-mail.d.ts","sourceRoot":"","sources":["../../src/server/send-mail.ts"],"names":[],"mappings":"AAOA,OAAO,EAAO,KAAK,GAAG,EAAM,KAAK,EAAE,EAAkB,KAAK,aAAa,EAAE,MAAM,kBAAkB,CAAC;AAClG,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,gBAAgB,CAAC;AAEhD,OAAO,EAKL,KAAK,YAAY,EAEjB,KAAK,eAAe,EAEpB,KAAK,eAAe,EACpB,KAAK,cAAc,EACpB,MAAM,gBAAgB,CAAC;AAKxB,OAAO,EAAwG,KAAK,GAAG,EAAE,MAAM,uBAAuB,CAAC;AACvJ,OAAO,EAAgB,KAAK,SAAS,EAAE,MAAM,oBAAoB,CAAC;AAElE;;;GAGG;AACH,MAAM,WAAW,WAAW;IAC1B,QAAQ,CAAC,MAAM,EAAE,aAAa,CAAC;IAC/B,QAAQ,CAAC,EAAE,CAAC,EAAE,SAAS,CAAC;CACzB;AAED;;;;;;;;GAQG;AACH,wBAAsB,QAAQ,CAAC,OAAO,EAAE,WAAW,EAAE,IAAI,EAAE,YAAY,EAAE,OAAO,GAAE,eAAoB,GAAG,OAAO,CAAC,cAAc,CAAC,CAqB/H;AAED;;;;GAIG;AACH,wBAAsB,iBAAiB,CAAC,MAAM,EAAE,aAAa,EAAE,IAAI,EAAE,YAAY,EAAE,OAAO,GAAE,eAAoB,GAAG,OAAO,CAAC,cAAc,CAAC,CAezI;AAsBD;;;GAGG;AACH,wBAAgB,aAAa,CAAC,MAAM,EAAE,aAAa,EAAE,IAAI,EAAE,IAAI,CAAC,SAAS,EAAE,QAAQ,CAAC,GAAG,MAAM,GAAG,IAAI,CAInG;AAYD,gHAAgH;AAChH,MAAM,MAAM,kBAAkB,GAC1B,CAAC,GAAG,CAAC,uBAAuB,CAAC,GAAG;IAAE,QAAQ,CAAC,MAAM,EAAE,SAAS,MAAM,EAAE,CAAA;CAAE,CAAC,GACvE,CAAC,GAAG,CAAC,qBAAqB,CAAC,GAAG;IAAE,QAAQ,CAAC,KAAK,EAAE,uBAAuB,CAAA;CAAE,CAAC,CAAC;AAE/E,MAAM,MAAM,iBAAiB,GAAG,EAAE,CAAC,eAAe,CAAC,GAAG,kBAAkB,CAAC;AAEzE,MAAM,WAAW,kBAAmB,SAAQ,eAAe;IACzD,oEAAoE;IACpE,QAAQ,CAAC,GAAG,CAAC,EAAE,GAAG,CAAC;CACpB;AAED;;;;;;GAMG;AACH,wBAAgB,WAAW,CAAC,MAAM,EAAE,aAAa,EAAE,IAAI,EAAE,YAAY,EAAE,OAAO,GAAE,kBAAuB,GAAG,iBAAiB,CAQ1H"}
|
package/dist/server/send-mail.js
CHANGED
|
@@ -1,7 +1,8 @@
|
|
|
1
1
|
// Sends one mail through the configured provider, with three rules: it never throws for a failed
|
|
2
2
|
// send (every failure is a result), nothing of the mail (address, subject, body, key) reaches a log
|
|
3
3
|
// or the result, and `headers` cannot replace the envelope or the sender (a mail's own reply-to is
|
|
4
|
-
// the `replyTo` field, checked like `to
|
|
4
|
+
// the `replyTo` field, checked like `to`; its sender is a name of `mailing({ senders })`, never an
|
|
5
|
+
// address). Attachments go only to a provider that declares it delivers them, and a
|
|
5
6
|
// log line describes them by count, content type and size, never by name or content. List mail (any kind but `transactional`) also gets a signed unsubscribe
|
|
6
7
|
// link in a footer and the RFC 8058 headers, and is refused for a recipient who unsubscribed.
|
|
7
8
|
import { err, ok, selectMessages } from "@softure-ai/core";
|
|
@@ -29,6 +30,8 @@ export async function sendMail(context, mail, options = {}) {
|
|
|
29
30
|
return err("mailing.invalid_input");
|
|
30
31
|
}
|
|
31
32
|
const valid = validation.value;
|
|
33
|
+
if (resolveSender(context.config, valid) === null)
|
|
34
|
+
return refuseSender(provider, valid);
|
|
32
35
|
if (!canCarryAttachments(provider, valid))
|
|
33
36
|
return refuseAttachments(provider, valid);
|
|
34
37
|
const secret = readUnsubscribeSecrets().current;
|
|
@@ -53,6 +56,8 @@ export async function sendMailUnchecked(config, mail, options = {}) {
|
|
|
53
56
|
logFailure(provider, "mailing.invalid_input", { fields: validation.fields });
|
|
54
57
|
return err("mailing.invalid_input");
|
|
55
58
|
}
|
|
59
|
+
if (resolveSender(config, validation.value) === null)
|
|
60
|
+
return refuseSender(provider, validation.value);
|
|
56
61
|
if (!canCarryAttachments(provider, validation.value))
|
|
57
62
|
return refuseAttachments(provider, validation.value);
|
|
58
63
|
const secret = readUnsubscribeSecrets().current;
|
|
@@ -80,6 +85,20 @@ async function deliver(provider, message, timeoutMs) {
|
|
|
80
85
|
function canCarryAttachments(provider, mail) {
|
|
81
86
|
return mail.attachments.length === 0 || provider.supportsAttachments === true;
|
|
82
87
|
}
|
|
88
|
+
/**
|
|
89
|
+
* The sender of `mail`: its named sender of `mailing({ senders })`, `from` when it names none, or `null` when the name
|
|
90
|
+
* is not configured (the mail must not go out: a request cannot pick a sender the app does not have).
|
|
91
|
+
*/
|
|
92
|
+
export function resolveSender(config, mail) {
|
|
93
|
+
const { from, senders = {} } = getMailingOptions(config);
|
|
94
|
+
if (mail.sender === null)
|
|
95
|
+
return from;
|
|
96
|
+
return Object.hasOwn(senders, mail.sender) ? (senders[mail.sender] ?? null) : null;
|
|
97
|
+
}
|
|
98
|
+
function refuseSender(provider, mail) {
|
|
99
|
+
logFailure(provider, "mailing.invalid_input", { fields: ["sender"], attachments: mail.attachments });
|
|
100
|
+
return err("mailing.invalid_input");
|
|
101
|
+
}
|
|
83
102
|
function refuseAttachments(provider, mail) {
|
|
84
103
|
logFailure(provider, "mailing.invalid_input", { fields: ["attachments"], cause: "provider_without_attachments", attachments: mail.attachments });
|
|
85
104
|
return err("mailing.invalid_input");
|
|
@@ -96,6 +115,8 @@ export function previewMail(config, mail, options = {}) {
|
|
|
96
115
|
const validation = validateMail(mail, sendOptions, getMailingOptions(config).attachments);
|
|
97
116
|
if (!validation.ok)
|
|
98
117
|
return { ...err("mailing.invalid_input"), fields: validation.fields };
|
|
118
|
+
if (resolveSender(config, validation.value) === null)
|
|
119
|
+
return { ...err("mailing.invalid_input"), fields: ["sender"] };
|
|
99
120
|
const secret = readUnsubscribeSecrets(env).current;
|
|
100
121
|
if (validation.value.kind !== TRANSACTIONAL_KIND && secret === null)
|
|
101
122
|
return { ...err("mailing.unavailable"), cause: "no_unsubscribe_secret" };
|
|
@@ -128,12 +149,16 @@ async function checkListMail(context, mail, secret) {
|
|
|
128
149
|
}
|
|
129
150
|
}
|
|
130
151
|
/**
|
|
131
|
-
* The message the provider receives: the
|
|
132
|
-
* mail the footer and headers signed with `secret` (which the caller checked is set).
|
|
152
|
+
* The message the provider receives: the resolved sender (see `resolveSender`), the mail's or the configured
|
|
153
|
+
* reply-to, and for list mail the footer and headers signed with `secret` (which the caller checked is set).
|
|
133
154
|
*/
|
|
134
155
|
function composeMessage(config, mail, secret) {
|
|
135
|
-
const {
|
|
136
|
-
const { idempotencyKey, kind, replyTo: mailReplyTo, attachments, ...content } = mail;
|
|
156
|
+
const { replyTo } = getMailingOptions(config);
|
|
157
|
+
const { idempotencyKey, kind, replyTo: mailReplyTo, sender, attachments, ...content } = mail;
|
|
158
|
+
const from = resolveSender(config, { sender });
|
|
159
|
+
// Every caller refused an unknown sender before composing.
|
|
160
|
+
if (from === null)
|
|
161
|
+
throw new Error("@softure-ai/mailing: composeMessage got a sender the config does not have");
|
|
137
162
|
const envelope = { from, replyTo: mailReplyTo ?? replyTo ?? null, idempotencyKey, ...(attachments.length === 0 ? {} : { attachments }) };
|
|
138
163
|
if (kind === TRANSACTIONAL_KIND || secret === null)
|
|
139
164
|
return { ...content, ...envelope };
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"send-mail.js","sourceRoot":"","sources":["../../src/server/send-mail.ts"],"names":[],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"send-mail.js","sourceRoot":"","sources":["../../src/server/send-mail.ts"],"names":[],"mappings":"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"}
|
|
@@ -8,6 +8,8 @@ export interface ValidMail {
|
|
|
8
8
|
readonly headers: Readonly<Record<string, string>>;
|
|
9
9
|
/** The mail's own reply-to; null to use the configured one. */
|
|
10
10
|
readonly replyTo: string | null;
|
|
11
|
+
/** The name of a configured sender; null for `from`. Its value is looked up in the config (`resolveSender`). */
|
|
12
|
+
readonly sender: string | null;
|
|
11
13
|
/** `transactional` or a list kind. */
|
|
12
14
|
readonly kind: string;
|
|
13
15
|
readonly idempotencyKey: string | null;
|
|
@@ -24,7 +26,7 @@ export type MailValidation = {
|
|
|
24
26
|
/**
|
|
25
27
|
* Checks one mail and its send options, its attachments against `limits` (default: the module's defaults; `sendMail`
|
|
26
28
|
* passes the configured ones). `fields` lists what failed (`to`, `subject`, `text`, `html`, `headers`, `replyTo`,
|
|
27
|
-
* `kind`, `attachments`, `idempotencyKey`, or `mail` when the input is not an object).
|
|
29
|
+
* `sender` (its shape only: whether the app configured it is `resolveSender`'s check), `kind`, `attachments`, `idempotencyKey`, or `mail` when the input is not an object).
|
|
28
30
|
*/
|
|
29
31
|
export declare function validateMail(mail: unknown, options?: unknown, limits?: AttachmentLimits): MailValidation;
|
|
30
32
|
//# sourceMappingURL=validate-mail.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"validate-mail.d.ts","sourceRoot":"","sources":["../../src/server/validate-mail.ts"],"names":[],"mappings":"AAIA,OAAO,EAAyF,KAAK,gBAAgB,EAAE,MAAM,mBAAmB,CAAC;AACjJ,OAAO,EAAsB,KAAK,cAAc,EAAE,MAAM,gBAAgB,CAAC;
|
|
1
|
+
{"version":3,"file":"validate-mail.d.ts","sourceRoot":"","sources":["../../src/server/validate-mail.ts"],"names":[],"mappings":"AAIA,OAAO,EAAyF,KAAK,gBAAgB,EAAE,MAAM,mBAAmB,CAAC;AACjJ,OAAO,EAAsB,KAAK,cAAc,EAAE,MAAM,gBAAgB,CAAC;AAqEzE,MAAM,WAAW,SAAS;IACxB,QAAQ,CAAC,EAAE,EAAE,MAAM,CAAC;IACpB,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;IACzB,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,IAAI,EAAE,MAAM,GAAG,IAAI,CAAC;IAC7B,QAAQ,CAAC,OAAO,EAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,MAAM,CAAC,CAAC,CAAC;IACnD,+DAA+D;IAC/D,QAAQ,CAAC,OAAO,EAAE,MAAM,GAAG,IAAI,CAAC;IAChC,gHAAgH;IAChH,QAAQ,CAAC,MAAM,EAAE,MAAM,GAAG,IAAI,CAAC;IAC/B,sCAAsC;IACtC,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,cAAc,EAAE,MAAM,GAAG,IAAI,CAAC;IACvC,oCAAoC;IACpC,QAAQ,CAAC,WAAW,EAAE,SAAS,cAAc,EAAE,CAAC;CACjD;AAED,MAAM,MAAM,cAAc,GAAG;IAAE,QAAQ,CAAC,EAAE,EAAE,IAAI,CAAC;IAAC,QAAQ,CAAC,KAAK,EAAE,SAAS,CAAA;CAAE,GAAG;IAAE,QAAQ,CAAC,EAAE,EAAE,KAAK,CAAC;IAAC,QAAQ,CAAC,MAAM,EAAE,SAAS,MAAM,EAAE,CAAA;CAAE,CAAC;AAE3I;;;;GAIG;AACH,wBAAgB,YAAY,CAAC,IAAI,EAAE,OAAO,EAAE,OAAO,GAAE,OAAY,EAAE,MAAM,GAAE,gBAA4C,GAAG,cAAc,CAwBvI"}
|
|
@@ -4,6 +4,7 @@ import { z } from "zod";
|
|
|
4
4
|
import { hasLineBreak, isHeaderName, isIdempotencyKey, isListMailHeader, isMailKind, isReservedHeader, isSingleAddress, MAX_SUBJECT_LENGTH } from "../address.js";
|
|
5
5
|
import { DEFAULT_ATTACHMENT_LIMITS, getContentTypeEssence, isAttachmentFilename, isContentType } from "../attachments.js";
|
|
6
6
|
import { TRANSACTIONAL_KIND } from "../contract.js";
|
|
7
|
+
import { SENDER_NAME } from "../options.js";
|
|
7
8
|
const headersSchema = z.record(z.string(), z.string()).superRefine((headers, context) => {
|
|
8
9
|
for (const [name, value] of Object.entries(headers)) {
|
|
9
10
|
if (!isHeaderName(name) || isReservedHeader(name) || hasLineBreak(value)) {
|
|
@@ -38,6 +39,7 @@ const mailFields = {
|
|
|
38
39
|
.optional(),
|
|
39
40
|
headers: headersSchema.optional(),
|
|
40
41
|
replyTo: z.string().trim().refine(isSingleAddress).optional(),
|
|
42
|
+
sender: z.string().regex(SENDER_NAME).optional(),
|
|
41
43
|
kind: z.string().refine(isMailKind).default(TRANSACTIONAL_KIND),
|
|
42
44
|
};
|
|
43
45
|
function createMailSchema(limits) {
|
|
@@ -64,7 +66,7 @@ const optionsSchema = z.object({
|
|
|
64
66
|
/**
|
|
65
67
|
* Checks one mail and its send options, its attachments against `limits` (default: the module's defaults; `sendMail`
|
|
66
68
|
* passes the configured ones). `fields` lists what failed (`to`, `subject`, `text`, `html`, `headers`, `replyTo`,
|
|
67
|
-
* `kind`, `attachments`, `idempotencyKey`, or `mail` when the input is not an object).
|
|
69
|
+
* `sender` (its shape only: whether the app configured it is `resolveSender`'s check), `kind`, `attachments`, `idempotencyKey`, or `mail` when the input is not an object).
|
|
68
70
|
*/
|
|
69
71
|
export function validateMail(mail, options = {}, limits = DEFAULT_ATTACHMENT_LIMITS) {
|
|
70
72
|
const parsedMail = getMailSchema(limits).safeParse(mail);
|
|
@@ -74,7 +76,7 @@ export function validateMail(mail, options = {}, limits = DEFAULT_ATTACHMENT_LIM
|
|
|
74
76
|
const fields = new Set(issues.map((issue) => (issue.path.length === 0 ? "mail" : String(issue.path[0]))));
|
|
75
77
|
return { ok: false, fields: [...fields] };
|
|
76
78
|
}
|
|
77
|
-
const { to, subject, text, html, headers, replyTo, kind, attachments = [] } = parsedMail.data;
|
|
79
|
+
const { to, subject, text, html, headers, replyTo, sender, kind, attachments = [] } = parsedMail.data;
|
|
78
80
|
return {
|
|
79
81
|
ok: true,
|
|
80
82
|
value: {
|
|
@@ -84,6 +86,7 @@ export function validateMail(mail, options = {}, limits = DEFAULT_ATTACHMENT_LIM
|
|
|
84
86
|
html: html ?? null,
|
|
85
87
|
headers: headers ?? {},
|
|
86
88
|
replyTo: replyTo ?? null,
|
|
89
|
+
sender: sender ?? null,
|
|
87
90
|
kind,
|
|
88
91
|
idempotencyKey: parsedOptions.data.idempotencyKey ?? null,
|
|
89
92
|
attachments,
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"validate-mail.js","sourceRoot":"","sources":["../../src/server/validate-mail.ts"],"names":[],"mappings":"AAAA,iGAAiG;AACjG,uFAAuF;AACvF,OAAO,EAAE,CAAC,EAAE,MAAM,KAAK,CAAC;AACxB,OAAO,EAAE,YAAY,EAAE,YAAY,EAAE,gBAAgB,EAAE,gBAAgB,EAAE,UAAU,EAAE,gBAAgB,EAAE,eAAe,EAAE,kBAAkB,EAAE,MAAM,eAAe,CAAC;AAClK,OAAO,EAAE,yBAAyB,EAAE,qBAAqB,EAAE,oBAAoB,EAAE,aAAa,EAAyB,MAAM,mBAAmB,CAAC;AACjJ,OAAO,EAAE,kBAAkB,EAAuB,MAAM,gBAAgB,CAAC;
|
|
1
|
+
{"version":3,"file":"validate-mail.js","sourceRoot":"","sources":["../../src/server/validate-mail.ts"],"names":[],"mappings":"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"}
|
package/module.json
CHANGED
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@softure-ai/mailing",
|
|
3
|
-
"version": "0.2.
|
|
3
|
+
"version": "0.2.5",
|
|
4
4
|
"description": "SOFTURE AI mailing module: sendMail over a provider adapter (Resend first) with plain-text and HTML bodies, sender and reply-to from config, idempotency keys, a timeout and a typed result; signed one-click unsubscribe (RFC 8058) with a suppression list for list mail; an exactly-once delivery ledger, campaigns sent from a content file by the softure-mail command, and a sender DNS check; a fake provider for tests.",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"type": "module",
|
package/src/cli/run.ts
CHANGED
|
@@ -96,11 +96,13 @@ import Writes deliveries the app made before it adopted the module into the l
|
|
|
96
96
|
stops the import before anything is written.
|
|
97
97
|
--dry-run check the file and change nothing
|
|
98
98
|
|
|
99
|
-
dns Checks SPF, DKIM and DMARC for
|
|
99
|
+
dns Checks SPF, DKIM and DMARC for every sender domain (default: the domains of "from"
|
|
100
|
+
and "senders"; the reply-to and inbound checks go with the domain of "from").
|
|
100
101
|
--domain <domain> check this domain instead
|
|
101
102
|
--dkim-selector <name> DKIM selector to look up (default resend; repeatable)
|
|
102
103
|
--spf-host <host> where SPF is published (default the domain; repeatable;
|
|
103
|
-
Resend publishes it on send.<domain>)
|
|
104
|
+
Resend publishes it on send.<domain>); with several sender
|
|
105
|
+
domains, a host counts for the domain it sits under
|
|
104
106
|
--dmarc-policy <p> require at least this DMARC policy (quarantine or reject)
|
|
105
107
|
and pct=100; a weaker record fails
|
|
106
108
|
--dmarc-sp <p> require at least this subdomain policy (sp, else p)
|
|
@@ -108,7 +110,8 @@ dns Checks SPF, DKIM and DMARC for the sender domain (default: the domain
|
|
|
108
110
|
--dmarc-aspf <a> require this SPF alignment (r or s; absent counts as r)
|
|
109
111
|
--reply-to <address> check that this address's domain accepts mail (MX, one SPF)
|
|
110
112
|
(default: replyTo of the config, when --domain is not given)
|
|
111
|
-
--return-path <host> a return-path host that must be a CNAME or have MX (repeatable
|
|
113
|
+
--return-path <host> a return-path host that must be a CNAME or have MX (repeatable;
|
|
114
|
+
with several sender domains, for the domain it sits under)
|
|
112
115
|
--resend-return-path check Resend's send.<domain> and rsend.<domain> CNAMEs
|
|
113
116
|
--inbound cloudflare check that Cloudflare Email Routing receives the reply-to domain's
|
|
114
117
|
mail (its MX and one SPF record that includes it)
|
|
@@ -333,26 +336,86 @@ function parseDmarcExpectation(values: ParsedValues): DmarcExpectation | undefin
|
|
|
333
336
|
return Object.keys(expectation).length === 0 ? undefined : expectation;
|
|
334
337
|
}
|
|
335
338
|
|
|
336
|
-
|
|
337
|
-
|
|
338
|
-
|
|
339
|
-
|
|
340
|
-
|
|
341
|
-
|
|
342
|
-
|
|
343
|
-
|
|
344
|
-
|
|
345
|
-
|
|
346
|
-
|
|
339
|
+
type DnsCommand = Extract<Command, { kind: "dns" }>;
|
|
340
|
+
|
|
341
|
+
/** One domain `softure-mail dns` checks, with the hosts given for it and, for the first, the reply-path checks. */
|
|
342
|
+
interface DnsTarget {
|
|
343
|
+
readonly domain: string;
|
|
344
|
+
readonly spfHosts: readonly string[] | undefined;
|
|
345
|
+
readonly returnPathHosts: readonly string[];
|
|
346
|
+
readonly replyTo: string | undefined;
|
|
347
|
+
readonly inbound: "cloudflare" | undefined;
|
|
348
|
+
}
|
|
349
|
+
|
|
350
|
+
async function runDns(command: DnsCommand, options: RunMailCliOptions, output: CliOutput): Promise<number> {
|
|
351
|
+
const targets = getDnsTargets(command, options.config);
|
|
352
|
+
if (typeof targets === "string") {
|
|
353
|
+
output.error(`softure-mail dns: ${targets}`);
|
|
354
|
+
return EXIT_FAILED;
|
|
355
|
+
}
|
|
356
|
+
let failed = 0;
|
|
357
|
+
for (const target of targets) failed += await checkDnsTarget(command, target, options, output);
|
|
358
|
+
return failed === 0 ? EXIT_OK : EXIT_FAILED;
|
|
359
|
+
}
|
|
360
|
+
|
|
361
|
+
/**
|
|
362
|
+
* The domains to check: `--domain` alone, else the distinct domains of `from` and `senders`, `from`'s first. With
|
|
363
|
+
* several, a host option goes to the domain it sits under (the longest that matches); one under none is an error.
|
|
364
|
+
*/
|
|
365
|
+
function getDnsTargets(command: DnsCommand, config: SoftureConfig | undefined): DnsTarget[] | string {
|
|
366
|
+
const single = (domain: string, replyTo: string | undefined): DnsTarget[] => [
|
|
367
|
+
{ domain, spfHosts: command.spfHosts, returnPathHosts: command.returnPathHosts, replyTo, inbound: command.inbound },
|
|
368
|
+
];
|
|
369
|
+
if (command.domain !== undefined) return single(command.domain, command.replyTo);
|
|
370
|
+
if (config === undefined) return "pass --domain <domain>, or run it with the app's config to check the sender's domain";
|
|
371
|
+
const mailing = getMailingOptions(config);
|
|
372
|
+
const domains = [...new Set([mailing.from, ...Object.values(mailing.senders ?? {})].map((sender) => getSenderDomain(sender).toLowerCase()))];
|
|
373
|
+
const replyTo = command.replyTo ?? mailing.replyTo;
|
|
374
|
+
const [first = ""] = domains;
|
|
375
|
+
if (domains.length === 1) return single(first, replyTo);
|
|
376
|
+
|
|
377
|
+
const spfHosts = assignHostsToDomains("--spf-host", command.spfHosts ?? [], domains);
|
|
378
|
+
if (typeof spfHosts === "string") return spfHosts;
|
|
379
|
+
const returnPathHosts = assignHostsToDomains("--return-path", command.returnPathHosts, domains);
|
|
380
|
+
if (typeof returnPathHosts === "string") return returnPathHosts;
|
|
381
|
+
return domains.map((domain, index) => ({
|
|
382
|
+
domain,
|
|
383
|
+
spfHosts: spfHosts.get(domain),
|
|
384
|
+
returnPathHosts: returnPathHosts.get(domain) ?? [],
|
|
385
|
+
replyTo: index === 0 ? replyTo : undefined,
|
|
386
|
+
inbound: index === 0 ? command.inbound : undefined,
|
|
387
|
+
}));
|
|
388
|
+
}
|
|
389
|
+
|
|
390
|
+
/** The hosts of `option` by the domain each sits under, or the error for one under none of `domains`. */
|
|
391
|
+
function assignHostsToDomains(option: string, hosts: readonly string[], domains: readonly string[]): Map<string, string[]> | string {
|
|
392
|
+
const byDomain = new Map<string, string[]>();
|
|
393
|
+
for (const host of hosts) {
|
|
394
|
+
const domain = findHostDomain(host, domains);
|
|
395
|
+
if (domain === null) return `${option} ${host} sits under none of the sender domains (${domains.join(", ")})`;
|
|
396
|
+
byDomain.set(domain, [...(byDomain.get(domain) ?? []), host]);
|
|
347
397
|
}
|
|
348
|
-
|
|
398
|
+
return byDomain;
|
|
399
|
+
}
|
|
400
|
+
|
|
401
|
+
/** The longest of `domains` that `host` is or sits under, or `null`. */
|
|
402
|
+
function findHostDomain(host: string, domains: readonly string[]): string | null {
|
|
403
|
+
const name = host.trim().toLowerCase().replace(/\.$/, "");
|
|
404
|
+
const matches = domains.filter((domain) => name === domain || name.endsWith(`.${domain}`));
|
|
405
|
+
return matches.reduce<string | null>((longest, domain) => (longest === null || domain.length > longest.length ? domain : longest), null);
|
|
406
|
+
}
|
|
407
|
+
|
|
408
|
+
/** Checks one domain and prints its report; returns how many checks failed. */
|
|
409
|
+
async function checkDnsTarget(command: DnsCommand, target: DnsTarget, options: RunMailCliOptions, output: CliOutput): Promise<number> {
|
|
410
|
+
const { domain, replyTo } = target;
|
|
411
|
+
const returnPath: ReturnPathHost[] = [...(command.resendReturnPath ? resendReturnPath(domain) : []), ...target.returnPathHosts.map((host) => ({ host }))];
|
|
349
412
|
const report = await checkSenderDns(domain, {
|
|
350
413
|
...(command.dkimSelectors === undefined ? {} : { dkimSelectors: command.dkimSelectors }),
|
|
351
|
-
...(
|
|
414
|
+
...(target.spfHosts === undefined ? {} : { spfHosts: target.spfHosts }),
|
|
352
415
|
...(command.expectDmarc === undefined ? {} : { expectDmarc: command.expectDmarc }),
|
|
353
416
|
...(replyTo === undefined ? {} : { replyTo }),
|
|
354
417
|
returnPath,
|
|
355
|
-
...(
|
|
418
|
+
...(target.inbound === undefined ? {} : { inbound: target.inbound }),
|
|
356
419
|
...(options.resolveTxt === undefined ? {} : { resolveTxt: options.resolveTxt }),
|
|
357
420
|
...(options.resolveMx === undefined ? {} : { resolveMx: options.resolveMx }),
|
|
358
421
|
...(options.resolveCname === undefined ? {} : { resolveCname: options.resolveCname }),
|
|
@@ -376,15 +439,16 @@ async function runDns(command: Extract<Command, { kind: "dns" }>, options: RunMa
|
|
|
376
439
|
const failedReply = countFailed(reply);
|
|
377
440
|
const failedPaths = countFailed(paths);
|
|
378
441
|
const failedInbound = countFailed(inbound);
|
|
379
|
-
|
|
442
|
+
const failed = failedAuthentication + failedReply + failedPaths + failedInbound;
|
|
443
|
+
if (failed === 0) {
|
|
380
444
|
output.log("receivers can authenticate mail from this domain");
|
|
381
|
-
return
|
|
445
|
+
return 0;
|
|
382
446
|
}
|
|
383
447
|
if (failedAuthentication > 0) output.log(`${String(failedAuthentication)} check(s) failed: list mail from this domain will land in spam or be refused`);
|
|
384
448
|
if (failedReply > 0) output.log("the reply-to domain does not accept mail: replies will bounce");
|
|
385
449
|
if (failedPaths > 0) output.log(`${String(failedPaths)} return-path host(s) failed: the provider cannot use them for bounces`);
|
|
386
450
|
if (failedInbound > 0) output.log("the inbound service does not receive this domain's mail: replies will not reach it");
|
|
387
|
-
return
|
|
451
|
+
return failed;
|
|
388
452
|
}
|
|
389
453
|
|
|
390
454
|
async function runCampaign(command: Extract<Command, { kind: "campaign" }>, options: RunMailCliOptions, output: CliOutput): Promise<number> {
|
package/src/contract.ts
CHANGED
|
@@ -130,6 +130,11 @@ export interface OutgoingMail {
|
|
|
130
130
|
* operator). Replaces `mailing({ replyTo })` for this mail; without it the configured one is used.
|
|
131
131
|
*/
|
|
132
132
|
readonly replyTo?: string;
|
|
133
|
+
/**
|
|
134
|
+
* The name of a sender of `mailing({ senders })`, e.g. `alerts`; without it the mail goes out from `from`. Never an
|
|
135
|
+
* address, so a request can never choose the sender. An unknown name is `mailing.invalid_input` (`fields=sender`).
|
|
136
|
+
*/
|
|
137
|
+
readonly sender?: string;
|
|
133
138
|
/**
|
|
134
139
|
* `transactional` (the default) for mail the recipient needs whatever they unsubscribed from:
|
|
135
140
|
* password resets, receipts, account notices. Any other kebab-case name (e.g. `newsletter`) is
|
|
@@ -189,7 +194,10 @@ export type SendMailFailure = Err<MailingErrorCode> & { readonly httpStatus?: nu
|
|
|
189
194
|
|
|
190
195
|
export type SendMailResult = Ok<SentMail> | SendMailFailure;
|
|
191
196
|
|
|
192
|
-
/**
|
|
197
|
+
/**
|
|
198
|
+
* What a provider receives: a validated mail with the sender from the configuration (the mail's named sender, else
|
|
199
|
+
* `from`) and the mail's or the configured reply-to.
|
|
200
|
+
*/
|
|
193
201
|
export interface ProviderMessage {
|
|
194
202
|
readonly from: string;
|
|
195
203
|
readonly to: string;
|
package/src/index.ts
CHANGED
|
@@ -17,7 +17,7 @@ export const MODULE_ID = "mailing";
|
|
|
17
17
|
export const mailing = defineModule({
|
|
18
18
|
manifest: {
|
|
19
19
|
id: MODULE_ID,
|
|
20
|
-
version: "0.2.
|
|
20
|
+
version: "0.2.5",
|
|
21
21
|
dependsOn: { jobs: "*?" },
|
|
22
22
|
dbSchema: "mailing",
|
|
23
23
|
tables: ["suppressions", "campaigns", "deliveries"],
|
package/src/options.ts
CHANGED
|
@@ -23,6 +23,13 @@ const RESERVED_LINK_PARAMS: ReadonlySet<string> = new Set(["r", "status"]);
|
|
|
23
23
|
const LINK_PARAM = /^[A-Za-z][A-Za-z0-9_-]{0,31}$/;
|
|
24
24
|
|
|
25
25
|
const MAX_LINK_PARAMS = 8;
|
|
26
|
+
|
|
27
|
+
/** A name of `mailing({ senders })`, the value of `OutgoingMail.sender`: a letter, then letters, digits, `_` or `-`. */
|
|
28
|
+
export const SENDER_NAME = /^[A-Za-z][A-Za-z0-9_-]{0,31}$/;
|
|
29
|
+
|
|
30
|
+
const sendersSchema = z
|
|
31
|
+
.record(z.string(), z.string().trim().refine(isMailbox, "must be an address or Name <address>, e.g. Alerts <alerts@example.com>"))
|
|
32
|
+
.refine((senders) => Object.keys(senders).every((name) => SENDER_NAME.test(name)), "every name must be a letter, then letters, digits, _ or -, at most 32 characters");
|
|
26
33
|
const linkParamNames = z.array(z.string().regex(LINK_PARAM, "must be a query name: a letter, then letters, digits, _ or -, at most 32 characters"));
|
|
27
34
|
|
|
28
35
|
/** Both forms of `params`, normalised to required and optional names, with the limits on all names together. */
|
|
@@ -78,6 +85,11 @@ export const mailingOptionsSchema = z.strictObject({
|
|
|
78
85
|
* domain the provider signs (DKIM), or DMARC rejects the mail.
|
|
79
86
|
*/
|
|
80
87
|
from: z.string().trim().refine(isMailbox, "must be an address or Name <address>, e.g. Plan <hello@example.com>"),
|
|
88
|
+
/**
|
|
89
|
+
* Named extra senders a mail picks with `OutgoingMail.sender`, e.g. `{ alerts: "App <alerts@example.com>" }`. Each
|
|
90
|
+
* is validated like `from` and must sit on a domain the provider signs; `softure-mail dns` checks every one.
|
|
91
|
+
*/
|
|
92
|
+
senders: sendersSchema.optional(),
|
|
81
93
|
/** Where replies go; may sit on another domain than `from` (DMARC does not check it). */
|
|
82
94
|
replyTo: z.string().trim().refine(isSingleAddress, "must be one address, e.g. support@example.com").optional(),
|
|
83
95
|
/**
|
package/src/server/deliveries.ts
CHANGED
|
@@ -13,7 +13,7 @@ import { HALTING_ERROR_CODES, TRANSACTIONAL_KIND, type MailingErrorCode, type Ou
|
|
|
13
13
|
import { DEFAULT_MAX_ATTEMPTS, DEFAULT_STALE_CLAIM_MS, DEFAULT_UNCERTAIN_CLAIM_MS } from "../options.js";
|
|
14
14
|
import { deliveries } from "../schema.js";
|
|
15
15
|
import { getMailingOptions } from "./options.js";
|
|
16
|
-
import { sendMail } from "./send-mail.js";
|
|
16
|
+
import { resolveSender, sendMail } from "./send-mail.js";
|
|
17
17
|
import { isSuppressed } from "./suppressions.js";
|
|
18
18
|
import { getRecipientKey } from "./unsubscribe-link.js";
|
|
19
19
|
import { validateMail } from "./validate-mail.js";
|
|
@@ -167,7 +167,8 @@ export async function forecastDelivery(ctx: DeliveryContext, delivery: Delivery,
|
|
|
167
167
|
if (age <= windows.staleClaimMs) return { status: "in-flight" };
|
|
168
168
|
if (age > windows.uncertainClaimMs && !windows.retakeUncertain) return { status: "uncertain" };
|
|
169
169
|
}
|
|
170
|
-
|
|
170
|
+
const validation = validateMail(delivery.mail, {}, getMailingOptions(ctx.config).attachments);
|
|
171
|
+
if (!validation.ok || resolveSender(ctx.config, validation.value) === null) return { status: "rejected", reason: "mailing.invalid_input" };
|
|
171
172
|
if (kind !== TRANSACTIONAL_KIND && (await isSuppressed(ctx, delivery.mail.to))) return { status: "rejected", reason: "mailing.suppressed" };
|
|
172
173
|
return { status: "send" };
|
|
173
174
|
}
|
package/src/server/send-mail.ts
CHANGED
|
@@ -1,7 +1,8 @@
|
|
|
1
1
|
// Sends one mail through the configured provider, with three rules: it never throws for a failed
|
|
2
2
|
// send (every failure is a result), nothing of the mail (address, subject, body, key) reaches a log
|
|
3
3
|
// or the result, and `headers` cannot replace the envelope or the sender (a mail's own reply-to is
|
|
4
|
-
// the `replyTo` field, checked like `to
|
|
4
|
+
// the `replyTo` field, checked like `to`; its sender is a name of `mailing({ senders })`, never an
|
|
5
|
+
// address). Attachments go only to a provider that declares it delivers them, and a
|
|
5
6
|
// log line describes them by count, content type and size, never by name or content. List mail (any kind but `transactional`) also gets a signed unsubscribe
|
|
6
7
|
// link in a footer and the RFC 8058 headers, and is refused for a recipient who unsubscribed.
|
|
7
8
|
import { err, type Err, ok, type Ok, selectMessages, type SoftureConfig } from "@softure-ai/core";
|
|
@@ -53,6 +54,7 @@ export async function sendMail(context: MailContext, mail: OutgoingMail, options
|
|
|
53
54
|
return err("mailing.invalid_input");
|
|
54
55
|
}
|
|
55
56
|
const valid = validation.value;
|
|
57
|
+
if (resolveSender(context.config, valid) === null) return refuseSender(provider, valid);
|
|
56
58
|
if (!canCarryAttachments(provider, valid)) return refuseAttachments(provider, valid);
|
|
57
59
|
const secret = readUnsubscribeSecrets().current;
|
|
58
60
|
if (valid.kind !== TRANSACTIONAL_KIND) {
|
|
@@ -78,6 +80,7 @@ export async function sendMailUnchecked(config: SoftureConfig, mail: OutgoingMai
|
|
|
78
80
|
logFailure(provider, "mailing.invalid_input", { fields: validation.fields });
|
|
79
81
|
return err("mailing.invalid_input");
|
|
80
82
|
}
|
|
83
|
+
if (resolveSender(config, validation.value) === null) return refuseSender(provider, validation.value);
|
|
81
84
|
if (!canCarryAttachments(provider, validation.value)) return refuseAttachments(provider, validation.value);
|
|
82
85
|
const secret = readUnsubscribeSecrets().current;
|
|
83
86
|
if (validation.value.kind !== TRANSACTIONAL_KIND && secret === null) {
|
|
@@ -107,6 +110,21 @@ function canCarryAttachments(provider: MailProvider, mail: ValidMail): boolean {
|
|
|
107
110
|
return mail.attachments.length === 0 || provider.supportsAttachments === true;
|
|
108
111
|
}
|
|
109
112
|
|
|
113
|
+
/**
|
|
114
|
+
* The sender of `mail`: its named sender of `mailing({ senders })`, `from` when it names none, or `null` when the name
|
|
115
|
+
* is not configured (the mail must not go out: a request cannot pick a sender the app does not have).
|
|
116
|
+
*/
|
|
117
|
+
export function resolveSender(config: SoftureConfig, mail: Pick<ValidMail, "sender">): string | null {
|
|
118
|
+
const { from, senders = {} } = getMailingOptions(config);
|
|
119
|
+
if (mail.sender === null) return from;
|
|
120
|
+
return Object.hasOwn(senders, mail.sender) ? (senders[mail.sender] ?? null) : null;
|
|
121
|
+
}
|
|
122
|
+
|
|
123
|
+
function refuseSender(provider: MailProvider, mail: ValidMail): SendMailResult {
|
|
124
|
+
logFailure(provider, "mailing.invalid_input", { fields: ["sender"], attachments: mail.attachments });
|
|
125
|
+
return err("mailing.invalid_input");
|
|
126
|
+
}
|
|
127
|
+
|
|
110
128
|
function refuseAttachments(provider: MailProvider, mail: ValidMail): SendMailResult {
|
|
111
129
|
logFailure(provider, "mailing.invalid_input", { fields: ["attachments"], cause: "provider_without_attachments", attachments: mail.attachments });
|
|
112
130
|
return err("mailing.invalid_input");
|
|
@@ -135,6 +153,7 @@ export function previewMail(config: SoftureConfig, mail: OutgoingMail, options:
|
|
|
135
153
|
const { env, ...sendOptions } = options;
|
|
136
154
|
const validation = validateMail(mail, sendOptions, getMailingOptions(config).attachments);
|
|
137
155
|
if (!validation.ok) return { ...err("mailing.invalid_input"), fields: validation.fields };
|
|
156
|
+
if (resolveSender(config, validation.value) === null) return { ...err("mailing.invalid_input"), fields: ["sender"] };
|
|
138
157
|
const secret = readUnsubscribeSecrets(env).current;
|
|
139
158
|
if (validation.value.kind !== TRANSACTIONAL_KIND && secret === null) return { ...err("mailing.unavailable"), cause: "no_unsubscribe_secret" };
|
|
140
159
|
return ok(composeMessage(config, validation.value, secret));
|
|
@@ -170,12 +189,15 @@ async function checkListMail(context: MailContext, mail: ValidMail, secret: stri
|
|
|
170
189
|
}
|
|
171
190
|
|
|
172
191
|
/**
|
|
173
|
-
* The message the provider receives: the
|
|
174
|
-
* mail the footer and headers signed with `secret` (which the caller checked is set).
|
|
192
|
+
* The message the provider receives: the resolved sender (see `resolveSender`), the mail's or the configured
|
|
193
|
+
* reply-to, and for list mail the footer and headers signed with `secret` (which the caller checked is set).
|
|
175
194
|
*/
|
|
176
195
|
function composeMessage(config: SoftureConfig, mail: ValidMail, secret: string | null): ProviderMessage {
|
|
177
|
-
const {
|
|
178
|
-
const { idempotencyKey, kind, replyTo: mailReplyTo, attachments, ...content } = mail;
|
|
196
|
+
const { replyTo } = getMailingOptions(config);
|
|
197
|
+
const { idempotencyKey, kind, replyTo: mailReplyTo, sender, attachments, ...content } = mail;
|
|
198
|
+
const from = resolveSender(config, { sender });
|
|
199
|
+
// Every caller refused an unknown sender before composing.
|
|
200
|
+
if (from === null) throw new Error("@softure-ai/mailing: composeMessage got a sender the config does not have");
|
|
179
201
|
const envelope = { from, replyTo: mailReplyTo ?? replyTo ?? null, idempotencyKey, ...(attachments.length === 0 ? {} : { attachments }) };
|
|
180
202
|
if (kind === TRANSACTIONAL_KIND || secret === null) return { ...content, ...envelope };
|
|
181
203
|
const links = buildUnsubscribeLinks(config, mail.to, secret);
|