mirror of
https://github.com/ansible/awx.git
synced 2026-01-15 11:50:42 -03:30
Optional tower cli (#3)
* Allow running tests without tower_cli * patch up test mutability * Fix test import error, warning mock * flake8 error Update documentation for non-converted modules
This commit is contained in:
parent
d8513a4e86
commit
2e4e687d69
@ -36,9 +36,6 @@ options:
|
||||
- Path to the Tower or AWX config file.
|
||||
type: path
|
||||
|
||||
requirements:
|
||||
- ansible-tower-cli >= 3.0.2
|
||||
|
||||
notes:
|
||||
- If no I(config_file) is provided we will attempt to use the tower-cli library
|
||||
defaults to find your Tower host information.
|
||||
|
||||
@ -33,7 +33,7 @@ class ItemNotDefined(Exception):
|
||||
|
||||
class TowerModule(AnsibleModule):
|
||||
url = None
|
||||
honorred_settings = ['host', 'username', 'password', 'verify_ssl', 'oauth_token']
|
||||
honorred_settings = ('host', 'username', 'password', 'verify_ssl', 'oauth_token')
|
||||
host = '127.0.0.1'
|
||||
username = None
|
||||
password = None
|
||||
@ -43,7 +43,6 @@ class TowerModule(AnsibleModule):
|
||||
session = None
|
||||
cookie_jar = CookieJar()
|
||||
authenticated = False
|
||||
json_output = {'changed': False}
|
||||
config_name = 'tower_cli.cfg'
|
||||
|
||||
def __init__(self, argument_spec, **kwargs):
|
||||
@ -58,6 +57,8 @@ class TowerModule(AnsibleModule):
|
||||
args.update(argument_spec)
|
||||
kwargs['supports_check_mode'] = True
|
||||
|
||||
self.json_output = {'changed': False}
|
||||
|
||||
# We have to take off mutually_exclusive_if in order to init with Ansible
|
||||
mutually_exclusive_if = kwargs.pop('mutually_exclusive_if', None)
|
||||
|
||||
@ -136,7 +137,7 @@ class TowerModule(AnsibleModule):
|
||||
raise ConfigFileException('The specified config file does not exist')
|
||||
|
||||
if not access(config_path, R_OK):
|
||||
raise ConfigFileException("The specified config file can not be read")
|
||||
raise ConfigFileException("The specified config file cannot be read")
|
||||
|
||||
# Read in the file contents:
|
||||
with open(config_path, 'r') as f:
|
||||
|
||||
@ -160,6 +160,10 @@ options:
|
||||
choices: ["present", "absent"]
|
||||
default: "present"
|
||||
type: str
|
||||
|
||||
requirements:
|
||||
- ansible-tower-cli >= 3.0.2
|
||||
|
||||
extends_documentation_fragment: awx.awx.auth
|
||||
'''
|
||||
|
||||
|
||||
@ -219,7 +219,12 @@ options:
|
||||
default: "present"
|
||||
choices: ["present", "absent"]
|
||||
type: str
|
||||
|
||||
requirements:
|
||||
- ansible-tower-cli >= 3.0.2
|
||||
|
||||
extends_documentation_fragment: awx.awx.auth
|
||||
|
||||
notes:
|
||||
- JSON for survey_spec can be found in Tower API Documentation. See
|
||||
U(https://docs.ansible.com/ansible-tower/latest/html/towerapi/api_ref.html#/Job_Templates/Job_Templates_job_templates_survey_spec_create)
|
||||
|
||||
@ -42,6 +42,10 @@ options:
|
||||
description:
|
||||
- Maximum time in seconds to wait for a job to finish.
|
||||
type: int
|
||||
|
||||
requirements:
|
||||
- ansible-tower-cli >= 3.0.2
|
||||
|
||||
extends_documentation_fragment: awx.awx.auth
|
||||
'''
|
||||
|
||||
|
||||
@ -39,6 +39,10 @@ options:
|
||||
default: "present"
|
||||
choices: ["present", "absent"]
|
||||
type: str
|
||||
|
||||
requirements:
|
||||
- ansible-tower-cli >= 3.0.2
|
||||
|
||||
extends_documentation_fragment: awx.awx.auth
|
||||
'''
|
||||
|
||||
|
||||
@ -191,6 +191,10 @@ options:
|
||||
default: "present"
|
||||
choices: ["present", "absent"]
|
||||
type: str
|
||||
|
||||
requirements:
|
||||
- ansible-tower-cli >= 3.0.2
|
||||
|
||||
extends_documentation_fragment: awx.awx.auth
|
||||
'''
|
||||
|
||||
|
||||
@ -68,6 +68,10 @@ options:
|
||||
default: "present"
|
||||
choices: ["present", "absent"]
|
||||
type: str
|
||||
|
||||
requirements:
|
||||
- ansible-tower-cli >= 3.0.2
|
||||
|
||||
extends_documentation_fragment: awx.awx.auth
|
||||
'''
|
||||
|
||||
|
||||
@ -44,6 +44,8 @@ options:
|
||||
|
||||
requirements:
|
||||
- "python >= 2.6"
|
||||
- ansible-tower-cli >= 3.0.2
|
||||
|
||||
extends_documentation_fragment: awx.awx.auth
|
||||
'''
|
||||
|
||||
|
||||
@ -81,6 +81,10 @@ options:
|
||||
default: "present"
|
||||
choices: ["present", "absent"]
|
||||
type: str
|
||||
|
||||
requirements:
|
||||
- ansible-tower-cli >= 3.0.2
|
||||
|
||||
extends_documentation_fragment: awx.awx.auth
|
||||
'''
|
||||
|
||||
|
||||
@ -5,7 +5,7 @@ import io
|
||||
import json
|
||||
import datetime
|
||||
import importlib
|
||||
from contextlib import redirect_stdout
|
||||
from contextlib import redirect_stdout, suppress
|
||||
from unittest import mock
|
||||
import logging
|
||||
|
||||
@ -16,6 +16,12 @@ import pytest
|
||||
from awx.main.tests.functional.conftest import _request
|
||||
from awx.main.models import Organization, Project, Inventory, Credential, CredentialType
|
||||
|
||||
try:
|
||||
import tower_cli # noqa
|
||||
HAS_TOWER_CLI = True
|
||||
except ImportError:
|
||||
HAS_TOWER_CLI = False
|
||||
|
||||
|
||||
logger = logging.getLogger('awx.main.tests')
|
||||
|
||||
@ -104,7 +110,11 @@ def run_module(request):
|
||||
with mock.patch.object(resource_module.TowerModule, '_load_params', new=mock_load_params):
|
||||
# Call the test utility (like a mock server) instead of issuing HTTP requests
|
||||
with mock.patch('ansible.module_utils.urls.Request.open', new=new_open):
|
||||
with mock.patch('tower_cli.api.Session.request', new=new_request):
|
||||
if HAS_TOWER_CLI:
|
||||
tower_cli_mgr = mock.patch('tower_cli.api.Session.request', new=new_request)
|
||||
else:
|
||||
tower_cli_mgr = suppress()
|
||||
with tower_cli_mgr:
|
||||
# Ansible modules return data to the mothership over stdout
|
||||
with redirect_stdout(stdout_buffer):
|
||||
try:
|
||||
@ -114,6 +124,9 @@ def run_module(request):
|
||||
|
||||
module_stdout = stdout_buffer.getvalue().strip()
|
||||
result = json.loads(module_stdout)
|
||||
# A module exception should never be a test expectation
|
||||
if 'exception' in result:
|
||||
raise Exception('Module encountered error:\n{0}'.format(result['exception']))
|
||||
return result
|
||||
|
||||
return rf
|
||||
|
||||
@ -25,11 +25,9 @@ def test_create_group(run_module, admin_user):
|
||||
|
||||
result.pop('invocation')
|
||||
assert result == {
|
||||
'credential_type': 'Nexus',
|
||||
'id': group.id,
|
||||
'name': 'Test Group',
|
||||
'changed': True,
|
||||
'state': 'present'
|
||||
}
|
||||
|
||||
|
||||
@ -54,8 +52,5 @@ def test_tower_group_idempotent(run_module, admin_user):
|
||||
result.pop('invocation')
|
||||
assert result == {
|
||||
'id': group.id,
|
||||
'credential_type': 'Nexus',
|
||||
'name': 'Test Group',
|
||||
'changed': False, # idempotency assertion
|
||||
'state': 'present'
|
||||
}
|
||||
|
||||
@ -38,8 +38,6 @@ def test_inventory_source_create(run_module, admin_user, base_inventory):
|
||||
assert result == {
|
||||
'id': inv_src.id,
|
||||
'name': 'foo',
|
||||
'state': 'present',
|
||||
'credential_type': 'Nexus'
|
||||
}
|
||||
|
||||
|
||||
@ -61,9 +59,7 @@ def test_create_inventory_source_implied_org(run_module, admin_user):
|
||||
|
||||
result.pop('invocation')
|
||||
assert result == {
|
||||
"credential_type": "Nexus",
|
||||
"name": "Test Inventory Source",
|
||||
"state": "present",
|
||||
"id": inv_src.id,
|
||||
}
|
||||
|
||||
@ -90,9 +86,7 @@ def test_create_inventory_source_multiple_orgs(run_module, admin_user):
|
||||
|
||||
result.pop('invocation')
|
||||
assert result == {
|
||||
"credential_type": "Nexus",
|
||||
"name": "Test Inventory Source",
|
||||
"state": "present",
|
||||
"id": inv_src.id,
|
||||
}
|
||||
|
||||
|
||||
@ -30,8 +30,6 @@ def test_create_organization(run_module, admin_user):
|
||||
assert result == {
|
||||
"name": "foo",
|
||||
"changed": True,
|
||||
"state": "present",
|
||||
"credential_type": "Nexus",
|
||||
"id": org.id,
|
||||
"invocation": {
|
||||
"module_args": module_args
|
||||
@ -55,8 +53,6 @@ def test_create_organization_with_venv(run_module, admin_user, mocker):
|
||||
org = Organization.objects.get(name='foo')
|
||||
result.pop('invocation')
|
||||
assert result == {
|
||||
"credential_type": "Nexus",
|
||||
"state": "present",
|
||||
"name": "foo",
|
||||
"id": org.id
|
||||
}
|
||||
|
||||
@ -3,20 +3,23 @@ __metaclass__ = type
|
||||
|
||||
import pytest
|
||||
|
||||
from unittest import mock
|
||||
|
||||
from awx.main.models import Project
|
||||
|
||||
|
||||
@pytest.mark.django_db
|
||||
def test_create_project(run_module, admin_user, organization):
|
||||
result = run_module('tower_project', dict(
|
||||
name='foo',
|
||||
organization=organization.name,
|
||||
scm_type='git',
|
||||
scm_url='https://foo.invalid',
|
||||
wait=False,
|
||||
scm_update_cache_timeout=5
|
||||
), admin_user)
|
||||
warning = ['scm_update_cache_timeout will be ignored since scm_update_on_launch was not set to true']
|
||||
with mock.patch('ansible.module_utils.basic.AnsibleModule.warn') as mock_warn:
|
||||
result = run_module('tower_project', dict(
|
||||
name='foo',
|
||||
organization=organization.name,
|
||||
scm_type='git',
|
||||
scm_url='https://foo.invalid',
|
||||
wait=False,
|
||||
scm_update_cache_timeout=5
|
||||
), admin_user)
|
||||
mock_warn.assert_called_once_with('scm_update_cache_timeout will be ignored since scm_update_on_launch was not set to true')
|
||||
assert result.pop('changed', None), result
|
||||
|
||||
proj = Project.objects.get(name='foo')
|
||||
@ -25,9 +28,6 @@ def test_create_project(run_module, admin_user, organization):
|
||||
|
||||
result.pop('invocation')
|
||||
assert result == {
|
||||
'credential_type': 'Nexus',
|
||||
'state': 'present',
|
||||
'name': 'foo',
|
||||
'id': proj.id,
|
||||
'warnings': warning
|
||||
'id': proj.id
|
||||
}
|
||||
|
||||
@ -2,6 +2,7 @@ from __future__ import (absolute_import, division, print_function)
|
||||
__metaclass__ = type
|
||||
|
||||
import pytest
|
||||
from unittest import mock
|
||||
import json
|
||||
|
||||
from awx.main.models import (
|
||||
@ -65,7 +66,9 @@ def test_receive_send_jt(run_module, admin_user, mocker):
|
||||
# recreate everything
|
||||
with mocker.patch('sys.stdin.isatty', return_value=True):
|
||||
with mocker.patch('tower_cli.models.base.MonitorableResource.wait'):
|
||||
result = run_module('tower_send', dict(assets=json.dumps(assets)), admin_user)
|
||||
# warns based on password_management param, but not security issue
|
||||
with mock.patch('ansible.module_utils.basic.AnsibleModule.warn'):
|
||||
result = run_module('tower_send', dict(assets=json.dumps(assets)), admin_user)
|
||||
|
||||
assert not result.get('failed'), result
|
||||
|
||||
|
||||
@ -23,8 +23,6 @@ def test_create_team(run_module, admin_user):
|
||||
assert result == {
|
||||
"changed": True,
|
||||
"name": "foo_team",
|
||||
"credential_type": "Nexus",
|
||||
"state": "present",
|
||||
"id": team.id if team else None,
|
||||
}
|
||||
team = Team.objects.get(name='foo_team')
|
||||
@ -50,10 +48,7 @@ def test_modify_team(run_module, admin_user):
|
||||
team.refresh_from_db()
|
||||
result.pop('invocation')
|
||||
assert result == {
|
||||
"state": "present",
|
||||
"changed": True,
|
||||
"name": "foo_team",
|
||||
"credential_type": "Nexus",
|
||||
"id": team.id,
|
||||
}
|
||||
assert team.description == 'fooin around'
|
||||
@ -66,9 +61,6 @@ def test_modify_team(run_module, admin_user):
|
||||
}, admin_user)
|
||||
result.pop('invocation')
|
||||
assert result == {
|
||||
"credential_type": "Nexus",
|
||||
"name": "foo_team",
|
||||
"id": team.id,
|
||||
"state": "present",
|
||||
"changed": False
|
||||
}
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user