You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
ansible/test/units/inventory/test_group.py

172 lines
4.8 KiB
Python

# Copyright 2018 Alan Rominger <arominge@redhat.com>
# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt)
from __future__ import annotations
import pytest
from ansible.inventory.group import Group
from ansible.inventory.host import Host
from ansible.errors import AnsibleError
def test_depth_update():
A = Group('A')
B = Group('B')
Z = Group('Z')
A.add_child_group(B)
A.add_child_group(Z)
assert A.depth == 0
assert Z.depth == 1
assert B.depth == 1
def test_depth_update_dual_branches():
alpha = Group('alpha')
A = Group('A')
alpha.add_child_group(A)
B = Group('B')
A.add_child_group(B)
Z = Group('Z')
alpha.add_child_group(Z)
beta = Group('beta')
B.add_child_group(beta)
Z.add_child_group(beta)
assert alpha.depth == 0 # apex
assert beta.depth == 3 # alpha -> A -> B -> beta
omega = Group('omega')
omega.add_child_group(alpha)
# verify that both paths are traversed to get the max depth value
assert B.depth == 3 # omega -> alpha -> A -> B
assert beta.depth == 4 # B -> beta
def test_depth_recursion():
A = Group('A')
B = Group('B')
A.add_child_group(B)
# hypothetical of adding B as child group to A
A.parent_groups.append(B)
B.child_groups.append(A)
# can't update depths of groups, because of loop
with pytest.raises(AnsibleError):
B._check_children_depth()
def test_loop_detection():
A = Group('A')
B = Group('B')
C = Group('C')
A.add_child_group(B)
B.add_child_group(C)
with pytest.raises(AnsibleError):
C.add_child_group(A)
def test_direct_host_ordering():
"""Hosts are returned in order they are added
"""
group = Group('A')
# host names not added in alphabetical order
host_name_list = ['z', 'b', 'c', 'a', 'p', 'q']
expected_hosts = []
for host_name in host_name_list:
h = Host(host_name)
group.add_host(h)
expected_hosts.append(h)
assert group.get_hosts() == expected_hosts
def test_sub_group_host_ordering():
"""With multiple nested groups, asserts that hosts are returned
in deterministic order
"""
top_group = Group('A')
expected_hosts = []
for name in ['z', 'b', 'c', 'a', 'p', 'q']:
child = Group('group_{0}'.format(name))
top_group.add_child_group(child)
host = Host('host_{0}'.format(name))
child.add_host(host)
expected_hosts.append(host)
assert top_group.get_hosts() == expected_hosts
def test_populates_descendant_hosts():
A = Group('A')
B = Group('B')
C = Group('C')
h = Host('h')
C.add_host(h)
A.add_child_group(B) # B is child of A
B.add_child_group(C) # C is descendant of A
A.add_child_group(B)
assert set(h.groups) == set([C, B, A])
h2 = Host('h2')
C.add_host(h2)
assert set(h2.groups) == set([C, B, A])
def test_ancestor_example():
# see docstring for Group._walk_relationship
groups = {}
for name in ['A', 'B', 'C', 'D', 'E', 'F']:
groups[name] = Group(name)
# first row
groups['A'].add_child_group(groups['D'])
groups['B'].add_child_group(groups['D'])
groups['B'].add_child_group(groups['E'])
groups['C'].add_child_group(groups['D'])
# second row
groups['D'].add_child_group(groups['E'])
groups['D'].add_child_group(groups['F'])
groups['E'].add_child_group(groups['F'])
assert (
set(groups['F'].get_ancestors()) ==
set([
groups['A'], groups['B'], groups['C'], groups['D'], groups['E']
])
)
def test_ancestors_recursive_loop_safe():
"""
The get_ancestors method may be referenced before circular parenting
checks, so the method is expected to be stable even with loops
"""
A = Group('A')
B = Group('B')
A.parent_groups.append(B)
B.parent_groups.append(A)
# finishes in finite time
assert A.get_ancestors() == set([A, B])
@pytest.mark.parametrize("priority, expected", [
pytest.param(5, 5, id="int"),
pytest.param('10', 10, id="string"),
pytest.param(-1, -1, id="negative number"),
])
def test_set_priority_valid_values(priority, expected):
"""Test that valid priority value is set"""
group = Group('test_group')
group.set_priority(priority)
assert group.priority == expected
@pytest.mark.parametrize("priority, expected", [
pytest.param('invalid', 1, id="invalid string"),
pytest.param(None, 1, id="None"),
pytest.param({'key': 'value'}, 1, id="dict"),
pytest.param(['item'], 1, id="list")
])
def test_set_priority_invalid_values(priority, expected):
"""Test that invalid priority value is handled gracefully with warnings"""
group = Group('test_group')
group.set_priority(priority)
assert group.priority == expected