Enable xenial/queens amulet tests

Updated amulet tests for xenial/queens.
Enable xenial/queens amulet test as part of extended tests.

Change-Id: I8990eadf781bd0d555267ce2cacb8ab53f78fa5b
This commit is contained in:
Robert Ayres 2018-03-05 14:33:25 +01:00
parent 672091e492
commit 64570f71f5
8 changed files with 493 additions and 95 deletions

View File

@ -21,6 +21,9 @@ from collections import OrderedDict
from charmhelpers.contrib.amulet.deployment import ( from charmhelpers.contrib.amulet.deployment import (
AmuletDeployment AmuletDeployment
) )
from charmhelpers.contrib.openstack.amulet.utils import (
OPENSTACK_RELEASES_PAIRS
)
DEBUG = logging.DEBUG DEBUG = logging.DEBUG
ERROR = logging.ERROR ERROR = logging.ERROR
@ -271,11 +274,8 @@ class OpenStackAmuletDeployment(AmuletDeployment):
release. release.
""" """
# Must be ordered by OpenStack release (not by Ubuntu release): # Must be ordered by OpenStack release (not by Ubuntu release):
(self.trusty_icehouse, self.trusty_kilo, self.trusty_liberty, for i, os_pair in enumerate(OPENSTACK_RELEASES_PAIRS):
self.trusty_mitaka, self.xenial_mitaka, self.xenial_newton, setattr(self, os_pair, i)
self.yakkety_newton, self.xenial_ocata, self.zesty_ocata,
self.xenial_pike, self.artful_pike, self.xenial_queens,
self.bionic_queens,) = range(13)
releases = { releases = {
('trusty', None): self.trusty_icehouse, ('trusty', None): self.trusty_icehouse,

View File

@ -50,6 +50,13 @@ ERROR = logging.ERROR
NOVA_CLIENT_VERSION = "2" NOVA_CLIENT_VERSION = "2"
OPENSTACK_RELEASES_PAIRS = [
'trusty_icehouse', 'trusty_kilo', 'trusty_liberty',
'trusty_mitaka', 'xenial_mitaka', 'xenial_newton',
'yakkety_newton', 'xenial_ocata', 'zesty_ocata',
'xenial_pike', 'artful_pike', 'xenial_queens',
'bionic_queens']
class OpenStackAmuletUtils(AmuletUtils): class OpenStackAmuletUtils(AmuletUtils):
"""OpenStack amulet utilities. """OpenStack amulet utilities.
@ -63,7 +70,34 @@ class OpenStackAmuletUtils(AmuletUtils):
super(OpenStackAmuletUtils, self).__init__(log_level) super(OpenStackAmuletUtils, self).__init__(log_level)
def validate_endpoint_data(self, endpoints, admin_port, internal_port, def validate_endpoint_data(self, endpoints, admin_port, internal_port,
public_port, expected): public_port, expected, openstack_release=None):
"""Validate endpoint data. Pick the correct validator based on
OpenStack release. Expected data should be in the v2 format:
{
'id': id,
'region': region,
'adminurl': adminurl,
'internalurl': internalurl,
'publicurl': publicurl,
'service_id': service_id}
"""
validation_function = self.validate_v2_endpoint_data
xenial_queens = OPENSTACK_RELEASES_PAIRS.index('xenial_queens')
if openstack_release and openstack_release >= xenial_queens:
validation_function = self.validate_v3_endpoint_data
expected = {
'id': expected['id'],
'region': expected['region'],
'region_id': 'RegionOne',
'url': self.valid_url,
'interface': self.not_null,
'service_id': expected['service_id']}
return validation_function(endpoints, admin_port, internal_port,
public_port, expected)
def validate_v2_endpoint_data(self, endpoints, admin_port, internal_port,
public_port, expected):
"""Validate endpoint data. """Validate endpoint data.
Validate actual endpoint data vs expected endpoint data. The ports Validate actual endpoint data vs expected endpoint data. The ports
@ -141,7 +175,86 @@ class OpenStackAmuletUtils(AmuletUtils):
if len(found) != expected_num_eps: if len(found) != expected_num_eps:
return 'Unexpected number of endpoints found' return 'Unexpected number of endpoints found'
def validate_svc_catalog_endpoint_data(self, expected, actual): def convert_svc_catalog_endpoint_data_to_v3(self, ep_data):
"""Convert v2 endpoint data into v3.
{
'service_name1': [
{
'adminURL': adminURL,
'id': id,
'region': region.
'publicURL': publicURL,
'internalURL': internalURL
}],
'service_name2': [
{
'adminURL': adminURL,
'id': id,
'region': region.
'publicURL': publicURL,
'internalURL': internalURL
}],
}
"""
self.log.warn("Endpoint ID and Region ID validation is limited to not "
"null checks after v2 to v3 conversion")
for svc in ep_data.keys():
assert len(ep_data[svc]) == 1, "Unknown data format"
svc_ep_data = ep_data[svc][0]
ep_data[svc] = [
{
'url': svc_ep_data['adminURL'],
'interface': 'admin',
'region': svc_ep_data['region'],
'region_id': self.not_null,
'id': self.not_null},
{
'url': svc_ep_data['publicURL'],
'interface': 'public',
'region': svc_ep_data['region'],
'region_id': self.not_null,
'id': self.not_null},
{
'url': svc_ep_data['internalURL'],
'interface': 'internal',
'region': svc_ep_data['region'],
'region_id': self.not_null,
'id': self.not_null}]
return ep_data
def validate_svc_catalog_endpoint_data(self, expected, actual,
openstack_release=None):
"""Validate service catalog endpoint data. Pick the correct validator
for the OpenStack version. Expected data should be in the v2 format:
{
'service_name1': [
{
'adminURL': adminURL,
'id': id,
'region': region.
'publicURL': publicURL,
'internalURL': internalURL
}],
'service_name2': [
{
'adminURL': adminURL,
'id': id,
'region': region.
'publicURL': publicURL,
'internalURL': internalURL
}],
}
"""
validation_function = self.validate_v2_svc_catalog_endpoint_data
xenial_queens = OPENSTACK_RELEASES_PAIRS.index('xenial_queens')
if openstack_release and openstack_release >= xenial_queens:
validation_function = self.validate_v3_svc_catalog_endpoint_data
expected = self.convert_svc_catalog_endpoint_data_to_v3(expected)
return validation_function(expected, actual)
def validate_v2_svc_catalog_endpoint_data(self, expected, actual):
"""Validate service catalog endpoint data. """Validate service catalog endpoint data.
Validate a list of actual service catalog endpoints vs a list of Validate a list of actual service catalog endpoints vs a list of
@ -367,13 +480,36 @@ class OpenStackAmuletUtils(AmuletUtils):
project_domain_name=None, project_name=None): project_domain_name=None, project_name=None):
"""Authenticate with Keystone""" """Authenticate with Keystone"""
self.log.debug('Authenticating with keystone...') self.log.debug('Authenticating with keystone...')
port = 5000 if not api_version:
if admin_port: api_version = 2
port = 35357 sess, auth = self.get_keystone_session(
base_ep = "http://{}:{}".format(keystone_ip.strip().decode('utf-8'), keystone_ip=keystone_ip,
port) username=username,
if not api_version or api_version == 2: password=password,
ep = base_ep + "/v2.0" api_version=api_version,
admin_port=admin_port,
user_domain_name=user_domain_name,
domain_name=domain_name,
project_domain_name=project_domain_name,
project_name=project_name
)
if api_version == 2:
client = keystone_client.Client(session=sess)
else:
client = keystone_client_v3.Client(session=sess)
# This populates the client.service_catalog
client.auth_ref = auth.get_access(sess)
return client
def get_keystone_session(self, keystone_ip, username, password,
api_version=False, admin_port=False,
user_domain_name=None, domain_name=None,
project_domain_name=None, project_name=None):
"""Return a keystone session object"""
ep = self.get_keystone_endpoint(keystone_ip,
api_version=api_version,
admin_port=admin_port)
if api_version == 2:
auth = v2.Password( auth = v2.Password(
username=username, username=username,
password=password, password=password,
@ -381,12 +517,7 @@ class OpenStackAmuletUtils(AmuletUtils):
auth_url=ep auth_url=ep
) )
sess = keystone_session.Session(auth=auth) sess = keystone_session.Session(auth=auth)
client = keystone_client.Client(session=sess)
# This populates the client.service_catalog
client.auth_ref = auth.get_access(sess)
return client
else: else:
ep = base_ep + "/v3"
auth = v3.Password( auth = v3.Password(
user_domain_name=user_domain_name, user_domain_name=user_domain_name,
username=username, username=username,
@ -397,10 +528,57 @@ class OpenStackAmuletUtils(AmuletUtils):
auth_url=ep auth_url=ep
) )
sess = keystone_session.Session(auth=auth) sess = keystone_session.Session(auth=auth)
client = keystone_client_v3.Client(session=sess) return (sess, auth)
# This populates the client.service_catalog
client.auth_ref = auth.get_access(sess) def get_keystone_endpoint(self, keystone_ip, api_version=None,
return client admin_port=False):
"""Return keystone endpoint"""
port = 5000
if admin_port:
port = 35357
base_ep = "http://{}:{}".format(keystone_ip.strip().decode('utf-8'),
port)
if api_version == 2:
ep = base_ep + "/v2.0"
else:
ep = base_ep + "/v3"
return ep
def get_default_keystone_session(self, keystone_sentry,
openstack_release=None):
"""Return a keystone session object and client object assuming standard
default settings
Example call in amulet tests:
self.keystone_session, self.keystone = u.get_default_keystone_session(
self.keystone_sentry,
openstack_release=self._get_openstack_release())
The session can then be used to auth other clients:
neutronclient.Client(session=session)
aodh_client.Client(session=session)
eyc
"""
self.log.debug('Authenticating keystone admin...')
api_version = 2
client_class = keystone_client.Client
# 11 => xenial_queens
if openstack_release and openstack_release >= 11:
api_version = 3
client_class = keystone_client_v3.Client
keystone_ip = keystone_sentry.info['public-address']
session, auth = self.get_keystone_session(
keystone_ip,
api_version=api_version,
username='admin',
password='openstack',
project_name='admin',
user_domain_name='admin_domain',
project_domain_name='admin_domain')
client = client_class(session=session)
# This populates the client.service_catalog
client.auth_ref = auth.get_access(session)
return session, client
def authenticate_keystone_admin(self, keystone_sentry, user, password, def authenticate_keystone_admin(self, keystone_sentry, user, password,
tenant=None, api_version=None, tenant=None, api_version=None,

View File

@ -384,6 +384,7 @@ class IdentityServiceContext(OSContextGenerator):
# so a missing value just indicates keystone needs # so a missing value just indicates keystone needs
# upgrading # upgrading
ctxt['admin_tenant_id'] = rdata.get('service_tenant_id') ctxt['admin_tenant_id'] = rdata.get('service_tenant_id')
ctxt['admin_domain_id'] = rdata.get('service_domain_id')
return ctxt return ctxt
return {} return {}

View File

@ -182,7 +182,7 @@ SWIFT_CODENAMES = OrderedDict([
('pike', ('pike',
['2.13.0', '2.15.0']), ['2.13.0', '2.15.0']),
('queens', ('queens',
['2.16.0']), ['2.16.0', '2.17.0']),
]) ])
# >= Liberty version->codename mapping # >= Liberty version->codename mapping

View File

@ -145,21 +145,16 @@ class CinderBasicDeployment(OpenStackAmuletDeployment):
self._get_openstack_release_string())) self._get_openstack_release_string()))
# Authenticate admin with keystone # Authenticate admin with keystone
self.keystone = u.authenticate_keystone_admin(self.keystone_sentry, self.keystone_session, self.keystone = u.get_default_keystone_session(
user='admin', self.keystone_sentry,
password='openstack', openstack_release=self._get_openstack_release())
tenant='admin')
# Authenticate admin with cinder endpoint # Authenticate admin with cinder endpoint
if self._get_openstack_release() >= self.xenial_pike: if self._get_openstack_release() >= self.xenial_pike:
api_version = 2 api_version = 2
else: else:
api_version = 1 api_version = 1
self.cinder = u.authenticate_cinder_admin(self.keystone_sentry, self.cinder = u.authenticate_cinder_admin(self.keystone, api_version)
username='admin',
password='openstack',
tenant='admin',
api_version=api_version)
# Authenticate admin with glance endpoint # Authenticate admin with glance endpoint
self.glance = u.authenticate_glance_admin(self.keystone) self.glance = u.authenticate_glance_admin(self.keystone)
@ -323,34 +318,48 @@ class CinderBasicDeployment(OpenStackAmuletDeployment):
def test_110_users(self): def test_110_users(self):
"""Verify expected users.""" """Verify expected users."""
u.log.debug('Checking keystone users...') u.log.debug('Checking keystone users...')
if self._get_openstack_release() < self.xenial_pike: if self._get_openstack_release() >= self.xenial_queens:
expected = [{
'name': 'cinder_cinderv2',
'enabled': True,
'tenantId': u.not_null,
'id': u.not_null,
'email': 'juju@localhost',
}]
else:
expected = [{ expected = [{
'name': 'cinderv2_cinderv3', 'name': 'cinderv2_cinderv3',
'enabled': True, 'enabled': True,
'tenantId': u.not_null, 'default_project_id': u.not_null,
'id': u.not_null, 'id': u.not_null,
'email': 'juju@localhost', 'email': 'juju@localhost',
}] }]
domain = self.keystone.domains.find(name='service_domain')
expected.append({ actual = self.keystone.users.list(domain=domain)
'name': 'admin', api_version = 3
'enabled': True, elif self._get_openstack_release() >= self.xenial_pike:
'tenantId': u.not_null, expected = [
'id': u.not_null, {'name': 'cinderv2_cinderv3',
'email': 'juju@localhost', 'enabled': True,
}) 'tenantId': u.not_null,
'id': u.not_null,
actual = self.keystone.users.list() 'email': 'juju@localhost'},
{'name': 'admin',
ret = u.validate_user_data(expected, actual) 'enabled': True,
'tenantId': u.not_null,
'id': u.not_null,
'email': 'juju@localhost'}
]
actual = self.keystone.users.list()
api_version = 2
else:
expected = [
{'name': 'cinder_cinderv2',
'enabled': True,
'tenantId': u.not_null,
'id': u.not_null,
'email': 'juju@localhost'},
{'name': 'admin',
'enabled': True,
'tenantId': u.not_null,
'id': u.not_null,
'email': 'juju@localhost'}
]
actual = self.keystone.users.list()
api_version = 2
ret = u.validate_user_data(expected, actual, api_version)
if ret: if ret:
amulet.raise_status(amulet.FAIL, msg=ret) amulet.raise_status(amulet.FAIL, msg=ret)
@ -381,7 +390,10 @@ class CinderBasicDeployment(OpenStackAmuletDeployment):
'volume': [endpoint_id]} 'volume': [endpoint_id]}
actual = self.keystone.service_catalog.get_endpoints() actual = self.keystone.service_catalog.get_endpoints()
ret = u.validate_svc_catalog_endpoint_data(expected, actual) ret = u.validate_svc_catalog_endpoint_data(
expected,
actual,
openstack_release=self._get_openstack_release())
if ret: if ret:
amulet.raise_status(amulet.FAIL, msg=ret) amulet.raise_status(amulet.FAIL, msg=ret)
@ -390,15 +402,35 @@ class CinderBasicDeployment(OpenStackAmuletDeployment):
u.log.debug('Checking cinder endpoint...') u.log.debug('Checking cinder endpoint...')
endpoints = self.keystone.endpoints.list() endpoints = self.keystone.endpoints.list()
admin_port = internal_port = public_port = '8776' admin_port = internal_port = public_port = '8776'
expected = {'id': u.not_null, if self._get_openstack_release() >= self.xenial_queens:
'region': 'RegionOne', expected = {
'adminurl': u.valid_url, 'id': u.not_null,
'internalurl': u.valid_url, 'region': 'RegionOne',
'publicurl': u.valid_url, 'region_id': 'RegionOne',
'service_id': u.not_null} 'url': u.valid_url,
'interface': u.not_null,
ret = u.validate_endpoint_data(endpoints, admin_port, internal_port, 'service_id': u.not_null}
public_port, expected) ret = u.validate_v3_endpoint_data(
endpoints,
admin_port,
internal_port,
public_port,
expected,
6)
else:
expected = {
'id': u.not_null,
'region': 'RegionOne',
'adminurl': u.valid_url,
'internalurl': u.valid_url,
'publicurl': u.valid_url,
'service_id': u.not_null}
ret = u.validate_v2_endpoint_data(
endpoints,
admin_port,
internal_port,
public_port,
expected)
if ret: if ret:
amulet.raise_status(amulet.FAIL, amulet.raise_status(amulet.FAIL,
msg='cinder endpoint: {}'.format(ret)) msg='cinder endpoint: {}'.format(ret))
@ -582,7 +614,19 @@ class CinderBasicDeployment(OpenStackAmuletDeployment):
'rabbit_password': rel_mq_ci['password'], 'rabbit_password': rel_mq_ci['password'],
'rabbit_host': rel_mq_ci['hostname'], 'rabbit_host': rel_mq_ci['hostname'],
} }
if self._get_openstack_release() >= self.trusty_mitaka: if self._get_openstack_release() >= self.xenial_queens:
expected['keystone_authtoken'] = {
'auth_uri': auth_uri.rstrip('/'),
'auth_url': auth_url.rstrip('/'),
'auth_type': 'password',
'project_domain_name': 'service_domain',
'user_domain_name': 'service_domain',
'project_name': 'services',
'username': rel_ks_ci['service_username'],
'password': rel_ks_ci['service_password'],
'signing_dir': '/var/cache/cinder'
}
elif self._get_openstack_release() >= self.trusty_mitaka:
expected['keystone_authtoken'] = { expected['keystone_authtoken'] = {
'auth_uri': auth_uri.rstrip('/'), 'auth_uri': auth_uri.rstrip('/'),
'auth_url': auth_url.rstrip('/'), 'auth_url': auth_url.rstrip('/'),

View File

@ -21,6 +21,9 @@ from collections import OrderedDict
from charmhelpers.contrib.amulet.deployment import ( from charmhelpers.contrib.amulet.deployment import (
AmuletDeployment AmuletDeployment
) )
from charmhelpers.contrib.openstack.amulet.utils import (
OPENSTACK_RELEASES_PAIRS
)
DEBUG = logging.DEBUG DEBUG = logging.DEBUG
ERROR = logging.ERROR ERROR = logging.ERROR
@ -271,11 +274,8 @@ class OpenStackAmuletDeployment(AmuletDeployment):
release. release.
""" """
# Must be ordered by OpenStack release (not by Ubuntu release): # Must be ordered by OpenStack release (not by Ubuntu release):
(self.trusty_icehouse, self.trusty_kilo, self.trusty_liberty, for i, os_pair in enumerate(OPENSTACK_RELEASES_PAIRS):
self.trusty_mitaka, self.xenial_mitaka, self.xenial_newton, setattr(self, os_pair, i)
self.yakkety_newton, self.xenial_ocata, self.zesty_ocata,
self.xenial_pike, self.artful_pike, self.xenial_queens,
self.bionic_queens,) = range(13)
releases = { releases = {
('trusty', None): self.trusty_icehouse, ('trusty', None): self.trusty_icehouse,

View File

@ -50,6 +50,13 @@ ERROR = logging.ERROR
NOVA_CLIENT_VERSION = "2" NOVA_CLIENT_VERSION = "2"
OPENSTACK_RELEASES_PAIRS = [
'trusty_icehouse', 'trusty_kilo', 'trusty_liberty',
'trusty_mitaka', 'xenial_mitaka', 'xenial_newton',
'yakkety_newton', 'xenial_ocata', 'zesty_ocata',
'xenial_pike', 'artful_pike', 'xenial_queens',
'bionic_queens']
class OpenStackAmuletUtils(AmuletUtils): class OpenStackAmuletUtils(AmuletUtils):
"""OpenStack amulet utilities. """OpenStack amulet utilities.
@ -63,7 +70,34 @@ class OpenStackAmuletUtils(AmuletUtils):
super(OpenStackAmuletUtils, self).__init__(log_level) super(OpenStackAmuletUtils, self).__init__(log_level)
def validate_endpoint_data(self, endpoints, admin_port, internal_port, def validate_endpoint_data(self, endpoints, admin_port, internal_port,
public_port, expected): public_port, expected, openstack_release=None):
"""Validate endpoint data. Pick the correct validator based on
OpenStack release. Expected data should be in the v2 format:
{
'id': id,
'region': region,
'adminurl': adminurl,
'internalurl': internalurl,
'publicurl': publicurl,
'service_id': service_id}
"""
validation_function = self.validate_v2_endpoint_data
xenial_queens = OPENSTACK_RELEASES_PAIRS.index('xenial_queens')
if openstack_release and openstack_release >= xenial_queens:
validation_function = self.validate_v3_endpoint_data
expected = {
'id': expected['id'],
'region': expected['region'],
'region_id': 'RegionOne',
'url': self.valid_url,
'interface': self.not_null,
'service_id': expected['service_id']}
return validation_function(endpoints, admin_port, internal_port,
public_port, expected)
def validate_v2_endpoint_data(self, endpoints, admin_port, internal_port,
public_port, expected):
"""Validate endpoint data. """Validate endpoint data.
Validate actual endpoint data vs expected endpoint data. The ports Validate actual endpoint data vs expected endpoint data. The ports
@ -141,7 +175,86 @@ class OpenStackAmuletUtils(AmuletUtils):
if len(found) != expected_num_eps: if len(found) != expected_num_eps:
return 'Unexpected number of endpoints found' return 'Unexpected number of endpoints found'
def validate_svc_catalog_endpoint_data(self, expected, actual): def convert_svc_catalog_endpoint_data_to_v3(self, ep_data):
"""Convert v2 endpoint data into v3.
{
'service_name1': [
{
'adminURL': adminURL,
'id': id,
'region': region.
'publicURL': publicURL,
'internalURL': internalURL
}],
'service_name2': [
{
'adminURL': adminURL,
'id': id,
'region': region.
'publicURL': publicURL,
'internalURL': internalURL
}],
}
"""
self.log.warn("Endpoint ID and Region ID validation is limited to not "
"null checks after v2 to v3 conversion")
for svc in ep_data.keys():
assert len(ep_data[svc]) == 1, "Unknown data format"
svc_ep_data = ep_data[svc][0]
ep_data[svc] = [
{
'url': svc_ep_data['adminURL'],
'interface': 'admin',
'region': svc_ep_data['region'],
'region_id': self.not_null,
'id': self.not_null},
{
'url': svc_ep_data['publicURL'],
'interface': 'public',
'region': svc_ep_data['region'],
'region_id': self.not_null,
'id': self.not_null},
{
'url': svc_ep_data['internalURL'],
'interface': 'internal',
'region': svc_ep_data['region'],
'region_id': self.not_null,
'id': self.not_null}]
return ep_data
def validate_svc_catalog_endpoint_data(self, expected, actual,
openstack_release=None):
"""Validate service catalog endpoint data. Pick the correct validator
for the OpenStack version. Expected data should be in the v2 format:
{
'service_name1': [
{
'adminURL': adminURL,
'id': id,
'region': region.
'publicURL': publicURL,
'internalURL': internalURL
}],
'service_name2': [
{
'adminURL': adminURL,
'id': id,
'region': region.
'publicURL': publicURL,
'internalURL': internalURL
}],
}
"""
validation_function = self.validate_v2_svc_catalog_endpoint_data
xenial_queens = OPENSTACK_RELEASES_PAIRS.index('xenial_queens')
if openstack_release and openstack_release >= xenial_queens:
validation_function = self.validate_v3_svc_catalog_endpoint_data
expected = self.convert_svc_catalog_endpoint_data_to_v3(expected)
return validation_function(expected, actual)
def validate_v2_svc_catalog_endpoint_data(self, expected, actual):
"""Validate service catalog endpoint data. """Validate service catalog endpoint data.
Validate a list of actual service catalog endpoints vs a list of Validate a list of actual service catalog endpoints vs a list of
@ -350,16 +463,13 @@ class OpenStackAmuletUtils(AmuletUtils):
deployment._auto_wait_for_status() deployment._auto_wait_for_status()
self.keystone_wait_for_propagation(sentry_relation_pairs, api_version) self.keystone_wait_for_propagation(sentry_relation_pairs, api_version)
def authenticate_cinder_admin(self, keystone_sentry, username, def authenticate_cinder_admin(self, keystone, api_version=2):
password, tenant, api_version=2):
"""Authenticates admin user with cinder.""" """Authenticates admin user with cinder."""
# NOTE(beisner): cinder python client doesn't accept tokens. self.log.debug('Authenticating cinder admin...')
keystone_ip = keystone_sentry.info['public-address']
ept = "http://{}:5000/v2.0".format(keystone_ip.strip().decode('utf-8'))
_clients = { _clients = {
1: cinder_client.Client, 1: cinder_client.Client,
2: cinder_clientv2.Client} 2: cinder_clientv2.Client}
return _clients[api_version](username, password, tenant, ept) return _clients[api_version](session=keystone.session)
def authenticate_keystone(self, keystone_ip, username, password, def authenticate_keystone(self, keystone_ip, username, password,
api_version=False, admin_port=False, api_version=False, admin_port=False,
@ -367,13 +477,36 @@ class OpenStackAmuletUtils(AmuletUtils):
project_domain_name=None, project_name=None): project_domain_name=None, project_name=None):
"""Authenticate with Keystone""" """Authenticate with Keystone"""
self.log.debug('Authenticating with keystone...') self.log.debug('Authenticating with keystone...')
port = 5000 if not api_version:
if admin_port: api_version = 2
port = 35357 sess, auth = self.get_keystone_session(
base_ep = "http://{}:{}".format(keystone_ip.strip().decode('utf-8'), keystone_ip=keystone_ip,
port) username=username,
if not api_version or api_version == 2: password=password,
ep = base_ep + "/v2.0" api_version=api_version,
admin_port=admin_port,
user_domain_name=user_domain_name,
domain_name=domain_name,
project_domain_name=project_domain_name,
project_name=project_name
)
if api_version == 2:
client = keystone_client.Client(session=sess)
else:
client = keystone_client_v3.Client(session=sess)
# This populates the client.service_catalog
client.auth_ref = auth.get_access(sess)
return client
def get_keystone_session(self, keystone_ip, username, password,
api_version=False, admin_port=False,
user_domain_name=None, domain_name=None,
project_domain_name=None, project_name=None):
"""Return a keystone session object"""
ep = self.get_keystone_endpoint(keystone_ip,
api_version=api_version,
admin_port=admin_port)
if api_version == 2:
auth = v2.Password( auth = v2.Password(
username=username, username=username,
password=password, password=password,
@ -381,12 +514,7 @@ class OpenStackAmuletUtils(AmuletUtils):
auth_url=ep auth_url=ep
) )
sess = keystone_session.Session(auth=auth) sess = keystone_session.Session(auth=auth)
client = keystone_client.Client(session=sess)
# This populates the client.service_catalog
client.auth_ref = auth.get_access(sess)
return client
else: else:
ep = base_ep + "/v3"
auth = v3.Password( auth = v3.Password(
user_domain_name=user_domain_name, user_domain_name=user_domain_name,
username=username, username=username,
@ -397,10 +525,57 @@ class OpenStackAmuletUtils(AmuletUtils):
auth_url=ep auth_url=ep
) )
sess = keystone_session.Session(auth=auth) sess = keystone_session.Session(auth=auth)
client = keystone_client_v3.Client(session=sess) return (sess, auth)
# This populates the client.service_catalog
client.auth_ref = auth.get_access(sess) def get_keystone_endpoint(self, keystone_ip, api_version=None,
return client admin_port=False):
"""Return keystone endpoint"""
port = 5000
if admin_port:
port = 35357
base_ep = "http://{}:{}".format(keystone_ip.strip().decode('utf-8'),
port)
if api_version == 2:
ep = base_ep + "/v2.0"
else:
ep = base_ep + "/v3"
return ep
def get_default_keystone_session(self, keystone_sentry,
openstack_release=None):
"""Return a keystone session object and client object assuming standard
default settings
Example call in amulet tests:
self.keystone_session, self.keystone = u.get_default_keystone_session(
self.keystone_sentry,
openstack_release=self._get_openstack_release())
The session can then be used to auth other clients:
neutronclient.Client(session=session)
aodh_client.Client(session=session)
eyc
"""
self.log.debug('Authenticating keystone admin...')
api_version = 2
client_class = keystone_client.Client
# 11 => xenial_queens
if openstack_release and openstack_release >= 11:
api_version = 3
client_class = keystone_client_v3.Client
keystone_ip = keystone_sentry.info['public-address']
session, auth = self.get_keystone_session(
keystone_ip,
api_version=api_version,
username='admin',
password='openstack',
project_name='admin',
user_domain_name='admin_domain',
project_domain_name='admin_domain')
client = client_class(session=session)
# This populates the client.service_catalog
client.auth_ref = auth.get_access(session)
return session, client
def authenticate_keystone_admin(self, keystone_sentry, user, password, def authenticate_keystone_admin(self, keystone_sentry, user, password,
tenant=None, api_version=None, tenant=None, api_version=None,