diff --git a/renew-certs.yaml b/renew-certs.yaml
index 89be60d4ebfff869abec951825f0b913ed6f67ba..886c1c95e1f6da5a92612a64212dafc6dc3850c1 100644
--- a/renew-certs.yaml
+++ b/renew-certs.yaml
@@ -3,12 +3,6 @@
   hosts:
     - localhost
   gather_facts: false
-  vars:
-    email: hostmaster@shore.co.il
-    acme_directory: https://acme-v02.api.letsencrypt.org/directory
-    # acme_directory: https://acme-staging-v02.api.letsencrypt.org/directory
-    acme_version: 2
-
   handlers:
     - name: Restart Nginx on host01
       delegate_to: host01
@@ -31,553 +25,39 @@
       command: docker kill --signal SIGHUP mail_imap_1
 
   tasks:
-    - name: Generate account key
-      community.crypto.openssl_privatekey:
-        mode: 0o0600
-        path: &account_key_src account.key
-        size: 4096
-        state: present
-        type: RSA
-      tags:
-        - always
-
-    - name: Register account
-      community.crypto.acme_account:
-        account_key_src: *account_key_src
-        acme_directory: |-
-            {{ acme_directory }}
-        acme_version: |-
-            {{ acme_version }}
-        contact:
-          - mailto:{{ email }}
-        select_crypto_backend: &crypto_backend cryptography
-        state: present
-        terms_agreed: true
-      tags:
-        - always
-
-    - name: Generate site key
-      community.crypto.openssl_privatekey:
-        mode: &mode 0o0600
-        path: &site_key_src |-
-            {{ playbook_dir }}/site.key
-        size: &size 4096
-        state: present
-        type: &type RSA
-      tags:
-        - ns4
-
-    - name: Generate site certificate signing request
-      community.crypto.openssl_csr:
-        common_name: ns4.shore.co.il
-        country_name: &country_name IL
-        digest: &digest sha256
-        email_address: |-
-            {{ email }}
-        locality_name: &locality_name Israel
-        organization_name: &organization_name Shore technologies
-        path: &site_csr_src site.csr
-        privatekey_path: *site_key_src
-        state: present
+    - name: Issue certificate for ns4
+      include_tasks: '{{ playbook_dir }}/tasks/renew-cert.yaml'
+      vars:
+        handlers:
+          - Restart Nginx on ns4
+        host: ns4
         subject_alt_name: |-
-          DNS:autoconfig.shore.co.il,DNS:registry.shore.co.il,DNS:www.shore.co.il,DNS:shore.co.il
-      register: acme_site_csr
-      tags:
-        - ns4
-
-    - name: Create site challenge
-      community.crypto.acme_certificate:
-        account_email: |-
-            {{ email }}
-        account_key_src: *account_key_src
-        acme_directory: |-
-            {{ acme_directory }}
-        acme_version: |
-            {{ acme_version }}
-        csr: *site_csr_src
-        fullchain_dest: &site_cert_src |-
-            {{ playbook_dir }}/site.crt
-        modify_account: false
-        remaining_days: 35
-        select_crypto_backend: *crypto_backend
-      register: acme_site_challenge
+          DNS:ns4.shore.co.il,DNS:autoconfig.shore.co.il,DNS:registry.shore.co.il,DNS:www.shore.co.il,DNS:shore.co.il
       tags:
         - ns4
 
-    - name: Debug site challenge
-      debug:
-        var: acme_site_challenge
-        verbosity: 1
-      tags:
-        - ns4
-
-    - name: Renew site cert
-      when: acme_site_challenge is changed
-      tags:
-        - ns4
-      block:
-
-        - name: Create ACME challenge directory
-          delegate_to: ns4
-          file:
-            path: /var/www/www.shore.co.il/.well-known/acme-challenge
-            state: directory
-
-        - name: Copy http-01 site challenge
-          delegate_to: ns4
-          with_dict: |
-              {{ acme_site_challenge['challenge_data'] }}
-          copy:
-            content: |-
-                {{ item.value['http-01']['resource_value'] }}
-            # yamllint disable-line rule:line-length
-            dest: /var/www/www.shore.co.il/{{ item.value['http-01']['resource'] }}
-            group: www-data
-            mode: 0o0644
-            owner: root
-
-        - name: Validate site challenge
-          community.crypto.acme_certificate:
-            account_email: |-
-                {{ email }}
-            account_key_src: *account_key_src
-            acme_directory: |-
-                {{ acme_directory }}
-            acme_version: |
-                {{ acme_version }}
-            challenge: http-01
-            csr: *site_csr_src
-            data: "{{ acme_site_challenge }}"
-            fullchain_dest: *site_cert_src
-            modify_account: false
-            remaining_days: 35
-            select_crypto_backend: *crypto_backend
-
-    - name: Copy site key, certificate to server
-      delegate_to: ns4
-      with_items:
-        - src: *site_key_src
-          dest: /var/ssl/site.key
-          mode: 0o0444
-        - src: *site_cert_src
-          dest: /var/ssl/site.crt
-          mode: 0o0444
-      copy:
-        src: |-
-            {{ item.src }}
-        dest: |-
-            {{ item.dest }}
-        mode: |-
-            {{ item.mode }}
-        owner: root
-        group: root
-      notify:
-        - Restart Nginx on ns4
-      tags:
-        - ns4
-
-    - name: Generate host key
-      community.crypto.openssl_privatekey:
-        mode: *mode
-        path: &host_key_src |-
-            {{ playbook_dir }}/host.key
-        size: *size
-        state: present
-        type: *type
-      tags:
-        - host01
-
-    - name: Generate host certificate signing request
-      community.crypto.openssl_csr:
-        common_name: ns1.shore.co.il
-        country_name: *country_name
-        digest: *digest
-        email_address: |-
-            {{ email }}
-        locality_name: *locality_name
-        organization_name: *organization_name
-        path: &host_csr_src host.csr
-        privatekey_path: *host_key_src
-        state: present
+    - name: Issue certificate for host01
+      include_tasks: '{{ playbook_dir }}/tasks/renew-cert.yaml'
+      vars:
+        handlers:
+          - Restart Nginx on host01
+        host: host01
         subject_alt_name: |-
-          DNS:lam.shore.co.il,DNS:nextcloud.shore.co.il,DNS:git.shore.co.il,DNS:code.shore.co.il
-      register: acme_host_csr
-      tags:
-        - host01
-
-    - name: Create host challenge
-      community.crypto.acme_certificate:
-        account_email: |-
-            {{ email }}
-        account_key_src: *account_key_src
-        acme_directory: |-
-            {{ acme_directory }}
-        acme_version: |
-            {{ acme_version }}
-        csr: *host_csr_src
-        fullchain_dest: &host_cert_src |-
-            {{ playbook_dir }}/host.crt
-        modify_account: false
-        remaining_days: 35
-        select_crypto_backend: *crypto_backend
-      register: acme_host_challenge
-      tags:
-        - host01
-
-    - name: Debug host challenge
-      debug:
-        var: acme_host_challenge
-        verbosity: 1
-      tags:
-        - host01
-
-    - name: Renew host cert
-      when: acme_host_challenge is changed
-      tags:
-        - host01
-      block:
-
-        - name: Create ACME challenge directory
-          delegate_to: host01
-          file:
-            path: /var/www/www.shore.co.il/.well-known/acme-challenge
-            state: directory
-
-        - name: Copy http-01 host challenge
-          delegate_to: host01
-          with_dict: |
-              {{ acme_host_challenge['challenge_data'] }}
-          copy:
-            content: |-
-                {{ item.value['http-01']['resource_value'] }}
-            # yamllint disable-line rule:line-length
-            dest: /var/www/www.shore.co.il/{{ item.value['http-01']['resource'] }}
-            group: www-data
-            mode: 0o0644
-            owner: root
-
-        - name: Validate host challenge
-          community.crypto.acme_certificate:
-            account_email: |-
-                {{ email }}
-            account_key_src: *account_key_src
-            acme_directory: |-
-                {{ acme_directory }}
-            acme_version: |
-                {{ acme_version }}
-            challenge: http-01
-            csr: *host_csr_src
-            data: "{{ acme_host_challenge }}"
-            fullchain_dest: *host_cert_src
-            modify_account: false
-            remaining_days: 35
-            select_crypto_backend: *crypto_backend
-
-    - name: Copy host key, certificate to server
-      delegate_to: host01
-      with_items:
-        - src: *host_key_src
-          dest: /var/ssl/site.key
-          mode: 0o0444
-        - src: *host_cert_src
-          dest: /var/ssl/site.crt
-          mode: 0o0444
-      copy:
-        src: |-
-            {{ item.src }}
-        dest: |-
-            {{ item.dest }}
-        mode: |-
-            {{ item.mode }}
-        owner: root
-        group: root
-      notify:
-        - Restart Nginx on host01
+          DNS:ns1.shore.co.il,DNS:lam.shore.co.il,DNS:nextcloud.shore.co.il,DNS:git.shore.co.il,DNS:code.shore.co.il
       tags:
         - host01
 
-    - name: Generate mail key
-      community.crypto.openssl_privatekey:
-        mode: *mode
-        path: &mail_key_src |-
-            {{ playbook_dir }}/mail.key
-        size: *size
-        state: present
-        type: *type
-      tags:
-        - mail
-
-    - name: Generate mail certificate signing request
-      community.crypto.openssl_csr:
-        common_name: smtp.shore.co.il
-        country_name: *country_name
-        digest: *digest
-        email_address: |-
-            {{ email }}
-        locality_name: *locality_name
-        organization_name: *organization_name
-        path: &mail_csr_src mail.csr
-        privatekey_path: *mail_key_src
-        state: present
+    - name: Issue certificate for smtp
+      include_tasks: '{{ playbook_dir }}/tasks/renew-cert.yaml'
+      vars:
+        delegate_host: host01
+        filename: mail
+        handlers:
+          - Reload Dovecot
+          - Reload Exim
+          - Restart Nginx on host01
+        host: mail
         subject_alt_name: |-
             DNS:smtp.shore.co.il,DNS:imap.shore.co.il,DNS:mta-sts.shore.co.il
-      register: acme_mail_csr
-      tags:
-        - mail
-
-    - name: Create mail challenge
-      community.crypto.acme_certificate:
-        account_email: |-
-            {{ email }}
-        account_key_src: *account_key_src
-        acme_directory: |-
-            {{ acme_directory }}
-        acme_version: |
-            {{ acme_version }}
-        csr: *mail_csr_src
-        fullchain_dest: &mail_cert_src |-
-            {{ playbook_dir }}/mail.crt
-        modify_account: false
-        remaining_days: 35
-        select_crypto_backend: *crypto_backend
-      register: acme_mail_challenge
-      tags:
-        - mail
-
-    - name: Debug mail challenge
-      debug:
-        var: acme_mail_challenge
-        verbosity: 1
-      tags:
-        - mail
-
-    - name: Renew mail cert
-      when: acme_mail_challenge is changed
-      tags:
-        - mail
-      block:
-
-        - name: Create ACME challenge directory
-          delegate_to: host01
-          file:
-            path: /var/www/mail.shore.co.il/.well-known/acme-challenge
-            state: directory
-
-        - name: Copy http-01 mail challenge
-          delegate_to: host01
-          with_dict: |
-              {{ acme_mail_challenge['challenge_data'] }}
-          copy:
-            content: |-
-                {{ item.value['http-01']['resource_value'] }}
-            # yamllint disable-line rule:line-length
-            dest: /var/www/mail.shore.co.il/{{ item.value['http-01']['resource'] }}
-            group: www-data
-            mode: 0o0644
-            owner: root
-
-        - name: Validate mail challenge
-          community.crypto.acme_certificate:
-            account_email: |-
-                {{ email }}
-            account_key_src: *account_key_src
-            acme_directory: |-
-                {{ acme_directory }}
-            acme_version: |
-                {{ acme_version }}
-            challenge: http-01
-            csr: *mail_csr_src
-            data: "{{ acme_mail_challenge }}"
-            fullchain_dest: *mail_cert_src
-            modify_account: false
-            remaining_days: 35
-            select_crypto_backend: *crypto_backend
-
-    - name: Copy mail key, certificate to server
-      delegate_to: host01
-      with_items:
-        - src: *mail_key_src
-          dest: /var/ssl/mail.key
-          mode: 0o0444
-        - src: *mail_cert_src
-          dest: /var/ssl/mail.crt
-          mode: 0o0444
-      copy:
-        src: |-
-            {{ item.src }}
-        dest: |-
-            {{ item.dest }}
-        mode: |-
-            {{ item.mode }}
-        owner: root
-        group: root
-      notify:
-        - Reload Dovecot
-        - Reload Exim
-        - Restart Nginx on host01
-      tags:
-        - mail
-
-    - name: Generate kodi key
-      community.crypto.openssl_privatekey:
-        mode: *mode
-        path: &kodi_key_src |-
-            {{ playbook_dir }}/kodi.key
-        size: *size
-        state: present
-        type: *type
-      tags:
-        - kodi
-
-    - name: Generate kodi certificate signing request
-      community.crypto.openssl_csr:
-        common_name: kodi.shore.co.il
-        country_name: *country_name
-        digest: *digest
-        email_address: |-
-            {{ email }}
-        locality_name: *locality_name
-        organization_name: *organization_name
-        path: &kodi_csr_src kodi.csr
-        privatekey_path: *kodi_key_src
-        state: present
-        subject_alt_name: |-
-            DNS:kodi.shore.co.il,DNS:library.shore.co.il,DNS:jellyfin.shore.co.il
-      register: acme_kodi_csr
-      tags:
-        - kodi
-
-    - name: Create kodi challenge
-      community.crypto.acme_certificate:
-        account_email: |-
-            {{ email }}
-        account_key_src: *account_key_src
-        acme_directory: |-
-            {{ acme_directory }}
-        acme_version: |
-            {{ acme_version }}
-        csr: *kodi_csr_src
-        fullchain_dest: &kodi_cert_src |-
-            {{ playbook_dir }}/kodi.crt
-        modify_account: false
-        remaining_days: 35
-        select_crypto_backend: *crypto_backend
-      register: acme_kodi_challenge
-      tags:
-        - kodi
-
-    - name: Debug kodi challenge
-      debug:
-        var: acme_kodi_challenge
-        verbosity: 1
-      tags:
-        - kodi
-
-    - name: Renew kodi cert
-      when: acme_kodi_challenge is changed
-      tags:
-        - kodi
-      block:
-
-        - name: Create ACME challenge directory
-          delegate_to: kodi
-          file:
-            path: /var/www/www.shore.co.il/.well-known/acme-challenge
-            state: directory
-
-        - name: Copy http-01 kodi challenge
-          delegate_to: kodi
-          with_dict: |
-              {{ acme_kodi_challenge['challenge_data'] }}
-          copy:
-            content: |-
-                {{ item.value['http-01']['resource_value'] }}
-            # yamllint disable-line rule:line-length
-            dest: /var/www/www.shore.co.il/{{ item.value['http-01']['resource'] }}
-            group: www-data
-            mode: 0o0644
-            owner: root
-
-        - name: Validate kodi challenge
-          community.crypto.acme_certificate:
-            account_email: |-
-                {{ email }}
-            account_key_src: *account_key_src
-            acme_directory: |-
-                {{ acme_directory }}
-            acme_version: |
-                {{ acme_version }}
-            challenge: http-01
-            csr: *kodi_csr_src
-            data: "{{ acme_kodi_challenge }}"
-            fullchain_dest: *kodi_cert_src
-            modify_account: false
-            remaining_days: 35
-            select_crypto_backend: *crypto_backend
-
-    - name: Copy kodi key, certificate to server
-      delegate_to: kodi
-      with_items:
-        - src: *kodi_key_src
-          dest: /var/ssl/site.key
-          mode: 0o0444
-        - src: *kodi_cert_src
-          dest: /var/ssl/site.crt
-          mode: 0o0444
-      copy:
-        src: |-
-            {{ item.src }}
-        dest: |-
-            {{ item.dest }}
-        mode: |-
-            {{ item.mode }}
-        owner: root
-        group: root
-      notify:
-        - Restart Nginx on kodi
-      tags:
-        - kodi
-
-    - name: Generate Diffie-Hellman parameters on host01
-      delegate_to: host01
-      community.crypto.openssl_dhparam:
-        force: true
-        mode: 0o0644
-        path: /var/ssl/dhparams
-        size: 4096
-        state: present
-      notify:
-        - Reload Dovecot
-        - Restart Nginx on host01
-      tags:
-        - mail
-        - host01
-        - dhparams
-
-    - name: Generate Diffie-Hellman parameters on ns4
-      delegate_to: ns4
-      community.crypto.openssl_dhparam:
-        force: true
-        mode: 0o0644
-        path: /var/ssl/dhparams
-        size: 4096
-        state: present
-      notify:
-        - Restart Nginx on ns4
-      tags:
-        - ns4
-        - dhparams
-
-    - name: Generate Diffie-Hellman parameters on kodi
-      delegate_to: kodi
-      community.crypto.openssl_dhparam:
-        force: true
-        mode: 0o0644
-        path: /var/ssl/dhparams
-        size: 4096
-        state: present
-      notify:
-        - Restart Nginx on kodi
       tags:
-        - kodi
-        - dhparams
+        - smtp
diff --git a/tasks/renew-cert.yaml b/tasks/renew-cert.yaml
new file mode 100644
index 0000000000000000000000000000000000000000..96ce9b3e0f83a5bb1705f9ac8b42139d2606149a
--- /dev/null
+++ b/tasks/renew-cert.yaml
@@ -0,0 +1,136 @@
+---
+- name: Generate account key
+  community.crypto.openssl_privatekey:
+    mode: 0o0600
+    path: &account_key_src account.key
+    size: 4096
+    state: present
+    type: RSA
+  tags:
+    - always
+
+- name: Register account
+  community.crypto.acme_account:
+    account_key_src: *account_key_src
+    acme_directory: &acme_directory |-
+      https://acme-v02.api.letsencrypt.org/directory
+    # acme_directory: &acme_directory |-
+    #   https://acme-staging-v02.api.letsencrypt.org/directory
+    acme_version: &acme_version 2
+    contact:
+      - mailto:hostmaster@shore.co.il
+    select_crypto_backend: &crypto_backend cryptography
+    state: present
+    terms_agreed: true
+  tags:
+    - always
+
+- name: Generate {{ host }} key
+  community.crypto.openssl_privatekey:
+    mode: &mode 0o0600
+    path: &key_src |-
+        {{ playbook_dir }}/{{ host }}.key
+    size: &size 4096
+    state: present
+    type: &type RSA
+
+- name: Generate {{ host }} certificate signing request
+  community.crypto.openssl_csr:
+    country_name: &country_name IL
+    digest: &digest sha256
+    email_address: &email hostmaster@shore.co.il
+    locality_name: &locality_name Israel
+    organization_name: &organization_name Shore technologies
+    path: &csr_src '{{ host }}.csr'
+    privatekey_path: *key_src
+    state: present
+    subject_alt_name: '{{ subject_alt_name }}'
+  register: acme_csr
+
+- name: Create {{ host }} challenge
+  community.crypto.acme_certificate:
+    account_email: *email
+    account_key_src: *account_key_src
+    acme_directory: *acme_directory
+    acme_version: *acme_version
+    csr: *csr_src
+    fullchain_dest: &cert_src |-
+        {{ playbook_dir }}/{{ host }}.crt
+    modify_account: false
+    remaining_days: 35
+    select_crypto_backend: *crypto_backend
+  register: acme_challenge
+
+- name: Debug {{ host }} challenge
+  debug:
+    var: acme_challenge
+    verbosity: 1
+
+- name: Renew {{ host }} cert
+  when: acme_challenge is changed
+  block:
+
+    - name: Create ACME challenge directory on {{ host }}
+      delegate_to: &delegate_to '{{ delegate_host|default(host) }}'
+      file:
+        path: /var/www/www.shore.co.il/.well-known/acme-challenge
+        state: directory
+
+    - name: Copy http-01 {{ host }} challenge
+      delegate_to: *delegate_to
+      with_dict: |
+          {{ acme_challenge['challenge_data'] }}
+      copy:
+        content: |-
+            {{ item.value['http-01']['resource_value'] }}
+        # yamllint disable-line rule:line-length
+        dest: /var/www/www.shore.co.il/{{ item.value['http-01']['resource'] }}
+        group: www-data
+        mode: 0o0644
+        owner: root
+
+    - name: Validate {{ host }} challenge
+      community.crypto.acme_certificate:
+        account_email: *email
+        account_key_src: *account_key_src
+        acme_directory: *acme_directory
+        acme_version: *acme_version
+        challenge: http-01
+        csr: *csr_src
+        data: "{{ acme_challenge }}"
+        fullchain_dest: *cert_src
+        modify_account: false
+        remaining_days: 35
+        select_crypto_backend: *crypto_backend
+
+- name: Copy {{ host }} key and certificate to server
+  delegate_to: *delegate_to
+  with_items:
+    - src: *key_src
+      dest: /var/ssl/{{ filename|default('site') }}.key
+      mode: 0o0444
+    - src: *cert_src
+      dest: /var/ssl/{{ filename|default('site') }}.crt
+      mode: 0o0444
+  copy:
+    src: |-
+        {{ item.src }}
+    dest: |-
+        {{ item.dest }}
+    mode: |-
+        {{ item.mode }}
+    owner: root
+    group: root
+  notify: '{{ handlers }}'
+
+- name: Generate Diffie-Hellman parameters on {{ host }}
+  delegate_to: *delegate_to
+  community.crypto.openssl_dhparam:
+    force: true
+    mode: 0o0644
+    path: /var/ssl/dhparams
+    size: 4096
+    state: present
+  notify: '{{ handlers }}'
+  tags:
+    - dhparams