From 7d7b9564ba32ded721f67002b712e6d3cafa8511 Mon Sep 17 00:00:00 2001 From: Lance Bragstad Date: Fri, 1 May 2020 01:02:12 +0000 Subject: [PATCH] Inject /v3 in token path for v3 plugins Without this, it's possible to get HTTP 404 errors from keystone if OS_AUTH_URL isn't versioned (e.g., https://keystone.example.com/ instead of https://keystone.example.com/v3), even if OS_IDENTITY_API is set to 3. This commit works around this issue by checking the AUTH_URL before building the token_url and appending '/v3' to the URL before sending the request. Closes-Bug: 1876317 Change-Id: Ic75f0c9b36022b884105b87bfe05f4f8292d53b2 (cherry picked from commit ad46262148e7b099e6c7239887e20ade5b8e6ac8) (cherry picked from commit 3ba2a3acf2a897de046873f3585463638e3567f6) --- keystoneauth1/identity/v3/base.py | 6 ++++- .../tests/unit/identity/test_identity_v3.py | 24 +++++++++++++++++++ .../notes/bug-1876317-1db97d1b12a3e4b4.yaml | 6 +++++ 3 files changed, 35 insertions(+), 1 deletion(-) create mode 100644 releasenotes/notes/bug-1876317-1db97d1b12a3e4b4.yaml diff --git a/keystoneauth1/identity/v3/base.py b/keystoneauth1/identity/v3/base.py index 20a86db7..bcd64412 100644 --- a/keystoneauth1/identity/v3/base.py +++ b/keystoneauth1/identity/v3/base.py @@ -173,9 +173,13 @@ class Auth(BaseAuth): if self.system_scope == 'all': body['auth']['scope'] = {'system': {'all': True}} + token_url = self.token_url + + if not self.auth_url.rstrip('/').endswith('v3'): + token_url = '%s/v3/auth/tokens' % self.auth_url.rstrip('/') + # NOTE(jamielennox): we add nocatalog here rather than in token_url # directly as some federation plugins require the base token_url - token_url = self.token_url if not self.include_catalog: token_url += '?nocatalog' diff --git a/keystoneauth1/tests/unit/identity/test_identity_v3.py b/keystoneauth1/tests/unit/identity/test_identity_v3.py index d928d4d0..be3d11dd 100644 --- a/keystoneauth1/tests/unit/identity/test_identity_v3.py +++ b/keystoneauth1/tests/unit/identity/test_identity_v3.py @@ -798,3 +798,27 @@ class V3IdentityPlugin(utils.TestCase): self.assertRequestHeaderEqual("Content-Type", "application/json") self.assertRequestHeaderEqual("Accept", "application/json") self.assertEqual(s.auth.auth_ref.auth_token, self.TEST_TOKEN) + + def test_authenticate_with_unversioned_endpoint(self): + self.stub_auth(json=self.TEST_RESPONSE_DICT) + # We use the root url here because it doesn't reference the API version + # (e.g., '/v3'). We want to make sure the authentication plugin handles + # this and appends /v3 if it's not present. + a = v3.Password(self.TEST_ROOT_URL, + username=self.TEST_USER, + password=self.TEST_PASS) + self.assertFalse(a.has_scope_parameters) + s = session.Session(auth=a) + + self.assertEqual({'X-Auth-Token': self.TEST_TOKEN}, + s.get_auth_headers()) + + req = {'auth': {'identity': + {'methods': ['password'], + 'password': {'user': {'name': self.TEST_USER, + 'password': self.TEST_PASS}}}}} + + self.assertRequestBodyIs(json=req) + self.assertRequestHeaderEqual('Content-Type', 'application/json') + self.assertRequestHeaderEqual('Accept', 'application/json') + self.assertEqual(s.auth.auth_ref.auth_token, self.TEST_TOKEN) diff --git a/releasenotes/notes/bug-1876317-1db97d1b12a3e4b4.yaml b/releasenotes/notes/bug-1876317-1db97d1b12a3e4b4.yaml new file mode 100644 index 00000000..4e33fb21 --- /dev/null +++ b/releasenotes/notes/bug-1876317-1db97d1b12a3e4b4.yaml @@ -0,0 +1,6 @@ +--- +fixes: + - | + [`bug 1876317 `_] + The v3 authentication plugins now attempt to add /v3 to the token path if + it's not present on the authentication URL.