mirror of https://github.com/ansible/ansible.git
Only template values in vars_prompt rather than all vars (#39304)
This allows the use of variables in vars_prompt fields but allows variables entered in the prompt to affect play vars rather than throwing an undefined error.
Add tests for vars_prompt
(cherry picked from commit 6d38167d49
)
pull/43532/merge
parent
3caa736403
commit
4cbf048996
@ -0,0 +1,2 @@
|
|||||||
|
bugfixes:
|
||||||
|
- vars_prompt - properly template play level variables in vars_prompt (https://github.com/ansible/ansible/issues/37984)
|
@ -0,0 +1 @@
|
|||||||
|
shippable/posix/group2
|
@ -0,0 +1,15 @@
|
|||||||
|
#!/usr/bin/env bash
|
||||||
|
|
||||||
|
set -eux
|
||||||
|
|
||||||
|
# Install passlib on RHEL and FreeBSD
|
||||||
|
dist=$(python -c 'import platform; print(platform.dist()[0])')
|
||||||
|
system=$(python -c 'import platform; print(platform.system())')
|
||||||
|
|
||||||
|
if [[ "$dist" == "redhat" || "$system" == "FreeBSD" ]]; then
|
||||||
|
pip install passlib
|
||||||
|
fi
|
||||||
|
|
||||||
|
# Interactively test vars_prompt
|
||||||
|
pip install pexpect
|
||||||
|
python test-vars_prompt.py -i ../../inventory "$@"
|
@ -0,0 +1,115 @@
|
|||||||
|
#!/usr/bin/env python
|
||||||
|
|
||||||
|
import os
|
||||||
|
import pexpect
|
||||||
|
import sys
|
||||||
|
|
||||||
|
from ansible.module_utils.six import PY2
|
||||||
|
|
||||||
|
if PY2:
|
||||||
|
log_buffer = sys.stdout
|
||||||
|
else:
|
||||||
|
log_buffer = sys.stdout.buffer
|
||||||
|
|
||||||
|
env_vars = {
|
||||||
|
'ANSIBLE_ROLES_PATH': './roles',
|
||||||
|
'ANSIBLE_NOCOLOR': 'True',
|
||||||
|
'ANSIBLE_RETRY_FILES_ENABLED': 'False',
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
def run_test(playbook, test_spec, args=None, timeout=10, env=None):
|
||||||
|
|
||||||
|
if not env:
|
||||||
|
env = os.environ.copy()
|
||||||
|
env.update(env_vars)
|
||||||
|
|
||||||
|
if not args:
|
||||||
|
args = sys.argv[1:]
|
||||||
|
|
||||||
|
vars_prompt_test = pexpect.spawn(
|
||||||
|
'ansible-playbook',
|
||||||
|
args=[playbook] + args,
|
||||||
|
timeout=timeout,
|
||||||
|
env=env,
|
||||||
|
)
|
||||||
|
|
||||||
|
vars_prompt_test.logfile = log_buffer
|
||||||
|
for item in test_spec[0]:
|
||||||
|
vars_prompt_test.expect(item[0])
|
||||||
|
if item[1]:
|
||||||
|
vars_prompt_test.send(item[1])
|
||||||
|
vars_prompt_test.expect(test_spec[1])
|
||||||
|
vars_prompt_test.expect(pexpect.EOF)
|
||||||
|
vars_prompt_test.close()
|
||||||
|
|
||||||
|
|
||||||
|
# These are the tests to run. Each test is a playbook and a test_spec.
|
||||||
|
#
|
||||||
|
# The test_spec is a list with two elements.
|
||||||
|
#
|
||||||
|
# The first element is a list of two element tuples. The first is the regexp to look
|
||||||
|
# for in the output, the second is the line to send.
|
||||||
|
#
|
||||||
|
# The last element is the last string of text to look for in the output.
|
||||||
|
#
|
||||||
|
tests = [
|
||||||
|
# Basic vars_prompt
|
||||||
|
{'playbook': 'vars_prompt-1.yml',
|
||||||
|
'test_spec': [
|
||||||
|
[('input:', 'some input\r')],
|
||||||
|
'"input": "some input"']},
|
||||||
|
|
||||||
|
# Custom prompt
|
||||||
|
{'playbook': 'vars_prompt-2.yml',
|
||||||
|
'test_spec': [
|
||||||
|
[('Enter some input:', 'some more input\r')],
|
||||||
|
'"input": "some more input"']},
|
||||||
|
|
||||||
|
# Test confirm, both correct and incorrect
|
||||||
|
{'playbook': 'vars_prompt-3.yml',
|
||||||
|
'test_spec': [
|
||||||
|
[('input:', 'confirm me\r'),
|
||||||
|
('confirm input:', 'confirm me\r')],
|
||||||
|
'"input": "confirm me"']},
|
||||||
|
|
||||||
|
{'playbook': 'vars_prompt-3.yml',
|
||||||
|
'test_spec': [
|
||||||
|
[('input:', 'confirm me\r'),
|
||||||
|
('confirm input:', 'incorrect\r'),
|
||||||
|
(r'\*\*\*\*\* VALUES ENTERED DO NOT MATCH \*\*\*\*', ''),
|
||||||
|
('input:', 'confirm me\r'),
|
||||||
|
('confirm input:', 'confirm me\r')],
|
||||||
|
'"input": "confirm me"']},
|
||||||
|
|
||||||
|
# Test private
|
||||||
|
{'playbook': 'vars_prompt-4.yml',
|
||||||
|
'test_spec': [
|
||||||
|
[('not_secret', 'this is displayed\r'),
|
||||||
|
('this is displayed', '')],
|
||||||
|
'"not_secret": "this is displayed"']},
|
||||||
|
|
||||||
|
# Test hashing
|
||||||
|
{'playbook': 'vars_prompt-5.yml',
|
||||||
|
'test_spec': [
|
||||||
|
[('password', 'Scenic-Improving-Payphone\r'),
|
||||||
|
('confirm password', 'Scenic-Improving-Payphone\r')],
|
||||||
|
r'"password": "\$6\$rounds=']},
|
||||||
|
|
||||||
|
# Test variables in prompt field
|
||||||
|
# https://github.com/ansible/ansible/issues/32723
|
||||||
|
{'playbook': 'vars_prompt-6.yml',
|
||||||
|
'test_spec': [
|
||||||
|
[('prompt from variable:', 'input\r')],
|
||||||
|
'']},
|
||||||
|
|
||||||
|
# Test play vars coming from vars_prompt
|
||||||
|
# https://github.com/ansible/ansible/issues/37984
|
||||||
|
{'playbook': 'vars_prompt-7.yml',
|
||||||
|
'test_spec': [
|
||||||
|
[('prompting for host:', 'testhost\r')],
|
||||||
|
r'testhost.*ok=1']},
|
||||||
|
]
|
||||||
|
|
||||||
|
for t in tests:
|
||||||
|
run_test(playbook=t['playbook'], test_spec=t['test_spec'])
|
@ -0,0 +1,15 @@
|
|||||||
|
- name: Basic vars_prompt test
|
||||||
|
hosts: testhost
|
||||||
|
become: no
|
||||||
|
gather_facts: no
|
||||||
|
|
||||||
|
vars_prompt:
|
||||||
|
- name: input
|
||||||
|
|
||||||
|
tasks:
|
||||||
|
- assert:
|
||||||
|
that:
|
||||||
|
- input == 'some input'
|
||||||
|
|
||||||
|
- debug:
|
||||||
|
var: input
|
@ -0,0 +1,16 @@
|
|||||||
|
- name: Test vars_prompt custom prompt
|
||||||
|
hosts: testhost
|
||||||
|
become: no
|
||||||
|
gather_facts: no
|
||||||
|
|
||||||
|
vars_prompt:
|
||||||
|
- name: input
|
||||||
|
prompt: "Enter some input"
|
||||||
|
|
||||||
|
tasks:
|
||||||
|
- assert:
|
||||||
|
that:
|
||||||
|
- input == 'some more input'
|
||||||
|
|
||||||
|
- debug:
|
||||||
|
var: input
|
@ -0,0 +1,17 @@
|
|||||||
|
- name: Test vars_prompt confirm
|
||||||
|
hosts: testhost
|
||||||
|
become: no
|
||||||
|
gather_facts: no
|
||||||
|
|
||||||
|
vars_prompt:
|
||||||
|
- name: input
|
||||||
|
confirm: yes
|
||||||
|
|
||||||
|
tasks:
|
||||||
|
- name:
|
||||||
|
assert:
|
||||||
|
that:
|
||||||
|
- input == 'confirm me'
|
||||||
|
|
||||||
|
- debug:
|
||||||
|
var: input
|
@ -0,0 +1,16 @@
|
|||||||
|
- name: Test vars_prompt not private
|
||||||
|
hosts: testhost
|
||||||
|
become: no
|
||||||
|
gather_facts: no
|
||||||
|
|
||||||
|
vars_prompt:
|
||||||
|
- name: not_secret
|
||||||
|
private: no
|
||||||
|
|
||||||
|
tasks:
|
||||||
|
- assert:
|
||||||
|
that:
|
||||||
|
- not_secret == 'this is displayed'
|
||||||
|
|
||||||
|
- debug:
|
||||||
|
var: not_secret
|
@ -0,0 +1,14 @@
|
|||||||
|
- name: Test vars_prompt hashing
|
||||||
|
hosts: testhost
|
||||||
|
become: no
|
||||||
|
gather_facts: no
|
||||||
|
|
||||||
|
vars_prompt:
|
||||||
|
- name: password
|
||||||
|
confirm: yes
|
||||||
|
encrypt: sha512_crypt
|
||||||
|
salt: 'jESIyad4F08hP3Ta'
|
||||||
|
|
||||||
|
tasks:
|
||||||
|
- debug:
|
||||||
|
var: password
|
@ -0,0 +1,20 @@
|
|||||||
|
- name: Test vars_prompt custom variables in prompt
|
||||||
|
hosts: testhost
|
||||||
|
become: no
|
||||||
|
gather_facts: no
|
||||||
|
|
||||||
|
vars:
|
||||||
|
prompt_var: prompt from variable
|
||||||
|
|
||||||
|
vars_prompt:
|
||||||
|
- name: input
|
||||||
|
prompt: "{{ prompt_var }}"
|
||||||
|
|
||||||
|
tasks:
|
||||||
|
- name:
|
||||||
|
assert:
|
||||||
|
that:
|
||||||
|
- input == 'input'
|
||||||
|
|
||||||
|
- debug:
|
||||||
|
var: input
|
@ -0,0 +1,12 @@
|
|||||||
|
- name: Test vars_prompt play vars
|
||||||
|
hosts: "{{ target_hosts }}"
|
||||||
|
become: no
|
||||||
|
gather_facts: no
|
||||||
|
|
||||||
|
vars_prompt:
|
||||||
|
- name: target_hosts
|
||||||
|
prompt: prompting for host
|
||||||
|
private: no
|
||||||
|
|
||||||
|
tasks:
|
||||||
|
- ping:
|
Loading…
Reference in New Issue