swift 2.23.3__py3-none-any.whl → 2.35.0__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- swift/__init__.py +29 -50
- swift/account/auditor.py +21 -118
- swift/account/backend.py +33 -28
- swift/account/reaper.py +37 -28
- swift/account/replicator.py +22 -0
- swift/account/server.py +60 -26
- swift/account/utils.py +28 -11
- swift-2.23.3.data/scripts/swift-account-audit → swift/cli/account_audit.py +23 -13
- swift-2.23.3.data/scripts/swift-config → swift/cli/config.py +2 -2
- swift/cli/container_deleter.py +5 -11
- swift-2.23.3.data/scripts/swift-dispersion-populate → swift/cli/dispersion_populate.py +8 -7
- swift/cli/dispersion_report.py +10 -9
- swift-2.23.3.data/scripts/swift-drive-audit → swift/cli/drive_audit.py +63 -21
- swift/cli/form_signature.py +3 -7
- swift-2.23.3.data/scripts/swift-get-nodes → swift/cli/get_nodes.py +8 -2
- swift/cli/info.py +154 -14
- swift/cli/manage_shard_ranges.py +705 -37
- swift-2.23.3.data/scripts/swift-oldies → swift/cli/oldies.py +25 -14
- swift-2.23.3.data/scripts/swift-orphans → swift/cli/orphans.py +7 -3
- swift/cli/recon.py +196 -67
- swift-2.23.3.data/scripts/swift-recon-cron → swift/cli/recon_cron.py +17 -20
- swift-2.23.3.data/scripts/swift-reconciler-enqueue → swift/cli/reconciler_enqueue.py +2 -3
- swift/cli/relinker.py +807 -126
- swift/cli/reload.py +135 -0
- swift/cli/ringbuilder.py +217 -20
- swift/cli/ringcomposer.py +0 -1
- swift/cli/shard-info.py +4 -3
- swift/common/base_storage_server.py +9 -20
- swift/common/bufferedhttp.py +48 -74
- swift/common/constraints.py +20 -15
- swift/common/container_sync_realms.py +9 -11
- swift/common/daemon.py +25 -8
- swift/common/db.py +195 -128
- swift/common/db_auditor.py +168 -0
- swift/common/db_replicator.py +95 -55
- swift/common/digest.py +141 -0
- swift/common/direct_client.py +144 -33
- swift/common/error_limiter.py +93 -0
- swift/common/exceptions.py +25 -1
- swift/common/header_key_dict.py +2 -9
- swift/common/http_protocol.py +373 -0
- swift/common/internal_client.py +129 -59
- swift/common/linkat.py +3 -4
- swift/common/manager.py +284 -67
- swift/common/memcached.py +390 -145
- swift/common/middleware/__init__.py +4 -0
- swift/common/middleware/account_quotas.py +211 -46
- swift/common/middleware/acl.py +3 -8
- swift/common/middleware/backend_ratelimit.py +230 -0
- swift/common/middleware/bulk.py +22 -34
- swift/common/middleware/catch_errors.py +1 -3
- swift/common/middleware/cname_lookup.py +6 -11
- swift/common/middleware/container_quotas.py +1 -1
- swift/common/middleware/container_sync.py +39 -17
- swift/common/middleware/copy.py +12 -0
- swift/common/middleware/crossdomain.py +22 -9
- swift/common/middleware/crypto/__init__.py +2 -1
- swift/common/middleware/crypto/crypto_utils.py +11 -15
- swift/common/middleware/crypto/decrypter.py +28 -11
- swift/common/middleware/crypto/encrypter.py +12 -17
- swift/common/middleware/crypto/keymaster.py +8 -15
- swift/common/middleware/crypto/kms_keymaster.py +2 -1
- swift/common/middleware/dlo.py +15 -11
- swift/common/middleware/domain_remap.py +5 -4
- swift/common/middleware/etag_quoter.py +128 -0
- swift/common/middleware/formpost.py +73 -70
- swift/common/middleware/gatekeeper.py +8 -1
- swift/common/middleware/keystoneauth.py +33 -3
- swift/common/middleware/list_endpoints.py +4 -4
- swift/common/middleware/listing_formats.py +85 -49
- swift/common/middleware/memcache.py +4 -95
- swift/common/middleware/name_check.py +3 -2
- swift/common/middleware/proxy_logging.py +160 -92
- swift/common/middleware/ratelimit.py +17 -10
- swift/common/middleware/read_only.py +6 -4
- swift/common/middleware/recon.py +59 -22
- swift/common/middleware/s3api/acl_handlers.py +25 -3
- swift/common/middleware/s3api/acl_utils.py +6 -1
- swift/common/middleware/s3api/controllers/__init__.py +6 -0
- swift/common/middleware/s3api/controllers/acl.py +3 -2
- swift/common/middleware/s3api/controllers/bucket.py +242 -137
- swift/common/middleware/s3api/controllers/logging.py +2 -2
- swift/common/middleware/s3api/controllers/multi_delete.py +43 -20
- swift/common/middleware/s3api/controllers/multi_upload.py +219 -133
- swift/common/middleware/s3api/controllers/obj.py +112 -8
- swift/common/middleware/s3api/controllers/object_lock.py +44 -0
- swift/common/middleware/s3api/controllers/s3_acl.py +2 -2
- swift/common/middleware/s3api/controllers/tagging.py +57 -0
- swift/common/middleware/s3api/controllers/versioning.py +36 -7
- swift/common/middleware/s3api/etree.py +22 -9
- swift/common/middleware/s3api/exception.py +0 -4
- swift/common/middleware/s3api/s3api.py +113 -41
- swift/common/middleware/s3api/s3request.py +384 -218
- swift/common/middleware/s3api/s3response.py +126 -23
- swift/common/middleware/s3api/s3token.py +16 -17
- swift/common/middleware/s3api/schema/delete.rng +1 -1
- swift/common/middleware/s3api/subresource.py +7 -10
- swift/common/middleware/s3api/utils.py +27 -10
- swift/common/middleware/slo.py +665 -358
- swift/common/middleware/staticweb.py +64 -37
- swift/common/middleware/symlink.py +51 -18
- swift/common/middleware/tempauth.py +76 -58
- swift/common/middleware/tempurl.py +191 -173
- swift/common/middleware/versioned_writes/__init__.py +51 -0
- swift/common/middleware/{versioned_writes.py → versioned_writes/legacy.py} +27 -26
- swift/common/middleware/versioned_writes/object_versioning.py +1482 -0
- swift/common/middleware/x_profile/exceptions.py +1 -4
- swift/common/middleware/x_profile/html_viewer.py +18 -19
- swift/common/middleware/x_profile/profile_model.py +1 -2
- swift/common/middleware/xprofile.py +10 -10
- swift-2.23.3.data/scripts/swift-container-server → swift/common/recon.py +13 -8
- swift/common/registry.py +147 -0
- swift/common/request_helpers.py +324 -57
- swift/common/ring/builder.py +67 -25
- swift/common/ring/composite_builder.py +1 -1
- swift/common/ring/ring.py +177 -51
- swift/common/ring/utils.py +1 -1
- swift/common/splice.py +10 -6
- swift/common/statsd_client.py +205 -0
- swift/common/storage_policy.py +49 -44
- swift/common/swob.py +86 -102
- swift/common/{utils.py → utils/__init__.py} +2163 -2772
- swift/common/utils/base.py +131 -0
- swift/common/utils/config.py +433 -0
- swift/common/utils/ipaddrs.py +256 -0
- swift/common/utils/libc.py +345 -0
- swift/common/utils/logs.py +859 -0
- swift/common/utils/timestamp.py +412 -0
- swift/common/wsgi.py +553 -535
- swift/container/auditor.py +14 -100
- swift/container/backend.py +490 -231
- swift/container/reconciler.py +126 -37
- swift/container/replicator.py +96 -22
- swift/container/server.py +358 -165
- swift/container/sharder.py +1540 -684
- swift/container/sync.py +94 -88
- swift/container/updater.py +53 -32
- swift/obj/auditor.py +153 -35
- swift/obj/diskfile.py +466 -217
- swift/obj/expirer.py +406 -124
- swift/obj/mem_diskfile.py +7 -4
- swift/obj/mem_server.py +1 -0
- swift/obj/reconstructor.py +523 -262
- swift/obj/replicator.py +249 -188
- swift/obj/server.py +207 -122
- swift/obj/ssync_receiver.py +145 -85
- swift/obj/ssync_sender.py +113 -54
- swift/obj/updater.py +652 -139
- swift/obj/watchers/__init__.py +0 -0
- swift/obj/watchers/dark_data.py +213 -0
- swift/proxy/controllers/account.py +11 -11
- swift/proxy/controllers/base.py +848 -604
- swift/proxy/controllers/container.py +433 -92
- swift/proxy/controllers/info.py +3 -2
- swift/proxy/controllers/obj.py +1000 -489
- swift/proxy/server.py +185 -112
- {swift-2.23.3.dist-info → swift-2.35.0.dist-info}/AUTHORS +58 -11
- {swift-2.23.3.dist-info → swift-2.35.0.dist-info}/METADATA +51 -56
- swift-2.35.0.dist-info/RECORD +201 -0
- {swift-2.23.3.dist-info → swift-2.35.0.dist-info}/WHEEL +1 -1
- {swift-2.23.3.dist-info → swift-2.35.0.dist-info}/entry_points.txt +43 -0
- swift-2.35.0.dist-info/pbr.json +1 -0
- swift/locale/de/LC_MESSAGES/swift.po +0 -1216
- swift/locale/en_GB/LC_MESSAGES/swift.po +0 -1207
- swift/locale/es/LC_MESSAGES/swift.po +0 -1085
- swift/locale/fr/LC_MESSAGES/swift.po +0 -909
- swift/locale/it/LC_MESSAGES/swift.po +0 -894
- swift/locale/ja/LC_MESSAGES/swift.po +0 -965
- swift/locale/ko_KR/LC_MESSAGES/swift.po +0 -964
- swift/locale/pt_BR/LC_MESSAGES/swift.po +0 -881
- swift/locale/ru/LC_MESSAGES/swift.po +0 -891
- swift/locale/tr_TR/LC_MESSAGES/swift.po +0 -832
- swift/locale/zh_CN/LC_MESSAGES/swift.po +0 -833
- swift/locale/zh_TW/LC_MESSAGES/swift.po +0 -838
- swift-2.23.3.data/scripts/swift-account-auditor +0 -23
- swift-2.23.3.data/scripts/swift-account-info +0 -51
- swift-2.23.3.data/scripts/swift-account-reaper +0 -23
- swift-2.23.3.data/scripts/swift-account-replicator +0 -34
- swift-2.23.3.data/scripts/swift-account-server +0 -23
- swift-2.23.3.data/scripts/swift-container-auditor +0 -23
- swift-2.23.3.data/scripts/swift-container-info +0 -55
- swift-2.23.3.data/scripts/swift-container-reconciler +0 -21
- swift-2.23.3.data/scripts/swift-container-replicator +0 -34
- swift-2.23.3.data/scripts/swift-container-sharder +0 -37
- swift-2.23.3.data/scripts/swift-container-sync +0 -23
- swift-2.23.3.data/scripts/swift-container-updater +0 -23
- swift-2.23.3.data/scripts/swift-dispersion-report +0 -24
- swift-2.23.3.data/scripts/swift-form-signature +0 -20
- swift-2.23.3.data/scripts/swift-init +0 -119
- swift-2.23.3.data/scripts/swift-object-auditor +0 -29
- swift-2.23.3.data/scripts/swift-object-expirer +0 -33
- swift-2.23.3.data/scripts/swift-object-info +0 -60
- swift-2.23.3.data/scripts/swift-object-reconstructor +0 -33
- swift-2.23.3.data/scripts/swift-object-relinker +0 -41
- swift-2.23.3.data/scripts/swift-object-replicator +0 -37
- swift-2.23.3.data/scripts/swift-object-server +0 -27
- swift-2.23.3.data/scripts/swift-object-updater +0 -23
- swift-2.23.3.data/scripts/swift-proxy-server +0 -23
- swift-2.23.3.data/scripts/swift-recon +0 -24
- swift-2.23.3.data/scripts/swift-ring-builder +0 -24
- swift-2.23.3.data/scripts/swift-ring-builder-analyzer +0 -22
- swift-2.23.3.data/scripts/swift-ring-composer +0 -22
- swift-2.23.3.dist-info/RECORD +0 -220
- swift-2.23.3.dist-info/pbr.json +0 -1
- {swift-2.23.3.dist-info → swift-2.35.0.dist-info}/LICENSE +0 -0
- {swift-2.23.3.dist-info → swift-2.35.0.dist-info}/top_level.txt +0 -0
swift/common/middleware/recon.py
CHANGED
@@ -20,12 +20,13 @@ import time
|
|
20
20
|
from resource import getpagesize
|
21
21
|
|
22
22
|
from swift import __version__ as swiftver
|
23
|
-
from swift import gettext_ as _
|
24
23
|
from swift.common.constraints import check_mount
|
25
24
|
from swift.common.storage_policy import POLICIES
|
26
25
|
from swift.common.swob import Request, Response
|
27
|
-
from swift.common.utils import get_logger,
|
28
|
-
|
26
|
+
from swift.common.utils import get_logger, SWIFT_CONF_FILE, md5_hash_for_file
|
27
|
+
from swift.common.recon import RECON_OBJECT_FILE, RECON_CONTAINER_FILE, \
|
28
|
+
RECON_ACCOUNT_FILE, RECON_DRIVE_FILE, RECON_RELINKER_FILE, \
|
29
|
+
DEFAULT_RECON_CACHE_PATH
|
29
30
|
|
30
31
|
|
31
32
|
class ReconMiddleware(object):
|
@@ -35,7 +36,7 @@ class ReconMiddleware(object):
|
|
35
36
|
/recon/load|mem|async... will return various system metrics.
|
36
37
|
|
37
38
|
Needs to be added to the pipeline and requires a filter
|
38
|
-
declaration in the object-server
|
39
|
+
declaration in the [account|container|object]-server conf file:
|
39
40
|
|
40
41
|
[filter:recon]
|
41
42
|
use = egg:swift#recon
|
@@ -48,15 +49,17 @@ class ReconMiddleware(object):
|
|
48
49
|
swift_dir = conf.get('swift_dir', '/etc/swift')
|
49
50
|
self.logger = get_logger(conf, log_route='recon')
|
50
51
|
self.recon_cache_path = conf.get('recon_cache_path',
|
51
|
-
|
52
|
+
DEFAULT_RECON_CACHE_PATH)
|
52
53
|
self.object_recon_cache = os.path.join(self.recon_cache_path,
|
53
|
-
|
54
|
+
RECON_OBJECT_FILE)
|
54
55
|
self.container_recon_cache = os.path.join(self.recon_cache_path,
|
55
|
-
|
56
|
+
RECON_CONTAINER_FILE)
|
56
57
|
self.account_recon_cache = os.path.join(self.recon_cache_path,
|
57
|
-
|
58
|
+
RECON_ACCOUNT_FILE)
|
58
59
|
self.drive_recon_cache = os.path.join(self.recon_cache_path,
|
59
|
-
|
60
|
+
RECON_DRIVE_FILE)
|
61
|
+
self.relink_recon_cache = os.path.join(self.recon_cache_path,
|
62
|
+
RECON_RELINKER_FILE)
|
60
63
|
self.account_ring_path = os.path.join(swift_dir, 'account.ring.gz')
|
61
64
|
self.container_ring_path = os.path.join(swift_dir, 'container.ring.gz')
|
62
65
|
|
@@ -66,26 +69,30 @@ class ReconMiddleware(object):
|
|
66
69
|
self.rings.append(os.path.join(swift_dir,
|
67
70
|
policy.ring_name + '.ring.gz'))
|
68
71
|
|
69
|
-
|
70
|
-
|
71
|
-
def _from_recon_cache(self, cache_keys, cache_file, openr=open):
|
72
|
+
def _from_recon_cache(self, cache_keys, cache_file, openr=open,
|
73
|
+
ignore_missing=False):
|
72
74
|
"""retrieve values from a recon cache file
|
73
75
|
|
74
76
|
:params cache_keys: list of cache items to retrieve
|
75
77
|
:params cache_file: cache file to retrieve items from.
|
76
78
|
:params openr: open to use [for unittests]
|
79
|
+
:params ignore_missing: Some recon stats are very temporary, in this
|
80
|
+
case it would be better to not log if things are missing.
|
77
81
|
:return: dict of cache items and their values or none if not found
|
78
82
|
"""
|
79
83
|
try:
|
80
84
|
with openr(cache_file, 'r') as f:
|
81
85
|
recondata = json.load(f)
|
82
|
-
return
|
83
|
-
except IOError:
|
84
|
-
|
86
|
+
return {key: recondata.get(key) for key in cache_keys}
|
87
|
+
except IOError as err:
|
88
|
+
if err.errno == errno.ENOENT and ignore_missing:
|
89
|
+
pass
|
90
|
+
else:
|
91
|
+
self.logger.exception('Error reading recon cache file')
|
85
92
|
except ValueError:
|
86
|
-
self.logger.exception(
|
93
|
+
self.logger.exception('Error parsing recon cache file')
|
87
94
|
except Exception:
|
88
|
-
self.logger.exception(
|
95
|
+
self.logger.exception('Error retrieving recon data')
|
89
96
|
return dict((key, None) for key in cache_keys)
|
90
97
|
|
91
98
|
def get_version(self):
|
@@ -127,7 +134,7 @@ class ReconMiddleware(object):
|
|
127
134
|
|
128
135
|
def get_async_info(self):
|
129
136
|
"""get # of async pendings"""
|
130
|
-
return self._from_recon_cache(['async_pending'],
|
137
|
+
return self._from_recon_cache(['async_pending', 'async_pending_last'],
|
131
138
|
self.object_recon_cache)
|
132
139
|
|
133
140
|
def get_driveaudit_error(self):
|
@@ -135,6 +142,13 @@ class ReconMiddleware(object):
|
|
135
142
|
return self._from_recon_cache(['drive_audit_errors'],
|
136
143
|
self.drive_recon_cache)
|
137
144
|
|
145
|
+
def get_sharding_info(self):
|
146
|
+
"""get sharding info"""
|
147
|
+
return self._from_recon_cache(["sharding_stats",
|
148
|
+
"sharding_time",
|
149
|
+
"sharding_last"],
|
150
|
+
self.container_recon_cache)
|
151
|
+
|
138
152
|
def get_replication_info(self, recon_type):
|
139
153
|
"""get replication info"""
|
140
154
|
replication_list = ['replication_time',
|
@@ -154,12 +168,19 @@ class ReconMiddleware(object):
|
|
154
168
|
else:
|
155
169
|
return None
|
156
170
|
|
171
|
+
def get_reconstruction_info(self):
|
172
|
+
"""get reconstruction info"""
|
173
|
+
reconstruction_list = ['object_reconstruction_last',
|
174
|
+
'object_reconstruction_time']
|
175
|
+
return self._from_recon_cache(reconstruction_list,
|
176
|
+
self.object_recon_cache)
|
177
|
+
|
157
178
|
def get_device_info(self):
|
158
179
|
"""get devices"""
|
159
180
|
try:
|
160
181
|
return {self.devices: os.listdir(self.devices)}
|
161
182
|
except Exception:
|
162
|
-
self.logger.exception(
|
183
|
+
self.logger.exception('Error listing devices')
|
163
184
|
return {self.devices: None}
|
164
185
|
|
165
186
|
def get_updater_info(self, recon_type):
|
@@ -168,7 +189,9 @@ class ReconMiddleware(object):
|
|
168
189
|
return self._from_recon_cache(['container_updater_sweep'],
|
169
190
|
self.container_recon_cache)
|
170
191
|
elif recon_type == 'object':
|
171
|
-
return self._from_recon_cache(['object_updater_sweep'
|
192
|
+
return self._from_recon_cache(['object_updater_sweep',
|
193
|
+
'object_updater_stats',
|
194
|
+
'object_updater_last'],
|
172
195
|
self.object_recon_cache)
|
173
196
|
else:
|
174
197
|
return None
|
@@ -255,7 +278,7 @@ class ReconMiddleware(object):
|
|
255
278
|
except IOError as err:
|
256
279
|
sums[ringfile] = None
|
257
280
|
if err.errno != errno.ENOENT:
|
258
|
-
self.logger.exception(
|
281
|
+
self.logger.exception('Error reading ringfile')
|
259
282
|
return sums
|
260
283
|
|
261
284
|
def get_swift_conf_md5(self):
|
@@ -265,7 +288,7 @@ class ReconMiddleware(object):
|
|
265
288
|
hexsum = md5_hash_for_file(SWIFT_CONF_FILE)
|
266
289
|
except IOError as err:
|
267
290
|
if err.errno != errno.ENOENT:
|
268
|
-
self.logger.exception(
|
291
|
+
self.logger.exception('Error reading swift.conf')
|
269
292
|
return {SWIFT_CONF_FILE: hexsum}
|
270
293
|
|
271
294
|
def get_quarantine_count(self):
|
@@ -330,6 +353,14 @@ class ReconMiddleware(object):
|
|
330
353
|
|
331
354
|
return time.time()
|
332
355
|
|
356
|
+
def get_relinker_info(self):
|
357
|
+
"""get relinker info, if any"""
|
358
|
+
|
359
|
+
stat_keys = ['devices', 'workers']
|
360
|
+
return self._from_recon_cache(stat_keys,
|
361
|
+
self.relink_recon_cache,
|
362
|
+
ignore_missing=True)
|
363
|
+
|
333
364
|
def GET(self, req):
|
334
365
|
root, rcheck, rtype = req.split_path(1, 3, True)
|
335
366
|
all_rtypes = ['account', 'container', 'object']
|
@@ -372,6 +403,12 @@ class ReconMiddleware(object):
|
|
372
403
|
content = self.get_driveaudit_error()
|
373
404
|
elif rcheck == "time":
|
374
405
|
content = self.get_time()
|
406
|
+
elif rcheck == "sharding":
|
407
|
+
content = self.get_sharding_info()
|
408
|
+
elif rcheck == "relinker":
|
409
|
+
content = self.get_relinker_info()
|
410
|
+
elif rcheck == "reconstruction" and rtype == 'object':
|
411
|
+
content = self.get_reconstruction_info()
|
375
412
|
else:
|
376
413
|
content = "Invalid path: %s" % req.path
|
377
414
|
return Response(request=req, status="404 Not Found",
|
@@ -128,9 +128,23 @@ class BaseAclHandler(object):
|
|
128
128
|
raise Exception('No permission to be checked exists')
|
129
129
|
|
130
130
|
if resource == 'object':
|
131
|
+
version_id = self.req.params.get('versionId')
|
132
|
+
if version_id is None:
|
133
|
+
query = {}
|
134
|
+
else:
|
135
|
+
query = {'version-id': version_id}
|
136
|
+
if self.req.method == 'HEAD':
|
137
|
+
# This HEAD for ACL is going to also be the definitive response
|
138
|
+
# to the client so we need to include client params. We don't
|
139
|
+
# do this for other client request methods because they may
|
140
|
+
# have invalid combinations of params and headers for a swift
|
141
|
+
# HEAD request.
|
142
|
+
part_number = self.req.params.get('partNumber')
|
143
|
+
if part_number is not None:
|
144
|
+
query['part-number'] = part_number
|
131
145
|
resp = self.req.get_acl_response(app, 'HEAD',
|
132
146
|
container, obj,
|
133
|
-
headers)
|
147
|
+
headers, query=query)
|
134
148
|
acl = resp.object_acl
|
135
149
|
elif resource == 'container':
|
136
150
|
resp = self.req.get_acl_response(app, 'HEAD',
|
@@ -162,8 +176,8 @@ class BaseAclHandler(object):
|
|
162
176
|
try:
|
163
177
|
elem = fromstring(body, ACL.root_tag)
|
164
178
|
acl = ACL.from_elem(
|
165
|
-
elem, True, self.req.allow_no_owner)
|
166
|
-
except(XMLSyntaxError, DocumentInvalid):
|
179
|
+
elem, True, self.req.conf.allow_no_owner)
|
180
|
+
except (XMLSyntaxError, DocumentInvalid):
|
167
181
|
raise MalformedACLError()
|
168
182
|
except Exception as e:
|
169
183
|
self.logger.error(e)
|
@@ -243,6 +257,9 @@ class S3AclHandler(BaseAclHandler):
|
|
243
257
|
"""
|
244
258
|
S3AclHandler: Handler for S3AclController
|
245
259
|
"""
|
260
|
+
def HEAD(self, app):
|
261
|
+
self._handle_acl(app, 'HEAD', permission='READ_ACP')
|
262
|
+
|
246
263
|
def GET(self, app):
|
247
264
|
self._handle_acl(app, 'HEAD', permission='READ_ACP')
|
248
265
|
|
@@ -460,4 +477,9 @@ ACL_MAP = {
|
|
460
477
|
# Initiate Multipart Upload
|
461
478
|
('POST', 'HEAD', 'container'):
|
462
479
|
{'Permission': 'WRITE'},
|
480
|
+
# Versioning
|
481
|
+
('PUT', 'POST', 'container'):
|
482
|
+
{'Permission': 'WRITE'},
|
483
|
+
('DELETE', 'GET', 'container'):
|
484
|
+
{'Permission': 'WRITE'},
|
463
485
|
}
|
@@ -41,6 +41,11 @@ def swift_acl_translate(acl, group='', user='', xml=False):
|
|
41
41
|
# ['HTTP_X_CONTAINER_READ', group + ':' + user]]
|
42
42
|
swift_acl['private'] = [['X-Container-Write', '.'],
|
43
43
|
['X-Container-Read', '.']]
|
44
|
+
|
45
|
+
# Swift doesn't have per-object ACLs, so this is best-effort
|
46
|
+
swift_acl['bucket-owner-full-control'] = swift_acl['private']
|
47
|
+
swift_acl['bucket-owner-read'] = swift_acl['private']
|
48
|
+
|
44
49
|
if xml:
|
45
50
|
# We are working with XML and need to parse it
|
46
51
|
try:
|
@@ -62,7 +67,7 @@ def swift_acl_translate(acl, group='', user='', xml=False):
|
|
62
67
|
else:
|
63
68
|
acl = 'unsupported'
|
64
69
|
|
65
|
-
if acl
|
70
|
+
if acl in ('authenticated-read', 'log-delivery-write'):
|
66
71
|
raise S3NotImplemented()
|
67
72
|
elif acl not in swift_acl:
|
68
73
|
raise ACLError()
|
@@ -31,6 +31,10 @@ from swift.common.middleware.s3api.controllers.logging import \
|
|
31
31
|
LoggingStatusController
|
32
32
|
from swift.common.middleware.s3api.controllers.versioning import \
|
33
33
|
VersioningController
|
34
|
+
from swift.common.middleware.s3api.controllers.tagging import \
|
35
|
+
TaggingController
|
36
|
+
from swift.common.middleware.s3api.controllers.object_lock import \
|
37
|
+
ObjectLockController
|
34
38
|
|
35
39
|
__all__ = [
|
36
40
|
'Controller',
|
@@ -47,6 +51,8 @@ __all__ = [
|
|
47
51
|
'LocationController',
|
48
52
|
'LoggingStatusController',
|
49
53
|
'VersioningController',
|
54
|
+
'TaggingController',
|
55
|
+
'ObjectLockController',
|
50
56
|
|
51
57
|
'UnsupportedController',
|
52
58
|
]
|
@@ -19,8 +19,9 @@ from swift.common.utils import public
|
|
19
19
|
|
20
20
|
from swift.common.middleware.s3api.exception import ACLError
|
21
21
|
from swift.common.middleware.s3api.controllers.base import Controller
|
22
|
-
from swift.common.middleware.s3api.s3response import
|
23
|
-
MalformedACLError, UnexpectedContent,
|
22
|
+
from swift.common.middleware.s3api.s3response import (
|
23
|
+
HTTPOk, S3NotImplemented, MalformedACLError, UnexpectedContent,
|
24
|
+
MissingSecurityHeader)
|
24
25
|
from swift.common.middleware.s3api.etree import Element, SubElement, tostring
|
25
26
|
from swift.common.middleware.s3api.acl_utils import swift_acl_translate, \
|
26
27
|
XMLNS_XSI
|