Add x-remove-versions-location for feature: disable versioning

We can set x-versions-location empty to remove this header in API, but
to keep consistent, we should allow x-remove-versions-location too. The
usage is post "x-remove-versions-locaion: x", just like ACL remove
headers.

Fixed: bug #1107592

Change-Id: I1271eec6401d4a0e8c1a7c2d63aeb8dfef00bf6d
This commit is contained in:
Kun Huang 2013-03-17 07:30:00 +08:00
parent c2f8f00a3e
commit 5c3f75ba6a
4 changed files with 45 additions and 4 deletions

View File

@ -15,7 +15,7 @@ container where the versions are stored. It is recommended to use a different
When data is ``PUT`` into a versioned container (a container with the
versioning flag turned on), the existing data in the file is redirected to a
new object and the data in the ``PUT`` request is saved as the data for the
versioned object. The new object name (for the previous version) is
versioned object. The new object name (for the previous version) is
``<versions_container>/<length><object_name>/<timestamp>``, where ``length``
is the 3-character zero-padded hexidecimal length of the ``<object_name>`` and
``<timestamp>`` is the timestamp of when the previous version was created.
@ -75,3 +75,15 @@ gone::
http://<storage_url>/container/myobject
curl -i -H "X-Auth-Token: <token>" \
http://<storage_url>/versions?prefix=008myobject/
---------------------------------------------------
How to Disable Object Versioning in a Swift Cluster
---------------------------------------------------
If you want to disable all functionality, set ``allow_versions`` back to
``False`` in the container server config.
Disable versioning a versioned container (x is any value except empty)::
curl -i -HPOST -H "X-Auth-Token: <token>" \
-H "X-Remove-Versions-Location: x" http://<storage_url>/container

View File

@ -278,17 +278,18 @@ class Controller(object):
if getattr(m, 'publicly_accessible', False):
self.allowed_methods.add(name)
def _x_remove_headers(self):
return []
def transfer_headers(self, src_headers, dst_headers):
st = self.server_type.lower()
x_remove = 'x-remove-%s-meta-' % st
x_remove_read = 'x-remove-%s-read' % st
x_remove_write = 'x-remove-%s-write' % st
x_meta = 'x-%s-meta-' % st
dst_headers.update((k.lower().replace('-remove', '', 1), '')
for k in src_headers
if k.lower().startswith(x_remove) or
k.lower() in (x_remove_read, x_remove_write))
k.lower() in self._x_remove_headers())
dst_headers.update((k.lower(), v)
for k, v in src_headers.iteritems()

View File

@ -50,6 +50,12 @@ class ContainerController(Controller):
self.account_name = unquote(account_name)
self.container_name = unquote(container_name)
def _x_remove_headers(self):
st = self.server_type.lower()
return ['x-remove-%s-read' % st,
'x-remove-%s-write' % st,
'x-remove-versions-location']
def clean_acls(self, req):
if 'swift.clean_acl' in req.environ:
for header in ('x-container-read', 'x-container-write'):

View File

@ -437,6 +437,17 @@ class TestController(unittest.TestCase):
self.read_acl = 'read_acl'
self.write_acl = 'write_acl'
def test_transfer_headers(self):
src_headers = {'x-remove-base-meta-owner': 'x',
'x-base-meta-size': '151M',
'new-owner': 'Kun'}
dst_headers = {'x-base-meta-owner': 'Gareth',
'x-base-meta-size': '150M'}
self.controller.transfer_headers(src_headers, dst_headers)
expected_headers = {'x-base-meta-owner': '',
'x-base-meta-size': '151M'}
self.assertEquals(dst_headers, expected_headers)
def check_account_info_return(self, partition, nodes, is_none=False):
if is_none:
p, n = None, None
@ -4318,6 +4329,17 @@ class TestContainerController(unittest.TestCase):
container_ring=FakeRing(),
object_ring=FakeRing())
def test_transfer_headers(self):
src_headers = {'x-remove-versions-location': 'x',
'x-container-read': '*:user'}
dst_headers = {'x-versions-location': 'backup'}
controller = swift.proxy.controllers.ContainerController(self.app,
'a', 'c')
controller.transfer_headers(src_headers, dst_headers)
expected_headers = {'x-versions-location': '',
'x-container-read': '*:user'}
self.assertEqual(dst_headers, expected_headers)
def assert_status_map(self, method, statuses, expected,
raise_exc=False, missing_container=False):
with save_globals():