Keep technical content intact while simplifying and clarifying descriptions
This commit is contained in:
@@ -1,211 +1,156 @@
|
||||
# 🔐 dynTLS
|
||||
# dynTLS
|
||||
|
||||
**Granular Let's Encrypt certificate management for multi-service environments**
|
||||
Provides flexible ACME backend integration, DNS/http challenges and per-service certificate deployment.
|
||||
Granular Let's Encrypt certificate management for multi-service environments.
|
||||
|
||||
This utility simplifies issuing and managing TLS certificates via Let’s Encrypt for multiple services and hosts (e.g. Postfix, Dovecot, web servers and others). It separates ACME handling from deployment logic, supports HTTP-01 and DNS-01 challenges and maps issued certificates cleanly to individual services.
|
||||
|
||||
Key features:
|
||||
|
||||
- 🔁 Automated issuance and renewal of Let’s Encrypt certificates
|
||||
- 🌐 Support for HTTP-01 and DNS-01 challenges via external ACME client
|
||||
- 🧩 Flexible ACME backend selection (e.g. customized `letsencrypt_master_local.sh`)
|
||||
- 🎯 Per-host and per-service certificate mapping with backup handling
|
||||
- 📜 Central configuration via `vars` file
|
||||
- 📂 Plain repository layout with optional contrib scripts under `./contrib/acme`
|
||||
|
||||
---
|
||||
This repository provides the backend components for issuing, renewing and deploying TLS certificates in self-hosted, multi-service environments. It separates ACME handling from deployment logic, supports HTTP-01 and DNS-01 challenge workflows and maps issued certificates cleanly to individual services and hosts.
|
||||
|
||||
## Outline
|
||||
|
||||
1. [Features](#features)
|
||||
2. [Installation](#installation)
|
||||
3. [Configuration](#configuration)
|
||||
4. [Directory Layout](#directory-layout)
|
||||
5. [CRON Job Example](#cron-job-example)
|
||||
6. [ACME Backend](#acme-backend)
|
||||
7. [License](#license)
|
||||
8. [Authors](#authors)
|
||||
9. [Project Home](#project-home)
|
||||
|
||||
---
|
||||
- [Features](#features)
|
||||
- [Installation](#installation)
|
||||
- [Configuration](#configuration)
|
||||
- [Directory Layout](#directory-layout)
|
||||
- [CRON Job Example](#cron-job-example)
|
||||
- [ACME Backend](#acme-backend)
|
||||
- [License](#license)
|
||||
- [Authors](#authors)
|
||||
- [Project Home](#project-home)
|
||||
|
||||
## Features
|
||||
|
||||
- Manages Let’s Encrypt certificates for multiple domains and services
|
||||
- Uses a configurable ACME backend script (e.g. `letsencrypt_master_local.sh`)
|
||||
- Supports HTTP-01 and DNS-01 challenges (e.g. via Bind/nsupdate, TSIG, `rndc`)
|
||||
- Validates hostnames, SAN lists and certificate expiration before deployment
|
||||
- Creates backups of replaced certificates and can prune old backups
|
||||
- Logs operations with log levels and domain-set IDs for better traceability
|
||||
- Certificate management for multiple domains and services
|
||||
- Configurable external ACME backend integration
|
||||
- HTTP-01 and DNS-01 challenge support
|
||||
- Per-host and per-service certificate mapping
|
||||
- Backup creation and optional backup pruning
|
||||
- Central configuration through a separate `vars` file
|
||||
- Log output with domain-set context for traceability
|
||||
- Designed for self-hosted Linux environments
|
||||
|
||||
## Installation
|
||||
|
||||
The following steps describe a simple, source-based installation.
|
||||
1. Clone the repository.
|
||||
2. Install the required packages for your platform.
|
||||
3. Copy `vars.example` to a local `vars` file.
|
||||
4. Adjust paths, ACME backend settings and domain/service mappings.
|
||||
5. Run the script manually once before enabling automation.
|
||||
|
||||
1. Clone the repository
|
||||
Example:
|
||||
|
||||
```bash
|
||||
git clone https://dev.town-square.de/cb601/dyntls.git /opt/dyntls
|
||||
|
||||
cd /opt/dyntls
|
||||
```
|
||||
2. Install required packages
|
||||
```sh
|
||||
sudo groupadd --system dyntls
|
||||
sudo install -d -m 0750 -o root -g dyntls /opt/dyntls
|
||||
git clone https://dev.town-square.de/cb601/dyntls.git /opt/dyntls
|
||||
|
||||
Make sure you have at least:
|
||||
- openssl
|
||||
- nsupdate / bind-utils (for DNS-01 with Bind, if used)
|
||||
- curl or wget (depending on your ACME script)
|
||||
cd /opt/dyntls
|
||||
|
||||
On RPM-based systems, for example:
|
||||
sudo cp vars.example vars
|
||||
sudo chown root:dyntls /opt/dyntls/dyntls.sh /opt/dyntls/vars
|
||||
sudo chmod 0750 /opt/dyntls/dyntls.sh
|
||||
sudo chmod 0640 /opt/dyntls/vars
|
||||
|
||||
```bash
|
||||
sudo dnf install openssl bind-utils curl -y
|
||||
```
|
||||
3. Prepare configuration
|
||||
sudo /opt/dyntls/dyntls.sh help
|
||||
```
|
||||
|
||||
Copy the example vars file and adapt it to your environment:
|
||||
|
||||
```bash
|
||||
sudo cp vars.example vars
|
||||
sudo chmod 640 vars
|
||||
```
|
||||
4. Test a dry run
|
||||
|
||||
Before using dynTLS in production, run a dry or staging-mode test (example):
|
||||
|
||||
```bash
|
||||
./dyntls.sh help
|
||||
```
|
||||
For DNS-01 workflows with BIND, ensure the required tools such as `nsupdate` and `rndc` are available and that the configured TSIG key and zone permissions are valid.
|
||||
|
||||
## Configuration
|
||||
|
||||
dynTLS is configured via a `vars` file (e.g. `vars` or `vars.example`) which defines:
|
||||
The backend is configured through a separate configuration file derived from `vars.example`.
|
||||
|
||||
- Base directories for PKI and HTTP token storage
|
||||
- ACME backend script path (`DYNTLS_LE_PROGRAM`)
|
||||
- Certificate renewal thresholds and backup behavior
|
||||
- Domain lists and service mappings
|
||||
Typical settings include:
|
||||
|
||||
Key options include, for example:
|
||||
- Base directories for PKI data and HTTP token storage
|
||||
- Path to the external ACME backend script via `DYNTLS_LE_PROGRAM`
|
||||
- Renewal thresholds and backup retention settings
|
||||
- Domain definitions, including CN and SAN sets
|
||||
- Service mapping definitions for certificate deployment targets
|
||||
- Optional DNS parameters for DNS-01 automation
|
||||
|
||||
- `DYNTLS_LE_PROGRAM` – path to the external ACME client script
|
||||
- `DYNTLS_PKI` – root PKI directory (certificates, keys, backups)
|
||||
- `DYNTLS_PKI_CERT_EXPIRE` – minimum remaining validity (days) before renewal
|
||||
- `DYNTLS_DOMAIN_LIST` – list of domains (CN + SANs) for a certificate
|
||||
- `DYNTLS_DOMAINSERVICE_LIST` – mapping from certificate CN to service target(s)
|
||||
Recommended workflow:
|
||||
|
||||
You can keep `vars.example` under version control and use a separate, local `vars` file (ignored by Git) for host-specific secrets and paths.
|
||||
1. Start from `vars.example`.
|
||||
2. Create an environment-specific copy, for example `vars`.
|
||||
3. Keep secrets and local overrides out of version control.
|
||||
4. Validate ACME execution, challenge handling and deployment paths before enabling cron-based automation.
|
||||
|
||||
## Directory Layout
|
||||
|
||||
Minimal plain layout in the repository:
|
||||
|
||||
```text
|
||||
./
|
||||
├── dyntls # main dynTLS script
|
||||
├── vars.example # example configuration
|
||||
├── LICENSE.md # project license
|
||||
├── README.md # this file
|
||||
.
|
||||
├── dyntls.sh
|
||||
├── vars.example
|
||||
├── README.md
|
||||
├── LICENSE
|
||||
└── contrib/
|
||||
└── acme/
|
||||
├── letsencrypt_master.sh
|
||||
└── letsencrypt_master_local.sh
|
||||
```
|
||||
|
||||
Suggested runtime layout on a host (example):
|
||||
Suggested runtime layout on a host:
|
||||
|
||||
| Path | Purpose |
|
||||
|-----------------------------|---------------------------------|
|
||||
| /opt/dyntls/dyntls.sh | Main script |
|
||||
| /opt/dyntls/vars.example | Example config (reference) |
|
||||
| /opt/dyntls/vars | User config (never overwritten) |
|
||||
| /etc/pki/httpd/certs | Issued certificates |
|
||||
| /etc/pki/httpd/private | Private keys |
|
||||
| /etc/pki/httpd/certs/backup | Certificate backups |
|
||||
| /var/log/dyntls/dyntls.log | dynTLS log file |
|
||||
| /etc/cron.daily/dyntls | Cron job script (optional) |
|
||||
| Path | Purpose |
|
||||
|------------------------------|-------------------------------------------------|
|
||||
| `/opt/dyntls/dyntls.sh` | Main script |
|
||||
| `/opt/dyntls/vars.example` | Reference configuration |
|
||||
| `/opt/dyntls/vars` | Local configuration with host-specific settings |
|
||||
| `/etc/pki/...` | Certificate and key deployment targets |
|
||||
| `/var/log/dyntls/dyntls.log` | dynTLS log file |
|
||||
| `/etc/cron.daily/dyntls` | Optional cron wrapper |
|
||||
|
||||
Adjust these paths in your `vars` file according to your distribution and service layout.
|
||||
Adjust all runtime paths in the `vars` file to match your distribution, PKI layout and service-specific deployment targets.
|
||||
|
||||
## CRON Job Example
|
||||
|
||||
To run the key generator daily, you have two options:
|
||||
The following examples show two common ways to automate certificate checks and renewals.
|
||||
|
||||
1. Crontab
|
||||
Crontab example:
|
||||
|
||||
You can add a daily cron job directly to the root user's crontab:
|
||||
```sh
|
||||
30 3 * * * /opt/dyntls/dyntls.sh update-cert
|
||||
#30 3 * * * /opt/dyntls/dyntls.sh -P update-cert
|
||||
```
|
||||
|
||||
Open the root crontab for editing:
|
||||
Running the job once per night at 03:30 is a reasonable default for typical `dynTLS` use cases.
|
||||
|
||||
```bash
|
||||
sudo crontab -e
|
||||
```
|
||||
System cron directory example:
|
||||
|
||||
Add the following line to run the script daily at 3:30 AM:
|
||||
```sh
|
||||
#!/bin/sh
|
||||
|
||||
```bash
|
||||
# Staging mode
|
||||
30 3 * * * /opt/dyntls/dyntls.sh update-cert
|
||||
|
||||
# Productive mode
|
||||
#30 3 * * * /opt/dyntls/dyntls.sh -P update-cert
|
||||
```
|
||||
/opt/dyntls/dyntls.sh update-cert
|
||||
#/opt/dyntls/dyntls.sh -P update-cert
|
||||
|
||||
*(Adjust the schedule as needed. This example runs the script daily.)*
|
||||
2. System Cron Daily Directory
|
||||
exit 0
|
||||
```
|
||||
|
||||
Create a script as `/etc/cron.daily/dyntls`:
|
||||
|
||||
```bash
|
||||
#!/bin/sh
|
||||
|
||||
# Staging mode
|
||||
/opt/dyntls/dyntls.sh update-cert
|
||||
|
||||
# Productive mode
|
||||
#/opt/dyntls/dyntls.sh -P update-cert
|
||||
|
||||
exit 0
|
||||
```
|
||||
|
||||
Ensure the script is executable:
|
||||
|
||||
```bash
|
||||
sudo chmod 750 /etc/cron.daily/dyntls
|
||||
```
|
||||
The commented lines illustrate a productive mode variant. Use a staging or non-productive mode first until ACME validation, deployment hooks and rollback behavior are verified.
|
||||
|
||||
## ACME Backend
|
||||
|
||||
dynTLS does not implement the ACME protocol itself. Instead, it delegates all ACME communication to an external client script configured via `DYNTLS_LE_PROGRAM`.
|
||||
dynTLS does not implement the ACME protocol itself. Instead, it delegates ACME communication to an external client script configured through `DYNTLS_LE_PROGRAM`.
|
||||
|
||||
In this repository, ACME-related scripts are placed under:
|
||||
In this repository, ACME-related helper scripts are located under `contrib/acme`:
|
||||
|
||||
- `contrib/acme/letsencrypt_master.sh`
|
||||
Upstream ACME client script, unchanged.
|
||||
- `contrib/acme/letsencrypt_master_local.sh`
|
||||
Local variant with customized `dns-01` challenge handling, for example using Bind/nsupdate, TSIG and `rndc` to manage internal DNS zones.
|
||||
- `letsencrypt_master.sh` for the upstream-oriented ACME helper
|
||||
- `letsencrypt_master_local.sh` for a locally adapted variant, for example with customized DNS-01 handling via BIND, `nsupdate`, TSIG and `rndc`
|
||||
|
||||
Both scripts are based on the upstream `ght-acme.sh` client (<https://github.com/bruncsak/ght-acme.sh>) and are licensed under the GNU GPLv2-or-later; see `LICENSE.md` and the script headers for details.
|
||||
|
||||
Example configuration in `vars`:
|
||||
Example configuration:
|
||||
|
||||
```bash
|
||||
# Use local ACME backend
|
||||
setvar DYNTLS_LE_PROGRAM "contrib/acme/letsencrypt_master_local.sh"
|
||||
|
||||
# Pass DNS parameters to the ACME script (exported to its environment)
|
||||
set_var DYNTLS_DNS_SERVER "root-dns.example365.tld"
|
||||
set_var DYNTLS_DNS_TSIG "/opt/dyntls/private/tsig.key"
|
||||
```sh
|
||||
set_var DYNTLS_LE_PROGRAM "contrib/acme/letsencrypt_master_local.sh"
|
||||
set_var DYNTLS_DNS_SERVER "root-dns.example365.tld"
|
||||
set_var DYNTLS_DNS_TSIG "/opt/dyntls/private/tsig.key"
|
||||
```
|
||||
|
||||
You can replace this with other ACME clients (e.g. acme.sh, lego) by pointing `DYNTLS_LE_PROGRAM` to your preferred script and ensuring its CLI options match your setup.
|
||||
You can replace the bundled backend helper with another ACME client integration if its invocation and parameter handling match your deployment workflow.
|
||||
|
||||
## License
|
||||
|
||||
[MIT](https://dev.town-square.de/cb601/dyntls/src/branch/main/LICENSE)
|
||||
|
||||
See `LICENSE.md` for details and third-party license information.
|
||||
See `LICENSE` for details and third-party licensing notes.
|
||||
|
||||
## Authors
|
||||
|
||||
@@ -216,4 +161,4 @@ CB-601 - the open tec Elevator
|
||||
|
||||
## Project Home
|
||||
|
||||
Project Home: <https://dev.town-square.de/cb601/dyntls>
|
||||
Project Home: [https://dev.town-square.de/cb601/dyntls](https://dev.town-square.de/cb601/dyntls)
|
||||
|
||||
Reference in New Issue
Block a user