---
# Copyright (c) Ansible Project
# GNU General Public License v3.0+ (see LICENSES/GPL-3.0-or-later.txt or https://www.gnu.org/licenses/gpl-3.0.txt)
# SPDX-License-Identifier: GPL-3.0-or-later

- block:
  - name: "({{ select_crypto_backend }}) Generate PKCS#12 file (check mode)"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible.p12'
      friendly_name: abracadabra
      privatekey_path: '{{ remote_tmp_dir }}/ansible_pkey1.pem'
      certificate_path: '{{ remote_tmp_dir }}/ansible1.crt'
      state: present
      return_content: true
    check_mode: true
    register: p12_standard_check

  - name: "({{ select_crypto_backend }}) Generate PKCS#12 file"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible.p12'
      friendly_name: abracadabra
      privatekey_path: '{{ remote_tmp_dir }}/ansible_pkey1.pem'
      certificate_path: '{{ remote_tmp_dir }}/ansible1.crt'
      state: present
      return_content: true
    register: p12_standard

  - name: "({{ select_crypto_backend }}) Generate PKCS#12 file again, idempotency (check mode)"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible.p12'
      friendly_name: abracadabra
      privatekey_path: '{{ remote_tmp_dir }}/ansible_pkey1.pem'
      certificate_path: '{{ remote_tmp_dir }}/ansible1.crt'
      state: present
      return_content: true
    check_mode: true
    register: p12_standard_idempotency_check

  - name: "({{ select_crypto_backend }}) Generate PKCS#12 file again, idempotency"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible.p12'
      friendly_name: abracadabra
      privatekey_path: '{{ remote_tmp_dir }}/ansible_pkey1.pem'
      certificate_path: '{{ remote_tmp_dir }}/ansible1.crt'
      state: present
      return_content: true
    register: p12_standard_idempotency

  - name: "({{ select_crypto_backend }}) Generate PKCS#12 file again, idempotency (empty other_certificates)"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible.p12'
      friendly_name: abracadabra
      privatekey_path: '{{ remote_tmp_dir }}/ansible_pkey1.pem'
      certificate_path: '{{ remote_tmp_dir }}/ansible1.crt'
      state: present
      return_content: true
      other_certificates: []
    register: p12_standard_idempotency_no_certs

  - name: "({{ select_crypto_backend }}) Read ansible_pkey1.pem"
    slurp:
      src: '{{ remote_tmp_dir }}/ansible_pkey1.pem'
    register: ansible_pkey_content

  - name: "({{ select_crypto_backend }}) Read ansible1.crt"
    slurp:
      src: '{{ remote_tmp_dir }}/ansible1.crt'
    register: ansible_crt_content

  - name: "({{ select_crypto_backend }}) Generate PKCS#12 file again, idempotency (private key from file)"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible.p12'
      friendly_name: abracadabra
      privatekey_content: '{{ ansible_pkey_content.content | b64decode }}'
      certificate_content: '{{ ansible_crt_content.content | b64decode }}'
      state: present
      return_content: true
    register: p12_standard_idempotency_2

  - name: "({{ select_crypto_backend }}) Read ansible.p12"
    slurp:
      src: '{{ remote_tmp_dir }}/ansible.p12'
    register: ansible_p12_content

  - name: "({{ select_crypto_backend }}) Validate PKCS#12"
    assert:
      that:
      - p12_standard.pkcs12 == ansible_p12_content.content
      - p12_standard_idempotency.pkcs12 == p12_standard.pkcs12

  - name: "({{ select_crypto_backend }}) Generate PKCS#12 file (force)"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible.p12'
      friendly_name: abracadabra
      privatekey_path: '{{ remote_tmp_dir }}/ansible_pkey1.pem'
      certificate_path: '{{ remote_tmp_dir }}/ansible1.crt'
      state: present
      force: true
    register: p12_force

  - name: "({{ select_crypto_backend }}) Generate PKCS#12 file (force + change mode)"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible.p12'
      friendly_name: abracadabra
      privatekey_path: '{{ remote_tmp_dir }}/ansible_pkey1.pem'
      certificate_path: '{{ remote_tmp_dir }}/ansible1.crt'
      state: present
      force: true
      mode: '0644'
    register: p12_force_and_mode

  - name: "({{ select_crypto_backend }}) Dump PKCS#12"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      src: '{{ remote_tmp_dir }}/ansible.p12'
      path: '{{ remote_tmp_dir }}/ansible_parse.pem'
      action: parse
      state: present
    register: p12_dumped

  - name: "({{ select_crypto_backend }}) Dump PKCS#12 file again, idempotency"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      src: '{{ remote_tmp_dir }}/ansible.p12'
      path: '{{ remote_tmp_dir }}/ansible_parse.pem'
      action: parse
      state: present
    register: p12_dumped_idempotency

  - name: "({{ select_crypto_backend }}) Dump PKCS#12, check mode"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      src: '{{ remote_tmp_dir }}/ansible.p12'
      path: '{{ remote_tmp_dir }}/ansible_parse.pem'
      action: parse
      state: present
    check_mode: true
    register: p12_dumped_check_mode

  - name: "({{ select_crypto_backend }}) Generate PKCS#12 file with multiple certs and passphrase"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible_multi_certs.p12'
      friendly_name: abracadabra
      passphrase: hunter3
      privatekey_path: '{{ remote_tmp_dir }}/ansible_pkey1.pem'
      certificate_path: '{{ remote_tmp_dir }}/ansible1.crt'
      other_certificates:
      - '{{ remote_tmp_dir }}/ansible2.crt'
      - '{{ remote_tmp_dir }}/ansible3.crt'
      state: present
    register: p12_multiple_certs

  - name: "({{ select_crypto_backend }}) Read ansible2.crt / ansible3.crt.crt"
    slurp:
      src: "{{ item }}"
    loop:
      - "{{ remote_tmp_dir ~ '/ansible2.crt' }}"
      - "{{ remote_tmp_dir ~ '/ansible3.crt' }}"
    register: ansible_other_content

  - name: "({{ select_crypto_backend }}) Generate PKCS#12 file with multiple certs and passphrase, again (idempotency)"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible_multi_certs.p12'
      friendly_name: abracadabra
      passphrase: hunter3
      privatekey_path: '{{ remote_tmp_dir }}/ansible_pkey1.pem'
      certificate_path: '{{ remote_tmp_dir }}/ansible1.crt'
      other_certificates_content:
      - "{{ ansible_other_content.results[0].content | b64decode }}"
      - "{{ ansible_other_content.results[1].content | b64decode }}"
      state: present
    register: p12_multiple_certs_idempotency

  - name: "({{ select_crypto_backend }}) Dump PKCS#12 with multiple certs and passphrase"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      src: '{{ remote_tmp_dir }}/ansible_multi_certs.p12'
      path: '{{ remote_tmp_dir }}/ansible_parse_multi_certs.pem'
      passphrase: hunter3
      action: parse
      state: present

  - name: "({{ select_crypto_backend }}) Generate PKCS#12 file (password fail 1)"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible_pw1.p12'
      friendly_name: abracadabra
      privatekey_path: '{{ remote_tmp_dir }}/ansible_pkey1.pem'
      privatekey_passphrase: hunter2
      certificate_path: '{{ remote_tmp_dir }}/ansible1.crt'
      state: present
    ignore_errors: true
    register: passphrase_error_1

  - name: "({{ select_crypto_backend }}) Generate PKCS#12 file (password fail 2)"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible_pw2.p12'
      friendly_name: abracadabra
      privatekey_path: '{{ remote_tmp_dir }}/privatekeypw.pem'
      privatekey_passphrase: wrong_password
      certificate_path: '{{ remote_tmp_dir }}/ansible1.crt'
      state: present
    ignore_errors: true
    register: passphrase_error_2

  - name: "({{ select_crypto_backend }}) Generate PKCS#12 file (password fail 3)"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible_pw3.p12'
      friendly_name: abracadabra
      privatekey_path: '{{ remote_tmp_dir }}/privatekeypw.pem'
      certificate_path: '{{ remote_tmp_dir }}/ansible1.crt'
      state: present
    ignore_errors: true
    register: passphrase_error_3

  - name: "({{ select_crypto_backend }}) Generate PKCS#12 file, no privatekey"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible_no_pkey.p12'
      friendly_name: abracadabra
      certificate_path: '{{ remote_tmp_dir }}/ansible1.crt'
      state: present
    register: p12_no_pkey

  - name: "({{ select_crypto_backend }}) Create broken PKCS#12"
    copy:
      dest: '{{ remote_tmp_dir }}/broken.p12'
      content: broken

  - name: "({{ select_crypto_backend }}) Regenerate broken PKCS#12"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/broken.p12'
      friendly_name: abracadabra
      privatekey_path: '{{ remote_tmp_dir }}/ansible_pkey1.pem'
      certificate_path: '{{ remote_tmp_dir }}/ansible1.crt'
      state: present
      force: true
      mode: '0644'
    register: output_broken

  - name: "({{ select_crypto_backend }}) Generate PKCS#12 file"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible_backup.p12'
      friendly_name: abracadabra
      privatekey_path: '{{ remote_tmp_dir }}/ansible_pkey1.pem'
      certificate_path: '{{ remote_tmp_dir }}/ansible1.crt'
      state: present
      backup: true
    register: p12_backup_1

  - name: "({{ select_crypto_backend }}) Generate PKCS#12 file (idempotent)"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible_backup.p12'
      friendly_name: abracadabra
      privatekey_path: '{{ remote_tmp_dir }}/ansible_pkey1.pem'
      certificate_path: '{{ remote_tmp_dir }}/ansible1.crt'
      state: present
      backup: true
    register: p12_backup_2

  - name: "({{ select_crypto_backend }}) Generate PKCS#12 file (change)"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible_backup.p12'
      friendly_name: abra
      privatekey_path: '{{ remote_tmp_dir }}/ansible_pkey1.pem'
      certificate_path: '{{ remote_tmp_dir }}/ansible1.crt'
      state: present
      force: true
      backup: true
    register: p12_backup_3

  - name: "({{ select_crypto_backend }}) Generate PKCS#12 file (remove)"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible_backup.p12'
      state: absent
      backup: true
      return_content: true
    register: p12_backup_4

  - name: "({{ select_crypto_backend }}) Generate PKCS#12 file (remove, idempotent)"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible_backup.p12'
      state: absent
      backup: true
    register: p12_backup_5

  - name: "({{ select_crypto_backend }}) Generate 'empty' PKCS#12 file"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible_empty.p12'
      friendly_name: abracadabra
      other_certificates:
      - '{{ remote_tmp_dir }}/ansible2.crt'
      - '{{ remote_tmp_dir }}/ansible3.crt'
      state: present
    register: p12_empty


  - name: "({{ select_crypto_backend }}) Generate 'empty' PKCS#12 file (idempotent)"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible_empty.p12'
      friendly_name: abracadabra
      other_certificates:
      - '{{ remote_tmp_dir }}/ansible3.crt'
      - '{{ remote_tmp_dir }}/ansible2.crt'
      state: present
    register: p12_empty_idem

  - name: "({{ select_crypto_backend }}) Generate 'empty' PKCS#12 file (idempotent, concatenated other certificates)"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible_empty.p12'
      friendly_name: abracadabra
      other_certificates:
      - '{{ remote_tmp_dir }}/ansible23.crt'
      other_certificates_parse_all: true
      state: present
    register: p12_empty_concat_idem

  - name: "({{ select_crypto_backend }}) Read ansible23.crt"
    slurp:
      src: "{{ remote_tmp_dir ~ '/ansible23.crt' }}"
    register: ansible_other_content_concat

  - name: "({{ select_crypto_backend }}) Generate 'empty' PKCS#12 file (idempotent, concatenated other certificates)"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible_empty.p12'
      friendly_name: abracadabra
      other_certificates_content:
      - "{{ ansible_other_content_concat.content | b64decode }}"
      other_certificates_parse_all: true
      state: present
    register: p12_empty_concat_content_idem

  - name: "({{ select_crypto_backend }}) Generate 'empty' PKCS#12 file (parse)"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      src: '{{ remote_tmp_dir }}/ansible_empty.p12'
      path: '{{ remote_tmp_dir }}/ansible_empty.pem'
      action: parse

  - name: "({{ select_crypto_backend }}) Generate PKCS#12 file passphrase and compatibility encryption"
    openssl_pkcs12:
      select_crypto_backend: '{{ select_crypto_backend }}'
      path: '{{ remote_tmp_dir }}/ansible_compatibility2022.p12'
      friendly_name: compat_fn
      encryption_level: compatibility2022
      iter_size: 3210
      passphrase: magicpassword
      privatekey_path: '{{ remote_tmp_dir }}/ansible_pkey1.pem'
      certificate_path: '{{ remote_tmp_dir }}/ansible1.crt'
      other_certificates:
      - '{{ remote_tmp_dir }}/ansible2.crt'
      - '{{ remote_tmp_dir }}/ansible3.crt'
      state: present
    register: p12_compatibility2022
    when:
      - select_crypto_backend == 'cryptography'
      - cryptography_version.stdout is version('38.0.0', '>=')

  - import_tasks: ../tests/validate.yml

  always:
  - name: "({{ select_crypto_backend }}) Delete PKCS#12 file"
    openssl_pkcs12:
      state: absent
      path: '{{ remote_tmp_dir }}/{{ item }}.p12'
    loop:
    - ansible
    - ansible_no_pkey
    - ansible_multi_certs
    - ansible_pw1
    - ansible_pw2
    - ansible_pw3
    - ansible_empty
    - ansible_compatibility2022
