Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
59 changes: 46 additions & 13 deletions otter/auth.py
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,8 @@
wrap_upstream_error,
)
from otter.util.retry import repeating_interval, retry, retry_times

from twisted.logger import Logger
LOG = Logger()

class _DoNothingLogger(BoundLog):
"""This class implements a do-nothing logger for the benefit of
Expand Down Expand Up @@ -261,11 +262,44 @@ def authenticate_tenant(self, tenant_id, log=None):
see :meth:`IAuthenticator.authenticate_tenant`
"""
auth = partial(self._auth_me, log=log)

d = user_for_tenant(self._admin_url,
self._identity_admin_user,
self._identity_admin_password,
tenant_id, log=log)
# request = {
# "auth": {
# "passwordCredentials": {
# "username": self._identity_admin_user,
# "password": self._identity_admin_password
# }
# }
# }
# if tenant_id:
# request['auth']['tenantId'] = tenant_id
token = ''
def set_token(token_val):
global token
token = token_val
# d = treq.post(
# append_segments(self._admin_url, 'tokens'),
# json.dumps(request),
# headers=headers(),
# log=log,
# pool=None
# )
# d.addCallback(check_success, [200, 203])
# d.addErrback(
# wrap_upstream_error, 'identity',
# ('authenticating', self._identity_admin_user), self._admin_url
# )
# d.addCallback(treq.json_content)
# d.addCallback(extract_token)
d = authenticate_user(self._url,
self._identity_admin_user,
self._identity_admin_password,
log=log)
d.addCallback(extract_token)
d.addCallback(set_token)
LOG.debug("RAHU3180: Token is : %(token)s"%{'token': token})
d.addCallback(lambda ignore: user_for_tenant(self._admin_url,
token,
log=log))

def impersonate(user):
iud = impersonate_user(self._admin_url,
Expand Down Expand Up @@ -371,7 +405,7 @@ def endpoints_for_token(auth_endpoint, identity_admin_token, user_token,
return d


def user_for_tenant(auth_endpoint, username, password, tenant_id, log=None):
def user_for_tenant(auth_endpoint, token, log=None):
"""
Use a super secret API to get the special actual username for a tenant id.

Expand All @@ -383,17 +417,16 @@ def user_for_tenant(auth_endpoint, username, password, tenant_id, log=None):
:return: Username of the magical identity:user-admin user for the tenantid.
"""
d = treq.get(
append_segments(auth_endpoint.replace('v2.0', 'v1.1'), 'mosso', str(tenant_id)),
auth=(username, password),
append_segments(auth_endpoint, 'users'),
headers=headers(token),
allow_redirects=False,
log=log)
d.addCallback(check_success, [301])
d.addErrback(wrap_upstream_error, 'identity', 'mosso', auth_endpoint)
d.addCallback(check_success, [200, 203])
d.addErrback(wrap_upstream_error, 'identity', 'users', auth_endpoint)
d.addCallback(treq.json_content)
d.addCallback(lambda user: user['user']['id'])
d.addCallback(lambda user: user['users'][0]['username'])
return d


def authenticate_user(auth_endpoint, username, password, tenant_id=None,
log=None, pool=None):
"""
Expand Down
5 changes: 5 additions & 0 deletions otter/integration/lib/autoscale.py
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,8 @@
repeating_interval,
terminal_errors_except
)
from twisted.logger import Logger
LOG = Logger()

pp = pprint.PrettyPrinter(indent=4)
verbosity = int(os.environ.get('AS_VERBOSITY', 0))
Expand Down Expand Up @@ -534,7 +536,9 @@ def wait_for_state(self, rcs, matcher, timeout=600, period=10, clock=None):
"""
def check(result):
response, group_state = result
LOG.debug("RAHU0808: mismatch result: %(result)s"%{'result': result})
mismatch = matcher.match(group_state['group'])

if mismatch:
msg("Waiting for group {} to reach desired group state.\n"
"Mismatch: {}"
Expand All @@ -545,6 +549,7 @@ def check(result):
return rcs

def poll():
# LOG.debug("RAHU8080: polling get_scaling_group: %(get_sg)s"%{'get_sg': self.get_scaling_group_state(rcs, [200])})
return self.get_scaling_group_state(rcs, [200]).addCallback(check)

return retry_and_timeout(
Expand Down
9 changes: 6 additions & 3 deletions otter/integration/tests/test_convergence.py
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,8 @@
tag
)
from otter.integration.lib.utils import diagnose

from twisted.logger import Logger
LOG = Logger()

# if this is None, the test will be skipped
convergence_tenant_auth_errors = os.environ.get(
Expand Down Expand Up @@ -689,7 +690,7 @@ def test_servers_that_build_for_too_long_time_out_and_are_replaced(self):
{"name": "default"}
])
yield group.start(self.rcs, self)

LOG.debug("RAHU1991 FAIL: self.rcs.token: %(token)s self.rcs.tenant: %(tenant)s"%{'rcs1':self.rcs, 'token':self.rcs.token, 'tenant':self.rcs.tenant})
initial_servers = yield wait_for_servers(
self.rcs, pool=self.helper.pool, group=group,
timeout=otter_build_timeout,
Expand Down Expand Up @@ -985,7 +986,8 @@ def test_recover_from_identity_auth_failures(self):
resources=get_resource_mapping(),
region=region
)

LOG.debug("RAHU3180: PASS identitity: %(identity)s rcs.token: %(token)s rcs.tenant:%(tenant)s"%{'rcs': rcs, 'identity': identity, 'token':rcs.token, 'tenant':rcs.tenant})
LOG.debug("RAHU3180 PASS: self.rcs.token: %(token)s self.rcs.tenant: %(tenant)s"%{'rcs1':self.rcs, 'token':self.rcs.token, 'tenant':self.rcs.tenant})
# inject behavior errors for this user, so that when otter
# impersonates, it gets failures
mimic_identity = MimicIdentity(pool=self.helper.pool, test_case=self,
Expand All @@ -1007,6 +1009,7 @@ def test_recover_from_identity_auth_failures(self):
min_entities=2,
max_entities=10)
yield self.helper.start_group_and_wait(group, rcs, desired=5)
LOG.debug("RAHU3180: PASS group created: %(group)s"%{'group':group})

@inlineCallbacks
def test_error_reasons_are_updated(self):
Expand Down
34 changes: 17 additions & 17 deletions otter/test/test_auth.py
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@
)
from otter.effect_dispatcher import get_simple_dispatcher
from otter.test.utils import SameJSON, iMock, mock_log, patch
from otter.util.http import APIError, UpstreamError
from otter.util.http import APIError, UpstreamError, headers


expected_headers = {'accept': ['application/json'],
Expand Down Expand Up @@ -299,18 +299,18 @@ def test_user_for_tenant(self):
the list of users for a given tenant.
"""
response = mock.Mock(code=200)
response_body = {'user': {'id': 'ausername'}}
response_body = {'users': [{'username': 'username'}]}
self.treq.json_content.return_value = succeed(response_body)
self.treq.get.return_value = succeed(response)

d = user_for_tenant('http://identity/v2.0', 'username', 'password',
111111, log=self.log)
d = user_for_tenant('http://identity/v2.0', 'auth-token',
log=self.log)

self.assertEqual(self.successResultOf(d), 'ausername')
self.assertEqual(self.successResultOf(d), 'username')

self.treq.get.assert_called_once_with(
'http://identity/v1.1/mosso/111111',
auth=('username', 'password'),
'http://identity/v2.0/users',
headers=headers('auth-token'),
allow_redirects=False, log=self.log)

def test_user_for_tenant_propagates_errors(self):
Expand All @@ -321,8 +321,7 @@ def test_user_for_tenant_propagates_errors(self):
self.treq.content.return_value = succeed('error_body')
self.treq.get.return_value = succeed(response)

d = user_for_tenant('http://identity/v2.0', 'username', 'password',
111111)
d = user_for_tenant('http://identity/v2.0', 'username', 'auth-token')
failure = self.failureResultOf(d)

self.assertTrue(failure.check(UpstreamError))
Expand Down Expand Up @@ -508,16 +507,16 @@ def test_authenticate_tenant_gets_user_for_specified_tenant(self):
endpoint.
"""
self.successResultOf(self.ia.authenticate_tenant(111111))
self.user_for_tenant.assert_called_once_with(self.admin_url, self.user,
self.password, 111111,
self.user_for_tenant.assert_called_once_with(self.admin_url,
'',
log=None)

self.user_for_tenant.reset_mock()

self.successResultOf(self.ia.authenticate_tenant(111111, log=self.log))

self.user_for_tenant.assert_called_once_with(self.admin_url, self.user,
self.password, 111111,
self.user_for_tenant.assert_called_once_with(self.admin_url,
'',
log=self.log)

def test_authenticate_tenant_impersonates_first_user(self):
Expand Down Expand Up @@ -550,10 +549,10 @@ def test_authenticate_tenant_retries_impersonates_first_user(self):
self.impersonate_user.assert_has_calls(
[mock.call(self.admin_url, None, 'test_user', log=self.log),
mock.call(self.admin_url, 'auth-token', 'test_user', log=self.log)])
self.authenticate_user.assert_called_once_with(self.url, self.user,
self.authenticate_user.assert_called_with(self.url, self.user,
self.password,
log=self.log)
self.log.msg.assert_called_once_with('Getting new identity admin token')
self.log.msg.assert_called_with('Getting new identity admin token')

def test_authenticate_tenant_gets_endpoints_for_the_impersonation_token(self):
"""
Expand All @@ -577,10 +576,10 @@ def test_authenticate_tenant_retries_getting_endpoints_for_the_impersonation_tok
self.endpoints_for_token.assert_has_calls(
[mock.call(self.admin_url, None, 'impersonation_token', log=self.log),
mock.call(self.admin_url, 'auth-token', 'impersonation_token', log=self.log)])
self.authenticate_user.assert_called_once_with(self.url, self.user,
self.authenticate_user.assert_called_with(self.url, self.user,
self.password,
log=self.log)
self.log.msg.assert_called_once_with('Getting new identity admin token')
self.log.msg.assert_called_with('Getting new identity admin token')

def test_authenticate_tenant_returns_impersonation_token_and_endpoint_list(self):
"""
Expand Down Expand Up @@ -988,3 +987,4 @@ def test_cache_ttl_defaults(self):
r = mock.Mock()
a = generate_authenticator(r, self.config)
self.assertEqual(a._ttl, 300)

4 changes: 3 additions & 1 deletion otter/util/http.py
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,8 @@

from otter.log.formatters import serialize_to_jsonable
from otter.util.config import config_value

from twisted.logger import Logger
LOG = Logger()

class RequestError(Exception):
"""
Expand Down Expand Up @@ -218,6 +219,7 @@ def check_success(response, success_codes, _treq=None):

:return: response or a deferred that errbacks with an APIError.
"""
LOG.debug("RAHU1618: response of call is ResponseCode: %(resp_code)s Response-Header: %(header)s Methode: %(meth)s url: %(url)s "%{'resp_code': response.code, 'header': response.headers, 'meth':response.request.method, 'url': response.request.absoluteURI})
if _treq is None:
_treq = treq

Expand Down
3 changes: 2 additions & 1 deletion requirements/mimic.txt
Original file line number Diff line number Diff line change
@@ -1 +1,2 @@
git+https://github.com/rackerlabs/mimic.git@594dd5c8e80b670fa2d0c42f5eec9645e14aa54e
#git+https://github.com/rackerlabs/mimic.git@594dd5c8e80b670fa2d0c42f5eec9645e14aa54e
git+ssh://github.com/rackerlabs/autoscale-mimic.git@autoscale-546