diff --git a/.gitignore b/.gitignore index 40ac6db6e..9f23f3aa2 100644 --- a/.gitignore +++ b/.gitignore @@ -46,3 +46,6 @@ tobiko.conf* # Infrared things .infrared workspace.tgz + +# Tripleo files +tripleo-hosts.yaml diff --git a/tobiko/tests/functional/tripleo/test_ansible.py b/tobiko/tests/functional/tripleo/test_ansible.py new file mode 100644 index 000000000..e16437048 --- /dev/null +++ b/tobiko/tests/functional/tripleo/test_ansible.py @@ -0,0 +1,56 @@ +# Copyright 2019 Red Hat +# +# Licensed under the Apache License, Version 2.0 (the "License"); you may +# not use this file except in compliance with the License. You may obtain +# a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT +# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the +# License for the specific language governing permissions and limitations +# under the License. +from __future__ import absolute_import + +import os + +import testtools +import yaml + +from tobiko import config +from tobiko import tripleo + + +CONF = config.CONF + + +@tripleo.skip_if_missing_undercloud +class InventoryFileTest(testtools.TestCase): + + @tripleo.skip_if_missing_tripleo_ansible_inventory + def test_get_tripleo_ansible_inventory(self): + inventory = tripleo.get_tripleo_ansible_inventory() + self.assertIn('Undercloud', inventory) + self.assertIn('Controller', inventory) + self.assertIn('Compute', inventory) + + @tripleo.skip_if_missing_tripleo_ansible_inventory + def test_get_tripleo_ansible_inventory_file(self): + inventory_file = tripleo.get_tripleo_ansible_inventory_file() + self.assertTrue(os.path.isfile(inventory_file)) + + def test_has_tripleo_ansible_inventory(self): + result = tripleo.has_tripleo_ansible_inventory() + inventory_file = tripleo.get_tripleo_ansible_inventory_file() + self.assertIs(inventory_file and os.path.isfile(inventory_file), + result) + + def test_read_tripleo_ansible_inventory(self): + inventory_yaml = tripleo.read_tripleo_ansible_inventory() + self.assertIsInstance(inventory_yaml, str) + self.assertTrue(inventory_yaml) + inventory = yaml.safe_load(inventory_yaml) + self.assertIn('Undercloud', inventory) + self.assertIn('Controller', inventory) + self.assertIn('Compute', inventory) diff --git a/tobiko/tripleo/__init__.py b/tobiko/tripleo/__init__.py index e69de29bb..316250771 100644 --- a/tobiko/tripleo/__init__.py +++ b/tobiko/tripleo/__init__.py @@ -0,0 +1,28 @@ +# Copyright 2020 Red Hat +# +# Licensed under the Apache License, Version 2.0 (the "License"); you may +# not use this file except in compliance with the License. You may obtain +# a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT +# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the +# License for the specific language governing permissions and limitations +# under the License. +from __future__ import absolute_import + +from tobiko.tripleo import _ansible +from tobiko.tripleo import _undercloud as undercloud + + +get_tripleo_ansible_inventory = _ansible.get_tripleo_ansible_inventory +get_tripleo_ansible_inventory_file = \ + _ansible.get_tripleo_ansible_inventory_file +has_tripleo_ansible_inventory = _ansible.has_tripleo_ansible_inventory +read_tripleo_ansible_inventory = _ansible.read_tripleo_ansible_inventory +skip_if_missing_tripleo_ansible_inventory = \ + _ansible.skip_if_missing_tripleo_ansible_inventory + +skip_if_missing_undercloud = undercloud.skip_if_missing_undercloud diff --git a/tobiko/tripleo/_ansible.py b/tobiko/tripleo/_ansible.py new file mode 100644 index 000000000..80117b4fa --- /dev/null +++ b/tobiko/tripleo/_ansible.py @@ -0,0 +1,85 @@ +# Copyright 2020 Red Hat +# +# Licensed under the Apache License, Version 2.0 (the "License"); you may +# not use this file except in compliance with the License. You may obtain +# a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT +# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the +# License for the specific language governing permissions and limitations +# under the License. +from __future__ import absolute_import + +import io +import os + +import yaml + +import tobiko +from tobiko.shell import sh +from tobiko.tripleo import _undercloud +from tobiko.tripleo import _config + + +def get_tripleo_ansible_inventory(): + inventory_file = get_tripleo_ansible_inventory_file() + with io.open(inventory_file, 'rb') as fd: + return yaml.safe_load(fd) + + +def has_tripleo_ansible_inventory(): + inventory_file = get_tripleo_ansible_inventory_file() + return inventory_file and os.path.isfile(inventory_file) + + +skip_if_missing_tripleo_ansible_inventory = \ + tobiko.skip_unless("Can't read TripleO Ansible inventory", + has_tripleo_ansible_inventory) + + +def get_tripleo_ansible_inventory_file(): + return tobiko.setup_fixture(TripleoAnsibleInventoryFixture).inventory_file + + +class TripleoAnsibleInventoryFixture(tobiko.SharedFixture): + + inventory_file = None + + def setup_fixture(self): + tripleo = _config.get_tripleo_config() + self.inventory_file = inventory_file = tobiko.tobiko_config_path( + tripleo.inventory_file) + if inventory_file and not os.path.isfile(inventory_file): + content = read_tripleo_ansible_inventory() + with io.open(inventory_file, 'w') as fd: + fd.write(content) + + +READ_TRIPLEO_ANSIBLE_INVENTORY_SCRIPT = """ +source {undercloud_rcfile} || exit 1 + +set -x + +INVENTORY_FILE=$(mktemp tripleo-hosts-XXXXXXXXXX.yaml) +tripleo-ansible-inventory --ansible_ssh_user "{overcloud_ssh_username}" \\ + --static-yaml-inventory "$INVENTORY_FILE" +RC=$? + +if [ $RC == 0 ]; then + cat "$INVENTORY_FILE" +fi +rm -fR "$INVENTORY_FILE" +exit $RC +""" + + +def read_tripleo_ansible_inventory(): + tripleo = _config.get_tripleo_config() + ssh_client = _undercloud.undercloud_ssh_client() + script = READ_TRIPLEO_ANSIBLE_INVENTORY_SCRIPT.format( + undercloud_rcfile=tripleo.undercloud_rcfile, + overcloud_ssh_username=tripleo.overcloud_ssh_username) + return sh.execute('/bin/bash', stdin=script, ssh_client=ssh_client).stdout diff --git a/tobiko/tripleo/_config.py b/tobiko/tripleo/_config.py new file mode 100644 index 000000000..1d22150df --- /dev/null +++ b/tobiko/tripleo/_config.py @@ -0,0 +1,28 @@ +# Copyright 2020 Red Hat +# +# Licensed under the Apache License, Version 2.0 (the "License"); you may +# not use this file except in compliance with the License. You may obtain +# a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT +# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the +# License for the specific language governing permissions and limitations +# under the License. +from __future__ import absolute_import + +import tobiko + + +class TripleoConfigFixture(tobiko.SharedFixture): + + tripleo = None + + def setup_fixture(self): + self.tripleo = tobiko.tobiko_config().tripleo + + +def get_tripleo_config(): + return tobiko.setup_fixture(TripleoConfigFixture).tripleo diff --git a/tobiko/tripleo/undercloud.py b/tobiko/tripleo/_undercloud.py similarity index 100% rename from tobiko/tripleo/undercloud.py rename to tobiko/tripleo/_undercloud.py