¿Cómo cambiar un usuario por tarea o conjunto de tareas?

160

Un tema recurrente que está en mis libros de jugadas ansibles es que a menudo debo ejecutar un comando con privilegios de sudo ( sudo: yes) porque me gustaría hacerlo para un determinado usuario. Idealmente, preferiría usar sudo para cambiar a ese usuario y ejecutar los comandos normalmente. Porque entonces no tendré que limpiar mis comandos de publicación habituales, como los directorios de chowning. Aquí hay un fragmento de uno de mis libros de jugadas:

- name: checkout repo
  git: repo=https://github.com/some/repo.git version=master dest={{ dst }}
  sudo: yes
- name: change perms
  file: dest={{ dst }} state=directory mode=0755 owner=some_user
  sudo: yes

Idealmente, podría ejecutar comandos o conjuntos de comandos como un usuario diferente, incluso si requiere sudo para su para ese usuario.

rgrinberg
fuente

Respuestas:

241

Con Ansible 1.9 o posterior

Usos del ansible become, become_usery become_methoddirectivas para lograr una escalada de privilegios. Puede aplicarlos a un juego completo o libro de jugadas, configurarlos en un libro de jugadas incluido o configurarlos para una tarea en particular.

- name: checkout repo
  git: repo=https://github.com/some/repo.git version=master dest={{ dst }}
  become: yes
  become_user: some_user

Puede usar become_withpara especificar cómo se logra la escalada de privilegios, siendo la predeterminada sudo.

La directiva está vigente para el alcance del bloque en el que se usa ( ejemplos ).

Consulte Hosts and Users para ver algunos ejemplos adicionales y Become (Privilege Escalation) para obtener documentación más detallada.

Además del alcance de la tarea becomey las become_userdirectivas, Ansible 1.9 agregó algunas nuevas variables y opciones de línea de comando para establecer estos valores para la duración de una jugada en ausencia de directivas explícitas:

A partir de Ansible 2.0.2.0, cuanto más viejo sudo/ sudo_usersintaxis describe a continuación sigue funcionando, pero los estados de notificación de desaprobación, "Esta característica se quitará en una versión futura."


Sintaxis anterior, obsoleta a partir de Ansible 1.9 y programada para su eliminación:

- name: checkout repo
  git: repo=https://github.com/some/repo.git version=master dest={{ dst }}
  sudo: yes
  sudo_user: some_user
Brett
fuente
44
Para especificar el sudo_user de una variable, use comillas alrededor de la plantilla de su variable, de esta manera, sudo_user: "{{ ansible_ssh_user }}"o obtendrá un error de sintaxis yaml.
Sumeet Pareek
Buena atrapada. Estaba tratando de hacer coincidir la formulación del problema con el OP lo más cerca posible, pero estoy de acuerdo en que usar la interpolación variable será la opción más común.
Brett
55
Desde Ansible 1.9, es el becomesistema en lugar de "sudo *".
AndiDog
2
La sintaxis 1.9+ para "Become" es correcta. También es posible que desee marcar "Become_method", ya que "su" podría ser mejor que el "sudo" predeterminado, dependiendo de la configuración de su sistema.
ElementalStorm
New Ansible variables and command line options are added to set these values for the duration of a play. @Brett, entonces, ¿eso significa que las tareas posteriores después de esto se ejecutarán some_usery no el usuario original remote_userque se usó para conectarse al host, es correcto?
JohnnyQ
43

En Ansible 2.x, puede usar el blockgrupo de tareas:

- block:
    - name: checkout repo
      git:
        repo: https://github.com/some/repo.git
        version: master
        dest: "{{ dst }}"
    - name: change perms
      file:
      dest: "{{ dst }}"
      state: directory
      mode: 0755
      owner: some_user
  become: yes
  become_user: some user
Arbab Nazar
fuente
26

En Ansible> 1.4 en realidad puede especificar un usuario remoto en el nivel de tarea que debería permitirle iniciar sesión como ese usuario y ejecutar ese comando sin recurrir a sudo. Si no puede iniciar sesión como ese usuario, la solución sudo_user también funcionará.

---
- hosts: webservers
  remote_user: root
  tasks:
    - name: test connection
      ping:
      remote_user: yourname

Ver http://docs.ansible.com/playbooks_intro.html#hosts-and-users

trcarden
fuente
Esta es la mejor solución para situaciones en las que no tiene privilegios de sudo
Darrel Holt
7

Una solución es usar la includedeclaración con remote_uservar (describir allí: http://docs.ansible.com/playbooks_roles.html ) pero debe hacerse en el libro de jugadas en lugar del nivel de tarea.

Guillaume Dedrie
fuente
Esta no es una buena solución para el caso de uso anterior. Sin embargo, no tuve conocimiento de esta solución durante mucho tiempo. Pensé que solo podía incluir roles.
ArjanSchouten
1

Puede especificar become_methodanular el método predeterminado establecido en ansible.cfg(si lo hay), y que se puede establecer en uno de sudo, su, pbrun, pfexec, doas, dzdo, ksu.

- name: I am confused
  command: 'whoami'
  become: true
  become_method: su
  become_user: some_user
  register: myidentity

- name: my secret identity
  debug:
    msg: '{{ myidentity.stdout }}'

Debe mostrar

TASK [my-task : my secret identity] ************************************************************
ok: [my_ansible_server] => {
    "msg": "some_user"
}
avi.elkharrat
fuente