In enterprise environments with strict security policies, we often encounter servers where:
- Only non-privileged users (e.g., 'foo') have SSH access
- No sudo privileges are granted to these users
- Root access requires manual
su
authentication
While expect scripts work, Ansible provides a more maintainable solution through its become system and su method.
Your inventory file or host vars need these parameters:
[webservers] server1 ansible_user=foo ansible_become=yes ansible_become_method=su ansible_become_user=root
Or in YAML format:
webservers: hosts: server1: ansible_user: foo ansible_become: yes ansible_become_method: su ansible_become_user: root
For security, never store passwords in plaintext. Use Ansible Vault:
# Create encrypted variable ansible-vault encrypt_string 'your_root_password' --name 'ansible_become_password'
Store the output in your inventory or group_vars:
webservers: hosts: server1: ansible_become_password: !vault | $ANSIBLE_VAULT;1.1;AES256 663864396537363962316266...
Here's a complete playbook to demonstrate privileged package installation:
--- - name: Install security updates hosts: webservers tasks: - name: Update package cache ansible.builtin.apt: update_cache: yes - name: Upgrade all packages ansible.builtin.apt: upgrade: dist autoremove: yes
For quick tasks without playbooks:
ansible server1 -m shell -a "whoami" --become --become-method=su --become-user=root
If you must interact with password prompts (not recommended):
- name: Example with explicit become ansible.builtin.command: /usr/bin/privileged_command become: yes become_method: su become_user: root vars: ansible_become_pass: "{{ root_password }}"
- Always use Ansible Vault for password storage
- Consider implementing SSH certificate authentication
- Regularly rotate root passwords
- Log all privilege escalations
Common issues and fixes:
# Enable verbose mode for debugging ANSIBLE_DEBUG=1 ansible-playbook playbook.yml # Check connection parameters ansible -m ping server1 --user=foo
In enterprise environments, we often encounter systems where direct SSH access as root is disabled for security reasons, and the available user account lacks sudo privileges. The standard workaround involves:
- SSH login as restricted user (foo)
- Using
su - root
with password authentication - Executing privileged commands
While Ansible typically expects either:
- SSH as root directly
- SSH with sudo privileges
Our situation requires a different approach since neither option is available.
Ansible's become
system supports this exact use case through the su
method. Here's how to configure it:
# ansible.cfg
[privilege_escalation]
become=True
become_method=su
become_user=root
become_ask_pass=True
Configure your inventory file with connection details:
[webservers]
web1.example.com ansible_user=foo ansible_become_pass=rootpassword
web2.example.com ansible_user=foo ansible_become_pass=rootpassword
Example playbook to demonstrate privilege escalation:
---
- name: Update system packages
hosts: webservers
tasks:
- name: Update all packages
yum:
name: '*'
state: latest
become: yes
become_method: su
For quick tasks without playbooks:
ansible webservers -m yum -a "name=httpd state=latest" --become --become-method=su --become-user=root -u foo -K
- Store passwords in Ansible Vault instead of plaintext
- Consider setting up SSH key-based authentication for the foo user
- Eventually migrate to proper sudo configuration
For environments requiring interactive password entry (like TTY restrictions):
# Using ansible expect module
- name: Privileged command with expect
expect:
command: su - root -c "yum update -y"
responses:
'Password:': "{{ root_password }}"