diff --git a/contrib/ldk-server-config.toml b/contrib/ldk-server-config.toml index ce569cad..64367a22 100644 --- a/contrib/ldk-server-config.toml +++ b/contrib/ldk-server-config.toml @@ -19,6 +19,7 @@ level = "Debug" # Log level (Error, Warn, Info, De [tls] #cert_path = "/path/to/tls.crt" # Path to TLS certificate, by default uses dir_path/tls.crt #key_path = "/path/to/tls.key" # Path to TLS private key, by default uses dir_path/tls.key +# For CA-signed certs, point cert_path/key_path to your ACME output files. #hosts = ["example.com"] # Allowed hosts for TLS, will always include "localhost" and "127.0.0.1" # Must set one of bitcoind, electrum, or esplora diff --git a/docs/configuration.md b/docs/configuration.md index 45f3020f..4eac6d98 100644 --- a/docs/configuration.md +++ b/docs/configuration.md @@ -71,7 +71,9 @@ Alternative Names. If no certificate exists, the server auto-generates a self-si P-256 cert. `localhost` and `127.0.0.1` are always included in the SANs. Add your server's public hostname or IP to `hosts` if clients connect remotely. -To bring your own certificate (e.g., from Let's Encrypt), set `cert_path` and `key_path`. +To bring your own certificate (for example, from a public CA), set `cert_path` and +`key_path`. The server reads these files on startup, so renewals require a restart. +See [Operations - TLS](operations.md#tls) for a recommended CA-signed flow. ### Bitcoin Backend diff --git a/docs/operations.md b/docs/operations.md index 1a8935dd..28e7f4c6 100644 --- a/docs/operations.md +++ b/docs/operations.md @@ -47,7 +47,7 @@ setup): ### What to Back Up | File | Priority | Description | -|----------------------------------------|--------------|----------------------------------------------------------------------------| +| -------------------------------------- | ------------ | -------------------------------------------------------------------------- | | `/keys_seed` | **Critical** | Node identity and master secret. Required to recover on-chain funds. | | `/ldk_node_data.sqlite` | **Critical** | Channel state and on-chain wallet data. Required to recover channel funds. | | `/ldk_server_data.sqlite` | Nice-to-have | Payment and forwarding history | @@ -80,6 +80,39 @@ setup): - Certificate includes `localhost` and `127.0.0.1` in SANs by default - Add your server's hostname/IP to `[tls] hosts` for remote access +### CA-Signed Certificates (Let's Encrypt / ACME) + +For production deployments, many operators prefer a publicly trusted certificate. The +recommended approach is to provision the certificate outside of LDK Server (via an ACME +client) and point `[tls] cert_path` and `key_path` to the resulting files. + +High-level flow: + +1. Choose a public hostname for the gRPC endpoint (e.g., `ldk.example.com`). +2. Set `grpc_service_address` to bind on the public interface. +3. Add the hostname to `[tls] hosts` so SANs match what clients connect to. +4. Use an ACME client (certbot, lego, acme.sh) to obtain a certificate for the hostname. +5. Configure `[tls] cert_path` and `key_path` to the ACME output files. +6. Restart the server after renewals (LDK Server reads TLS files at startup). + +Example (certbot with a pre-provisioned DNS or HTTP-01 flow): + +```toml +[node] +grpc_service_address = "0.0.0.0:3536" + +[tls] +cert_path = "/etc/letsencrypt/live/ldk.example.com/fullchain.pem" +key_path = "/etc/letsencrypt/live/ldk.example.com/privkey.pem" +hosts = ["ldk.example.com"] +``` + +Notes: + +- Ensure the `ldk-server` process can read the cert and key files. +- After a renewal, restart the service to pick up the new certificate. +- If you want zero-downtime renewals, place a reverse proxy in front and terminate TLS there. + ### Network Exposure The gRPC service binds to `127.0.0.1:3536` by default. For remote access, either: @@ -129,7 +162,7 @@ scrape_configs: username: prometheus password: secret static_configs: - - targets: [ 'localhost:3536' ] + - targets: ["localhost:3536"] ``` ### Available Metrics