summaryrefslogtreecommitdiffstats
path: root/test/unit/proxy/controllers
diff options
context:
space:
mode:
authorPeter Portante <peter.portante@redhat.com>2013-10-24 16:15:25 -0400
committerLuis Pabon <lpabon@redhat.com>2013-10-28 11:51:51 -0700
commit286a1308db72c5cfdd6ce16aff3f291ebce257c2 (patch)
treeaabb3c54a29d6236f5ade0a229c477378a6c832c /test/unit/proxy/controllers
parent6b8d7c59195327484ac0f14bd1c29e4f75415e3b (diff)
Rebase to OpenStack Swift Havana (1.10.0)
Change-Id: I90821230a1a7100c74d97cccc9c445251d0f65e7 Signed-off-by: Peter Portante <peter.portante@redhat.com> Reviewed-on: http://review.gluster.org/6157 Reviewed-by: Luis Pabon <lpabon@redhat.com> Tested-by: Luis Pabon <lpabon@redhat.com>
Diffstat (limited to 'test/unit/proxy/controllers')
-rw-r--r--test/unit/proxy/controllers/test_account.py24
-rw-r--r--test/unit/proxy/controllers/test_base.py160
-rw-r--r--test/unit/proxy/controllers/test_container.py24
-rwxr-xr-xtest/unit/proxy/controllers/test_obj.py64
4 files changed, 239 insertions, 33 deletions
diff --git a/test/unit/proxy/controllers/test_account.py b/test/unit/proxy/controllers/test_account.py
index 4d67d65..394ada7 100644
--- a/test/unit/proxy/controllers/test_account.py
+++ b/test/unit/proxy/controllers/test_account.py
@@ -1,4 +1,4 @@
-# Copyright (c) 2010-2012 OpenStack, LLC.
+# Copyright (c) 2010-2012 OpenStack Foundation
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
@@ -40,6 +40,28 @@ class TestAccountController(unittest.TestCase):
self.assertEqual(headers_to_account_info(resp.headers),
resp.environ['swift.account/AUTH_bob'])
+ def test_swift_owner(self):
+ owner_headers = {
+ 'x-account-meta-temp-url-key': 'value',
+ 'x-account-meta-temp-url-key-2': 'value'}
+ controller = proxy_server.AccountController(self.app, 'a')
+
+ req = Request.blank('/a')
+ with mock.patch('swift.proxy.controllers.base.http_connect',
+ fake_http_connect(200, 200, headers=owner_headers)):
+ resp = controller.HEAD(req)
+ self.assertEquals(2, resp.status_int // 100)
+ for key in owner_headers:
+ self.assertTrue(key not in resp.headers)
+
+ req = Request.blank('/a', environ={'swift_owner': True})
+ with mock.patch('swift.proxy.controllers.base.http_connect',
+ fake_http_connect(200, 200, headers=owner_headers)):
+ resp = controller.HEAD(req)
+ self.assertEquals(2, resp.status_int // 100)
+ for key in owner_headers:
+ self.assertTrue(key in resp.headers)
+
if __name__ == '__main__':
unittest.main()
diff --git a/test/unit/proxy/controllers/test_base.py b/test/unit/proxy/controllers/test_base.py
index 02692eb..8214b98 100644
--- a/test/unit/proxy/controllers/test_base.py
+++ b/test/unit/proxy/controllers/test_base.py
@@ -1,4 +1,4 @@
-# Copyright (c) 2010-2012 OpenStack, LLC.
+# Copyright (c) 2010-2012 OpenStack Foundation
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
@@ -16,9 +16,9 @@
import unittest
from mock import patch
from swift.proxy.controllers.base import headers_to_container_info, \
- headers_to_account_info, get_container_info, get_container_memcache_key, \
- get_account_info, get_account_memcache_key, _get_cache_key, get_info, \
- Controller
+ headers_to_account_info, headers_to_object_info, get_container_info, \
+ get_container_memcache_key, get_account_info, get_account_memcache_key, \
+ get_object_env_key, _get_cache_key, get_info, get_object_info, Controller
from swift.common.swob import Request
from swift.common.utils import split_path
from test.unit import fake_http_connect, FakeRing, FakeMemcache
@@ -29,12 +29,18 @@ FakeResponse_status_int = 201
class FakeResponse(object):
- def __init__(self, headers, env, account, container):
+ def __init__(self, headers, env, account, container, obj):
self.headers = headers
self.status_int = FakeResponse_status_int
self.environ = env
- cache_key, env_key = _get_cache_key(account, container)
- if container:
+ if obj:
+ env_key = get_object_env_key(account, container, obj)
+ else:
+ cache_key, env_key = _get_cache_key(account, container)
+
+ if account and container and obj:
+ info = headers_to_object_info(headers, FakeResponse_status_int)
+ elif account and container:
info = headers_to_container_info(headers, FakeResponse_status_int)
else:
info = headers_to_account_info(headers, FakeResponse_status_int)
@@ -42,18 +48,27 @@ class FakeResponse(object):
class FakeRequest(object):
- def __init__(self, env, path):
+ def __init__(self, env, path, swift_source=None):
self.environ = env
(version, account, container, obj) = split_path(path, 2, 4, True)
self.account = account
self.container = container
- stype = container and 'container' or 'account'
- self.headers = {'x-%s-object-count' % (stype): 1000,
- 'x-%s-bytes-used' % (stype): 6666}
+ self.obj = obj
+ if obj:
+ stype = 'object'
+ self.headers = {'content-length': 5555,
+ 'content-type': 'text/plain'}
+ else:
+ stype = container and 'container' or 'account'
+ self.headers = {'x-%s-object-count' % (stype): 1000,
+ 'x-%s-bytes-used' % (stype): 6666}
+ if swift_source:
+ meta = 'x-%s-meta-fakerequest-swift-source' % stype
+ self.headers[meta] = swift_source
def get_response(self, app):
return FakeResponse(self.headers, self.environ, self.account,
- self.container)
+ self.container, self.obj)
class FakeCache(object):
@@ -73,6 +88,21 @@ class TestFuncs(unittest.TestCase):
def test_GETorHEAD_base(self):
base = Controller(self.app)
+ req = Request.blank('/a/c/o/with/slashes')
+ with patch('swift.proxy.controllers.base.'
+ 'http_connect', fake_http_connect(200)):
+ resp = base.GETorHEAD_base(req, 'object', FakeRing(), 'part',
+ '/a/c/o/with/slashes')
+ self.assertTrue('swift.object/a/c/o/with/slashes' in resp.environ)
+ self.assertEqual(
+ resp.environ['swift.object/a/c/o/with/slashes']['status'], 200)
+ req = Request.blank('/a/c/o')
+ with patch('swift.proxy.controllers.base.'
+ 'http_connect', fake_http_connect(200)):
+ resp = base.GETorHEAD_base(req, 'object', FakeRing(), 'part',
+ '/a/c/o')
+ self.assertTrue('swift.object/a/c/o' in resp.environ)
+ self.assertEqual(resp.environ['swift.object/a/c/o']['status'], 200)
req = Request.blank('/a/c')
with patch('swift.proxy.controllers.base.'
'http_connect', fake_http_connect(200)):
@@ -101,7 +131,7 @@ class TestFuncs(unittest.TestCase):
self.assertEquals(info_a['bytes'], 6666)
self.assertEquals(info_a['total_object_count'], 1000)
# Make sure the env cache is set
- self.assertEquals(env, {'swift.account/a': info_a})
+ self.assertEquals(env.get('swift.account/a'), info_a)
# Do an env cached call to account
info_a = get_info(None, env, 'a')
@@ -110,7 +140,7 @@ class TestFuncs(unittest.TestCase):
self.assertEquals(info_a['bytes'], 6666)
self.assertEquals(info_a['total_object_count'], 1000)
# Make sure the env cache is set
- self.assertEquals(env, {'swift.account/a': info_a})
+ self.assertEquals(env.get('swift.account/a'), info_a)
# This time do env cached call to account and non cached to container
with patch('swift.proxy.controllers.base.'
@@ -121,11 +151,12 @@ class TestFuncs(unittest.TestCase):
self.assertEquals(info_c['bytes'], 6666)
self.assertEquals(info_c['object_count'], 1000)
# Make sure the env cache is set
- self.assertEquals(env['swift.account/a'], info_a)
- self.assertEquals(env['swift.container/a/c'], info_c)
+ self.assertEquals(env.get('swift.account/a'), info_a)
+ self.assertEquals(env.get('swift.container/a/c'), info_c)
- # This time do a non cached call to account than non cached to container
- env = {} # abandon previous call to env
+ # This time do a non cached call to account than non cached to
+ # container
+ env = {} # abandon previous call to env
with patch('swift.proxy.controllers.base.'
'_prepare_pre_auth_info_request', FakeRequest):
info_c = get_info(None, env, 'a', 'c')
@@ -134,10 +165,11 @@ class TestFuncs(unittest.TestCase):
self.assertEquals(info_c['bytes'], 6666)
self.assertEquals(info_c['object_count'], 1000)
# Make sure the env cache is set
- self.assertEquals(env['swift.account/a'], info_a)
- self.assertEquals(env['swift.container/a/c'], info_c)
+ self.assertEquals(env.get('swift.account/a'), info_a)
+ self.assertEquals(env.get('swift.container/a/c'), info_c)
- # This time do an env cached call to container while account is not cached
+ # This time do an env cached call to container while account is not
+ # cached
del(env['swift.account/a'])
info_c = get_info(None, env, 'a', 'c')
# Check that you got proper info
@@ -145,7 +177,7 @@ class TestFuncs(unittest.TestCase):
self.assertEquals(info_c['bytes'], 6666)
self.assertEquals(info_c['object_count'], 1000)
# Make sure the env cache is set and account still not cached
- self.assertEquals(env, {'swift.container/a/c': info_c})
+ self.assertEquals(env.get('swift.container/a/c'), info_c)
# Do a non cached call to account not found with ret_not_found
env = {}
@@ -161,7 +193,7 @@ class TestFuncs(unittest.TestCase):
self.assertEquals(info_a['bytes'], 6666)
self.assertEquals(info_a['total_object_count'], 1000)
# Make sure the env cache is set
- self.assertEquals(env, {'swift.account/a': info_a})
+ self.assertEquals(env.get('swift.account/a'), info_a)
# Do a cached call to account not found with ret_not_found
info_a = get_info(None, env, 'a', ret_not_found=True)
@@ -170,7 +202,7 @@ class TestFuncs(unittest.TestCase):
self.assertEquals(info_a['bytes'], 6666)
self.assertEquals(info_a['total_object_count'], 1000)
# Make sure the env cache is set
- self.assertEquals(env, {'swift.account/a': info_a})
+ self.assertEquals(env.get('swift.account/a'), info_a)
# Do a non cached call to account not found without ret_not_found
env = {}
@@ -191,6 +223,21 @@ class TestFuncs(unittest.TestCase):
self.assertEquals(info_a, None)
self.assertEquals(env['swift.account/a']['status'], 404)
+ def test_get_container_info_swift_source(self):
+ req = Request.blank("/v1/a/c", environ={'swift.cache': FakeCache({})})
+ with patch('swift.proxy.controllers.base.'
+ '_prepare_pre_auth_info_request', FakeRequest):
+ resp = get_container_info(req.environ, 'app', swift_source='MC')
+ self.assertEquals(resp['meta']['fakerequest-swift-source'], 'MC')
+
+ def test_get_object_info_swift_source(self):
+ req = Request.blank("/v1/a/c/o",
+ environ={'swift.cache': FakeCache({})})
+ with patch('swift.proxy.controllers.base.'
+ '_prepare_pre_auth_info_request', FakeRequest):
+ resp = get_object_info(req.environ, 'app', swift_source='LU')
+ self.assertEquals(resp['meta']['fakerequest-swift-source'], 'LU')
+
def test_get_container_info_no_cache(self):
req = Request.blank("/v1/AUTH_account/cont",
environ={'swift.cache': FakeCache({})})
@@ -217,11 +264,18 @@ class TestFuncs(unittest.TestCase):
cache_key = get_container_memcache_key("account", "cont")
env_key = 'swift.%s' % cache_key
req = Request.blank("/v1/account/cont",
- environ={ env_key: {'bytes': 3867},
- 'swift.cache': FakeCache({})})
+ environ={env_key: {'bytes': 3867},
+ 'swift.cache': FakeCache({})})
resp = get_container_info(req.environ, 'xxx')
self.assertEquals(resp['bytes'], 3867)
+ def test_get_account_info_swift_source(self):
+ req = Request.blank("/v1/a", environ={'swift.cache': FakeCache({})})
+ with patch('swift.proxy.controllers.base.'
+ '_prepare_pre_auth_info_request', FakeRequest):
+ resp = get_account_info(req.environ, 'a', swift_source='MC')
+ self.assertEquals(resp['meta']['fakerequest-swift-source'], 'MC')
+
def test_get_account_info_no_cache(self):
req = Request.blank("/v1/AUTH_account",
environ={'swift.cache': FakeCache({})})
@@ -266,11 +320,33 @@ class TestFuncs(unittest.TestCase):
cache_key = get_account_memcache_key("account")
env_key = 'swift.%s' % cache_key
req = Request.blank("/v1/account",
- environ={ env_key: {'bytes': 3867},
- 'swift.cache': FakeCache({})})
+ environ={env_key: {'bytes': 3867},
+ 'swift.cache': FakeCache({})})
resp = get_account_info(req.environ, 'xxx')
self.assertEquals(resp['bytes'], 3867)
+ def test_get_object_info_env(self):
+ cached = {'status': 200,
+ 'length': 3333,
+ 'type': 'application/json',
+ 'meta': {}}
+ env_key = get_object_env_key("account", "cont", "obj")
+ req = Request.blank("/v1/account/cont/obj",
+ environ={env_key: cached,
+ 'swift.cache': FakeCache({})})
+ resp = get_object_info(req.environ, 'xxx')
+ self.assertEquals(resp['length'], 3333)
+ self.assertEquals(resp['type'], 'application/json')
+
+ def test_get_object_info_no_env(self):
+ req = Request.blank("/v1/account/cont/obj",
+ environ={'swift.cache': FakeCache({})})
+ with patch('swift.proxy.controllers.base.'
+ '_prepare_pre_auth_info_request', FakeRequest):
+ resp = get_object_info(req.environ, 'xxx')
+ self.assertEquals(resp['length'], 5555)
+ self.assertEquals(resp['type'], 'text/plain')
+
def test_headers_to_container_info_missing(self):
resp = headers_to_container_info({}, 404)
self.assertEquals(resp['status'], 404)
@@ -329,3 +405,31 @@ class TestFuncs(unittest.TestCase):
self.assertEquals(
resp,
headers_to_account_info(headers.items(), 200))
+
+ def test_headers_to_object_info_missing(self):
+ resp = headers_to_object_info({}, 404)
+ self.assertEquals(resp['status'], 404)
+ self.assertEquals(resp['length'], None)
+ self.assertEquals(resp['etag'], None)
+
+ def test_headers_to_object_info_meta(self):
+ headers = {'X-Object-Meta-Whatevs': 14,
+ 'x-object-meta-somethingelse': 0}
+ resp = headers_to_object_info(headers.items(), 200)
+ self.assertEquals(len(resp['meta']), 2)
+ self.assertEquals(resp['meta']['whatevs'], 14)
+ self.assertEquals(resp['meta']['somethingelse'], 0)
+
+ def test_headers_to_object_info_values(self):
+ headers = {
+ 'content-length': '1024',
+ 'content-type': 'application/json',
+ }
+ resp = headers_to_object_info(headers.items(), 200)
+ self.assertEquals(resp['length'], '1024')
+ self.assertEquals(resp['type'], 'application/json')
+
+ headers['x-unused-header'] = 'blahblahblah'
+ self.assertEquals(
+ resp,
+ headers_to_object_info(headers.items(), 200))
diff --git a/test/unit/proxy/controllers/test_container.py b/test/unit/proxy/controllers/test_container.py
index c2e9483..63e6b0e 100644
--- a/test/unit/proxy/controllers/test_container.py
+++ b/test/unit/proxy/controllers/test_container.py
@@ -1,4 +1,4 @@
-# Copyright (c) 2010-2012 OpenStack, LLC.
+# Copyright (c) 2010-2012 OpenStack Foundation
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
@@ -40,6 +40,28 @@ class TestContainerController(unittest.TestCase):
self.assertEqual(headers_to_container_info(resp.headers),
resp.environ['swift.container/a/c'])
+ def test_swift_owner(self):
+ owner_headers = {
+ 'x-container-read': 'value', 'x-container-write': 'value',
+ 'x-container-sync-key': 'value', 'x-container-sync-to': 'value'}
+ controller = proxy_server.ContainerController(self.app, 'a', 'c')
+
+ req = Request.blank('/a/c')
+ with mock.patch('swift.proxy.controllers.base.http_connect',
+ fake_http_connect(200, 200, headers=owner_headers)):
+ resp = controller.HEAD(req)
+ self.assertEquals(2, resp.status_int // 100)
+ for key in owner_headers:
+ self.assertTrue(key not in resp.headers)
+
+ req = Request.blank('/a/c', environ={'swift_owner': True})
+ with mock.patch('swift.proxy.controllers.base.http_connect',
+ fake_http_connect(200, 200, headers=owner_headers)):
+ resp = controller.HEAD(req)
+ self.assertEquals(2, resp.status_int // 100)
+ for key in owner_headers:
+ self.assertTrue(key in resp.headers)
+
if __name__ == '__main__':
unittest.main()
diff --git a/test/unit/proxy/controllers/test_obj.py b/test/unit/proxy/controllers/test_obj.py
index e4af789..cae62b0 100755
--- a/test/unit/proxy/controllers/test_obj.py
+++ b/test/unit/proxy/controllers/test_obj.py
@@ -1,5 +1,5 @@
#!/usr/bin/env python
-# Copyright (c) 2010-2012 OpenStack, LLC.
+# Copyright (c) 2010-2012 OpenStack Foundation
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
@@ -15,9 +15,28 @@
# limitations under the License.
import unittest
+from contextlib import contextmanager
+import mock
+
+import swift
from swift.proxy import server as proxy_server
-from test.unit import FakeRing, FakeMemcache
+from test.unit import FakeRing, FakeMemcache, fake_http_connect
+
+
+@contextmanager
+def set_http_connect(*args, **kwargs):
+ old_connect = swift.proxy.controllers.base.http_connect
+ new_connect = fake_http_connect(*args, **kwargs)
+ swift.proxy.controllers.base.http_connect = new_connect
+ swift.proxy.controllers.obj.http_connect = new_connect
+ swift.proxy.controllers.account.http_connect = new_connect
+ swift.proxy.controllers.container.http_connect = new_connect
+ yield new_connect
+ swift.proxy.controllers.base.http_connect = old_connect
+ swift.proxy.controllers.obj.http_connect = old_connect
+ swift.proxy.controllers.account.http_connect = old_connect
+ swift.proxy.controllers.container.http_connect = old_connect
class TestObjControllerWriteAffinity(unittest.TestCase):
@@ -44,7 +63,8 @@ class TestObjControllerWriteAffinity(unittest.TestCase):
def test_iter_nodes_local_first_moves_locals_first(self):
controller = proxy_server.ObjectController(self.app, 'a', 'c', 'o')
- self.app.write_affinity_is_local_fn = (lambda node: node['region'] == 1)
+ self.app.write_affinity_is_local_fn = (
+ lambda node: node['region'] == 1)
self.app.write_affinity_node_count = lambda ring: 4
all_nodes = self.app.object_ring.get_part_nodes(1)
@@ -59,6 +79,44 @@ class TestObjControllerWriteAffinity(unittest.TestCase):
# we don't skip any nodes
self.assertEqual(sorted(all_nodes), sorted(local_first_nodes))
+ def test_connect_put_node_timeout(self):
+ controller = proxy_server.ObjectController(self.app, 'a', 'c', 'o')
+ self.app.conn_timeout = 0.1
+ with set_http_connect(200, slow_connect=True):
+ nodes = [dict(ip='', port='', device='')]
+ res = controller._connect_put_node(nodes, '', '', {}, ('', ''))
+ self.assertTrue(res is None)
+
+
+class TestObjController(unittest.TestCase):
+
+ def test_PUT_log_info(self):
+ # mock out enough to get to the area of the code we want to test
+ with mock.patch('swift.proxy.controllers.obj.check_object_creation',
+ mock.MagicMock(return_value=None)):
+ app = mock.MagicMock()
+ app.container_ring.get_nodes.return_value = (1, [2])
+ app.object_ring.get_nodes.return_value = (1, [2])
+ controller = proxy_server.ObjectController(app, 'a', 'c', 'o')
+ controller.container_info = mock.MagicMock(return_value={
+ 'partition': 1,
+ 'nodes': [{}],
+ 'write_acl': None,
+ 'sync_key': None,
+ 'versions': None})
+ # and now test that we add the header to log_info
+ req = swift.common.swob.Request.blank('/v1/a/c/o')
+ req.headers['x-copy-from'] = 'somewhere'
+ controller.PUT(req)
+ self.assertEquals(
+ req.environ.get('swift.log_info'), ['x-copy-from:somewhere'])
+ # and then check that we don't do that for originating POSTs
+ req = swift.common.swob.Request.blank('/v1/a/c/o')
+ req.method = 'POST'
+ req.headers['x-copy-from'] = 'elsewhere'
+ controller.PUT(req)
+ self.assertEquals(req.environ.get('swift.log_info'), None)
+
if __name__ == '__main__':
unittest.main()