Merge "Increase name-length limits for internal accounts"
This commit is contained in:
commit
8359f43079
@ -21,7 +21,6 @@ from swift.account.utils import account_listing_response
|
|||||||
from swift.common.middleware.acl import parse_acl, format_acl
|
from swift.common.middleware.acl import parse_acl, format_acl
|
||||||
from swift.common.utils import public
|
from swift.common.utils import public
|
||||||
from swift.common.constraints import check_metadata
|
from swift.common.constraints import check_metadata
|
||||||
from swift.common import constraints
|
|
||||||
from swift.common.http import HTTP_NOT_FOUND, HTTP_GONE
|
from swift.common.http import HTTP_NOT_FOUND, HTTP_GONE
|
||||||
from swift.proxy.controllers.base import Controller, clear_info_cache, \
|
from swift.proxy.controllers.base import Controller, clear_info_cache, \
|
||||||
set_info_cache
|
set_info_cache
|
||||||
@ -53,11 +52,11 @@ class AccountController(Controller):
|
|||||||
|
|
||||||
def GETorHEAD(self, req):
|
def GETorHEAD(self, req):
|
||||||
"""Handler for HTTP GET/HEAD requests."""
|
"""Handler for HTTP GET/HEAD requests."""
|
||||||
if len(self.account_name) > constraints.MAX_ACCOUNT_NAME_LENGTH:
|
length_limit = self.get_name_length_limit()
|
||||||
|
if len(self.account_name) > length_limit:
|
||||||
resp = HTTPBadRequest(request=req)
|
resp = HTTPBadRequest(request=req)
|
||||||
resp.body = 'Account name length of %d longer than %d' % \
|
resp.body = 'Account name length of %d longer than %d' % \
|
||||||
(len(self.account_name),
|
(len(self.account_name), length_limit)
|
||||||
constraints.MAX_ACCOUNT_NAME_LENGTH)
|
|
||||||
# Don't cache this. We know the account doesn't exist because
|
# Don't cache this. We know the account doesn't exist because
|
||||||
# the name is bad; we don't need to cache that because it's
|
# the name is bad; we don't need to cache that because it's
|
||||||
# really cheap to recompute.
|
# really cheap to recompute.
|
||||||
@ -117,11 +116,11 @@ class AccountController(Controller):
|
|||||||
error_response = check_metadata(req, 'account')
|
error_response = check_metadata(req, 'account')
|
||||||
if error_response:
|
if error_response:
|
||||||
return error_response
|
return error_response
|
||||||
if len(self.account_name) > constraints.MAX_ACCOUNT_NAME_LENGTH:
|
length_limit = self.get_name_length_limit()
|
||||||
|
if len(self.account_name) > length_limit:
|
||||||
resp = HTTPBadRequest(request=req)
|
resp = HTTPBadRequest(request=req)
|
||||||
resp.body = 'Account name length of %d longer than %d' % \
|
resp.body = 'Account name length of %d longer than %d' % \
|
||||||
(len(self.account_name),
|
(len(self.account_name), length_limit)
|
||||||
constraints.MAX_ACCOUNT_NAME_LENGTH)
|
|
||||||
return resp
|
return resp
|
||||||
account_partition, accounts = \
|
account_partition, accounts = \
|
||||||
self.app.account_ring.get_nodes(self.account_name)
|
self.app.account_ring.get_nodes(self.account_name)
|
||||||
@ -136,11 +135,11 @@ class AccountController(Controller):
|
|||||||
@public
|
@public
|
||||||
def POST(self, req):
|
def POST(self, req):
|
||||||
"""HTTP POST request handler."""
|
"""HTTP POST request handler."""
|
||||||
if len(self.account_name) > constraints.MAX_ACCOUNT_NAME_LENGTH:
|
length_limit = self.get_name_length_limit()
|
||||||
|
if len(self.account_name) > length_limit:
|
||||||
resp = HTTPBadRequest(request=req)
|
resp = HTTPBadRequest(request=req)
|
||||||
resp.body = 'Account name length of %d longer than %d' % \
|
resp.body = 'Account name length of %d longer than %d' % \
|
||||||
(len(self.account_name),
|
(len(self.account_name), length_limit)
|
||||||
constraints.MAX_ACCOUNT_NAME_LENGTH)
|
|
||||||
return resp
|
return resp
|
||||||
error_response = check_metadata(req, 'account')
|
error_response = check_metadata(req, 'account')
|
||||||
if error_response:
|
if error_response:
|
||||||
|
@ -46,6 +46,7 @@ from swift.common.utils import Timestamp, config_true_value, \
|
|||||||
GreenAsyncPile, quorum_size, parse_content_type, \
|
GreenAsyncPile, quorum_size, parse_content_type, \
|
||||||
document_iters_to_http_response_body
|
document_iters_to_http_response_body
|
||||||
from swift.common.bufferedhttp import http_connect
|
from swift.common.bufferedhttp import http_connect
|
||||||
|
from swift.common import constraints
|
||||||
from swift.common.exceptions import ChunkReadTimeout, ChunkWriteTimeout, \
|
from swift.common.exceptions import ChunkReadTimeout, ChunkWriteTimeout, \
|
||||||
ConnectionTimeout, RangeAlreadyComplete
|
ConnectionTimeout, RangeAlreadyComplete
|
||||||
from swift.common.header_key_dict import HeaderKeyDict
|
from swift.common.header_key_dict import HeaderKeyDict
|
||||||
@ -1979,3 +1980,17 @@ class Controller(object):
|
|||||||
resp.headers = headers
|
resp.headers = headers
|
||||||
|
|
||||||
return resp
|
return resp
|
||||||
|
|
||||||
|
def get_name_length_limit(self):
|
||||||
|
if self.account_name.startswith(self.app.auto_create_account_prefix):
|
||||||
|
multiplier = 2
|
||||||
|
else:
|
||||||
|
multiplier = 1
|
||||||
|
|
||||||
|
if self.server_type == 'Account':
|
||||||
|
return constraints.MAX_ACCOUNT_NAME_LENGTH * multiplier
|
||||||
|
elif self.server_type == 'Container':
|
||||||
|
return constraints.MAX_CONTAINER_NAME_LENGTH * multiplier
|
||||||
|
else:
|
||||||
|
raise ValueError(
|
||||||
|
"server_type can only be 'account' or 'container'")
|
||||||
|
@ -18,7 +18,6 @@ from swift import gettext_ as _
|
|||||||
from six.moves.urllib.parse import unquote
|
from six.moves.urllib.parse import unquote
|
||||||
from swift.common.utils import public, csv_append, Timestamp
|
from swift.common.utils import public, csv_append, Timestamp
|
||||||
from swift.common.constraints import check_metadata
|
from swift.common.constraints import check_metadata
|
||||||
from swift.common import constraints
|
|
||||||
from swift.common.http import HTTP_ACCEPTED, is_success
|
from swift.common.http import HTTP_ACCEPTED, is_success
|
||||||
from swift.proxy.controllers.base import Controller, delay_denial, \
|
from swift.proxy.controllers.base import Controller, delay_denial, \
|
||||||
cors_validation, set_info_cache, clear_info_cache
|
cors_validation, set_info_cache, clear_info_cache
|
||||||
@ -151,11 +150,11 @@ class ContainerController(Controller):
|
|||||||
if not req.environ.get('swift_owner'):
|
if not req.environ.get('swift_owner'):
|
||||||
for key in self.app.swift_owner_headers:
|
for key in self.app.swift_owner_headers:
|
||||||
req.headers.pop(key, None)
|
req.headers.pop(key, None)
|
||||||
if len(self.container_name) > constraints.MAX_CONTAINER_NAME_LENGTH:
|
length_limit = self.get_name_length_limit()
|
||||||
|
if len(self.container_name) > length_limit:
|
||||||
resp = HTTPBadRequest(request=req)
|
resp = HTTPBadRequest(request=req)
|
||||||
resp.body = 'Container name length of %d longer than %d' % \
|
resp.body = 'Container name length of %d longer than %d' % \
|
||||||
(len(self.container_name),
|
(len(self.container_name), length_limit)
|
||||||
constraints.MAX_CONTAINER_NAME_LENGTH)
|
|
||||||
return resp
|
return resp
|
||||||
account_partition, accounts, container_count = \
|
account_partition, accounts, container_count = \
|
||||||
self.account_info(self.account_name, req)
|
self.account_info(self.account_name, req)
|
||||||
|
@ -7643,10 +7643,9 @@ class TestContainerController(unittest.TestCase):
|
|||||||
def assert_status_map(self, method, statuses, expected,
|
def assert_status_map(self, method, statuses, expected,
|
||||||
raise_exc=False, missing_container=False):
|
raise_exc=False, missing_container=False):
|
||||||
with save_globals():
|
with save_globals():
|
||||||
kwargs = {}
|
kwargs = {'missing_container': missing_container}
|
||||||
if raise_exc:
|
if raise_exc:
|
||||||
kwargs['raise_exc'] = raise_exc
|
kwargs['raise_exc'] = raise_exc
|
||||||
kwargs['missing_container'] = missing_container
|
|
||||||
set_http_connect(*statuses, **kwargs)
|
set_http_connect(*statuses, **kwargs)
|
||||||
self.app.memcache.store = {}
|
self.app.memcache.store = {}
|
||||||
req = Request.blank('/v1/a/c', headers={'Content-Length': '0',
|
req = Request.blank('/v1/a/c', headers={'Content-Length': '0',
|
||||||
@ -7954,16 +7953,35 @@ class TestContainerController(unittest.TestCase):
|
|||||||
missing_container=True)
|
missing_container=True)
|
||||||
|
|
||||||
def test_PUT_max_container_name_length(self):
|
def test_PUT_max_container_name_length(self):
|
||||||
with save_globals():
|
|
||||||
limit = constraints.MAX_CONTAINER_NAME_LENGTH
|
limit = constraints.MAX_CONTAINER_NAME_LENGTH
|
||||||
controller = proxy_server.ContainerController(self.app, 'account',
|
controller = proxy_server.ContainerController(self.app, 'account',
|
||||||
'1' * limit)
|
'1' * limit)
|
||||||
self.assert_status_map(controller.PUT,
|
self.assert_status_map(controller.PUT, (200, 201, 201, 201), 201,
|
||||||
(200, 201, 201, 201), 201,
|
|
||||||
missing_container=True)
|
missing_container=True)
|
||||||
controller = proxy_server.ContainerController(self.app, 'account',
|
controller = proxy_server.ContainerController(self.app, 'account',
|
||||||
'2' * (limit + 1))
|
'2' * (limit + 1))
|
||||||
self.assert_status_map(controller.PUT, (201, 201, 201), 400,
|
self.assert_status_map(controller.PUT, (), 400,
|
||||||
|
missing_container=True)
|
||||||
|
|
||||||
|
# internal auto-created-accounts get higher limits
|
||||||
|
limit *= 2
|
||||||
|
controller = proxy_server.ContainerController(self.app, '.account',
|
||||||
|
'3' * limit)
|
||||||
|
self.assert_status_map(controller.PUT, (200, 201, 201, 201), 201,
|
||||||
|
missing_container=True)
|
||||||
|
controller = proxy_server.ContainerController(self.app, '.account',
|
||||||
|
'4' * (limit + 1))
|
||||||
|
self.assert_status_map(controller.PUT, (), 400,
|
||||||
|
missing_container=True)
|
||||||
|
|
||||||
|
self.app.auto_create_account_prefix = 'acc'
|
||||||
|
controller = proxy_server.ContainerController(self.app, 'account',
|
||||||
|
'1' * limit)
|
||||||
|
self.assert_status_map(controller.PUT, (200, 201, 201, 201), 201,
|
||||||
|
missing_container=True)
|
||||||
|
controller = proxy_server.ContainerController(self.app, 'account',
|
||||||
|
'2' * (limit + 1))
|
||||||
|
self.assert_status_map(controller.PUT, (), 400,
|
||||||
missing_container=True)
|
missing_container=True)
|
||||||
|
|
||||||
def test_PUT_connect_exceptions(self):
|
def test_PUT_connect_exceptions(self):
|
||||||
@ -9093,14 +9111,39 @@ class TestAccountController(unittest.TestCase):
|
|||||||
test_status_map((204, 500, 404), 503)
|
test_status_map((204, 500, 404), 503)
|
||||||
|
|
||||||
def test_PUT_max_account_name_length(self):
|
def test_PUT_max_account_name_length(self):
|
||||||
with save_globals():
|
|
||||||
self.app.allow_account_management = True
|
self.app.allow_account_management = True
|
||||||
limit = constraints.MAX_ACCOUNT_NAME_LENGTH
|
limit = constraints.MAX_ACCOUNT_NAME_LENGTH
|
||||||
controller = proxy_server.AccountController(self.app, '1' * limit)
|
controller = proxy_server.AccountController(self.app, '1' * limit)
|
||||||
self.assert_status_map(controller.PUT, (201, 201, 201), 201)
|
self.assert_status_map(controller.PUT, (201, 201, 201), 201)
|
||||||
controller = proxy_server.AccountController(
|
controller = proxy_server.AccountController(
|
||||||
self.app, '2' * (limit + 1))
|
self.app, '2' * (limit + 1))
|
||||||
self.assert_status_map(controller.PUT, (201, 201, 201), 400)
|
self.assert_status_map(controller.PUT, (), 400)
|
||||||
|
|
||||||
|
# internal auto-created accounts get higher limits
|
||||||
|
limit *= 2
|
||||||
|
controller = proxy_server.AccountController(
|
||||||
|
self.app, '.' + '3' * (limit - 1))
|
||||||
|
self.assert_status_map(controller.PUT, (201, 201, 201), 201)
|
||||||
|
controller = proxy_server.AccountController(
|
||||||
|
self.app, '.' + '4' * limit)
|
||||||
|
self.assert_status_map(controller.PUT, (), 400)
|
||||||
|
|
||||||
|
self.app.auto_create_account_prefix = 'FOO_'
|
||||||
|
limit /= 2
|
||||||
|
controller = proxy_server.AccountController(
|
||||||
|
self.app, '.' + '5' * (limit - 1))
|
||||||
|
self.assert_status_map(controller.PUT, (201, 201, 201), 201)
|
||||||
|
controller = proxy_server.AccountController(
|
||||||
|
self.app, '.' + '6' * limit)
|
||||||
|
self.assert_status_map(controller.PUT, (), 400)
|
||||||
|
|
||||||
|
limit *= 2
|
||||||
|
controller = proxy_server.AccountController(
|
||||||
|
self.app, 'FOO_' + '7' * (limit - 4))
|
||||||
|
self.assert_status_map(controller.PUT, (201, 201, 201), 201)
|
||||||
|
controller = proxy_server.AccountController(
|
||||||
|
self.app, 'FOO_' + '8' * (limit - 3))
|
||||||
|
self.assert_status_map(controller.PUT, (), 400)
|
||||||
|
|
||||||
def test_PUT_connect_exceptions(self):
|
def test_PUT_connect_exceptions(self):
|
||||||
with save_globals():
|
with save_globals():
|
||||||
|
Loading…
Reference in New Issue
Block a user