# -*- coding: utf-8 -*- # Copyright: (c) 2019, Ansible Project # GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt) # Make coding more python3-ish from __future__ import (absolute_import, division, print_function) __metaclass__ = type import os import functools import pytest import tempfile from io import StringIO from ansible import context from ansible.cli.galaxy import GalaxyCLI from ansible.galaxy import api, role, Galaxy from ansible.module_utils.common.text.converters import to_text from ansible.utils import context_objects as co def call_galaxy_cli(args): orig = co.GlobalCLIArgs._Singleton__instance co.GlobalCLIArgs._Singleton__instance = None try: GalaxyCLI(args=['ansible-galaxy', 'role'] + args).run() finally: co.GlobalCLIArgs._Singleton__instance = orig @pytest.fixture(autouse='function') def reset_cli_args(): co.GlobalCLIArgs._Singleton__instance = None yield co.GlobalCLIArgs._Singleton__instance = None @pytest.fixture(autouse=True) def galaxy_server(): context.CLIARGS._store = {'ignore_certs': False} galaxy_api = api.GalaxyAPI(None, 'test_server', 'https://galaxy.ansible.com') return galaxy_api @pytest.fixture(autouse=True) def init_role_dir(tmp_path_factory): test_dir = to_text(tmp_path_factory.mktemp('test-ÅÑŚÌβŁÈ Roles Input')) namespace = 'ansible_namespace' role = 'role' skeleton_path = os.path.join(os.path.dirname(os.path.split(__file__)[0]), 'cli', 'test_data', 'role_skeleton') call_galaxy_cli(['init', '%s.%s' % (namespace, role), '-c', '--init-path', test_dir, '--role-skeleton', skeleton_path]) def mock_NamedTemporaryFile(mocker, **args): mock_ntf = mocker.MagicMock() mock_ntf.write = mocker.MagicMock() mock_ntf.close = mocker.MagicMock() mock_ntf.name = None return mock_ntf @pytest.fixture def init_mock_temp_file(mocker, monkeypatch): monkeypatch.setattr(tempfile, 'NamedTemporaryFile', functools.partial(mock_NamedTemporaryFile, mocker)) @pytest.fixture(autouse=True) def mock_role_download_api(mocker, monkeypatch): mock_role_api = mocker.MagicMock() mock_role_api.side_effect = [ StringIO(u''), ] monkeypatch.setattr(role, 'open_url', mock_role_api) return mock_role_api def test_role_download_github(init_mock_temp_file, mocker, galaxy_server, mock_role_download_api, monkeypatch): mock_api = mocker.MagicMock() mock_api.side_effect = [ StringIO(u'{"available_versions":{"v1":"v1/"}}'), StringIO(u'{"results":[{"id":"123","github_user":"test_owner","github_repo": "test_role"}]}'), StringIO(u'{"results":[{"name": "0.0.1"},{"name": "0.0.2"}]}'), ] monkeypatch.setattr(api, 'open_url', mock_api) role.GalaxyRole(Galaxy(), galaxy_server, 'test_owner.test_role', version="0.0.1").install() assert mock_role_download_api.call_count == 1 assert mock_role_download_api.mock_calls[0][1][0] == 'https://github.com/test_owner/test_role/archive/0.0.1.tar.gz' def test_role_download_github_default_version(init_mock_temp_file, mocker, galaxy_server, mock_role_download_api, monkeypatch): mock_api = mocker.MagicMock() mock_api.side_effect = [ StringIO(u'{"available_versions":{"v1":"v1/"}}'), StringIO(u'{"results":[{"id":"123","github_user":"test_owner","github_repo": "test_role"}]}'), StringIO(u'{"results":[{"name": "0.0.1"},{"name": "0.0.2"}]}'), ] monkeypatch.setattr(api, 'open_url', mock_api) role.GalaxyRole(Galaxy(), galaxy_server, 'test_owner.test_role').install() assert mock_role_download_api.call_count == 1 assert mock_role_download_api.mock_calls[0][1][0] == 'https://github.com/test_owner/test_role/archive/0.0.2.tar.gz' def test_role_download_github_no_download_url_for_version(init_mock_temp_file, mocker, galaxy_server, mock_role_download_api, monkeypatch): mock_api = mocker.MagicMock() mock_api.side_effect = [ StringIO(u'{"available_versions":{"v1":"v1/"}}'), StringIO(u'{"results":[{"id":"123","github_user":"test_owner","github_repo": "test_role"}]}'), StringIO(u'{"results":[{"name": "0.0.1"},{"name": "0.0.2","download_url":"http://localhost:8080/test_owner/test_role/0.0.2.tar.gz"}]}'), ] monkeypatch.setattr(api, 'open_url', mock_api) role.GalaxyRole(Galaxy(), galaxy_server, 'test_owner.test_role', version="0.0.1").install() assert mock_role_download_api.call_count == 1 assert mock_role_download_api.mock_calls[0][1][0] == 'https://github.com/test_owner/test_role/archive/0.0.1.tar.gz' def test_role_download_url(init_mock_temp_file, mocker, galaxy_server, mock_role_download_api, monkeypatch): mock_api = mocker.MagicMock() mock_api.side_effect = [ StringIO(u'{"available_versions":{"v1":"v1/"}}'), StringIO(u'{"results":[{"id":"123","github_user":"test_owner","github_repo": "test_role"}]}'), StringIO(u'{"results":[{"name": "0.0.1","download_url":"http://localhost:8080/test_owner/test_role/0.0.1.tar.gz"},' u'{"name": "0.0.2","download_url":"http://localhost:8080/test_owner/test_role/0.0.2.tar.gz"}]}'), ] monkeypatch.setattr(api, 'open_url', mock_api) role.GalaxyRole(Galaxy(), galaxy_server, 'test_owner.test_role', version="0.0.1").install() assert mock_role_download_api.call_count == 1 assert mock_role_download_api.mock_calls[0][1][0] == 'http://localhost:8080/test_owner/test_role/0.0.1.tar.gz' def test_role_download_url_default_version(init_mock_temp_file, mocker, galaxy_server, mock_role_download_api, monkeypatch): mock_api = mocker.MagicMock() mock_api.side_effect = [ StringIO(u'{"available_versions":{"v1":"v1/"}}'), StringIO(u'{"results":[{"id":"123","github_user":"test_owner","github_repo": "test_role"}]}'), StringIO(u'{"results":[{"name": "0.0.1","download_url":"http://localhost:8080/test_owner/test_role/0.0.1.tar.gz"},' u'{"name": "0.0.2","download_url":"http://localhost:8080/test_owner/test_role/0.0.2.tar.gz"}]}'), ] monkeypatch.setattr(api, 'open_url', mock_api) role.GalaxyRole(Galaxy(), galaxy_server, 'test_owner.test_role').install() assert mock_role_download_api.call_count == 1 assert mock_role_download_api.mock_calls[0][1][0] == 'http://localhost:8080/test_owner/test_role/0.0.2.tar.gz'