summaryrefslogtreecommitdiffstats
path: root/test/integration/targets/inventory
diff options
context:
space:
mode:
Diffstat (limited to 'test/integration/targets/inventory')
-rw-r--r--test/integration/targets/inventory/1/2/3/extra_vars_relative.yml19
-rw-r--r--test/integration/targets/inventory/1/2/inventory.yml3
-rw-r--r--test/integration/targets/inventory/1/vars.yml1
-rw-r--r--test/integration/targets/inventory/aliases2
-rw-r--r--test/integration/targets/inventory/extra_vars_constructed.yml5
-rw-r--r--test/integration/targets/inventory/host_vars_constructed.yml6
-rw-r--r--test/integration/targets/inventory/inv_with_host_vars.yml5
-rw-r--r--test/integration/targets/inventory/inv_with_int.yml6
-rw-r--r--test/integration/targets/inventory/inventory_plugins/contructed_with_hostvars.py44
-rw-r--r--test/integration/targets/inventory/playbook.yml4
-rwxr-xr-xtest/integration/targets/inventory/runme.sh114
-rw-r--r--test/integration/targets/inventory/strategy.yml12
-rw-r--r--test/integration/targets/inventory/test_empty.yml0
13 files changed, 221 insertions, 0 deletions
diff --git a/test/integration/targets/inventory/1/2/3/extra_vars_relative.yml b/test/integration/targets/inventory/1/2/3/extra_vars_relative.yml
new file mode 100644
index 0000000..fa50a5a
--- /dev/null
+++ b/test/integration/targets/inventory/1/2/3/extra_vars_relative.yml
@@ -0,0 +1,19 @@
+- hosts: localhost
+ gather_facts: false
+ vars:
+ conditions:
+ - my is defined
+ - my == 'var'
+ - "'webservers' in groups"
+ - "'web_host.example.com' in groups['webservers']"
+ tasks:
+ - name: Make sure all is loaded
+ assert:
+ that: '{{conditions}}'
+
+ - name: Reload inventory, forces extra vars re-eval from diff basedir
+ meta: refresh_inventory
+
+ - name: Make sure all is loaded, again
+ assert:
+ that: '{{conditions}}'
diff --git a/test/integration/targets/inventory/1/2/inventory.yml b/test/integration/targets/inventory/1/2/inventory.yml
new file mode 100644
index 0000000..b6c31ad
--- /dev/null
+++ b/test/integration/targets/inventory/1/2/inventory.yml
@@ -0,0 +1,3 @@
+plugin: ansible.builtin.constructed
+groups:
+ webservers: inventory_hostname.startswith('web')
diff --git a/test/integration/targets/inventory/1/vars.yml b/test/integration/targets/inventory/1/vars.yml
new file mode 100644
index 0000000..c114584
--- /dev/null
+++ b/test/integration/targets/inventory/1/vars.yml
@@ -0,0 +1 @@
+my: var
diff --git a/test/integration/targets/inventory/aliases b/test/integration/targets/inventory/aliases
new file mode 100644
index 0000000..1d28bdb
--- /dev/null
+++ b/test/integration/targets/inventory/aliases
@@ -0,0 +1,2 @@
+shippable/posix/group5
+context/controller
diff --git a/test/integration/targets/inventory/extra_vars_constructed.yml b/test/integration/targets/inventory/extra_vars_constructed.yml
new file mode 100644
index 0000000..ee6f5fd
--- /dev/null
+++ b/test/integration/targets/inventory/extra_vars_constructed.yml
@@ -0,0 +1,5 @@
+plugin: ansible.builtin.constructed
+strict: true
+use_extra_vars: True
+compose:
+ example: " 'hello' + from_extras"
diff --git a/test/integration/targets/inventory/host_vars_constructed.yml b/test/integration/targets/inventory/host_vars_constructed.yml
new file mode 100644
index 0000000..eec5250
--- /dev/null
+++ b/test/integration/targets/inventory/host_vars_constructed.yml
@@ -0,0 +1,6 @@
+plugin: ansible.legacy.contructed_with_hostvars
+groups:
+ host_var1_defined: host_var1 is defined
+keyed_groups:
+ - key: host_var2
+ prefix: host_var2
diff --git a/test/integration/targets/inventory/inv_with_host_vars.yml b/test/integration/targets/inventory/inv_with_host_vars.yml
new file mode 100644
index 0000000..7403505
--- /dev/null
+++ b/test/integration/targets/inventory/inv_with_host_vars.yml
@@ -0,0 +1,5 @@
+all:
+ hosts:
+ host1:
+ host_var1: 'defined'
+ host_var2: 'defined'
diff --git a/test/integration/targets/inventory/inv_with_int.yml b/test/integration/targets/inventory/inv_with_int.yml
new file mode 100644
index 0000000..5b2f21d
--- /dev/null
+++ b/test/integration/targets/inventory/inv_with_int.yml
@@ -0,0 +1,6 @@
+all:
+ hosts:
+ testing123:
+ x:
+ a: 1
+ 0: 2
diff --git a/test/integration/targets/inventory/inventory_plugins/contructed_with_hostvars.py b/test/integration/targets/inventory/inventory_plugins/contructed_with_hostvars.py
new file mode 100644
index 0000000..7ca445a
--- /dev/null
+++ b/test/integration/targets/inventory/inventory_plugins/contructed_with_hostvars.py
@@ -0,0 +1,44 @@
+# Copyright (c) 2022 Ansible Project
+# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt)
+
+from __future__ import (absolute_import, division, print_function)
+__metaclass__ = type
+
+DOCUMENTATION = '''
+ name: constructed_with_hostvars
+ options:
+ plugin:
+ description: the load name of the plugin
+ extends_documentation_fragment:
+ - constructed
+'''
+
+from ansible.errors import AnsibleParserError
+from ansible.module_utils._text import to_native
+from ansible.plugins.inventory import BaseInventoryPlugin, Constructable
+
+
+class InventoryModule(BaseInventoryPlugin, Constructable):
+
+ NAME = 'constructed_with_hostvars'
+
+ def verify_file(self, path):
+ return super(InventoryModule, self).verify_file(path) and path.endswith(('constructed.yml', 'constructed.yaml'))
+
+ def parse(self, inventory, loader, path, cache=True):
+ super(InventoryModule, self).parse(inventory, loader, path, cache)
+ config = self._read_config_data(path)
+
+ strict = self.get_option('strict')
+ try:
+ for host in inventory.hosts:
+ hostvars = {}
+
+ # constructed groups based on conditionals
+ self._add_host_to_composed_groups(self.get_option('groups'), hostvars, host, strict=strict, fetch_hostvars=True)
+
+ # constructed groups based variable values
+ self._add_host_to_keyed_groups(self.get_option('keyed_groups'), hostvars, host, strict=strict, fetch_hostvars=True)
+
+ except Exception as e:
+ raise AnsibleParserError("failed to parse %s: %s " % (to_native(path), to_native(e)), orig_exc=e)
diff --git a/test/integration/targets/inventory/playbook.yml b/test/integration/targets/inventory/playbook.yml
new file mode 100644
index 0000000..5e07361
--- /dev/null
+++ b/test/integration/targets/inventory/playbook.yml
@@ -0,0 +1,4 @@
+- hosts: all
+ gather_facts: false
+ tasks:
+ - ping:
diff --git a/test/integration/targets/inventory/runme.sh b/test/integration/targets/inventory/runme.sh
new file mode 100755
index 0000000..8dcac40
--- /dev/null
+++ b/test/integration/targets/inventory/runme.sh
@@ -0,0 +1,114 @@
+#!/usr/bin/env bash
+
+set -eux
+
+empty_limit_file="$(mktemp)"
+touch "${empty_limit_file}"
+
+tmpdir="$(mktemp -d)"
+
+cleanup() {
+ if [[ -f "${empty_limit_file}" ]]; then
+ rm -rf "${empty_limit_file}"
+ fi
+ rm -rf "$tmpdir"
+}
+
+trap 'cleanup' EXIT
+
+# https://github.com/ansible/ansible/issues/52152
+# Ensure that non-matching limit causes failure with rc 1
+if ansible-playbook -i ../../inventory --limit foo playbook.yml; then
+ echo "Non-matching limit should cause failure"
+ exit 1
+fi
+
+# Ensure that non-existing limit file causes failure with rc 1
+if ansible-playbook -i ../../inventory --limit @foo playbook.yml; then
+ echo "Non-existing limit file should cause failure"
+ exit 1
+fi
+
+if ! ansible-playbook -i ../../inventory --limit @"$tmpdir" playbook.yml 2>&1 | grep 'must be a file'; then
+ echo "Using a directory as a limit file should throw proper AnsibleError"
+ exit 1
+fi
+
+# Ensure that empty limit file does not cause IndexError #59695
+ansible-playbook -i ../../inventory --limit @"${empty_limit_file}" playbook.yml
+
+ansible-playbook -i ../../inventory "$@" strategy.yml
+ANSIBLE_TRANSFORM_INVALID_GROUP_CHARS=always ansible-playbook -i ../../inventory "$@" strategy.yml
+ANSIBLE_TRANSFORM_INVALID_GROUP_CHARS=never ansible-playbook -i ../../inventory "$@" strategy.yml
+
+# test extra vars
+ansible-inventory -i testhost, -i ./extra_vars_constructed.yml --list -e 'from_extras=hey ' "$@"|grep '"example": "hellohey"'
+
+# test host vars from previous inventory sources
+ansible-inventory -i ./inv_with_host_vars.yml -i ./host_vars_constructed.yml --graph "$@" | tee out.txt
+if [[ "$(grep out.txt -ce '.*host_var[1|2]_defined')" != 2 ]]; then
+ cat out.txt
+ echo "Expected groups host_var1_defined and host_var2_defined to both exist"
+ exit 1
+fi
+
+# Do not fail when all inventories fail to parse.
+# Do not fail when any inventory fails to parse.
+ANSIBLE_INVENTORY_UNPARSED_FAILED=False ANSIBLE_INVENTORY_ANY_UNPARSED_IS_FAILED=False ansible -m ping localhost -i /idontexist "$@"
+
+# Fail when all inventories fail to parse.
+# Do not fail when just one inventory fails to parse.
+if ANSIBLE_INVENTORY_UNPARSED_FAILED=True ANSIBLE_INVENTORY_ANY_UNPARSED_IS_FAILED=False ansible -m ping localhost -i /idontexist; then
+ echo "All inventories failed/did not exist, should cause failure"
+ echo "ran with: ANSIBLE_INVENTORY_UNPARSED_FAILED=True ANSIBLE_INVENTORY_ANY_UNPARSED_IS_FAILED=False"
+ exit 1
+fi
+
+# Same as above but ensuring no failure we *only* fail when all inventories fail to parse.
+# Fail when all inventories fail to parse.
+# Do not fail when just one inventory fails to parse.
+ANSIBLE_INVENTORY_UNPARSED_FAILED=True ANSIBLE_INVENTORY_ANY_UNPARSED_IS_FAILED=False ansible -m ping localhost -i /idontexist -i ../../inventory "$@"
+# Fail when all inventories fail to parse.
+# Do not fail when just one inventory fails to parse.
+
+# Fail when any inventories fail to parse.
+if ANSIBLE_INVENTORY_ANY_UNPARSED_IS_FAILED=True ansible -m ping localhost -i /idontexist -i ../../inventory; then
+ echo "One inventory failed/did not exist, should NOT cause failure"
+ echo "ran with: ANSIBLE_INVENTORY_UNPARSED_FAILED=True ANSIBLE_INVENTORY_ANY_UNPARSED_IS_FAILED=False"
+ exit 1
+fi
+
+# Test parsing an empty config
+set +e
+ANSIBLE_INVENTORY_UNPARSED_FAILED=True ANSIBLE_INVENTORY_ENABLED=constructed ansible-inventory -i ./test_empty.yml --list "$@"
+rc_failed_inventory="$?"
+set -e
+if [[ "$rc_failed_inventory" != 1 ]]; then
+ echo "Config was empty so inventory was not parsed, should cause failure"
+ exit 1
+fi
+
+# Ensure we don't throw when an empty directory is used as inventory
+ansible-playbook -i "$tmpdir" playbook.yml
+
+# Ensure we can use a directory of inventories
+cp ../../inventory "$tmpdir"
+ansible-playbook -i "$tmpdir" playbook.yml
+
+# ... even if it contains another empty directory
+mkdir "$tmpdir/empty"
+ansible-playbook -i "$tmpdir" playbook.yml
+
+if ANSIBLE_INVENTORY_ANY_UNPARSED_IS_FAILED=True ansible -m ping localhost -i "$tmpdir"; then
+ echo "Empty directory should cause failure when ANSIBLE_INVENTORY_ANY_UNPARSED_IS_FAILED=True"
+ exit 1
+fi
+
+# ensure we don't traceback on inventory due to variables with int as key
+ansible-inventory -i inv_with_int.yml --list "$@"
+
+# test in subshell relative paths work mid play for extra vars in inventory refresh
+{
+ cd 1/2
+ ansible-playbook -e @../vars.yml -i 'web_host.example.com,' -i inventory.yml 3/extra_vars_relative.yml "$@"
+}
diff --git a/test/integration/targets/inventory/strategy.yml b/test/integration/targets/inventory/strategy.yml
new file mode 100644
index 0000000..5c1cbd2
--- /dev/null
+++ b/test/integration/targets/inventory/strategy.yml
@@ -0,0 +1,12 @@
+- name: Check that 'invalid' group works, problem exposed in #58980
+ hosts: localhost
+ tasks:
+ - name: add a host to a group, that has - to trigger substitution
+ add_host:
+ name: localhost
+ groups: Not-Working
+
+ - name: group hosts by distribution, with dash to trigger substitution
+ group_by:
+ key: "{{ ansible_distribution }}-{{ ansible_distribution_version }}"
+ changed_when: false
diff --git a/test/integration/targets/inventory/test_empty.yml b/test/integration/targets/inventory/test_empty.yml
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/test/integration/targets/inventory/test_empty.yml