From 5bda80152d8318779157cceaf4fa1b2427173815 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Alexander=20K=C3=A4b?= <alexander.kaeb@h-da.de> Date: Thu, 23 Feb 2023 13:57:55 +0100 Subject: [PATCH] feat(node-certs): Add tasks to generate node certificates As some communication to the graylog instance needs to be encrypted using node certificates add tasks that will generate certificates for the nodes the sidecar service will be installed on. Implements #1 --- README.md | 31 ++++++++++++++++++++ defaults/main.yml | 7 +++++ tasks/main.yml | 4 +++ tasks/node-certs.yml | 70 ++++++++++++++++++++++++++++++++++++++++++++ 4 files changed, 112 insertions(+) create mode 100644 tasks/node-certs.yml diff --git a/README.md b/README.md index 30c9eb1..40aa4b7 100644 --- a/README.md +++ b/README.md @@ -30,4 +30,35 @@ graylog_sidecar_server_url: # SECRET: token to be used for sidecars graylog_sidecar_server_api_token: +``` + +## Node Certificates + +For node certificates to be generated you will need to create an additional host group +named `sidecar-ca` with a single host, that stores the CA certificate that should be +used for client certificate generation. + +The CA file must be available at: `/etc/graylog/sidecar/sidecar-ca.pem` +The CA file's key must be available at: `/etc/graylog/sidecar/sidecar-ca.key` + +The location of the files can be configured via variable. The name of the files however +must be as specified. The following variables are available in regard to the node +certificates. + +```yaml +# Whether to generate node certificates (default: true) +generate_node_certs: true + +# The local directory where certs are stored before being uploaded +tmp_cert_dir: "/tmp/graylog-sidecar-certs" + +# The path where the CA certificate and key should be fetched from +# the remote machine specified in the 'sidecar-ca' host group +gl_sidecar_ca_path: "/etc/graylog/sidecar" + +# The directory where client certs should be stored at +sidecar_cert_dir: "/etc/graylog/sidecar" + +# The time in days the client certificates will be valid +cert_valid_days: 1095 ``` \ No newline at end of file diff --git a/defaults/main.yml b/defaults/main.yml index 173f5cc..5f1d297 100644 --- a/defaults/main.yml +++ b/defaults/main.yml @@ -7,3 +7,10 @@ install_filebeat: true filebeat_repo_urls: "RedHat": "https://artifacts.elastic.co/packages/oss-8.x/yum" "Debian": "https://artifacts.elastic.co/packages/oss-8.x/apt" + +# --- OTHER --- +generate_node_certs: true +tmp_cert_dir: "/tmp/graylog-sidecar-certs" # local directory +gl_sidecar_ca_path: "/etc/graylog/sidecar" +sidecar_cert_dir: "/etc/graylog/sidecar" +cert_valid_days: 1095 \ No newline at end of file diff --git a/tasks/main.yml b/tasks/main.yml index 0ecd2f4..5e79877 100644 --- a/tasks/main.yml +++ b/tasks/main.yml @@ -65,3 +65,7 @@ cmd: update-crypto-policies --set DEFAULT changed_when: false become: true + +- name: Generate Node certificates + ansible.builtin.import_tasks: node-certs.yml + when: generate_node_certs diff --git a/tasks/node-certs.yml b/tasks/node-certs.yml new file mode 100644 index 0000000..462bb21 --- /dev/null +++ b/tasks/node-certs.yml @@ -0,0 +1,70 @@ +--- +- name: Fail if 'sidecar-ca' host group is missing # noqa: run_once[task] + ansible.builtin.fail: + msg: "Please add a host group 'sidecar-ca' with the host storing the CA file first" + run_once: true + when: "not ({{ groups['sidecar-ca'] is defined }})" + +- name: Node Certificates | Create temporary directopry for certificates # noqa: run_once[task] + ansible.builtin.file: + path: "{{ tmp_cert_dir }}" + state: directory + mode: 0755 + run_once: true + delegate_to: localhost + +- name: Node Certificates | Fetch Sidecar CA Cert + ansible.builtin.fetch: + src: "{{ item }}" + dest: "{{ tmp_cert_dir }}/" + flat: true + with_items: + - "{{ gl_sidecar_ca_path }}/gl-sidecar.pem" + - "{{ gl_sidecar_ca_path }}/gl-sidecar.key" + delegate_to: "{{ groups['sidecar-ca'] | first }}" + become: true + run_once: true + +- name: Node Certificates + delegate_to: localhost + block: + - name: Node Certificates | Generate private keys + community.crypto.openssl_privatekey: + path: "{{ tmp_cert_dir }}/sidecar-{{ inventory_hostname }}.key" + return_content: true + state: present + + - name: Node Certificates | Create CSRs + community.crypto.openssl_csr_pipe: + privatekey_path: "{{ tmp_cert_dir }}/sidecar-{{ inventory_hostname }}.key" + common_name: "{{ ansible_fqdn }}" # CN + subject_alt_name: + - "DNS:{{ inventory_hostname }}" + - "DNS:{{ ansible_fqdn }}" + - "IP:{{ ansible_default_ipv6.address }}" + # - "IP:{{ ansible_default_ipv4.address }}" + register: "node_csr" + + - name: Node Certificates | Generate Certificates + community.crypto.x509_certificate: + path: "{{ tmp_cert_dir }}/sidecar-{{ inventory_hostname }}.pem" + csr_content: "{{ node_csr.csr }}" + provider: ownca + ownca_path: "{{ tmp_cert_dir }}/gl-sidecar.pem" + ownca_privatekey_path: "{{ tmp_cert_dir }}/gl-sidecar.key" + ownca_privatekey_passphrase: "{{ ca_passphrase }}" + ownca_not_after: "+{{ cert_valid_days }}d" + ownca_not_before: "-1d" # valid since yesterday + +- name: Node Certificates | Copy Certificates + become: true + block: + - name: Node Certificates | Copy Node certificates + ansible.builtin.copy: + src: "{{ tmp_cert_dir }}/{{ item }}" + dest: "{{ sidecar_cert_dir }}" + mode: 0600 + with_items: + - "sidecar-{{ inventory_hostname }}.key" + - "sidecar-{{ inventory_hostname }}.pem" + - "gl-sidecar.pem" \ No newline at end of file -- GitLab