panel-notifications: the start puts the server's name into OpenDKIM's tables
test / test (push) Canceled after 0s

Found on the test server after the rollout of b905f3e: the SigningTable had
the three sending domains and no line for selfpost.mixfed.ru. The tables are
rebuilt when a domain is added or deleted, and nothing had done either since
the upgrade - notifications would have gone out unsigned until something did.
The e2e stand did not show it: it adds a domain right after its start.

The notifier now asks at its start whether the table on disk has the line
and rebuilds the tables once if it does not (domain.Service.EnsureServerSigned).
A failure is logged and costs the signature, not the message.

Checked on Windows: go vet clean; go test ./internal/domain passes apart from
TestWriteLoadPrivateKeyRoundtrip, which fails there on file modes and always
did; the new test holds one rebuild, none the second time, and that a longer
name is not taken for the server's.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
mix
2026-10-12 16:27:34 +03:00
co-authored by Claude Opus 5.5
parent b905f3e560
commit 400aa76737
4 changed files with 84 additions and 0 deletions
+18
View File
@@ -163,6 +163,24 @@ func (o *OpenDKIM) Rebuild(domains []SigningDomain) error {
return o.reload()
}
// signs reports whether the SigningTable on disk has a line for name. A table
// that does not exist yet signs nothing.
func (o *OpenDKIM) signs(name string) (bool, error) {
data, err := os.ReadFile(o.signingTablePath)
if os.IsNotExist(err) {
return false, nil
}
if err != nil {
return false, fmt.Errorf("read SigningTable: %w", err)
}
for _, line := range strings.Split(string(data), "\n") {
if strings.HasPrefix(line, "*@"+name+" ") {
return true, nil
}
}
return false, nil
}
// Reload asks OpenDKIM to re-read its tables without regenerating them. It
// backs the panel's manual reload button (architecture.md § Panel HTTP
// surface).