def list(self, project=None, domain=None, group=None, default_project=None, **kwargs): """List users. If project, domain or group are provided, then filter users with those attributes. If ``**kwargs`` are provided, then filter users with attributes matching ``**kwargs``. .. warning:: The project argument is deprecated, use default_project instead. If both default_project and project is provided, the default_project will be used. """ if project: LOG.warning(_LW("The project argument is deprecated, " "use default_project instead.")) default_project_id = base.getid(default_project) or base.getid(project) if group: base_url = '/groups/%s' % base.getid(group) else: base_url = None return super(UserManager, self).list( base_url=base_url, domain_id=base.getid(domain), default_project_id=default_project_id, **kwargs)
def get_auth_ref_from_keyring(self, **kwargs): """Retrieve auth_ref from keyring. If auth_ref is found in keyring, (keyring_key, auth_ref) is returned. Otherwise, (keyring_key, None) is returned. :returns: (keyring_key, auth_ref) or (keyring_key, None) :returns: or (None, None) if use_keyring is not set in the object """ keyring_key = None auth_ref = None if self.use_keyring: keyring_key = self._build_keyring_key(**kwargs) try: auth_ref = keyring.get_password("keystoneclient_auth", keyring_key) if auth_ref: auth_ref = pickle.loads(auth_ref) # nosec if auth_ref.will_expire_soon(self.stale_duration): # token has expired, don't use it auth_ref = None except Exception as e: auth_ref = None _logger.warning( _LW('Unable to retrieve token from keyring %s'), e) return (keyring_key, auth_ref)
def update(self, user, name=None, domain=None, project=None, password=None, email=None, description=None, enabled=None, default_project=None, **kwargs): """Update a user. .. warning:: The project argument is deprecated, use default_project instead. If both default_project and project is provided, the default_project will be used. """ if project: LOG.warning(_LW("The project argument is deprecated, " "use default_project instead.")) default_project_id = base.getid(default_project) or base.getid(project) user_data = base.filter_none(name=name, domain_id=base.getid(domain), default_project_id=default_project_id, password=password, email=email, description=description, enabled=enabled, **kwargs) return self._update('/users/%s' % base.getid(user), {'user': user_data}, 'user', method='PATCH', log=False)
def create(self, name, domain=None, project=None, password=None, email=None, description=None, enabled=True, default_project=None, **kwargs): """Create a user. .. warning:: The project argument is deprecated, use default_project instead. If both default_project and project is provided, the default_project will be used. """ if project: LOG.warning(_LW("The project argument is deprecated, " "use default_project instead.")) default_project_id = base.getid(default_project) or base.getid(project) user_data = base.filter_none(name=name, domain_id=base.getid(domain), default_project_id=default_project_id, password=password, email=email, description=description, enabled=enabled, **kwargs) return self._create('/users', {'user': user_data}, 'user', log=not bool(password))
def store_auth_ref_into_keyring(self, keyring_key): """Store auth_ref into keyring. """ if self.use_keyring: try: keyring.set_password("keystoneclient_auth", keyring_key, pickle.dumps(self.auth_ref)) except Exception as e: _logger.warning(_LW("Failed to store token into keyring %s"), e)
def _do_create_plugin(self, session): plugin = None try: disc = self.get_discovery(session, self.auth_url, authenticated=False) except (exceptions.DiscoveryFailure, exceptions.HTTPError, exceptions.ConnectionError): LOG.warn(_LW('Discovering versions from the identity service ' 'failed when creating the password plugin. ' 'Attempting to determine version from URL.')) url_parts = urlparse.urlparse(self.auth_url) path = url_parts.path.lower() if path.startswith('/v2.0') and not self._has_domain_scope: plugin = self.create_plugin(session, (2, 0), self.auth_url) elif path.startswith('/v3'): plugin = self.create_plugin(session, (3, 0), self.auth_url) else: disc_data = disc.version_data() for data in disc_data: version = data['version'] if (discover.version_match((2,), version) and self._has_domain_scope): # NOTE(jamielennox): if there are domain parameters there # is no point even trying against v2 APIs. continue plugin = self.create_plugin(session, version, data['url'], raw_status=data['raw_status']) if plugin: break if plugin: return plugin # so there were no URLs that i could use for auth of any version. msg = _('Could not determine a suitable URL for the plugin') raise exceptions.DiscoveryFailure(msg)
def raw_version_data(self, allow_experimental=False, allow_deprecated=True, allow_unknown=False): """Get raw version information from URL. Raw data indicates that only minimal validation processing is performed on the data, so what is returned here will be the data in the same format it was received from the endpoint. :param bool allow_experimental: Allow experimental version endpoints. :param bool allow_deprecated: Allow deprecated version endpoints. :param bool allow_unknown: Allow endpoints with an unrecognised status. :returns: The endpoints returned from the server that match the criteria. :rtype: list """ versions = [] for v in self._data: try: status = v['status'] except KeyError: _LOGGER.warning(_LW('Skipping over invalid version data. ' 'No stability status in version.')) continue status = status.lower() if status in self.CURRENT_STATUSES: versions.append(v) elif status in self.DEPRECATED_STATUSES: if allow_deprecated: versions.append(v) elif status in self.EXPERIMENTAL_STATUSES: if allow_experimental: versions.append(v) elif allow_unknown: versions.append(v) return versions
def __init__(self, username=None, tenant_id=None, tenant_name=None, password=None, auth_url=None, region_name=None, endpoint=None, token=None, debug=False, auth_ref=None, use_keyring=False, force_new_token=False, stale_duration=None, user_id=None, user_domain_id=None, user_domain_name=None, domain_id=None, domain_name=None, project_id=None, project_name=None, project_domain_id=None, project_domain_name=None, trust_id=None, session=None, service_name=None, interface='admin', endpoint_override=None, auth=None, user_agent=USER_AGENT, connect_retries=None, **kwargs): # set baseline defaults self.user_id = None self.username = None self.user_domain_id = None self.user_domain_name = None self.domain_id = None self.domain_name = None self.project_id = None self.project_name = None self.project_domain_id = None self.project_domain_name = None self.auth_url = None self._endpoint = None self._management_url = None self.trust_id = None # if loading from a dictionary passed in via auth_ref, # load values from AccessInfo parsing that dictionary if auth_ref: self.auth_ref = access.AccessInfo.factory(**auth_ref) self.version = self.auth_ref.version self.user_id = self.auth_ref.user_id self.username = self.auth_ref.username self.user_domain_id = self.auth_ref.user_domain_id self.domain_id = self.auth_ref.domain_id self.domain_name = self.auth_ref.domain_name self.project_id = self.auth_ref.project_id self.project_name = self.auth_ref.project_name self.project_domain_id = self.auth_ref.project_domain_id auth_urls = self.auth_ref.service_catalog.get_urls( service_type='identity', endpoint_type='public', region_name=region_name) self.auth_url = auth_urls[0] management_urls = self.auth_ref.service_catalog.get_urls( service_type='identity', endpoint_type='admin', region_name=region_name) self._management_url = management_urls[0] self.auth_token_from_user = self.auth_ref.auth_token self.trust_id = self.auth_ref.trust_id if self.auth_ref.has_service_catalog() and not region_name: region_name = self.auth_ref.service_catalog.region_name else: self.auth_ref = None # allow override of the auth_ref defaults from explicit # values provided to the client # apply deprecated variables first, so modern variables override them if tenant_id: self.project_id = tenant_id if tenant_name: self.project_name = tenant_name # user-related attributes self.password = password if user_id: self.user_id = user_id if username: self.username = username if user_domain_id: self.user_domain_id = user_domain_id elif not (user_id or user_domain_name): self.user_domain_id = 'default' if user_domain_name: self.user_domain_name = user_domain_name # domain-related attributes if domain_id: self.domain_id = domain_id if domain_name: self.domain_name = domain_name # project-related attributes if project_id: self.project_id = project_id if project_name: self.project_name = project_name if project_domain_id: self.project_domain_id = project_domain_id elif not (project_id or project_domain_name): self.project_domain_id = 'default' if project_domain_name: self.project_domain_name = project_domain_name # trust-related attributes if trust_id: self.trust_id = trust_id # endpoint selection if auth_url: self.auth_url = auth_url.rstrip('/') if token: self.auth_token_from_user = token else: self.auth_token_from_user = None if endpoint: self._endpoint = endpoint.rstrip('/') self._auth_token = None if not session: kwargs['session'] = _FakeRequestSession() session = client_session.Session.construct(kwargs) session.auth = self super(HTTPClient, self).__init__(session=session) self.domain = '' self.debug_log = debug # NOTE(jamielennox): unfortunately we can't just use **kwargs here as # it would incompatibly limit the kwargs that can be passed to __init__ # try and keep this list in sync with adapter.Adapter.__init__ version = ( _discover.normalize_version_number(self.version) if self.version else None) self._adapter = _KeystoneAdapter(session, service_type='identity', service_name=service_name, interface=interface, region_name=region_name, endpoint_override=endpoint_override, version=version, auth=auth, user_agent=user_agent, connect_retries=connect_retries) # keyring setup if use_keyring and keyring is None: _logger.warning(_LW('Failed to load keyring modules.')) self.use_keyring = use_keyring and keyring is not None self.force_new_token = force_new_token self.stale_duration = stale_duration or access.STALE_TOKEN_DURATION self.stale_duration = int(self.stale_duration)
def _send_request(self, url, method, redirect, log, logger, connect_retries, connect_retry_delay=0.5, **kwargs): # NOTE(jamielennox): We handle redirection manually because the # requests lib follows some browser patterns where it will redirect # POSTs as GETs for certain statuses which is not want we want for an # API. See: https://en.wikipedia.org/wiki/Post/Redirect/Get # NOTE(jamielennox): The interaction between retries and redirects are # handled naively. We will attempt only a maximum number of retries and # redirects rather than per request limits. Otherwise the extreme case # could be redirects * retries requests. This will be sufficient in # most cases and can be fixed properly if there's ever a need. try: try: resp = self.session.request(method, url, **kwargs) except requests.exceptions.SSLError as e: msg = _('SSL exception connecting to %(url)s: ' '%(error)s') % {'url': url, 'error': e} raise exceptions.SSLError(msg) except requests.exceptions.Timeout: msg = _('Request to %s timed out') % url raise exceptions.RequestTimeout(msg) except requests.exceptions.ConnectionError: msg = _('Unable to establish connection to %s') % url raise exceptions.ConnectionRefused(msg) except (exceptions.RequestTimeout, exceptions.ConnectionRefused) as e: if connect_retries <= 0: raise logger.info(_LI('Failure: %(e)s. Retrying in %(delay).1fs.'), {'e': e, 'delay': connect_retry_delay}) time.sleep(connect_retry_delay) return self._send_request( url, method, redirect, log, logger, connect_retries=connect_retries - 1, connect_retry_delay=connect_retry_delay * 2, **kwargs) if log: self._http_log_response(resp, logger) if resp.status_code in self._REDIRECT_STATUSES: # be careful here in python True == 1 and False == 0 if isinstance(redirect, bool): redirect_allowed = redirect else: redirect -= 1 redirect_allowed = redirect >= 0 if not redirect_allowed: return resp try: location = resp.headers['location'] except KeyError: logger.warning(_LW("Failed to redirect request to %s as new " "location was not provided."), resp.url) else: # NOTE(jamielennox): We don't pass through connect_retry_delay. # This request actually worked so we can reset the delay count. new_resp = self._send_request( location, method, redirect, log, logger, connect_retries=connect_retries, **kwargs) if not isinstance(new_resp.history, list): new_resp.history = list(new_resp.history) new_resp.history.insert(0, resp) resp = new_resp return resp
def is_ans1_token(token): """Deprecated. Use is_asn1_token() instead.""" LOG.warning(_LW('The function is_ans1_token() is deprecated, ' 'use is_asn1_token() instead.')) return is_asn1_token(token)
def get_endpoint(self, session, service_type=None, interface=None, region_name=None, service_name=None, version=None, **kwargs): """Return a valid endpoint for a service. If a valid token is not present then a new one will be fetched using the session and kwargs. :param session: A session object that can be used for communication. :type session: keystoneclient.session.Session :param string service_type: The type of service to lookup the endpoint for. This plugin will return None (failure) if service_type is not provided. :param string interface: The exposure of the endpoint. Should be `public`, `internal`, `admin`, or `auth`. `auth` is special here to use the `auth_url` rather than a URL extracted from the service catalog. Defaults to `public`. :param string region_name: The region the endpoint should exist in. (optional) :param string service_name: The name of the service in the catalog. (optional) :param tuple version: The minimum version number required for this endpoint. (optional) :raises keystoneclient.exceptions.HttpError: An error from an invalid HTTP response. :return: A valid endpoint URL or None if not available. :rtype: string or None """ # NOTE(jamielennox): if you specifically ask for requests to be sent to # the auth url then we can ignore many of the checks. Typically if you # are asking for the auth endpoint it means that there is no catalog to # query however we still need to support asking for a specific version # of the auth_url for generic plugins. if interface is base.AUTH_INTERFACE: url = self.auth_url service_type = service_type or 'identity' else: if not service_type: LOG.warning(_LW( 'Plugin cannot return an endpoint without knowing the ' 'service type that is required. Add service_type to ' 'endpoint filtering data.')) return None if not interface: interface = 'public' service_catalog = self.get_access(session).service_catalog url = service_catalog.url_for(service_type=service_type, endpoint_type=interface, region_name=region_name, service_name=service_name) if not version: # NOTE(jamielennox): This may not be the best thing to default to # but is here for backwards compatibility. It may be worth # defaulting to the most recent version. return url # NOTE(jamielennox): For backwards compatibility people might have a # versioned endpoint in their catalog even though they want to use # other endpoint versions. So we support a list of client defined # situations where we can strip the version component from a URL before # doing discovery. hacked_url = _discover.get_catalog_discover_hack(service_type, url) try: disc = self.get_discovery(session, hacked_url, authenticated=False) except (exceptions.DiscoveryFailure, exceptions.HTTPError, exceptions.ConnectionError): # NOTE(jamielennox): Again if we can't contact the server we fall # back to just returning the URL from the catalog. This may not be # the best default but we need it for now. LOG.warning(_LW( 'Failed to contact the endpoint at %s for discovery. Fallback ' 'to using that endpoint as the base url.'), url) else: url = disc.url_for(version) return url
def __init__(self, username=None, tenant_id=None, tenant_name=None, password=None, auth_url=None, region_name=None, endpoint=None, token=None, debug=False, auth_ref=None, use_keyring=False, force_new_token=False, stale_duration=None, user_id=None, user_domain_id=None, user_domain_name=None, domain_id=None, domain_name=None, project_id=None, project_name=None, project_domain_id=None, project_domain_name=None, trust_id=None, session=None, **kwargs): """Construct a new http client :param string user_id: User ID for authentication. (optional) :param string username: Username for authentication. (optional) :param string user_domain_id: User's domain ID for authentication. (optional) :param string user_domain_name: User's domain name for authentication. (optional) :param string password: Password for authentication. (optional) :param string domain_id: Domain ID for domain scoping. (optional) :param string domain_name: Domain name for domain scoping. (optional) :param string project_id: Project ID for project scoping. (optional) :param string project_name: Project name for project scoping. (optional) :param string project_domain_id: Project's domain ID for project scoping. (optional) :param string project_domain_name: Project's domain name for project scoping. (optional) :param string auth_url: Identity service endpoint for authorization. :param string region_name: Name of a region to select when choosing an endpoint from the service catalog. :param integer timeout: DEPRECATED: use session. (optional) :param string endpoint: A user-supplied endpoint URL for the identity service. Lazy-authentication is possible for API service calls if endpoint is set at instantiation. (optional) :param string token: Token for authentication. (optional) :param string cacert: DEPRECATED: use session. (optional) :param string key: DEPRECATED: use session. (optional) :param string cert: DEPRECATED: use session. (optional) :param boolean insecure: DEPRECATED: use session. (optional) :param string original_ip: DEPRECATED: use session. (optional) :param boolean debug: DEPRECATED: use logging configuration. (optional) :param dict auth_ref: To allow for consumers of the client to manage their own caching strategy, you may initialize a client with a previously captured auth_reference (token). If there are keyword arguments passed that also exist in auth_ref, the value from the argument will take precedence. :param boolean use_keyring: Enables caching auth_ref into keyring. default: False (optional) :param boolean force_new_token: Keyring related parameter, forces request for new token. default: False (optional) :param integer stale_duration: Gap in seconds to determine if token from keyring is about to expire. default: 30 (optional) :param string tenant_name: Tenant name. (optional) The tenant_name keyword argument is deprecated, use project_name instead. :param string tenant_id: Tenant id. (optional) The tenant_id keyword argument is deprecated, use project_id instead. :param string trust_id: Trust ID for trust scoping. (optional) :param object session: A Session object to be used for communicating with the identity service. """ # set baseline defaults self.user_id = None self.username = None self.user_domain_id = None self.user_domain_name = None self.domain_id = None self.domain_name = None self.project_id = None self.project_name = None self.project_domain_id = None self.project_domain_name = None self.region_name = None self.auth_url = None self._endpoint = None self._management_url = None self.trust_id = None # if loading from a dictionary passed in via auth_ref, # load values from AccessInfo parsing that dictionary if auth_ref: self.auth_ref = access.AccessInfo.factory(**auth_ref) self.version = self.auth_ref.version self.user_id = self.auth_ref.user_id self.username = self.auth_ref.username self.user_domain_id = self.auth_ref.user_domain_id self.domain_id = self.auth_ref.domain_id self.domain_name = self.auth_ref.domain_name self.project_id = self.auth_ref.project_id self.project_name = self.auth_ref.project_name self.project_domain_id = self.auth_ref.project_domain_id self.auth_url = self.auth_ref.auth_url[0] self._management_url = self.auth_ref.management_url[0] self.auth_token_from_user = self.auth_ref.auth_token self.trust_id = self.auth_ref.trust_id if self.auth_ref.has_service_catalog(): self.region_name = self.auth_ref.service_catalog.region_name else: self.auth_ref = None # allow override of the auth_ref defaults from explicit # values provided to the client # apply deprecated variables first, so modern variables override them if tenant_id: self.project_id = tenant_id if tenant_name: self.project_name = tenant_name # user-related attributes self.password = password if user_id: self.user_id = user_id if username: self.username = username if user_domain_id: self.user_domain_id = user_domain_id elif not (user_id or user_domain_name): self.user_domain_id = 'default' if user_domain_name: self.user_domain_name = user_domain_name # domain-related attributes if domain_id: self.domain_id = domain_id if domain_name: self.domain_name = domain_name # project-related attributes if project_id: self.project_id = project_id if project_name: self.project_name = project_name if project_domain_id: self.project_domain_id = project_domain_id elif not (project_id or project_domain_name): self.project_domain_id = 'default' if project_domain_name: self.project_domain_name = project_domain_name # trust-related attributes if trust_id: self.trust_id = trust_id # endpoint selection if auth_url: self.auth_url = auth_url.rstrip('/') if token: self.auth_token_from_user = token else: self.auth_token_from_user = None if endpoint: self._endpoint = endpoint.rstrip('/') if region_name: self.region_name = region_name self._auth_token = None if not session: kwargs['session'] = _FakeRequestSession() session = client_session.Session.construct(kwargs) session.auth = self super(HTTPClient, self).__init__(session=session) self.domain = '' self.debug_log = debug # keyring setup if use_keyring and keyring is None: _logger.warning(_LW('Failed to load keyring modules.')) self.use_keyring = use_keyring and keyring is not None self.force_new_token = force_new_token self.stale_duration = stale_duration or access.STALE_TOKEN_DURATION self.stale_duration = int(self.stale_duration)
def get_endpoint(self, session, service_type=None, interface=None, region_name=None, service_name=None, version=None, **kwargs): """Return a valid endpoint for a service. If a valid token is not present then a new one will be fetched using the session and kwargs. :param session: A session object that can be used for communication. :type session: keystoneclient.session.Session :param string service_type: The type of service to lookup the endpoint for. This plugin will return None (failure) if service_type is not provided. :param string interface: The exposure of the endpoint. Should be `public`, `internal`, `admin`, or `auth`. `auth` is special here to use the `auth_url` rather than a URL extracted from the service catalog. Defaults to `public`. :param string region_name: The region the endpoint should exist in. (optional) :param string service_name: The name of the service in the catalog. (optional) :param tuple version: The minimum version number required for this endpoint. (optional) :raises keystoneclient.exceptions.HttpError: An error from an invalid HTTP response. :return: A valid endpoint URL or None if not available. :rtype: string or None """ # NOTE(jamielennox): if you specifically ask for requests to be sent to # the auth url then we can ignore the rest of the checks. Typically if # you are asking for the auth endpoint it means that there is no # catalog to query anyway. if interface is base.AUTH_INTERFACE: return self.auth_url if not service_type: LOG.warn(_LW('Plugin cannot return an endpoint without knowing ' 'the service type that is required. Add service_type ' 'to endpoint filtering data.')) return None if not interface: interface = 'public' service_catalog = self.get_access(session).service_catalog url = service_catalog.url_for(service_type=service_type, endpoint_type=interface, region_name=region_name, service_name=service_name) if not version: # NOTE(jamielennox): This may not be the best thing to default to # but is here for backwards compatibility. It may be worth # defaulting to the most recent version. return url # NOTE(jamielennox): For backwards compatibility people might have a # versioned endpoint in their catalog even though they want to use # other endpoint versions. So we support a list of client defined # situations where we can strip the version component from a URL before # doing discovery. hacked_url = _discover.get_catalog_discover_hack(service_type, url) try: disc = self.get_discovery(session, hacked_url, authenticated=False) except (exceptions.DiscoveryFailure, exceptions.HTTPError, exceptions.ConnectionError): # NOTE(jamielennox): Again if we can't contact the server we fall # back to just returning the URL from the catalog. This may not be # the best default but we need it for now. LOG.warn(_LW('Failed to contact the endpoint at %s for discovery. ' 'Fallback to using that endpoint as the base url.'), url) else: url = disc.url_for(version) return url
def _send_request(self, url, method, redirect, log, logger, connect_retries, connect_retry_delay=0.5, **kwargs): # NOTE(jamielennox): We handle redirection manually because the # requests lib follows some browser patterns where it will redirect # POSTs as GETs for certain statuses which is not want we want for an # API. See: https://en.wikipedia.org/wiki/Post/Redirect/Get # NOTE(jamielennox): The interaction between retries and redirects are # handled naively. We will attempt only a maximum number of retries and # redirects rather than per request limits. Otherwise the extreme case # could be redirects * retries requests. This will be sufficient in # most cases and can be fixed properly if there's ever a need. try: try: resp = self.session.request(method, url, **kwargs) except requests.exceptions.SSLError as e: msg = _('SSL exception connecting to %(url)s: ' '%(error)s') % { 'url': url, 'error': e } raise exceptions.SSLError(msg) except requests.exceptions.Timeout: msg = _('Request to %s timed out') % url raise exceptions.RequestTimeout(msg) except requests.exceptions.ConnectionError: msg = _('Unable to establish connection to %s') % url raise exceptions.ConnectionRefused(msg) except (exceptions.RequestTimeout, exceptions.ConnectionRefused) as e: if connect_retries <= 0: raise logger.info(_LI('Failure: %(e)s. Retrying in %(delay).1fs.'), { 'e': e, 'delay': connect_retry_delay }) time.sleep(connect_retry_delay) return self._send_request(url, method, redirect, log, logger, connect_retries=connect_retries - 1, connect_retry_delay=connect_retry_delay * 2, **kwargs) if log: self._http_log_response(resp, logger) if resp.status_code in self._REDIRECT_STATUSES: # be careful here in python True == 1 and False == 0 if isinstance(redirect, bool): redirect_allowed = redirect else: redirect -= 1 redirect_allowed = redirect >= 0 if not redirect_allowed: return resp try: location = resp.headers['location'] except KeyError: logger.warning( _LW("Failed to redirect request to %s as new " "location was not provided."), resp.url) else: # NOTE(jamielennox): We don't pass through connect_retry_delay. # This request actually worked so we can reset the delay count. new_resp = self._send_request(location, method, redirect, log, logger, connect_retries=connect_retries, **kwargs) if not isinstance(new_resp.history, list): new_resp.history = list(new_resp.history) new_resp.history.insert(0, resp) resp = new_resp return resp
def __init__(self, username=None, tenant_id=None, tenant_name=None, password=None, auth_url=None, region_name=None, endpoint=None, token=None, debug=False, auth_ref=None, use_keyring=False, force_new_token=False, stale_duration=None, user_id=None, user_domain_id=None, user_domain_name=None, domain_id=None, domain_name=None, project_id=None, project_name=None, project_domain_id=None, project_domain_name=None, trust_id=None, session=None, service_name=None, interface='admin', endpoint_override=None, auth=None, user_agent=USER_AGENT, connect_retries=None, **kwargs): # set baseline defaults self.user_id = None self.username = None self.user_domain_id = None self.user_domain_name = None self.domain_id = None self.domain_name = None self.project_id = None self.project_name = None self.project_domain_id = None self.project_domain_name = None self.auth_url = None self._endpoint = None self._management_url = None self.trust_id = None # if loading from a dictionary passed in via auth_ref, # load values from AccessInfo parsing that dictionary if auth_ref: self.auth_ref = access.AccessInfo.factory(**auth_ref) self.version = self.auth_ref.version self.user_id = self.auth_ref.user_id self.username = self.auth_ref.username self.user_domain_id = self.auth_ref.user_domain_id self.domain_id = self.auth_ref.domain_id self.domain_name = self.auth_ref.domain_name self.project_id = self.auth_ref.project_id self.project_name = self.auth_ref.project_name self.project_domain_id = self.auth_ref.project_domain_id self.auth_url = self.auth_ref.auth_url[0] self._management_url = self.auth_ref.management_url[0] self.auth_token_from_user = self.auth_ref.auth_token self.trust_id = self.auth_ref.trust_id if self.auth_ref.has_service_catalog() and not region_name: region_name = self.auth_ref.service_catalog.region_name else: self.auth_ref = None # allow override of the auth_ref defaults from explicit # values provided to the client # apply deprecated variables first, so modern variables override them if tenant_id: self.project_id = tenant_id if tenant_name: self.project_name = tenant_name # user-related attributes self.password = password if user_id: self.user_id = user_id if username: self.username = username if user_domain_id: self.user_domain_id = user_domain_id elif not (user_id or user_domain_name): self.user_domain_id = 'default' if user_domain_name: self.user_domain_name = user_domain_name # domain-related attributes if domain_id: self.domain_id = domain_id if domain_name: self.domain_name = domain_name # project-related attributes if project_id: self.project_id = project_id if project_name: self.project_name = project_name if project_domain_id: self.project_domain_id = project_domain_id elif not (project_id or project_domain_name): self.project_domain_id = 'default' if project_domain_name: self.project_domain_name = project_domain_name # trust-related attributes if trust_id: self.trust_id = trust_id # endpoint selection if auth_url: self.auth_url = auth_url.rstrip('/') if token: self.auth_token_from_user = token else: self.auth_token_from_user = None if endpoint: self._endpoint = endpoint.rstrip('/') self._auth_token = None if not session: kwargs['session'] = _FakeRequestSession() session = client_session.Session.construct(kwargs) session.auth = self super(HTTPClient, self).__init__(session=session) self.domain = '' self.debug_log = debug # NOTE(jamielennox): unfortunately we can't just use **kwargs here as # it would incompatibly limit the kwargs that can be passed to __init__ # try and keep this list in sync with adapter.Adapter.__init__ self._adapter = _KeystoneAdapter(session, service_type='identity', service_name=service_name, interface=interface, region_name=region_name, endpoint_override=endpoint_override, version=self.version, auth=auth, user_agent=user_agent, connect_retries=connect_retries) # keyring setup if use_keyring and keyring is None: _logger.warning(_LW('Failed to load keyring modules.')) self.use_keyring = use_keyring and keyring is not None self.force_new_token = force_new_token self.stale_duration = stale_duration or access.STALE_TOKEN_DURATION self.stale_duration = int(self.stale_duration)