- PVSM.RU - https://www.pvsm.ru -
Всем привет!
В этой статье я опишу как мы решали проблему централизованного обновления сертификатов Let's Encrypt и управления инфраструктурой с помощью ansible.
В нашем решении мы будем использовать:
Я предложу два варианта архитектуры, при которой наше решение может быть полезным. В свою очередь вы можете в комментариях предложить свои варианты.
Вариант 1: У вас есть несколько frontend серверов с public ip (к примеру 3), обслуживающих несколько доменов. Эти домены могут добавляться/удаляться. Чтобы не следить за каждым из frontend серверов — удобнее это сделать на одном letsencrypt server
'е:
Вариант 2: У вас есть только один сервер с public ip, а сертификаты вам нужны на серверах внутри сети:
Репозиторий с ролями доступны по ссылке [1].
В репозитории находится 4 роли:
nginx
и копирует базовые конфиги. Сама по себе роль не запускается из playbook. Она запускается по meta зависимости из других ролей.rsyncd
на хосте letsencrypt server
. В meta зависимостях имеет роль nginx-simple
. Соответственно, сначала установится nginx
, а потом проиграется роль letsencrypt server
.incron
и скопирует базовый конфиг. Роль так же не запускается на прямую как и nginx-simple
.incron
и nginx-simple
. После них роль front
копирует необходимые для example.com конфиги nginx
, добавляет задачу в cron
забирать новые сертификаты с letsencrypt server
и задачу в incron
проверять изменения файлов и выполнять хук nginx -s reload
Перейдем к практике:
Изначально у нас имеются:
letsencrypt server
)front
)На всех серверах установлена Ubuntu 16.04.
Для начала установим на все хосты nginx из общей роли nginx-simple
и раскидаем общие для всех хостов конфиги nginx (nginx.conf, параметры ssl, пути к сертификатам, etc).
Для letsencrypt server'а в шаблоне .../site-available/default.conf
папка .well_known
будет находиться в /var/www/
:
{% if letsencrypt_server %}
location /.well-known {
root /var/www/;
}
Для сервера/серверов группы front
, так как папка .well_known
используется не только для получения сертификатов, но и для другого ПО, мы импортируем в конфиг example.conf
letsencrypt-proxy.conf
и nginx будет искать папку локально на сервере front, используя дерективу try_file
:
{% if nginx_proxy_well_known %}
try_files $uri $uri/ @letsencrypt;
{% endif %}
Конфиги для домена заполнятся в зависимости от переменных из inventory. В репозитории это домен example.com
Так же, в зависимости от переменной letsencrypt_server
, роль nginx-simple
установит на letsencrypt server certbot
и добавит cron task на обновление сертификатов.
Так как мы решали эту задачу до появления wildcard сертификата от Let's Encrypt, мы рассмотрим оба варианта получения сертификата.
На сервере letsencrypt server выполняем:
certbot certonly --agree-tos -d example.ru --webroot -w /var/www/
Если доменов больше одного — дописываем последующие, используя ключ -d
.
Для получения wildcard сертификата нам нужно будет добавить в DNS TXT записи. На текущий момент это единственный вариант получения такого сертификата:
certbot certonly --agree-tos -d example.ru -d *.example.ru --preferred-challenges dns --manual --server https://acme-v02.api.letsencrypt.org/directory
Certbot напишет какие TXT записи вам нужно будет добавить.
Сертификаты мы получили, осталось настроить копирование их на front сервер/сервера. Для этого мы настроим rsyncd
на сервере letsencrypt с правами на чтение для ограниченого списка ip адресов:
hosts allow = {{ hosts_allow }}
hosts deny = *
list = true
use chroot = no
[cert]
path = /etc/letsencrypt/live/
uid = root
gid = root
read only = true
Каждые 5 минут cron task с серверов front будет проверять обновились ли сертификаты и забирать их. Т.к. сертификаты ротируются, в папке /etc/letsencrypt/live/{{ domain }}
лежат симлинки. Добавим ключ -L
чтобы вытаскивать оригиналы файлов:
/usr/bin/rsync -zavL --chmod=D0750,F640 --delete rsync://{{ hostvars['letsencrypt-server'].ansible_eth0.ipv4.address }}/cert /etc/letsencrypt/live/
Мы настроили nginx, получили сертификаты, забрали их на front сервер. Осталось определить, что файлы в папке /etc/letsencrypt/live/{{ domain }}
изменились и выполнить хук nginx -s reload
В этом нам поможет подсистема ядра linux inotify
и демон incron
. Подробнее о них можно прочесть тут [2].
Роль incron
установит нужные пакеты, а из шаблона роли front
добавится задача на мониторинг сертификатов и нужный хук:
/etc/letsencrypt/live/{{ domain }}/ IN_CREATE,IN_DELETE,IN_MODIFY,IN_MOVED_TO nginx -s reload
Мы постарались подробно описать весь процесс установки и настройки, а т.к. все описано в плейбуках ansible — статья получилась очень компактной. Как любят часто говорить — "чуть больше 100 строчек кода". На вопросы, критику и замечания с удовольствием ответим в комментариях.
Автор: Asten
Источник [3]
Сайт-источник PVSM.RU: https://www.pvsm.ru
Путь до страницы источника: https://www.pvsm.ru/nginx/276835
Ссылки в тексте:
[1] ссылке: https://github.com/asteny/letsencrypt-server
[2] тут: https://habrahabr.ru/post/66569/
[3] Источник: https://habrahabr.ru/post/352720/?utm_campaign=352720
Нажмите здесь для печати.