
- name: "Fetch existing API tokens via curl inside admin container"
  command: >-
    docker compose exec -T admin \
      curl -s -X GET {{ mailu_api_base_url }}/token \
        -H "Authorization: Bearer {{ MAILU_API_TOKEN }}"
  args:
    chdir: "{{ MAILU_DOCKER_DIR }}"
  register: mailu_tokens_cli
  changed_when: false
  no_log: "{{ MASK_CREDENTIALS_IN_LOGS | bool }}"

- name: "Extract existing token info for '{{ mailu_user_key }};{{ mailu_user_name }}'"
  set_fact:
    mailu_user_existing_token: >-
      {{ (
           mailu_tokens_cli.stdout
           | default('[]')
           | from_json
           | selectattr('comment','equalto', mailu_user_key ~ " - ansible.infinito")
           | list
         ).0 | default(None) }}

- name: "Delete existing API token for '{{ mailu_user_key }};{{ mailu_user_name }}' if local token missing but remote exists"
  command: >-
    docker compose exec -T admin \
      curl -s -X DELETE {{ mailu_api_base_url }}/token/{{ mailu_user_existing_token.id }} \
        -H "Authorization: Bearer {{ MAILU_API_TOKEN }}"
  args:
    chdir: "{{ MAILU_DOCKER_DIR }}"
  when:
    - users[mailu_user_key].mailu_token is not defined
    - mailu_user_existing_token is not none
    - mailu_user_existing_token.id is defined
  register: mailu_token_delete
  changed_when: mailu_token_delete.rc == 0
  no_log: "{{ MASK_CREDENTIALS_IN_LOGS | bool }}"

- name: "Create API token for '{{ mailu_user_key }};{{ mailu_user_name }}' if no local token defined"
  command: >-
    docker compose exec -T admin
    curl -sS -f -X POST {{ mailu_api_base_url }}/token
      -H "Authorization: Bearer {{ MAILU_API_TOKEN }}"
      -H "Content-Type: application/json"
      -d '{{ {
            "comment": mailu_user_key ~ " - ansible.infinito",
            "email": users[mailu_user_key].email,
            "ip": mailu_token_ip
          } | to_json }}'
  args:
    chdir: "{{ MAILU_DOCKER_DIR }}"
  when: users[mailu_user_key].mailu_token is not defined
  register: mailu_token_creation
  # If curl sees 4xx/5xx it returns non-zero due to -f → fail the task.
  failed_when:
    - mailu_token_creation.rc != 0
    # Fallback: if some gateway returns 200 but embeds an error JSON.
    - mailu_token_creation.rc == 0 and
      (mailu_token_creation.stdout is search('"code"\\s*:\\s*4\\d\\d') or
       mailu_token_creation.stdout is search('cannot be found'))
  # Only mark changed when a token is actually present in the JSON.
  changed_when: mailu_token_creation.stdout is search('"token"\\s*:')
  no_log: "{{ MASK_CREDENTIALS_IN_LOGS | bool }}"

- name: "Set mailu_token for '{{ mailu_user_key }};{{ mailu_user_name }}' in users dict if newly created"
  set_fact:
    users: >-
      {{ users
         | combine({
             mailu_user_key: (
               users[mailu_user_key]
               | combine({
                   'mailu_token': (mailu_token_creation.stdout | from_json).token
                 })
             )
           }, recursive=True)
      }}
  when: users[mailu_user_key].mailu_token is not defined
  no_log: "{{ MASK_CREDENTIALS_IN_LOGS | bool }}"
