Настоящая почта: docker-compose.public.yml (MX, DKIM, Let's Encrypt через lego), сертификат перечитывается без перезапуска
continuous-integration/drone/pr Build is passing
continuous-integration/drone/pr Build is passing
- ReloadingKeyManager: сертификат и ключ из PEM (PKCS#8, RSA, EC/SEC1 как у lego), раз в минуту проверяет файлы и перечитывает их; битый файл оставляет прежний сертификат; поколения по алиасам. - docker-compose.public.yml: порты 25/587/465/993 на публичном адресе ВМ, OUTBOUND_MODE=mx, DKIM, SPF/DMARC, регистрация закрыта, без ловушки; сервис acme (lego v5.5.2, HTTP-01 на :80, EC256, продление за 30 дней, хук кладёт пару в том tls для uid 10001). - README: раздел «Настоящая почта», DNS-записи, перечитка сертификата. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
@@ -22,6 +22,7 @@ import java.security.KeyPair;
|
||||
import java.security.KeyPairGenerator;
|
||||
import java.security.SecureRandom;
|
||||
import java.security.cert.X509Certificate;
|
||||
import java.time.Clock;
|
||||
import java.time.Duration;
|
||||
import java.time.Instant;
|
||||
import java.util.Base64;
|
||||
@@ -30,7 +31,8 @@ import java.util.Date;
|
||||
/**
|
||||
* Certificate for SMTP TLS (STARTTLS and implicit TLS):
|
||||
* <ul>
|
||||
* <li>{@code cert} and {@code key} given (PEM: certificate chain and PKCS#8 key, e.g. from Let's Encrypt) — used as is;</li>
|
||||
* <li>{@code cert} and {@code key} given (PEM: certificate chain and the key — PKCS#8, RSA or EC, e.g. from Let's Encrypt) —
|
||||
* used as is and read again when the files change ({@link ReloadingKeyManager}, checked once a minute);</li>
|
||||
* <li>otherwise a self-signed certificate for the server hostname, created once in {@code dir} and reused —
|
||||
* enough for encryption between our own services; other servers deliver over it too (MX delivery does not
|
||||
* check certificates, RFC 7435 opportunistic TLS).</li>
|
||||
@@ -41,6 +43,7 @@ public final class SmtpTls {
|
||||
private static final Logger log = LoggerFactory.getLogger(SmtpTls.class);
|
||||
static final String CERT_FILE = "smtp-cert.pem";
|
||||
static final String KEY_FILE = "smtp-key.pem";
|
||||
static final Duration RELOAD_CHECK = Duration.ofMinutes(1);
|
||||
|
||||
private SmtpTls() {
|
||||
}
|
||||
@@ -67,7 +70,8 @@ public final class SmtpTls {
|
||||
log.info("SMTP TLS: self-signed certificate {}", cert);
|
||||
}
|
||||
}
|
||||
return SslContextBuilder.forServer(cert.toFile(), key.toFile())
|
||||
// Read again when the files change (a renewed Let's Encrypt certificate) — no restart needed
|
||||
return SslContextBuilder.forServer(new ReloadingKeyManager(cert, key, RELOAD_CHECK, Clock.systemUTC()))
|
||||
.protocols("TLSv1.3", "TLSv1.2")
|
||||
.build();
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user