@wraps.dev/cli 2.24.0 → 2.25.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 +1 -1
- package/dist/api-lambda.zip +0 -0
- package/dist/cli.js +56 -11
- package/dist/cli.js.map +1 -1
- package/dist/console/assets/{index-5HGEQ1Ul.js → index-P0x5JCC4.js} +1 -1
- package/dist/console/index.html +1 -1
- package/dist/lambda/event-processor/.bundled +1 -1
- package/dist/lambda/inbound-processor/.bundled +1 -1
- package/dist/lambda/sms-event-processor/.bundled +1 -1
- package/dist/selfhost-migrations/0063_greedy_legion.sql +17 -0
- package/dist/selfhost-migrations/meta/0063_snapshot.json +7282 -0
- package/dist/selfhost-migrations/meta/_journal.json +7 -0
- package/package.json +5 -5
package/README.md
CHANGED
|
@@ -502,7 +502,7 @@ DMARC (TXT)
|
|
|
502
502
|
Policy for how receivers handle emails failing DKIM/SPF checks
|
|
503
503
|
|
|
504
504
|
TXT _dmarc.example.com
|
|
505
|
-
→ v=DMARC1; p=quarantine; rua=mailto:postmaster@example.com
|
|
505
|
+
→ v=DMARC1; p=quarantine; sp=quarantine; np=reject; rua=mailto:postmaster@example.com
|
|
506
506
|
```
|
|
507
507
|
|
|
508
508
|
## Hosting Provider Integration
|
package/dist/api-lambda.zip
CHANGED
|
Binary file
|
package/dist/cli.js
CHANGED
|
@@ -3047,7 +3047,7 @@ async function previewDNSChanges(hostedZoneId, domain, dkimTokens, region, custo
|
|
|
3047
3047
|
});
|
|
3048
3048
|
const dmarcName = `_dmarc.${domain}`;
|
|
3049
3049
|
const dmarcRuaDomain = mailFromDomain || domain;
|
|
3050
|
-
const proposedDMARC = `"v=DMARC1; p=quarantine; rua=mailto:postmaster@${dmarcRuaDomain}"`;
|
|
3050
|
+
const proposedDMARC = `"v=DMARC1; p=quarantine; sp=quarantine; np=reject; rua=mailto:postmaster@${dmarcRuaDomain}"`;
|
|
3051
3051
|
const existingDMARC = findExistingRecord(existingRecords, dmarcName, "TXT");
|
|
3052
3052
|
const existingDMARCValue = getRecordValue(existingDMARC);
|
|
3053
3053
|
let dmarcStatus = "new";
|
|
@@ -3209,7 +3209,7 @@ async function createSelectedDNSRecords(hostedZoneId, domain, dkimTokens, region
|
|
|
3209
3209
|
TTL: 1800,
|
|
3210
3210
|
ResourceRecords: [
|
|
3211
3211
|
{
|
|
3212
|
-
Value: `"v=DMARC1; p=quarantine; rua=mailto:postmaster@${dmarcRuaDomain}"`
|
|
3212
|
+
Value: `"v=DMARC1; p=quarantine; sp=quarantine; np=reject; rua=mailto:postmaster@${dmarcRuaDomain}"`
|
|
3213
3213
|
}
|
|
3214
3214
|
]
|
|
3215
3215
|
}
|
|
@@ -3332,7 +3332,7 @@ async function createDNSRecords(hostedZoneId, domain, dkimTokens, region, custom
|
|
|
3332
3332
|
TTL: 1800,
|
|
3333
3333
|
ResourceRecords: [
|
|
3334
3334
|
{
|
|
3335
|
-
Value: `"v=DMARC1; p=quarantine; rua=mailto:postmaster@${dmarcRuaDomain}"`
|
|
3335
|
+
Value: `"v=DMARC1; p=quarantine; sp=quarantine; np=reject; rua=mailto:postmaster@${dmarcRuaDomain}"`
|
|
3336
3336
|
}
|
|
3337
3337
|
]
|
|
3338
3338
|
}
|
|
@@ -3556,7 +3556,7 @@ var init_cloudflare = __esm({
|
|
|
3556
3556
|
const dmarcSuccess = await this.createRecord(
|
|
3557
3557
|
`_dmarc.${domain}`,
|
|
3558
3558
|
"TXT",
|
|
3559
|
-
`v=DMARC1; p=quarantine; rua=mailto:postmaster@${mailFromDomain || domain}`
|
|
3559
|
+
`v=DMARC1; p=quarantine; sp=quarantine; np=reject; rua=mailto:postmaster@${mailFromDomain || domain}`
|
|
3560
3560
|
);
|
|
3561
3561
|
if (dmarcSuccess) {
|
|
3562
3562
|
recordsCreated++;
|
|
@@ -3942,7 +3942,7 @@ var init_vercel = __esm({
|
|
|
3942
3942
|
const dmarcSuccess = await this.createRecord(
|
|
3943
3943
|
`_dmarc.${domain}`,
|
|
3944
3944
|
"TXT",
|
|
3945
|
-
`v=DMARC1; p=quarantine; rua=mailto:postmaster@${mailFromDomain || domain}`
|
|
3945
|
+
`v=DMARC1; p=quarantine; sp=quarantine; np=reject; rua=mailto:postmaster@${mailFromDomain || domain}`
|
|
3946
3946
|
);
|
|
3947
3947
|
if (dmarcSuccess) {
|
|
3948
3948
|
recordsCreated++;
|
|
@@ -4211,7 +4211,7 @@ function buildEmailDNSRecords(data) {
|
|
|
4211
4211
|
records.push({
|
|
4212
4212
|
name: `_dmarc.${domain}`,
|
|
4213
4213
|
type: "TXT",
|
|
4214
|
-
value: `v=DMARC1; p=quarantine; rua=mailto:postmaster@${dmarcRuaDomain}`,
|
|
4214
|
+
value: `v=DMARC1; p=quarantine; sp=quarantine; np=reject; rua=mailto:postmaster@${dmarcRuaDomain}`,
|
|
4215
4215
|
category: "dmarc"
|
|
4216
4216
|
});
|
|
4217
4217
|
if (customTrackingDomain) {
|
|
@@ -6263,7 +6263,7 @@ Verification should complete within a few minutes.`,
|
|
|
6263
6263
|
),
|
|
6264
6264
|
"",
|
|
6265
6265
|
pc10.bold("DMARC Record (TXT):"),
|
|
6266
|
-
` ${pc10.cyan(`_dmarc.${domain}`)} ${pc10.dim("TXT")} "v=DMARC1; p=quarantine; rua=mailto:postmaster@${dmarcRuaDomain}"`
|
|
6266
|
+
` ${pc10.cyan(`_dmarc.${domain}`)} ${pc10.dim("TXT")} "v=DMARC1; p=quarantine; sp=quarantine; np=reject; rua=mailto:postmaster@${dmarcRuaDomain}"`
|
|
6267
6267
|
);
|
|
6268
6268
|
if (outputs.mailFromDomain) {
|
|
6269
6269
|
dnsLines.push(
|
|
@@ -6492,7 +6492,7 @@ ${domainStrings.join("\n")}`);
|
|
|
6492
6492
|
),
|
|
6493
6493
|
"",
|
|
6494
6494
|
pc10.bold("DMARC Record (TXT):"),
|
|
6495
|
-
` ${pc10.cyan(`_dmarc.${domain.domain}`)} ${pc10.dim("TXT")} "v=DMARC1; p=quarantine; rua=mailto:postmaster@${dmarcRuaDomain}"`
|
|
6495
|
+
` ${pc10.cyan(`_dmarc.${domain.domain}`)} ${pc10.dim("TXT")} "v=DMARC1; p=quarantine; sp=quarantine; np=reject; rua=mailto:postmaster@${dmarcRuaDomain}"`
|
|
6496
6496
|
);
|
|
6497
6497
|
}
|
|
6498
6498
|
if (domain.mailFromDomain && domain.mailFromStatus !== "SUCCESS") {
|
|
@@ -15408,6 +15408,9 @@ async function checkDmarc(domain) {
|
|
|
15408
15408
|
valid: false,
|
|
15409
15409
|
policy: null,
|
|
15410
15410
|
subdomainPolicy: null,
|
|
15411
|
+
nonExistentSubdomainPolicy: null,
|
|
15412
|
+
testing: false,
|
|
15413
|
+
psd: null,
|
|
15411
15414
|
percentage: 100,
|
|
15412
15415
|
reportingEnabled: false,
|
|
15413
15416
|
ruaAddresses: [],
|
|
@@ -15460,6 +15463,21 @@ function parseDmarcRecord(record, result) {
|
|
|
15460
15463
|
} else {
|
|
15461
15464
|
result.subdomainPolicy = result.policy;
|
|
15462
15465
|
}
|
|
15466
|
+
const np = tags.get("np");
|
|
15467
|
+
if (np) {
|
|
15468
|
+
if (["none", "quarantine", "reject"].includes(np)) {
|
|
15469
|
+
result.nonExistentSubdomainPolicy = np;
|
|
15470
|
+
} else {
|
|
15471
|
+
result.warnings.push(`Invalid non-existent subdomain policy (np): ${np}`);
|
|
15472
|
+
}
|
|
15473
|
+
}
|
|
15474
|
+
if (tags.get("t") === "y") {
|
|
15475
|
+
result.testing = true;
|
|
15476
|
+
}
|
|
15477
|
+
const psd = tags.get("psd");
|
|
15478
|
+
if (psd && ["y", "n", "u"].includes(psd)) {
|
|
15479
|
+
result.psd = psd;
|
|
15480
|
+
}
|
|
15463
15481
|
const pct = tags.get("pct");
|
|
15464
15482
|
if (pct) {
|
|
15465
15483
|
const pctNum = Number.parseInt(pct, 10);
|
|
@@ -15468,7 +15486,9 @@ function parseDmarcRecord(record, result) {
|
|
|
15468
15486
|
} else {
|
|
15469
15487
|
result.percentage = pctNum;
|
|
15470
15488
|
if (pctNum < 100) {
|
|
15471
|
-
result.warnings.push(
|
|
15489
|
+
result.warnings.push(
|
|
15490
|
+
`pct=${pctNum} is deprecated (DMARCbis receivers ignore it; enforcement is all-or-nothing). Use t=y while testing instead.`
|
|
15491
|
+
);
|
|
15472
15492
|
}
|
|
15473
15493
|
}
|
|
15474
15494
|
}
|
|
@@ -15533,6 +15553,17 @@ function parseDmarcRecord(record, result) {
|
|
|
15533
15553
|
if (result.subdomainPolicy === "none" && result.policy !== "none") {
|
|
15534
15554
|
result.warnings.push("Subdomain policy is less strict than domain policy");
|
|
15535
15555
|
}
|
|
15556
|
+
const enforcing = result.policy === "quarantine" || result.policy === "reject";
|
|
15557
|
+
if (result.testing && result.policy !== "none") {
|
|
15558
|
+
result.warnings.push(
|
|
15559
|
+
"t=y (testing) is set \u2014 receivers will not enforce the policy"
|
|
15560
|
+
);
|
|
15561
|
+
}
|
|
15562
|
+
if (enforcing && !result.nonExistentSubdomainPolicy) {
|
|
15563
|
+
result.warnings.push(
|
|
15564
|
+
"No np= set \u2014 add np=reject to block spoofing from non-existent subdomains (DMARCbis)"
|
|
15565
|
+
);
|
|
15566
|
+
}
|
|
15536
15567
|
if (!result.reportingEnabled) {
|
|
15537
15568
|
result.warnings.push("No aggregate reporting configured (rua=)");
|
|
15538
15569
|
}
|
|
@@ -16686,11 +16717,18 @@ function collectDmarcIssues(dmarc, deductions, bonuses) {
|
|
|
16686
16717
|
reason: "DMARC policy is none (not enforcing)"
|
|
16687
16718
|
});
|
|
16688
16719
|
}
|
|
16689
|
-
if (dmarc.
|
|
16720
|
+
if (dmarc.testing && dmarc.policy !== "none") {
|
|
16690
16721
|
deductions.push({
|
|
16691
16722
|
check: "dmarc",
|
|
16692
16723
|
points: 2,
|
|
16693
|
-
reason:
|
|
16724
|
+
reason: "DMARC testing mode (t=y) \u2014 receivers won't enforce the policy"
|
|
16725
|
+
});
|
|
16726
|
+
}
|
|
16727
|
+
if (dmarc.percentage < 100) {
|
|
16728
|
+
deductions.push({
|
|
16729
|
+
check: "dmarc",
|
|
16730
|
+
points: 1,
|
|
16731
|
+
reason: `DMARC pct=${dmarc.percentage} is deprecated (DMARCbis receivers ignore it; enforcement is inconsistent)`
|
|
16694
16732
|
});
|
|
16695
16733
|
}
|
|
16696
16734
|
if (!dmarc.reportingEnabled) {
|
|
@@ -16707,6 +16745,13 @@ function collectDmarcIssues(dmarc, deductions, bonuses) {
|
|
|
16707
16745
|
reason: "DMARC strict alignment configured"
|
|
16708
16746
|
});
|
|
16709
16747
|
}
|
|
16748
|
+
if ((dmarc.policy === "quarantine" || dmarc.policy === "reject") && dmarc.nonExistentSubdomainPolicy === "reject") {
|
|
16749
|
+
bonuses.push({
|
|
16750
|
+
check: "dmarc",
|
|
16751
|
+
points: 1,
|
|
16752
|
+
reason: "np=reject blocks non-existent subdomain spoofing (DMARCbis)"
|
|
16753
|
+
});
|
|
16754
|
+
}
|
|
16710
16755
|
}
|
|
16711
16756
|
function collectInfraIssues(checks, deductions, bonuses) {
|
|
16712
16757
|
if (checks.mx.exists) {
|