From 8b2dc8f40fc39514ae6fa0d4bc2b8b3ab963a097 Mon Sep 17 00:00:00 2001 From: Mix Date: Sun, 18 Oct 2026 09:56:44 +0300 Subject: [PATCH] design: server-dmarc-hint - the server's own name gets a DMARC record MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Owner, 2026-10-18: "Оба предложения делаем" (the roadmap's server-dmarc-hint, from the security audit's S3). Settings › Notification mail gets a third record after DKIM and SPF: DMARC at _dmarc., value v=DMARC1; p=reject, with a help line - without it a receiver does not refuse mail forged in the server's name, a false password-reset message included; only the panel sends as this name, signed, so reject is safe. Health's Notification mail card gets the DMARC row; Help's Notifications topic names all three records. check.py: 0 violations; outlines.json rewritten for the third record of the Settings box (record×2 -> record×3). Co-Authored-By: Claude Opus 5.5 --- docs/assets/panel-redesign/panel/health.html | 1 + docs/assets/panel-redesign/panel/help.html | 2 +- docs/assets/panel-redesign/panel/outlines.json | 2 +- docs/assets/panel-redesign/panel/settings.html | 12 ++++++++++++ docs/assets/panel-redesign/panel/src/health.html | 1 + docs/assets/panel-redesign/panel/src/help.html | 2 +- docs/assets/panel-redesign/panel/src/settings.html | 12 ++++++++++++ 7 files changed, 29 insertions(+), 3 deletions(-) diff --git a/docs/assets/panel-redesign/panel/health.html b/docs/assets/panel-redesign/panel/health.html index 385647a..c377255 100644 --- a/docs/assets/panel-redesign/panel/health.html +++ b/docs/assets/panel-redesign/panel/health.html @@ -158,6 +158,7 @@ DKIM
sp2026._domainkey.mail.example.orgpublished SPF
mail.example.orgmissing + DMARC
_dmarc.mail.example.orgmissing
diff --git a/docs/assets/panel-redesign/panel/help.html b/docs/assets/panel-redesign/panel/help.html index 5b4f24b..baefdc5 100644 --- a/docs/assets/panel-redesign/panel/help.html +++ b/docs/assets/panel-redesign/panel/help.html @@ -147,7 +147,7 @@

Backup and moving a domain

Full backup downloads one archive of the whole instance: data/ (the database, DKIM keys and application credentials), docker-compose.yml, .env and certs/. Both it and a domain's export ask for your account password - the one you sign in with - at every download, so a session left open is not enough to take them; a wrong one counts against the limit of a password change, ten in 15 minutes. The Postfix queue is not in it. The backup is taken while the server is running, and Postfix keeps moving messages through the queue, so a copy could hold a message twice or miss it; mail still waiting for delivery is therefore not carried over, and a restored server starts with an empty queue. To keep the queue, stop the container and archive the project directory instead. The private key in certs/ has to be readable by the panel: give it to group 10997 on the host (chgrp 10997, chmod 640), a group only the panel is in, so Postfix's daemons cannot read it. Until then the panel refuses to make a backup and names the file, rather than hand over an archive without the key. It holds secrets, so leave Encrypt with a password ticked: the file is sealed as .spbk, the password is not stored, and without it nothing can be recovered. To restore, unpack it into an empty project directory (decrypt a .spbk first with selfpost-backup -decrypt) and start the same SelfPost version that made it; the panel refuses data from another version. The reverse-proxy configuration and mail.log are not included. One domain moves on its own: Export domain on its settings page writes a .json (or encrypted .spde) with its DKIM key and its applications' passwords, and Import a domain here reads it into another instance, so the published DNS needs no change.

Users and roles

The two roles are a reach, not a rank: every user is an administrator and signs in with a username and password. Global reaches the whole server — Overview, Server, the queue and every domain — and is the only role that adds or deletes domains and users. Domain reaches only the domains assigned to it, outbound and inbound separately (the same name on both lists is two assignments); All includes domains added later, and a domain user needs at least one domain or All on either list. The only global user cannot be demoted or deleted, and you cannot delete the account you are signed in with. A new password set here signs that user out everywhere; set for yourself, it keeps the session you set it from. Adding a user, changing a user's password, e-mail or role, and deleting a user ask for your own account password, as a backup does, with the same limit on wrong guesses.

Settings

Settings holds what is true of the whole instance. The time zone is the container's, TZ in .env (UTC when it is not set): every time the panel shows and every day it counts is that zone's, as are the stamps Postfix writes in mail.log, so the two always agree; changing it is a restart of the container. The one exception is the day a DMARC report covers, which is the reporter's, counted in UTC. Log retention is how many days the Outbound log keeps its rows, from 7 to 365 and 90 by default; a sweep every six hours deletes older ones, and it is the main driver of how fast /data grows. With the inbound relay on there is a second number, for the Inbound log, with the same range. It does not change the rotation of mail.log, which is daily with about two weeks kept. The sending rate limit shown under it is level 1, the per-client-IP ceiling set in .env: changing it needs a restart, and no level-2 limit can exceed it. Notifications are turned on or off here for everyone.

-

Notifications

The panel writes to its users when something needs them, from postmaster@ the server's hostname. Four things are reported. A sending domain's SPF, DKIM or DMARC record stops matching: sent once two hourly checks in a row have found it so, and once more when the record matches again. A level-2 rate limit refuses mail: sent at the first refusal, then at most once a day for the same sending domain. The TLS certificate is 14 days from expiry, and again at 3 days if it is still the same certificate. A message has waited in the queue for more than three days, with one more message when none is left. A global user is told all of it; a domain administrator is told about the DNS records and limits of their own domains.

Each user turns notifications on or off under Account and needs an e-mail there; Server › Settings turns them off for everyone. They are the panel's own mail: not rows of the Outbound log, and not counted against any limit.

For that mail to arrive, the server's own name needs two DNS records of its own, as each of your domains does: a DKIM key, which the panel generates and signs notifications with, and an SPF record, v=spf1 a -all. Server › Settings gives both with the values to publish and whether they are in place, and its Re-check DNS checks them again once they are published; Server › Health shows them too. Without them notifications are still sent, and a receiver may file them as spam. Mail of your domains does not depend on either.

+

Notifications

The panel writes to its users when something needs them, from postmaster@ the server's hostname. Four things are reported. A sending domain's SPF, DKIM or DMARC record stops matching: sent once two hourly checks in a row have found it so, and once more when the record matches again. A level-2 rate limit refuses mail: sent at the first refusal, then at most once a day for the same sending domain. The TLS certificate is 14 days from expiry, and again at 3 days if it is still the same certificate. A message has waited in the queue for more than three days, with one more message when none is left. A global user is told all of it; a domain administrator is told about the DNS records and limits of their own domains.

Each user turns notifications on or off under Account and needs an e-mail there; Server › Settings turns them off for everyone. They are the panel's own mail: not rows of the Outbound log, and not counted against any limit.

For that mail to arrive, the server's own name needs DNS records of its own, as each of your domains does: a DKIM key, which the panel generates and signs notifications with, an SPF record, v=spf1 a -all, and a DMARC record, v=DMARC1; p=reject, which has receivers refuse mail forged in the server's name - a false password-reset message among it; only the panel sends as this name, signed, so reject is safe. Server › Settings gives all three with the values to publish and whether they are in place, and its Re-check DNS checks them again once they are published; Server › Health shows them too. Without them notifications are still sent, and a receiver may file them as spam. Mail of your domains depends on none of them.

05

Account

diff --git a/docs/assets/panel-redesign/panel/outlines.json b/docs/assets/panel-redesign/panel/outlines.json index 18f7b01..61f021b 100644 --- a/docs/assets/panel-redesign/panel/outlines.json +++ b/docs/assets/panel-redesign/panel/outlines.json @@ -402,7 +402,7 @@ }, { "is-6": [ - "box[Notification mail]:record×2", + "box[Notification mail]:record×3", "box[Sending rate limits]:body", "box[Time zone]:body" ] diff --git a/docs/assets/panel-redesign/panel/settings.html b/docs/assets/panel-redesign/panel/settings.html index ce70198..3986007 100644 --- a/docs/assets/panel-redesign/panel/settings.html +++ b/docs/assets/panel-redesign/panel/settings.html @@ -128,6 +128,18 @@

Notifications are sent without it, and a receiver may file them as spam.

+ +
+

DMARC

missingFor the server's own name, not for your domains
+
+
+
+
+
+
+
+

Without it a receiver does not refuse mail forged in the server's name - a false password-reset message included. Only the panel sends as this name, signed, so reject is safe.

+
diff --git a/docs/assets/panel-redesign/panel/src/health.html b/docs/assets/panel-redesign/panel/src/health.html index 70341fa..ffc329e 100644 --- a/docs/assets/panel-redesign/panel/src/health.html +++ b/docs/assets/panel-redesign/panel/src/health.html @@ -92,6 +92,7 @@ DKIM
sp2026._domainkey.mail.example.orgpublished SPF
mail.example.orgmissing + DMARC
_dmarc.mail.example.orgmissing
diff --git a/docs/assets/panel-redesign/panel/src/help.html b/docs/assets/panel-redesign/panel/src/help.html index 9ef664c..ebd18e3 100644 --- a/docs/assets/panel-redesign/panel/src/help.html +++ b/docs/assets/panel-redesign/panel/src/help.html @@ -81,7 +81,7 @@

Backup and moving a domain

Full backup downloads one archive of the whole instance: data/ (the database, DKIM keys and application credentials), docker-compose.yml, .env and certs/. Both it and a domain's export ask for your account password - the one you sign in with - at every download, so a session left open is not enough to take them; a wrong one counts against the limit of a password change, ten in 15 minutes. The Postfix queue is not in it. The backup is taken while the server is running, and Postfix keeps moving messages through the queue, so a copy could hold a message twice or miss it; mail still waiting for delivery is therefore not carried over, and a restored server starts with an empty queue. To keep the queue, stop the container and archive the project directory instead. The private key in certs/ has to be readable by the panel: give it to group 10997 on the host (chgrp 10997, chmod 640), a group only the panel is in, so Postfix's daemons cannot read it. Until then the panel refuses to make a backup and names the file, rather than hand over an archive without the key. It holds secrets, so leave Encrypt with a password ticked: the file is sealed as .spbk, the password is not stored, and without it nothing can be recovered. To restore, unpack it into an empty project directory (decrypt a .spbk first with selfpost-backup -decrypt) and start the same SelfPost version that made it; the panel refuses data from another version. The reverse-proxy configuration and mail.log are not included. One domain moves on its own: Export domain on its settings page writes a .json (or encrypted .spde) with its DKIM key and its applications' passwords, and Import a domain here reads it into another instance, so the published DNS needs no change.

Users and roles

The two roles are a reach, not a rank: every user is an administrator and signs in with a username and password. Global reaches the whole server — Overview, Server, the queue and every domain — and is the only role that adds or deletes domains and users. Domain reaches only the domains assigned to it, outbound and inbound separately (the same name on both lists is two assignments); All includes domains added later, and a domain user needs at least one domain or All on either list. The only global user cannot be demoted or deleted, and you cannot delete the account you are signed in with. A new password set here signs that user out everywhere; set for yourself, it keeps the session you set it from. Adding a user, changing a user's password, e-mail or role, and deleting a user ask for your own account password, as a backup does, with the same limit on wrong guesses.

Settings

Settings holds what is true of the whole instance. The time zone is the container's, TZ in .env (UTC when it is not set): every time the panel shows and every day it counts is that zone's, as are the stamps Postfix writes in mail.log, so the two always agree; changing it is a restart of the container. The one exception is the day a DMARC report covers, which is the reporter's, counted in UTC. Log retention is how many days the Outbound log keeps its rows, from 7 to 365 and 90 by default; a sweep every six hours deletes older ones, and it is the main driver of how fast /data grows. With the inbound relay on there is a second number, for the Inbound log, with the same range. It does not change the rotation of mail.log, which is daily with about two weeks kept. The sending rate limit shown under it is level 1, the per-client-IP ceiling set in .env: changing it needs a restart, and no level-2 limit can exceed it. Notifications are turned on or off here for everyone.

-

Notifications

The panel writes to its users when something needs them, from postmaster@ the server's hostname. Four things are reported. A sending domain's SPF, DKIM or DMARC record stops matching: sent once two hourly checks in a row have found it so, and once more when the record matches again. A level-2 rate limit refuses mail: sent at the first refusal, then at most once a day for the same sending domain. The TLS certificate is 14 days from expiry, and again at 3 days if it is still the same certificate. A message has waited in the queue for more than three days, with one more message when none is left. A global user is told all of it; a domain administrator is told about the DNS records and limits of their own domains.

Each user turns notifications on or off under Account and needs an e-mail there; Server › Settings turns them off for everyone. They are the panel's own mail: not rows of the Outbound log, and not counted against any limit.

For that mail to arrive, the server's own name needs two DNS records of its own, as each of your domains does: a DKIM key, which the panel generates and signs notifications with, and an SPF record, v=spf1 a -all. Server › Settings gives both with the values to publish and whether they are in place, and its Re-check DNS checks them again once they are published; Server › Health shows them too. Without them notifications are still sent, and a receiver may file them as spam. Mail of your domains does not depend on either.

+

Notifications

The panel writes to its users when something needs them, from postmaster@ the server's hostname. Four things are reported. A sending domain's SPF, DKIM or DMARC record stops matching: sent once two hourly checks in a row have found it so, and once more when the record matches again. A level-2 rate limit refuses mail: sent at the first refusal, then at most once a day for the same sending domain. The TLS certificate is 14 days from expiry, and again at 3 days if it is still the same certificate. A message has waited in the queue for more than three days, with one more message when none is left. A global user is told all of it; a domain administrator is told about the DNS records and limits of their own domains.

Each user turns notifications on or off under Account and needs an e-mail there; Server › Settings turns them off for everyone. They are the panel's own mail: not rows of the Outbound log, and not counted against any limit.

For that mail to arrive, the server's own name needs DNS records of its own, as each of your domains does: a DKIM key, which the panel generates and signs notifications with, an SPF record, v=spf1 a -all, and a DMARC record, v=DMARC1; p=reject, which has receivers refuse mail forged in the server's name - a false password-reset message among it; only the panel sends as this name, signed, so reject is safe. Server › Settings gives all three with the values to publish and whether they are in place, and its Re-check DNS checks them again once they are published; Server › Health shows them too. Without them notifications are still sent, and a receiver may file them as spam. Mail of your domains depends on none of them.

05

Account

diff --git a/docs/assets/panel-redesign/panel/src/settings.html b/docs/assets/panel-redesign/panel/src/settings.html index 92a35b6..912d06b 100644 --- a/docs/assets/panel-redesign/panel/src/settings.html +++ b/docs/assets/panel-redesign/panel/src/settings.html @@ -62,6 +62,18 @@

Notifications are sent without it, and a receiver may file them as spam.

+ +
+

DMARC

missingFor the server's own name, not for your domains
+
+
+
+
+
+
+
+

Without it a receiver does not refuse mail forged in the server's name - a false password-reset message included. Only the panel sends as this name, signed, so reject is safe.

+