From 125238612f58481316db68d7087252bb7729f447 Mon Sep 17 00:00:00 2001 From: Janie Richling Date: Sat, 4 Jul 2015 17:08:32 -0500 Subject: [PATCH] Add CORS unit tests to base In earlier versions of swift when a request was made with an existing origin, but without any CORS settings in the container, it was possible to get an unhandled exception due to a method call on the "None" return of cors.get('allow_origin', ''). Unit tests have been added to assert that this problem cannot go undetected again. Change-Id: Ia74896dabe1cf5a307c551b15a43ab1fd789c213 Fixes: bug 1468782 --- swift/proxy/controllers/base.py | 3 ++- test/unit/proxy/controllers/test_base.py | 33 +++++++++++++++++++++++- 2 files changed, 34 insertions(+), 2 deletions(-) diff --git a/swift/proxy/controllers/base.py b/swift/proxy/controllers/base.py index 953a85af58..89f3e8e4f2 100644 --- a/swift/proxy/controllers/base.py +++ b/swift/proxy/controllers/base.py @@ -1617,7 +1617,8 @@ class Controller(object): list_from_csv(req.headers['Access-Control-Request-Headers'])) # Populate the response with the CORS preflight headers - if cors.get('allow_origin', '').strip() == '*': + if cors.get('allow_origin') and \ + cors.get('allow_origin').strip() == '*': headers['access-control-allow-origin'] = '*' else: headers['access-control-allow-origin'] = req_origin_value diff --git a/test/unit/proxy/controllers/test_base.py b/test/unit/proxy/controllers/test_base.py index 30c213e0b4..8df8b37bf2 100644 --- a/test/unit/proxy/controllers/test_base.py +++ b/test/unit/proxy/controllers/test_base.py @@ -128,7 +128,7 @@ class FakeApp(object): reason = RESPONSE_REASONS[response.status_int][0] start_response('%d %s' % (response.status_int, reason), [(k, v) for k, v in response.headers.items()]) - # It's a bit strnage, but the get_info cache stuff relies on the + # It's a bit strange, but the get_info cache stuff relies on the # app setting some keys in the environment as it makes requests # (in particular GETorHEAD_base) - so our fake does the same _set_info_cache(self, environ, response.account, @@ -436,6 +436,37 @@ class TestFuncs(unittest.TestCase): self.assertEquals(resp['length'], 5555) self.assertEquals(resp['type'], 'text/plain') + def test_options(self): + base = Controller(self.app) + base.account_name = 'a' + base.container_name = 'c' + origin = 'http://m.com' + self.app.cors_allow_origin = [origin] + req = Request.blank('/v1/a/c/o', + environ={'swift.cache': FakeCache()}, + headers={'Origin': origin, + 'Access-Control-Request-Method': 'GET'}) + + with patch('swift.proxy.controllers.base.' + 'http_connect', fake_http_connect(200)): + resp = base.OPTIONS(req) + self.assertEqual(resp.status_int, 200) + + def test_options_unauthorized(self): + base = Controller(self.app) + base.account_name = 'a' + base.container_name = 'c' + self.app.cors_allow_origin = ['http://NOT_IT'] + req = Request.blank('/v1/a/c/o', + environ={'swift.cache': FakeCache()}, + headers={'Origin': 'http://m.com', + 'Access-Control-Request-Method': 'GET'}) + + with patch('swift.proxy.controllers.base.' + 'http_connect', fake_http_connect(200)): + resp = base.OPTIONS(req) + self.assertEqual(resp.status_int, 401) + def test_headers_to_container_info_missing(self): resp = headers_to_container_info({}, 404) self.assertEquals(resp['status'], 404)