Search code examples
ansiblesudo

ansible: become fails when trying to switch user (timeout error)


I need to be able to login into a remote server, switch user and then, do whatever it is required.

I played with ansible and found the "become" tool, so I tried it, after all... it allows dzdo.

My playbook became something like this:

- name: Create  empty  file
  file: path=touchedFile.txt  state=touch
  become: true
  become_method: dzdo
  become_user: userid

I ran it and got: "Sorry, user someuser is not allowed to execute '/bin/sh -c echo BECOME-SUCCESS-xklihidlmxpfvxxnbquvsqrgfjlyrsah; /usr/bin/python /tmp/ansible-tmp-1513185770.1-52571838933499/command.py'

Mmm... I thought that maybe it is trying to execute something like this:

dzdo touch touchedFile.txt

Unfortunately, it doesn't work like that in my company. The policy forces us to log in as ourselves and then switch to the required user like this:

dzdo su - userid

I did a bit of research and tried running several commands in a single block, my logic thought that if I switched users first, then everything else would be executed as the other user. My playbook was updated to look like this:

- name: Create  empty  file
  shell: |
    dzdo su - userid
    touch  touchedFile.txt

It failed and I tried this then:

- name: Create  empty  file
  command: "{{ item }}"
  with_items:
    - dzdo su - userid
    - touch  touchedFile.txt

And failed again... both approaches create touchedFile.txt but as my user and not the one they should...

Is there a way to do what I need directly with Ansible? Or do I need to start looking for more complex alternatives? In the past I achieved what I'm trying to do now with a script that mainly used "expect", but it was prone to errors... that's why I'm looking for better alternatives.

EDIT 2018-01-08: I can now use "sudo su - userid" without the need of a password; but somehow Ansible always expect input from the user, a timeout occurs and my play fails:

fatal: [240]: FAILED! => {
    "failed": true, 
    "msg": "Timeout (12s) waiting for privilege escalation prompt: "
}

One thing I noticed is that Ansible is doing the following:

EXEC ssh -vvv -C -o ControlMaster=auto -o ControlPersist=60s -o StrictHostKeyChecking=no
 -o 'IdentityFile="./.ssh/fatCamel"' -o KbdInteractiveAuthentication=no
 -o PreferredAuthentications=gssapi-with-mic,gssapi-keyex,hostbased,publickey
 -o PasswordAuthentication=no -o User=login_userid -o ConnectTimeout=10
 -o ControlPath=/Users/local_userid/.ansible/cp/446eee77f4
 -tt server_url '/bin/sh -c '"'"'sudo su - sudo_userid -u root /bin/sh
 -c '"'"'"'"'"'"'"'"'echo BECOME-SUCCESS-hsyxhtaoxiepyjexaffecfiblmjezopu;
 /usr/bin/python /u/users/login_userid/.ansible/tmp/ansible-tmp-1515438271.05-219108659465262/command.py;
 rm -rf "/u/users/login_userid/.ansible/tmp/ansible-tmp-1515438271.05-219108659465262/"
 > /dev/null 2>&1'"'"'"'"'"'"'"'"' && sleep 0'"'"''

This part is what I caught my attention sudo su - sudo_userid -u root

If I try to run it in the server (copy&paste) it also fails... Why is Ansible adding the "-u root" and is there a way to prevent it from doing so? I will never be granted ROOT access to any server.

Also, I am setting the ansible_become_pass variable to the correct value... but it still fails.

By the way, I check several bugs reported to Ansible (like https://github.com/ansible/ansible/issues/23921), and my error is similar, but their work-arounds don't work with my case.

Any help will be much appreciated!!


Solution

  • I have finally found a work-around for my problem, and I'm sharing this answer in case someone finds it useful.

    Ansible become module is great, but for my company it is not working. As I explained in the question, it is adding a "-u root" at the end of the sudo, which makes the whole command to fail.

    I was able to make it work with the following snippet:

    - name: Create empty file as sudo_userid
      command: "sudo su - sudo_userid -c 'touch touchedFile.txt'"
    

    I did several tests, and all of them worked! I didn't even got an Ansible warning!

    So, cheers everyone!