Автоматизация SSL сертификатов Let's Encrypt: выпуск, продление, мониторинг
Меня зовут Семёнов Евгений Сергеевич, директор АйТи Фреш. За 15 лет я повидал столько просроченных SSL на продакшене, что завёл негласное правило: каждый внешний сервис — только автоматизированная ротация. Ручной certbot на 10 серверах раз в 3 месяца — это прямой путь к утренним звонкам «у нас сайт не открывается». Расскажу, как поднять автоматику, мониторить сроки и спать спокойно.
Почему 90 дней — это благо
Let's Encrypt выпускает сертификаты на 90 дней именно ради того, чтобы никто не надеялся на ручное обновление. 90 дней — это принудительная автоматизация. Я всегда объясняю клиентам: короткий срок жизни — плюс, потому что он заставляет сразу сделать всё правильно.
Certbot vs acme.sh
| Параметр | certbot | acme.sh |
|---|---|---|
| Язык | Python | Bash |
| Зависимости | Много (Python, pip) | Только curl и openssl |
| DNS-провайдеры | ~20 | 140+ |
| Wildcard | Да | Да |
| Деплой-хуки | Есть | Удобнее |
| Старт | apt install | curl | sh |
Базовый certbot для nginx
sudo apt install certbot python3-certbot-nginx
sudo certbot --nginx -d itfresh.ru -d www.itfresh.ru \
--agree-tos -m boss@itfresh.ru --no-eff-email \
--redirect --hsts --staple-ocsp
# certbot сам добавит задачу в systemd timer
sudo systemctl list-timers | grep certbot
acme.sh для wildcard через Cloudflare
curl https://get.acme.sh | sh -s email=boss@itfresh.ru
# Учётные данные Cloudflare
export CF_Token="xxx"
export CF_Account_ID="yyy"
~/.acme.sh/acme.sh --issue -d itfresh.ru -d '*.itfresh.ru' --dns dns_cf \
--keylength ec-384 --server letsencrypt
~/.acme.sh/acme.sh --install-cert -d itfresh.ru \
--key-file /etc/ssl/itfresh/key.pem \
--fullchain-file /etc/ssl/itfresh/fullchain.pem \
--reloadcmd "systemctl reload nginx"
Cron автоматически добавляется и раз в день проверяет, не пора ли обновлять.
DNS-01 для закрытых сервисов
У нас на практике часть сервисов (Grafana, внутренние дашборды) живёт в приватной подсети и не доступна снаружи. Классический HTTP-01 не работает. DNS-01 — идеален: подтверждение идёт через TXT-запись, сам сервер может оставаться за файрволом.
~/.acme.sh/acme.sh --issue -d grafana.corp.itfresh.ru \
--dns dns_cf \
--server letsencrypt --force
Мониторинг сроков — обязателен
Автоматика — не повод не мониторить. Я всегда ставлю двойной контроль: внутри сервера (скрипт, проверяющий локальный файл) и снаружи (HTTP-зонд с проверкой Not After).
#!/bin/bash
# /usr/local/bin/ssl-check.sh
DOMAIN=$1
DAYS_LEFT=$(( ( $(date -d "$(openssl s_client -servername $DOMAIN -connect $DOMAIN:443 \
< /dev/null 2>/dev/null | openssl x509 -noout -enddate | cut -d= -f2)" +%s) - $(date +%s) ) / 86400 ))
if [ $DAYS_LEFT -lt 20 ]; then
curl -s -X POST https://api.telegram.org/bot$TOKEN/sendMessage \
-d chat_id=$CHATID \
-d text="SSL $DOMAIN истекает через $DAYS_LEFT дней!"
fi
# Cron: 0 9 * * * /usr/local/bin/ssl-check.sh itfresh.ru
Интеграция с Zabbix и Prometheus
На серьёзных проектах я подключаю blackbox_exporter или template App SSL Certificate Check в Zabbix. Дашборд показывает таблицу «домен — дней до истечения», сортировка по возрастанию. Алерты отправляются при пороге 21 день и 7 дней.
# prometheus.yml
scrape_configs:
- job_name: blackbox-ssl
metrics_path: /probe
params:
module: [tcp_connect_ssl]
static_configs:
- targets:
- itfresh.ru:443
- api.itfresh.ru:443
relabel_configs:
- source_labels: [__address__]
target_label: __param_target
- target_label: __address__
replacement: blackbox:9115
Центральное хранилище сертификатов
Если серверов много — не выпускайте на каждом. Я использую один «сертификат-сервер» за Let's Encrypt и распространяю файлы по остальным через Ansible или rsync. Это проще, чем объяснять DNS-провайдеру API-ключи каждому серверу.
# Пример Ansible-таска
- name: Distribute SSL certificate
ansible.builtin.copy:
src: /etc/ssl/itfresh/fullchain.pem
dest: /etc/ssl/itfresh/fullchain.pem
owner: root
group: root
mode: '0644'
notify: reload nginx
Мини-кейс: SaaS на 12 доменов
В апреле 2025 года клиент — SaaS для логистов — обратился с болью: 12 клиентских доменов, каждый с wildcard SSL, продление вручную, раз в квартал кто-то забывает, сайт 2–4 часа лежит. Разбор показал: сертификаты стояли на разных Ubuntu-серверах, certbot был у каждого свой, cron иногда ломался из-за ротации IP в Cloudflare. За 2 рабочих дня мы вынесли всё на один «cert-master» (виртуалка на Dell Xeon Platinum 8280 в дата-центре МТС), переключились на acme.sh с DNS-01 через Cloudflare API, настроили Ansible-раскатку и двойной мониторинг — локальный скрипт + blackbox_exporter. С мая по декабрь — ноль инцидентов с SSL. Стоимость работ — 38 000 руб., экономия на простоях — порядка 300 000 руб./год.
Типичные грабли
- Rate limit Let's Encrypt. 50 сертификатов на домен/неделю, 5 повторных выпусков того же набора SAN. Тестируйте на staging-сервере
--server https://acme-staging-v02.api.letsencrypt.org/directory. - Забыли reload сервиса. Сертификат обновился, но nginx держит старый в памяти — пока не сделаешь reload, клиенты видят просрочку.
- Deploy-hook не тот. На Apache — apachectl graceful, на HAProxy — специальный механизм SSL binds.
- Неправильный owner файлов. Сервис postfix/dovecot/prosody не читает от root — проверяйте mode и owner.
- HTTP-01 и перенаправление. Если редирект http→https без исключения
/.well-known/acme-challenge, валидация падает.
Backup сертификатов и аккаунта
Папка ~/.acme.sh/ или /etc/letsencrypt/ — это всё состояние. Бэкапим в репозиторий git (приватный) или в зашифрованный бэкап. Потеря аккаунта — не катастрофа, но неудобство.
tar czf letsencrypt-backup-$(date +%F).tar.gz /etc/letsencrypt/
gpg -c letsencrypt-backup-*.tar.gz
rsync -a letsencrypt-backup-*.tar.gz.gpg backup@nas:/backups/
Настроим автоматический выпуск SSL под ключ
Автоматизация Let's Encrypt, wildcard через DNS-01, мониторинг в Zabbix/Prometheus, алерты в Telegram. От 15 000 руб. за 1–5 доменов, от 40 000 за масштабируемую инфраструктуру.
Телефон: +7 903 729-62-41
Telegram: @ITfresh_Boss
Семёнов Евгений Сергеевич, директор АйТи Фреш
FAQ — частые вопросы по Let's Encrypt
- Сколько действует сертификат Let's Encrypt?
- 90 дней. Рекомендуется автоматическое продление за 30 дней до истечения.
- Что такое DNS-01 challenge?
- Метод валидации домена через создание TXT-записи в DNS. Позволяет выпускать wildcard-сертификаты.
- Можно ли использовать Let's Encrypt внутри корпоративной сети?
- Да, через DNS-01 challenge. Сервер не должен быть доступен из интернета.
- Certbot или acme.sh — что выбрать?
- Certbot — Python, проще для базовых кейсов. Acme.sh — pure bash, легче, поддерживает больше DNS-провайдеров.
- Как мониторить срок действия SSL?
- Zabbix, Prometheus blackbox_exporter или cron-скрипт с openssl s_client, отправляющий в Telegram.