From c18960368eeae785a70124b74874ff6e80f0003c Mon Sep 17 00:00:00 2001 From: Phillip Berndt Date: Mon, 15 May 2023 17:08:49 +0200 Subject: [PATCH] Add tests for signature/Host header mismatch See #65 and #34. This adds a failing test that would be fixed by 8e1417. --- .../test/test_requests_aws4auth.py | 42 +++++++++++++------ 1 file changed, 30 insertions(+), 12 deletions(-) diff --git a/requests_aws4auth/test/test_requests_aws4auth.py b/requests_aws4auth/test/test_requests_aws4auth.py index dd25dc2..ebedad9 100644 --- a/requests_aws4auth/test/test_requests_aws4auth.py +++ b/requests_aws4auth/test/test_requests_aws4auth.py @@ -942,14 +942,16 @@ def test_duplicate_headers(self): self.assertEqual(cano_headers, cano_expected) self.assertEqual(signed_headers, signed_expected) - def test_netloc_port(self): + def test_netloc_port_is_stripped_for_standard_port(self): """ - Test that change in d190dcb doesn't regress - strip port from netloc - before generating signature when Host header is not already present in - request. + Test that change in d190dcb doesn't regress: When urllib3 is used, + the Host header is not part of the prepared request, but generated later, + and the port is stripped from that header if it is the standard HTTPS port. + This verifies that if the URL explicitly contains the port the library + still generates a signature with the correct Host header. """ - req = requests.Request('GET', 'http://amazonaws.com:8443') + req = requests.Request('GET', 'https://amazonaws.com:443') preq = req.prepare() self.assertNotIn('host', preq.headers) result = AWS4Auth.get_canonical_headers(preq, include=['host']) @@ -957,23 +959,39 @@ def test_netloc_port(self): expected = 'host:amazonaws.com\n' self.assertEqual(cano_hdrs, expected) - def test_netloc_port_using_httpx(self): + def test_netloc_port_is_kept_for_non_standard_port(self): """ - Test that change in d190dcb doesn't regress - strip port from netloc - before generating signature when Host header is not already present in - request. + When urllib3 is used, the Host header is not part of the prepared request, + but generated later, and the port is kept in the header if it is not the + standard HTTPS port. d190dcb has a bug that also strips non-standard ports + from the signature, causing signature and host header to mismatch. This is + a regression test for that bug. """ - req = httpx.Request('GET', 'http://amazonaws.com:8443') + req = requests.Request('GET', 'https://amazonaws.com:8443') + preq = req.prepare() + self.assertNotIn('host', preq.headers) + result = AWS4Auth.get_canonical_headers(preq, include=['host']) + cano_hdrs, signed_hdrs = result + expected = 'host:amazonaws.com:8443\n' + self.assertEqual(cano_hdrs, expected) + + def test_netloc_port_is_kept_for_standard_port_using_httpx(self): + """ + httpx is not affected by the issue d190dcb tries to fix, since it includes + the Host header in the prepared request. This test verifies that the + correct signature is generated. + + """ + req = httpx.Request('GET', 'http://amazonaws.com:443') req._prepare({}) self.assertIn('host', req.headers) result = AWS4Auth.get_canonical_headers(req, include=['host']) cano_hdrs, signed_hdrs = result - expected = 'host:amazonaws.com:8443\n' + expected = 'host:amazonaws.com:443\n' self.assertEqual(cano_hdrs, expected) - class AWS4Auth_GetCanonicalRequest_Test(unittest.TestCase): def test_amz1(self):