Example #1
0
def test_csphost_new_init():
    """Tests Host.__new__ and Host.__init__"""
    from apyfal.configuration import Configuration
    from apyfal.host import Host
    from apyfal.host._csp import CSPHost
    from apyfal.host.aws import AWSHost
    from apyfal.exceptions import HostConfigurationException

    # Mock arguments and configuration
    # Note that host_type is not specified here
    config = Configuration()
    try:
        for section in list(config._sections):
            if section.startswith('host'):
                del config._sections[section]
    except KeyError:
        pass
    kwargs = {
        'region': 'region',
        'project_id': 'project_id',
        'client_id': 'client_id',
        'auth_url': 'auth_url',
        'interface': 'interface',
        'config': config
    }

    # Test: Existing CSP class and module
    assert isinstance(Host(host_type="AWS", **kwargs), AWSHost)

    # Test: Not existing CSP module
    with pytest.raises(HostConfigurationException):
        Host(host_type="no_existing_csp")

    # Test: Existing CSP module, with no valid class
    with pytest.raises(HostConfigurationException):
        Host(host_type="_csp")

    # Test: direct instantiation of subclass without specify host_type
    host = AWSHost(**kwargs)

    # Test: repr
    assert repr(host) == str(host)

    # Test: Instantiation with missing mandatory arguments
    with pytest.raises(HostConfigurationException):
        Host(host_type="AWS", config=config)

    kwargs_no_client_id = kwargs.copy()
    del kwargs_no_client_id['client_id']
    with pytest.raises(HostConfigurationException):
        Host(host_type="AWS", **kwargs_no_client_id)

    # Test: Abstract class
    class UncompletedCSP(CSPHost):
        """Uncompleted CSP class"""

    with pytest.raises(TypeError):
        UncompletedCSP()
Example #2
0
def accelize_credentials_available():
    """
    Checks in Accelize credentials are available.
    Skips test if not, else, returns configuration.

    Returns:
        apyfal.configuration.Configuration
    """
    from apyfal.configuration import Configuration
    config = Configuration()
    if not has_accelize_credential(config):
        pytest.skip('Accelize Credentials required')
    return config
Example #3
0
def test_configuration_access_token_real_no_cred():
    """Tests AcceleratorClient.access_token

    with Accelize server
    Test parts that don't needs credentials"""
    from apyfal.exceptions import ClientAuthenticationException
    from apyfal.configuration import Configuration

    config = Configuration()
    try:
        del config._sections['accelize']
    except KeyError:
        pass
    config['accelize']['client_id'] = 'bad_client_id'
    config['accelize']['secret_id'] = 'bad_secret_id'

    # Test: Bad client_id
    with pytest.raises(ClientAuthenticationException):
        assert config.access_token
Example #4
0
def test_host_init():
    """Tests Host.__new__ and Host.__init__"""
    from apyfal.configuration import Configuration
    from apyfal.host import Host
    from apyfal.exceptions import HostConfigurationException

    # Mock arguments and configuration
    # Note that host_type is not specified here
    config = Configuration()
    try:
        del config._sections['host']
    except KeyError:
        pass
    # Test: Not existing host module
    with pytest.raises(HostConfigurationException):
        Host(host_type="no_existing_csp")

    # Test: Instantiation of without specify host_type
    host = Host(config=config)
    assert host.__class__ is Host

    # Test: repr
    assert repr(host) == str(host)

    # Test: Passing host_ip
    url = 'http://127.0.0.1'
    host = Host(config=config, host_ip=url)
    host.start()
    assert host.url == url

    # Test: Passing nothing
    host = Host(config=config)
    with pytest.raises(HostConfigurationException):
        host.start()

    # Test: iter_hosts empty default
    assert list(host._iter_hosts()) == []

    # Test: iter_hosts with proper _iter_host
    def _iter_hosts():
        """dummy iter_host"""
        for index in range(2):
            yield dict(public_ip='127.0.0.1',
                       host_name='prefix_accelize_pytest%d_000000000000' %
                       index)

    host._iter_hosts = _iter_hosts
    assert list(host.iter_hosts()) == [{
        'public_ip':
        '127.0.0.1',
        'host_name':
        'prefix_accelize_pytest%d_000000000000' % index,
        'accelerator':
        'pytest%d' % index,
        'url':
        'http://127.0.0.1',
        'host_type':
        host.host_type,
        '_repr': ("<apyfal.host.Host name='prefix_accelize_"
                  "pytest%d_000000000000'>") % index
    } for index in range(2)]

    # Test: iter_hosts without public ip
    def _iter_hosts():
        """dummy iter_host"""
        for index in range(2):
            yield dict(host_name='prefix_accelize_pytest%d_000000000000' %
                       index)

    host._iter_hosts = _iter_hosts
    assert list(host.iter_hosts()) == [{
        'host_name':
        'prefix_accelize_pytest%d_000000000000' % index,
        'accelerator':
        'pytest%d' % index,
        'host_type':
        host.host_type,
        '_repr': ("<apyfal.host.Host name='prefix_accelize_"
                  "pytest%d_000000000000'>") % index
    } for index in range(2)]

    # Test: iter_hosts host_name_prefix
    prefix = 'prefix'
    host = Host(config=config, host_name_prefix=prefix)
    assert host._host_name_prefix == prefix
    assert host._host_name_match is None

    list(host.iter_hosts(host_name_prefix=True))
    assert host._host_name_match is not None
    assert not host._is_accelerator_host('accelize_pytest_000000000000')
    assert not host._is_accelerator_host('other_accelize_pytest_000000000000')
    assert host._is_accelerator_host('prefix_accelize_pytest_000000000000')

    list(host.iter_hosts(host_name_prefix=False))
    assert host._is_accelerator_host('accelize_pytest_000000000000')
    assert host._is_accelerator_host('other_accelize_pytest_000000000000')
    assert host._is_accelerator_host('prefix_accelize_pytest_000000000000')

    list(host.iter_hosts(host_name_prefix='other'))
    assert not host._is_accelerator_host('accelize_pytest_000000000000')
    assert host._is_accelerator_host('other_accelize_pytest_000000000000')
    assert not host._is_accelerator_host('prefix_accelize_pytest_000000000000')

    # Test: not instance names
    list(host.iter_hosts(host_name_prefix=False))
    assert not host._is_accelerator_host('pytest_000000000000')
    assert not host._is_accelerator_host('accelize_000000000000')
    assert not host._is_accelerator_host('accelize_prefix')
    assert not host._is_accelerator_host('accelize_prefix_000')
Example #5
0
def test_configuration_access_token():
    """Tests Configuration.access_token

    without Accelize server"""
    from apyfal.configuration import Configuration, METERING_SERVER
    import apyfal.exceptions as exc

    # Mocks some variables
    access_token = 'dummy_token'
    client_id = 'dummy_client_id',
    secret_id = 'dummy_secret_id'

    # Mocks requests in utilities

    class Response:
        """Fake requests.Response"""
        status_code = 200
        text = json.dumps({'access_token': access_token})

        @staticmethod
        def raise_for_status():
            """Do nothing"""

    class DummySession(requests.Session):
        """Fake requests.Session"""
        @staticmethod
        def post(url, data, auth, **_):
            """Checks input arguments and returns fake response"""
            # Checks input arguments
            assert METERING_SERVER in url
            assert client_id in auth
            assert secret_id in auth

            # Returns fake response
            return Response()

    # Monkey patch requests in utilities
    requests_session = requests.Session
    requests.Session = DummySession

    # Tests
    try:
        # Test: No credential provided
        config = Configuration()
        try:
            del config._sections['accelize']
        except KeyError:
            pass
        with pytest.raises(exc.ClientAuthenticationException):
            assert config.access_token

        # Test: Everything OK
        config = Configuration()
        assert config['accelize'] is not None  # Creates section if not exists
        config._sections['accelize']['client_id'] = client_id
        config._sections['accelize']['secret_id'] = secret_id
        assert config.access_token == access_token

        # Test: Check dict features
        assert len(config) == len(config._sections)
        for section in config:
            assert section in config._sections
            assert section in config

        config._sections['accelize']['test_value'] = '1,2,3'
        assert config['accelize'].get_literal('test_value') == (1, 2, 3)
        config._sections['accelize']['test_value'] = '1\n2\n3'
        assert config['accelize'].get_list('test_value') == ["1", "2", "3"]
        assert config['accelize'].get_literal('no_value') is None
        assert config['accelize'].get_list('no_value') == []

        # Test cached value
        del config._sections['accelize']
        assert config.access_token == access_token

        # Test: Authentication failed
        config = Configuration()
        try:
            del config._sections['accelize']
        except KeyError:
            pass
        Response.status_code = 400
        with pytest.raises(exc.ClientAuthenticationException):
            assert config.access_token

    # Restore requests
    finally:
        requests.Session = requests_session
Example #6
0
def test_csphost_user_data(tmpdir):
    """Tests Host._user_data"""
    from apyfal.configuration import Configuration
    from apyfal.exceptions import HostConfigurationException
    import apyfal.configuration as _cfg

    # Mock CSP class
    class DummyCSP(get_dummy_csp_class()):
        """Dummy CSP"""
        @property
        def host_name(self):
            """Return fake result"""
            return 'host_name'

        def _get_instance(self):
            """Do nothing"""

        def _status(self):
            """Do nothing"""

    config_content = ("[dummy]\n" "dummy1 = dummy1\n" "dummy2 = dummy2\n")
    config_file = tmpdir.join('dummy.conf')
    config_file.write(config_content)
    config = Configuration(str(config_file))

    script_content = ("#!/usr/bin/env bash\n"
                      "script line 1\n"
                      "script line 2")
    script_file = tmpdir.join('dummy.sh')
    script_file.write(script_content)

    ssl_crt_content = "public_key"
    ssl_crt_file = tmpdir.join('dummy.crt')
    ssl_crt_file.write(ssl_crt_content)

    ssl_key_content = "private_key"
    ssl_key_file = tmpdir.join('dummy.key')
    ssl_key_file.write(ssl_key_content)

    # Test: No user data
    assert DummyCSP._SH_FLAG in DummyCSP(client_id='client_id',
                                         secret_id='secret_id',
                                         region='region')._user_data.decode()

    # Test: Get user data
    user_data = DummyCSP(client_id='client_id',
                         secret_id='secret_id',
                         region='region',
                         init_config=config,
                         init_script=str(script_file))._user_data.decode()

    # Test: Check shebang
    assert user_data.count('#!') == 1
    assert DummyCSP._SH_FLAG in user_data

    # Test: Check configuration file presence
    for line in config_content.splitlines():
        assert line in user_data

    # Test: Check script file presence
    for line in script_content.splitlines()[1:]:
        assert line in user_data

    # Test: Check path
    assert DummyCSP._HOME in user_data

    # Test: Certificate
    user_data = DummyCSP(client_id='client_id',
                         secret_id='secret_id',
                         region='region',
                         ssl_cert_crt=str(ssl_crt_file),
                         ssl_cert_key=str(ssl_key_file))._user_data.decode()

    assert ssl_key_content in user_data
    assert ssl_crt_content in user_data
    assert DummyCSP._SSL_CERT_CRT in user_data
    assert DummyCSP._SSL_CERT_KEY in user_data

    # Test: Generated certificate
    user_data = DummyCSP(client_id='client_id',
                         secret_id='secret_id',
                         region='region',
                         ssl_cert_crt=str(ssl_crt_file),
                         ssl_cert_key=str(ssl_key_file),
                         ssl_cert_generate=True)._user_data.decode()

    assert ssl_crt_file.read_text('utf-8') in user_data
    assert ssl_key_file.read_text('utf-8') in user_data

    # Test: Generated temporary certificate
    cfg_apyfal_cert_crt = _cfg.APYFAL_CERT_CRT
    cfg_apyfal_cert_key = _cfg.APYFAL_CERT_KEY
    _cfg.APYFAL_CERT_KEY = str(tmpdir.join('dummy_generated.key'))
    _cfg.APYFAL_CERT_CRT = str(tmpdir.join('dummy_generated.crt'))
    try:
        csp = DummyCSP(client_id='client_id',
                       secret_id='secret_id',
                       region='region',
                       ssl_cert_generate=True)
        user_data = csp._user_data.decode()

        with open(csp._ssl_cert_crt, 'rt') as file:
            tmp_crt_content = file.read()
        with open(csp._ssl_cert_key, 'rt') as file:
            tmp_key_content = file.read()

        assert tmp_key_content in user_data
        assert tmp_crt_content in user_data

        # Test: Already generated, should not recreate certificates
        csp = DummyCSP(client_id='client_id',
                       secret_id='secret_id',
                       region='region',
                       ssl_cert_generate=True)
        user_data = csp._user_data.decode()
        assert tmp_key_content in user_data
        assert tmp_crt_content in user_data

    finally:
        _cfg.APYFAL_CERT_KEY = cfg_apyfal_cert_key
        _cfg.APYFAL_CERT_CRT = cfg_apyfal_cert_crt

    # Test: Missing key
    with pytest.raises(HostConfigurationException):
        assert DummyCSP(client_id='client_id',
                        secret_id='secret_id',
                        region='region',
                        ssl_cert_key=str(ssl_key_file))._user_data

    # Test: Missing crt
    with pytest.raises(HostConfigurationException):
        assert DummyCSP(client_id='client_id',
                        secret_id='secret_id',
                        region='region',
                        ssl_cert_crt=str(ssl_crt_file))._user_data

    # Test: Disabled certificate
    csp = DummyCSP(client_id='client_id',
                   secret_id='secret_id',
                   region='region',
                   ssl_cert_crt=False)
    assert csp._ssl_cert_crt is False
Example #7
0
def run_full_real_test_sequence(host_type, environment):
    """Run common real tests for all CSP.

    Args:
        host_type (str): CSP host_type.
        environment (dict): Environment to use
    """
    from apyfal.configuration import Configuration
    from apyfal.exceptions import AcceleratorException
    from apyfal import iter_accelerators

    # Skip if no correct configuration with this host_type
    config = Configuration()

    if config['host']['host_type'] != host_type:
        config['host']['host_type'] = host_type
        try:
            del config['host']['client_id']
        except KeyError:
            pass
        try:
            del config['host']['secret_id']
        except KeyError:
            pass

    section = config['host.%s' % host_type]
    if not section['client_id'] or not section['secret_id']:
        pytest.skip('No configuration for %s.' % host_type)

    elif section['region'] not in environment:
        pytest.skip("No configuration for '%s' region on %s." %
                    (section['region'], host_type))

    # Enable logger
    from apyfal import get_logger
    get_logger(stdout=True)

    # Defines testing prefix. Used to easily found CSP object linked to a
    # particular test.
    testing_prefix = datetime.now().strftime('ApyfalTesting%H%M%S')

    # Add accelerator to environment
    environment['accelerator'] = 'apyfal_testing'
    config['host']['host_name_prefix'] = testing_prefix

    # Changes Host parameter prefix for default names
    # TODO: replace 'apyfal_testing' by testing_prefix variable once full
    #       clean up of CSP objects is implemented.
    from apyfal.host import Host
    host_parameter_prefix = Host._PARAMETER_PREFIX
    Host._PARAMETER_PREFIX = 'ApyfalTesting'

    # Tests:
    instance_id_term = None
    instance_id_stop = None
    instance_id_keep = None

    try:
        # Start and terminate
        print('Test: Start and terminate')
        with Host(config=config, stop_mode='term') as csp_term:
            csp_term.start(accel_parameters=environment)
            instance_id_term = csp_term.instance_id

        # Start and stop, then terminate
        # Also check getting instance handle with ID
        print('Test: Start and stop')
        with Host(config=config, stop_mode='stop') as csp_stop:
            csp_stop.start(accel_parameters=environment)
            instance_id_stop = csp_stop.instance_id

        print('Test: Start from stopped and terminate')
        with Host(config=config,
                  instance_id=instance_id_stop,
                  stop_mode='term') as csp:
            csp.start(accel_parameters=environment)
            assert csp.instance_id == instance_id_stop

        # Start and keep, then
        # Also check getting instance handle with URL
        print('Test: Start and keep')
        with Host(config=config, stop_mode='keep') as csp_keep:
            csp_keep.start(accel_parameters=environment)
            instance_id_keep = csp_keep.instance_id
            instance_url_keep = csp_keep.url

        print('Test: Reuse with instance IP/URL')
        with Host(config=config, host_ip=instance_url_keep) as csp:
            csp.start(accel_parameters=environment)
            assert csp.url == instance_url_keep

        print('Test: Reuse with instance ID and terminate')
        with Host(config=config,
                  instance_id=instance_id_keep,
                  stop_mode='term') as csp:
            csp.start(accel_parameters=environment)
            assert csp.instance_id == instance_id_keep

    # Clean up testing environment
    finally:
        # Restore prefix value
        Host._PARAMETER_PREFIX = host_parameter_prefix

        # Stops all instances
        time.sleep(5)
        for accelerator in iter_accelerators(config=config):
            instance_id = None
            try:
                instance_id = accelerator.host.instance_id
                accelerator.stop('term')
            except AcceleratorException:
                pass
            assert instance_id not in (instance_id_term, instance_id_stop,
                                       instance_id_keep)