From c0638a8d6478ae9d8c3be9d7a65c636bc4262f54 Mon Sep 17 00:00:00 2001 From: Robin Sonnabend <robin@fsmpi.rwth-aachen.de> Date: Sat, 22 Feb 2020 16:42:32 +0100 Subject: [PATCH] Finish acmebot role --- acmebot/defaults/main.yml | 22 +++---- acmebot/files/acmebot.service | 26 ++++++++ acmebot/files/acmebot.timer | 11 ++++ acmebot/files/service-after.conf | 2 - acmebot/tasks/main.yml | 96 +++++++++++++++++------------ webserver/templates/ssl-certificate | 6 +- 6 files changed, 105 insertions(+), 58 deletions(-) create mode 100644 acmebot/files/acmebot.service create mode 100644 acmebot/files/acmebot.timer delete mode 100644 acmebot/files/service-after.conf diff --git a/acmebot/defaults/main.yml b/acmebot/defaults/main.yml index edc0c96..23557df 100644 --- a/acmebot/defaults/main.yml +++ b/acmebot/defaults/main.yml @@ -1,7 +1,8 @@ --- acmebot_account_mail: "{{ adminaddr }}" -acmebot_after_nginx_proxy: true +acmebot_version: "v2.6.0" +acmebot_enable_update_check: true acmebot_settings: {} acmebot_default_settings: @@ -20,9 +21,8 @@ acmebot_default_settings: - "google_pilot" file_user: root - file_group: ssl-cert + file_group: root - # TODO default to both key types or single one? default to non-/custom params? key_size: 4096 # null to turn off RSA certificates key_curve: "secp384r1" # null to turn off ECDSA certificates key_cipher: null @@ -63,12 +63,11 @@ acmebot_default_key_suffixes: # set to null for specified certs to use dns-01 for those acmebot_directories: {} acmebot_default_directories: - pid: "/run" + pid: "/run/acmebot" log: "/var/log/acmebot" resource: "/var/lib/acmebot" temp: null - # TODO layout equivalent to acmetool private_key: /etc/ssl/acmebot/privkey backup_key: /etc/ssl/acmebot/backup_privkey previous_key: null @@ -78,7 +77,7 @@ acmebot_default_directories: chain: /etc/ssl/acmebot/chain # maybe null param: /etc/ssl/acmebot/params # maybe null challenge: /etc/ssl/acmebot/challenges # for dns-01 only - http_challenge: /var/www/acme-challenge # maybe null + http_challenge: "/var/run/acme/acme-challenge" # maybe null hpkp: /etc/ssl/acmebot/hpkp # maybe null ocsp: /etc/ssl/acmebot/ocsp # maybe null sct: "/etc/ssl/acmebot/scts/{name}/{key_type}" # maybe null @@ -90,13 +89,12 @@ acmebot_file_names: {} acmebot_default_file_names: log: "acmebot.log" - # TODO layout equivalent to acmetool - private_key: "{name}{suffix}.key" - backup_key: "{name}_backup{suffix}.key" - previous_key: "{name}_previous{suffix}.key" - full_key: "{name}_full{suffix}.key" + private_key: "{name}{suffix}.pem" + backup_key: "{name}_backup{suffix}.pem" + previous_key: "{name}_previous{suffix}.pem" + full_key: "{name}_full{suffix}.pem" certificate: "{name}{suffix}.pem" - full_certificate: "{name}+root{suffix}.pem" + full_certificate: "{name}{suffix}.pem" chain: "{name}_chain{suffix}.pem" param: "{name}_param.pem" challenge: "{name}" diff --git a/acmebot/files/acmebot.service b/acmebot/files/acmebot.service new file mode 100644 index 0000000..8ba466a --- /dev/null +++ b/acmebot/files/acmebot.service @@ -0,0 +1,26 @@ +[Unit] +Description=Reconcile Let's Encrypt certificates +Documentation=file:/usr/share/doc/acmebot/README.rst.gz +After=nss-lookup.target +After=apache2.service nginx.service bind9.service nginx-proxy.service + +[Service] +Type=oneshot +ExecStart=/usr/local/sbin/acmebot --accept +TimeoutStartSec=5min +CapabilityBoundingSet=CAP_CHOWN +NoNewPrivileges=yes +PrivateTmp=yes +PrivateDevices=yes +ProtectSystem=strict +ReadWritePaths=/etc/ssl +ConfigurationDirectory=acmebot +RuntimeDirectory=acmebot acme/acme-challenge +StateDirectory=acmebot +LogsDirectory=acmebot +ProtectHome=yes +ProtectKernelTunables=yes +ProtectControlGroups=yes +RestrictRealtime=yes +RestrictAddressFamilies=AF_UNIX AF_INET AF_INET6 + diff --git a/acmebot/files/acmebot.timer b/acmebot/files/acmebot.timer new file mode 100644 index 0000000..02c80b1 --- /dev/null +++ b/acmebot/files/acmebot.timer @@ -0,0 +1,11 @@ +[Unit] +Description=Reconcile Let's Encrypt certificates twice daily + +[Timer] +OnCalendar=*-*-* 00,12:00:00 +RandomizedDelaySec=1h +Persistent=yes + +[Install] +WantedBy=timers.target + diff --git a/acmebot/files/service-after.conf b/acmebot/files/service-after.conf deleted file mode 100644 index a54ec72..0000000 --- a/acmebot/files/service-after.conf +++ /dev/null @@ -1,2 +0,0 @@ -[Unit] -After=nginx-proxy.service diff --git a/acmebot/tasks/main.yml b/acmebot/tasks/main.yml index 5cb2fcb..dfb7b45 100644 --- a/acmebot/tasks/main.yml +++ b/acmebot/tasks/main.yml @@ -1,40 +1,53 @@ --- -# TODO import account info from acmetool if present -- name: ensure acmebot is installed +- name: ensure requirements for acmebot are installed apt: - name: acmebot + name: + - python3-appdirs + - python3-pyparsing + - python3-packaging + - python3-openssl + - python3-dns + - python3-cryptography + - python3-asn1crypto + - python3-acme + - python3-yaml state: present -- name: ensure we can modify the systemd unit +- name: get the acmebot repository + git: + repo: https://github.com/plinss/acmebot.git + dest: /opt/acmebot + version: "{{acmebot_version}}" + environment: + TMPDIR: /root/.ansible/tmp + +- name: add acmebot to path file: - path: /etc/systemd/system/acmebot.service.d - state: directory - owner: root - group: root - mode: '0755' - notify: - - reload systemd service files - when: acmebot_after_nginx_proxy + src: /opt/acmebot/acmebot + dest: /usr/local/sbin/acmebot + state: link -- name: ensure systemd waits for proxy service +- name: install systemd units copy: - src: service-after.conf - dest: /etc/systemd/system/acmebot.service.d/nginx-proxy.conf + src: "{{item}}" + dest: /etc/systemd/system/ owner: root group: root mode: '0644' + with_items: + - "acmebot.service" + - "acmebot.timer" notify: - reload systemd service files - when: acmebot_after_nginx_proxy -- name: ensure systemd does not wait for proxy service +- name: create the acmebot config directory file: - path: /etc/systemd/system/acmebot.service.d/nginx-proxy.conf - state: absent - notify: - - reload systemd service files - when: not acmebot_after_nginx_proxy + path: /etc/acmebot + state: directory + owner: root + group: root + mode: '0755' - name: ensure the acmebot is configured template: @@ -57,27 +70,28 @@ notify: - update certificates -# TODO initial run accepting TOS -- name: check if acmebot is configured - command: acmetool status - register: acmetool_status - changed_when: false -- name: initially configure acmebot - command: acmebot --detail - when: not acmetool_status.stdout is search(acmetool_endpoint) - -# TODO force run when cert store does not match configured certificates -- name: test if the desired certificates are present - stat: - path: "/var/lib/acme/live/{{item.hostnames[0]}}" - register: live_stat - changed_when: not live_stat.stat.exists - with_items: "{{acmetool_certificates}}" - notify: - - update certificates - - name: ensure certificates are updated regularly systemd: name: acmebot.timer enabled: true state: started + +- name: check for updates daily + file: + src: /opt/acmebot/update-check.sh + dest: /etc/cron.daily/acmebot-update-check.sH + state: link + when: acmebot_enable_update_check + +- name: don't check for updates daily + file: + path: /etc/cron.daily/acmebot-update-check.sh + state: absent + when: not acmebot_enable_update_check + +- name: rotate acmebot logs + file: + src: /opt/acmebot/logrotate.d/acmebot + dest: /etc/logrotate.d/acmebot + state: link + diff --git a/webserver/templates/ssl-certificate b/webserver/templates/ssl-certificate index 87bcc8a..5ddb5e2 100644 --- a/webserver/templates/ssl-certificate +++ b/webserver/templates/ssl-certificate @@ -1,6 +1,6 @@ - ssl_certificate {{server.certificate|default("/var/lib/acme/live/" + server.server_name + "/fullchain")}}; - ssl_trusted_certificate {{server.certificate|default("/var/lib/acme/live/" + server.server_name + "/fullchain")}}; - ssl_certificate_key {{server.private_key|default("/var/lib/acme/live/" + server.server_name + "/privkey")}}; + ssl_certificate {{server.certificate|default("/etc/ssl/acmebot/cert/" + server.server_name + ".pem")}}; + ssl_trusted_certificate {{server.certificate|default("/etc/ssl/acmebot/cert/" + server.server_name + ".pem")}}; + ssl_certificate_key {{server.private_key|default("/etc/ssl/acmebot/privkey/" + server.server_name + ".pem")}}; {% set strength = server.cipher_strength|default(cipher_strength) %} ssl_protocols {{protocols[strength]}}; -- GitLab