From a56ce5817f814531151b2c4bc6da78f4c2b0ed02 Mon Sep 17 00:00:00 2001 From: Julien Danjou Date: Thu, 24 Jan 2013 17:46:29 +0100 Subject: [PATCH] Use AuthRef for some client fields This tackles some TODO items left over. Change-Id: Ib062744acbf56f05d09857d244b78b35c0ef4d39 Signed-off-by: Julien Danjou --- keystoneclient/access.py | 10 +++++++++- keystoneclient/client.py | 9 +++++++++ keystoneclient/v2_0/client.py | 30 +++++++++--------------------- tests/fakes.py | 4 ++-- 4 files changed, 29 insertions(+), 24 deletions(-) diff --git a/keystoneclient/access.py b/keystoneclient/access.py index 1dc86705a..346315f98 100644 --- a/keystoneclient/access.py +++ b/keystoneclient/access.py @@ -18,7 +18,7 @@ import datetime from keystoneclient.openstack.common import timeutils - +from keystoneclient import service_catalog # gap, in seconds, to determine whether the given token is about to expire STALE_TOKEN_DURATION = 30 @@ -28,6 +28,14 @@ class AccessInfo(dict): """An object for encapsulating a raw authentication token from keystone and helper methods for extracting useful values from that token.""" + def __init__(self, *args, **kwargs): + super(AccessInfo, self).__init__(*args, **kwargs) + self.service_catalog = service_catalog.ServiceCatalog( + resource_dict=self, region_name=self.get('region_name')) + + def has_service_catalog(self): + return 'serviceCatalog' in self + def will_expire_soon(self, stale_duration=None): """ Determines if expiration is about to occur. diff --git a/keystoneclient/client.py b/keystoneclient/client.py index 5b2f1253a..ae91f898c 100644 --- a/keystoneclient/client.py +++ b/keystoneclient/client.py @@ -328,6 +328,15 @@ class HTTPClient(object): def serialize(self, entity): return json.dumps(entity) + @property + def service_catalog(self): + """Returns this client's service catalog.""" + return self.auth_ref.service_catalog + + def has_service_catalog(self): + """Returns True if this client provides a service catalog.""" + return self.auth_ref.has_service_catalog() + def request(self, url, method, **kwargs): """ Send an http request with the specified characteristics. diff --git a/keystoneclient/v2_0/client.py b/keystoneclient/v2_0/client.py index 788bfa7c3..9f7553f74 100644 --- a/keystoneclient/v2_0/client.py +++ b/keystoneclient/v2_0/client.py @@ -16,7 +16,6 @@ import logging from keystoneclient import client from keystoneclient import exceptions -from keystoneclient import service_catalog from keystoneclient.v2_0 import ec2 from keystoneclient.v2_0 import endpoints from keystoneclient.v2_0 import roles @@ -133,11 +132,6 @@ class Client(client.HTTPClient): if self.management_url is None: self.authenticate() - #TODO(heckj): move to a method on auth_ref - def has_service_catalog(self): - """Returns True if this client provides a service catalog.""" - return hasattr(self, 'service_catalog') - def process_token(self): """ Extract and process information from the new auth_ref. @@ -147,12 +141,20 @@ class Client(client.HTTPClient): # list of tenants for introspection, and leave to client user # to determine what to do. Otherwise, load up the service catalog if self.auth_ref.scoped: + if not self.auth_ref.tenant_id: + raise exceptions.AuthorizationFailure( + "Token didn't provide tenant_id") + if not self.auth_ref.user_id: + raise exceptions.AuthorizationFailure( + "Token didn't provide user_id") if self.management_url is None and self.auth_ref.management_url: self.management_url = self.auth_ref.management_url[0] self.tenant_name = self.auth_ref.tenant_name self.tenant_id = self.auth_ref.tenant_id self.user_id = self.auth_ref.user_id - self._extract_service_catalog(self.auth_url, self.auth_ref) + + self.auth_user_id = self.auth_ref.user_id + self.auth_tenant_id = self.auth_ref.tenant_id def get_raw_token_from_identity_service(self, auth_url, username=None, password=None, tenant_name=None, @@ -201,17 +203,3 @@ class Client(client.HTTPClient): params['auth']['tenantName'] = tenant_name resp, body = self.request(url, 'POST', body=params, headers=headers) return body['access'] - - # TODO(heckj): remove entirely in favor of access.AccessInfo and - # associated methods - def _extract_service_catalog(self, url, body): - """ Set the client's service catalog from the response data. """ - self.service_catalog = service_catalog.ServiceCatalog( - body, region_name=self.region_name) - try: - sc = self.service_catalog.get_token() - # Save these since we have them and they'll be useful later - self.auth_tenant_id = sc.get('tenant_id') - self.auth_user_id = sc.get('user_id') - except KeyError: - raise exceptions.AuthorizationFailure() diff --git a/tests/fakes.py b/tests/fakes.py index ab41aa206..feafd5238 100644 --- a/tests/fakes.py +++ b/tests/fakes.py @@ -6,7 +6,7 @@ wrong the tests might raise AssertionError. I've indicated in comments the places where actual behavior differs from the spec. """ -from keystoneclient import service_catalog +from keystoneclient import access def assert_has_keys(dict, required=[], optional=[]): @@ -67,7 +67,7 @@ class FakeClient(object): cl_obj.auth_user_id = '1' cl_obj.tenant_id = '1' cl_obj.auth_tenant_id = '1' - cl_obj.service_catalog = service_catalog.ServiceCatalog({ + cl_obj.auth_ref = access.AccessInfo({ "token": { "expires": "2012-02-05T00:00:00", "id": "887665443383838",