¿Cómo puedo evitar que ansible escriba contraseñas en los archivos de registro?

22

Estoy configurando un servidor MySQL y quiero que Ansible establezca la mysql-rootcontraseña durante la instalación.

Con la ayuda de internet se me ocurrió esta solución:

- name: Set MySQL root password before installing
  debconf: name='mysql-server' question='mysql-server/root_password' value='{{mysql_root_pwd | quote}}' vtype='password'
- name: Confirm MySQL root password before installing
  debconf: name='mysql-server' question='mysql-server/root_password_again' value='{{mysql_root_pwd | quote}}' vtype='password'
- name: Install Mysql
  apt: pkg=mysql-server state=latest

mysql_root_pwdes una variable cargada desde la Bóveda de Ansible. Esto funciona bien, pero ahora en el servidor hay muchas líneas en el registro:

Apr 10 14:39:59 servername ansible-debconf: Invoked with value=THEPASSWORD vtype=password question=mysql-server/root_password name=mysql-server unseen=None
Apr 10 14:39:59 servername ansible-debconf: Invoked with value=THEPASSWORD vtype=password question=mysql-server/root_password_again name=mysql-server unseen=None

¿Cómo puedo evitar que Ansible escriba contraseñas de texto claro en los archivos de registro?

claus
fuente

Respuestas:

28

Para evitar que se registre una tarea con información confidencial, en syslog u otro, configure no_log: true en la tarea:

- name: secret stuff
  command: "echo {{secret_root_password}} | sudo su -"
  no_log: true

La ejecución de la tarea aún se registrará, pero con pocos detalles. Además, el módulo utilizado debe admitir no_log, por lo que debe probar módulos personalizados.

Consulte las preguntas frecuentes de Ansible para obtener más detalles. Se puede aplicar a un libro de jugadas completo, sin embargo, el resultado se vuelve un poco desagradable con "censurado". mensajes

Bill Carlson
fuente
2
Entre otras cosas, eso es lo que dice esta respuesta serverfault.com/a/682823/9517
user9517 es compatible con GoFundMonica el
9

El comportamiento observado parece ser un error en el módulo debconf. Presenté un informe de error .

El usuario bcoca en github señaló que se puede usar la no_log: truedirectiva en tareas, que establecen contraseñas, para evitar el registro. Esta es una solución alternativa, que funciona para mí hasta que se solucione el error.

claus
fuente
Recibo un error cuando uso esa directiva. ¿Alguna idea de lo que estoy haciendo mal? ERROR: no_log is not a legal parameter in an Ansible task or handler
Bouke Versteegh
2
Resulta que tenía una versión antigua de ansible! Para solucionar (en Ubuntu): sudo apt-add-repository ppa:ansible/ansible, sudo apt-get update,sudo apt-get install ansible
Bouke Versteegh
El mismo problema para mí, pero no puedo hacer que n_log: verdadero funcione como se esperaba. Mi versión de Ansible es 1.7.2. Lo que es tuyo ?
jmcollin92
@ jmcollin92 Actualmente uso 2.1. Hay una guía aquí sobre cómo instalar la última versión de la fuente. Lo uso como ansible todavía está madurando.
claus
2

Lo resolví actualizando la versión Ansible a 1.6.1

sudo pip install ansible==1.6.1
0x3bfc
fuente
2

Según los documentos de Ansible :

log_path

Si está presente y configurado ansible.cfg, Ansible registrará información sobre ejecuciones en la ubicación designada. Asegúrese de que el usuario que ejecuta Ansible tenga permisos en el archivo de registro:

log_path=/var/log/ansible.log 

Este comportamiento no está activado de forma predeterminada. Tenga en cuenta que ansible, sin esta configuración, registrará los argumentos del módulo llamados al registro del sistema de las máquinas administradas. Los argumentos de contraseña están excluidos.

Parece que la configuración log_pathen su nodo de control dará como resultado que no haya registros en los nodos de destino.

Droopy4096
fuente
En realidad, tengo un ansible.cfg en mi directorio local, donde llamo ansible, configurando el log_path. El registro local se crea correctamente y se actualiza después de una nueva ejecución (el registro funciona). Esto no (aunque el documento que señaló lo promete) impide que el host remoto inicie sesión. ¿También la afirmación "Se excluyen los argumentos de contraseña" parece no ser 100% verdadera? ¿Es esto un error (o incluso dos)?
claus
2
@claus "argumentos de contraseña extraídos" solo se aplica a los módulos donde el argumento de contraseña es explícito. Ansible no sabe qué argumento sería contraseña y cuál no con comandos generales como debconf, shell, raw, etc.
Droopy4096
Desplácese hacia la derecha en mi libro de jugadas inicial. Dice vtype='password'. Eso debería ser lo suficientemente explícito en mi humilde opinión? Supongo que el mensaje de registro también es creado por el módulo debconf.
Claus
Esto es incorrecto. La documentación debe decir con mayor precisión "Tenga en cuenta que ansible, independientemente de esta configuración , registrará los argumentos del módulo llamados al registro del sistema de las máquinas administradas".
augurar
2

Hay una mejor manera que simplemente no_log: True

- name: write in string variables login and password
  set_fact:
    temp_user: "{{ USER_VAR }}"
    temp_pass: "{{ PASSWORD_VAR }}"


- name: Your operation with password in output
  shell: '/opt/hello.sh'
  ignore_errors: True
  no_log: True
  register: myregister

- debug:
    msg: '{{ myregister.stderr | regex_replace(temp_user) | regex_replace(temp_pass) }}'
  when: myregister.stderr != ""

- debug:
    msg: '{{ myregister.stdout | regex_replace(temp_user) | regex_replace(temp_pass) }}'
  when: myregister.stdout != ""

- fail:
    msg: "error shell /opt/hello.sh"
  when: myregister.stderr != ""

Como puede ver, necesita agregar:

ignore_errors: true
no_log: true

Y luego realice la salida del resultado del comando con regex_replace, donde:

USER_VAR - variable de inicio de sesión

PASSWORD_VAR - variable de contraseña

Con este enfoque, no solo ocultará las contraseñas y los inicios de sesión, sino que también obtendrá el resultado de su operación

TheDESTROS
fuente
1

Esta es una adición a la respuesta de TheDESTROS de este hilo:

  1. escribe una plantilla, que envuelve el comando con un secreto:

wrapper-script.sh.j2

echo {{ secret_eg_from_ansible_vault }} | su - "ls -l"
  1. Invoque el script de envoltura y elimínelo de inmediato:
- name: create template
  template:
    src: wrapper-script.sh.j2
    dest: /tmp/wrapper-script.sh
    mode: 0700
  no_log: True
- name: invoke command with secret and remove it
  shell: /tmp/wrapper-script.sh; rm -f /tmp/wrapper-script.sh

Necesita un poco menos de código y puede encontrar los comandos en sus registros. Solo hay una caverna, si hay un secreto en los comandos stdout. Si desea evitar la plantilla externa, el copymódulo con el parámetro contentpuede ayudar a escribir un pequeño script de envoltura sobre la marcha.

Christian Kaiser
fuente
1

El no_log: trueenfoque se utilizará como último recurso si otros intentos fallan porque hará que la ejecución de la tarea sea totalmente opaca y no tendrá idea de cuándo falla.

Las prácticas de seguridad recomiendan dar credenciales de stdin o, cuando no sea posible, usar archivos de credenciales (o incluso ejecutables).

Aquí hay un ejemplo sobre cómo realizar un inicio de sesión de podman seguro evitando exponer la contraseña:

- name: secured login
  become: true
  command: >
    podman login --username={{ user }} --password-stdin ...
  args:
    stdin: "{{ secret }}"
  register: result

Con esto, el secreto no se expondrá, resultpero aún podrá ver la salida del comando.

La mayoría de las herramientas que necesitan iniciar sesión implementan uno de los enfoques más seguros mencionados. Usar credenciales en CLI en el código es como tener 123456como contraseña de su banco.

Sorin
fuente