swift 2.23.2__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.2.data/scripts/swift-account-audit → swift/cli/account_audit.py +23 -13
- swift-2.23.2.data/scripts/swift-config → swift/cli/config.py +2 -2
- swift/cli/container_deleter.py +5 -11
- swift-2.23.2.data/scripts/swift-dispersion-populate → swift/cli/dispersion_populate.py +8 -7
- swift/cli/dispersion_report.py +10 -9
- swift-2.23.2.data/scripts/swift-drive-audit → swift/cli/drive_audit.py +63 -21
- swift/cli/form_signature.py +3 -7
- swift-2.23.2.data/scripts/swift-get-nodes → swift/cli/get_nodes.py +8 -2
- swift/cli/info.py +183 -29
- swift/cli/manage_shard_ranges.py +708 -37
- swift-2.23.2.data/scripts/swift-oldies → swift/cli/oldies.py +25 -14
- swift-2.23.2.data/scripts/swift-orphans → swift/cli/orphans.py +7 -3
- swift/cli/recon.py +196 -67
- swift-2.23.2.data/scripts/swift-recon-cron → swift/cli/recon_cron.py +17 -20
- swift-2.23.2.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 +198 -127
- 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 +396 -147
- 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 -81
- 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 +52 -19
- swift/common/middleware/tempauth.py +76 -58
- swift/common/middleware/tempurl.py +192 -174
- 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.2.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} +2191 -2762
- 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 +555 -536
- swift/container/auditor.py +14 -100
- swift/container/backend.py +552 -227
- swift/container/reconciler.py +126 -37
- swift/container/replicator.py +96 -22
- swift/container/server.py +397 -176
- swift/container/sharder.py +1580 -639
- 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 +213 -122
- swift/obj/ssync_receiver.py +145 -85
- swift/obj/ssync_sender.py +113 -54
- swift/obj/updater.py +653 -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 +452 -86
- swift/proxy/controllers/info.py +3 -2
- swift/proxy/controllers/obj.py +1009 -490
- swift/proxy/server.py +185 -112
- swift-2.35.0.dist-info/AUTHORS +501 -0
- swift-2.35.0.dist-info/LICENSE +202 -0
- {swift-2.23.2.dist-info → swift-2.35.0.dist-info}/METADATA +52 -61
- swift-2.35.0.dist-info/RECORD +201 -0
- {swift-2.23.2.dist-info → swift-2.35.0.dist-info}/WHEEL +1 -1
- {swift-2.23.2.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.2.data/scripts/swift-account-auditor +0 -23
- swift-2.23.2.data/scripts/swift-account-info +0 -51
- swift-2.23.2.data/scripts/swift-account-reaper +0 -23
- swift-2.23.2.data/scripts/swift-account-replicator +0 -34
- swift-2.23.2.data/scripts/swift-account-server +0 -23
- swift-2.23.2.data/scripts/swift-container-auditor +0 -23
- swift-2.23.2.data/scripts/swift-container-info +0 -51
- swift-2.23.2.data/scripts/swift-container-reconciler +0 -21
- swift-2.23.2.data/scripts/swift-container-replicator +0 -34
- swift-2.23.2.data/scripts/swift-container-sharder +0 -33
- swift-2.23.2.data/scripts/swift-container-sync +0 -23
- swift-2.23.2.data/scripts/swift-container-updater +0 -23
- swift-2.23.2.data/scripts/swift-dispersion-report +0 -24
- swift-2.23.2.data/scripts/swift-form-signature +0 -20
- swift-2.23.2.data/scripts/swift-init +0 -119
- swift-2.23.2.data/scripts/swift-object-auditor +0 -29
- swift-2.23.2.data/scripts/swift-object-expirer +0 -33
- swift-2.23.2.data/scripts/swift-object-info +0 -60
- swift-2.23.2.data/scripts/swift-object-reconstructor +0 -33
- swift-2.23.2.data/scripts/swift-object-relinker +0 -41
- swift-2.23.2.data/scripts/swift-object-replicator +0 -37
- swift-2.23.2.data/scripts/swift-object-server +0 -27
- swift-2.23.2.data/scripts/swift-object-updater +0 -23
- swift-2.23.2.data/scripts/swift-proxy-server +0 -23
- swift-2.23.2.data/scripts/swift-recon +0 -24
- swift-2.23.2.data/scripts/swift-ring-builder +0 -24
- swift-2.23.2.data/scripts/swift-ring-builder-analyzer +0 -22
- swift-2.23.2.data/scripts/swift-ring-composer +0 -22
- swift-2.23.2.dist-info/DESCRIPTION.rst +0 -166
- swift-2.23.2.dist-info/RECORD +0 -220
- swift-2.23.2.dist-info/metadata.json +0 -1
- swift-2.23.2.dist-info/pbr.json +0 -1
- {swift-2.23.2.dist-info → swift-2.35.0.dist-info}/top_level.txt +0 -0
swift/account/server.py
CHANGED
@@ -15,9 +15,9 @@
|
|
15
15
|
|
16
16
|
import json
|
17
17
|
import os
|
18
|
+
import sys
|
18
19
|
import time
|
19
20
|
import traceback
|
20
|
-
from swift import gettext_ as _
|
21
21
|
|
22
22
|
from eventlet import Timeout
|
23
23
|
|
@@ -26,12 +26,14 @@ from swift.account.backend import AccountBroker, DATADIR
|
|
26
26
|
from swift.account.utils import account_listing_response, get_response_headers
|
27
27
|
from swift.common.db import DatabaseConnectionError, DatabaseAlreadyExists
|
28
28
|
from swift.common.request_helpers import get_param, \
|
29
|
-
split_and_validate_path
|
29
|
+
split_and_validate_path, validate_internal_account, \
|
30
|
+
validate_internal_container, constrain_req_limit
|
30
31
|
from swift.common.utils import get_logger, hash_path, public, \
|
31
32
|
Timestamp, storage_directory, config_true_value, \
|
32
33
|
timing_stats, replication, get_log_line, \
|
33
|
-
config_fallocate_value, fs_has_free_space
|
34
|
-
from swift.common.constraints import valid_timestamp, check_utf8,
|
34
|
+
config_fallocate_value, fs_has_free_space, parse_options
|
35
|
+
from swift.common.constraints import valid_timestamp, check_utf8, \
|
36
|
+
check_drive, AUTO_CREATE_ACCOUNT_PREFIX
|
35
37
|
from swift.common import constraints
|
36
38
|
from swift.common.db_replicator import ReplicatorRpc
|
37
39
|
from swift.common.base_storage_server import BaseStorageServer
|
@@ -42,6 +44,33 @@ from swift.common.swob import HTTPAccepted, HTTPBadRequest, \
|
|
42
44
|
HTTPPreconditionFailed, HTTPConflict, Request, \
|
43
45
|
HTTPInsufficientStorage, HTTPException, wsgi_to_str
|
44
46
|
from swift.common.request_helpers import is_sys_or_user_meta
|
47
|
+
from swift.common.wsgi import run_wsgi
|
48
|
+
|
49
|
+
|
50
|
+
def get_account_name_and_placement(req):
|
51
|
+
"""
|
52
|
+
Split and validate path for an account.
|
53
|
+
|
54
|
+
:param req: a swob request
|
55
|
+
|
56
|
+
:returns: a tuple of path parts as strings
|
57
|
+
"""
|
58
|
+
drive, part, account = split_and_validate_path(req, 3)
|
59
|
+
validate_internal_account(account)
|
60
|
+
return drive, part, account
|
61
|
+
|
62
|
+
|
63
|
+
def get_container_name_and_placement(req):
|
64
|
+
"""
|
65
|
+
Split and validate path for a container.
|
66
|
+
|
67
|
+
:param req: a swob request
|
68
|
+
|
69
|
+
:returns: a tuple of path parts as strings
|
70
|
+
"""
|
71
|
+
drive, part, account, container = split_and_validate_path(req, 3, 4)
|
72
|
+
validate_internal_container(account, container)
|
73
|
+
return drive, part, account, container
|
45
74
|
|
46
75
|
|
47
76
|
class AccountController(BaseStorageServer):
|
@@ -58,10 +87,12 @@ class AccountController(BaseStorageServer):
|
|
58
87
|
self.replicator_rpc = ReplicatorRpc(self.root, DATADIR, AccountBroker,
|
59
88
|
self.mount_check,
|
60
89
|
logger=self.logger)
|
61
|
-
self.auto_create_account_prefix =
|
62
|
-
|
90
|
+
self.auto_create_account_prefix = AUTO_CREATE_ACCOUNT_PREFIX
|
91
|
+
|
63
92
|
swift.common.db.DB_PREALLOCATION = \
|
64
93
|
config_true_value(conf.get('db_preallocation', 'f'))
|
94
|
+
swift.common.db.QUERY_LOGGING = \
|
95
|
+
config_true_value(conf.get('db_query_logging', 'f'))
|
65
96
|
self.fallocate_reserve, self.fallocate_is_percent = \
|
66
97
|
config_fallocate_value(conf.get('fallocate_reserve', '1%'))
|
67
98
|
|
@@ -96,7 +127,7 @@ class AccountController(BaseStorageServer):
|
|
96
127
|
@timing_stats()
|
97
128
|
def DELETE(self, req):
|
98
129
|
"""Handle HTTP DELETE request."""
|
99
|
-
drive, part, account =
|
130
|
+
drive, part, account = get_account_name_and_placement(req)
|
100
131
|
try:
|
101
132
|
check_drive(self.root, drive, self.mount_check)
|
102
133
|
except ValueError:
|
@@ -120,7 +151,7 @@ class AccountController(BaseStorageServer):
|
|
120
151
|
@timing_stats()
|
121
152
|
def PUT(self, req):
|
122
153
|
"""Handle HTTP PUT request."""
|
123
|
-
drive, part, account, container =
|
154
|
+
drive, part, account, container = get_container_name_and_placement(req)
|
124
155
|
try:
|
125
156
|
check_drive(self.root, drive, self.mount_check)
|
126
157
|
except ValueError:
|
@@ -145,8 +176,9 @@ class AccountController(BaseStorageServer):
|
|
145
176
|
broker.initialize(timestamp.internal)
|
146
177
|
except DatabaseAlreadyExists:
|
147
178
|
pass
|
148
|
-
if req.headers.get('x-account-override-deleted', 'no').lower() !=
|
149
|
-
'yes' and broker.is_deleted()
|
179
|
+
if (req.headers.get('x-account-override-deleted', 'no').lower() !=
|
180
|
+
'yes' and broker.is_deleted()) \
|
181
|
+
or not os.path.exists(broker.db_file):
|
150
182
|
return HTTPNotFound(request=req)
|
151
183
|
broker.put_container(container, req.headers['x-put-timestamp'],
|
152
184
|
req.headers['x-delete-timestamp'],
|
@@ -185,7 +217,7 @@ class AccountController(BaseStorageServer):
|
|
185
217
|
@timing_stats()
|
186
218
|
def HEAD(self, req):
|
187
219
|
"""Handle HTTP HEAD request."""
|
188
|
-
drive, part, account =
|
220
|
+
drive, part, account = get_account_name_and_placement(req)
|
189
221
|
out_content_type = listing_formats.get_listing_content_type(req)
|
190
222
|
try:
|
191
223
|
check_drive(self.root, drive, self.mount_check)
|
@@ -198,25 +230,18 @@ class AccountController(BaseStorageServer):
|
|
198
230
|
return self._deleted_response(broker, req, HTTPNotFound)
|
199
231
|
headers = get_response_headers(broker)
|
200
232
|
headers['Content-Type'] = out_content_type
|
233
|
+
headers['Content-Length'] = 0
|
201
234
|
return HTTPNoContent(request=req, headers=headers, charset='utf-8')
|
202
235
|
|
203
236
|
@public
|
204
237
|
@timing_stats()
|
205
238
|
def GET(self, req):
|
206
239
|
"""Handle HTTP GET request."""
|
207
|
-
drive, part, account =
|
240
|
+
drive, part, account = get_account_name_and_placement(req)
|
208
241
|
prefix = get_param(req, 'prefix')
|
209
242
|
delimiter = get_param(req, 'delimiter')
|
210
|
-
limit = constraints.ACCOUNT_LISTING_LIMIT
|
211
|
-
given_limit = get_param(req, 'limit')
|
212
243
|
reverse = config_true_value(get_param(req, 'reverse'))
|
213
|
-
|
214
|
-
limit = int(given_limit)
|
215
|
-
if limit > constraints.ACCOUNT_LISTING_LIMIT:
|
216
|
-
return HTTPPreconditionFailed(
|
217
|
-
request=req,
|
218
|
-
body='Maximum limit is %d' %
|
219
|
-
constraints.ACCOUNT_LISTING_LIMIT)
|
244
|
+
limit = constrain_req_limit(req, constraints.ACCOUNT_LISTING_LIMIT)
|
220
245
|
marker = get_param(req, 'marker', '')
|
221
246
|
end_marker = get_param(req, 'end_marker')
|
222
247
|
out_content_type = listing_formats.get_listing_content_type(req)
|
@@ -262,7 +287,7 @@ class AccountController(BaseStorageServer):
|
|
262
287
|
@timing_stats()
|
263
288
|
def POST(self, req):
|
264
289
|
"""Handle HTTP POST request."""
|
265
|
-
drive, part, account =
|
290
|
+
drive, part, account = get_account_name_and_placement(req)
|
266
291
|
req_timestamp = valid_timestamp(req)
|
267
292
|
try:
|
268
293
|
check_drive(self.root, drive, self.mount_check)
|
@@ -280,8 +305,8 @@ class AccountController(BaseStorageServer):
|
|
280
305
|
start_time = time.time()
|
281
306
|
req = Request(env)
|
282
307
|
self.logger.txn_id = req.headers.get('x-trans-id', None)
|
283
|
-
if not check_utf8(wsgi_to_str(req.path_info)):
|
284
|
-
res = HTTPPreconditionFailed(body='Invalid UTF8
|
308
|
+
if not check_utf8(wsgi_to_str(req.path_info), internal=True):
|
309
|
+
res = HTTPPreconditionFailed(body='Invalid UTF8')
|
285
310
|
else:
|
286
311
|
try:
|
287
312
|
# disallow methods which are not publicly accessible
|
@@ -292,8 +317,8 @@ class AccountController(BaseStorageServer):
|
|
292
317
|
except HTTPException as error_response:
|
293
318
|
res = error_response
|
294
319
|
except (Exception, Timeout):
|
295
|
-
self.logger.exception(
|
296
|
-
|
320
|
+
self.logger.exception('ERROR __call__ error with %(method)s'
|
321
|
+
' %(path)s ',
|
297
322
|
{'method': req.method, 'path': req.path})
|
298
323
|
res = HTTPInternalServerError(body=traceback.format_exc())
|
299
324
|
if self.log_requests:
|
@@ -317,3 +342,12 @@ def app_factory(global_conf, **local_conf):
|
|
317
342
|
conf = global_conf.copy()
|
318
343
|
conf.update(local_conf)
|
319
344
|
return AccountController(conf)
|
345
|
+
|
346
|
+
|
347
|
+
def main():
|
348
|
+
conf_file, options = parse_options(test_config=True)
|
349
|
+
sys.exit(run_wsgi(conf_file, 'account-server', **options))
|
350
|
+
|
351
|
+
|
352
|
+
if __name__ == '__main__':
|
353
|
+
main()
|
swift/account/utils.py
CHANGED
@@ -15,8 +15,7 @@
|
|
15
15
|
|
16
16
|
import json
|
17
17
|
|
18
|
-
import
|
19
|
-
|
18
|
+
from swift.common import constraints
|
20
19
|
from swift.common.middleware import listing_formats
|
21
20
|
from swift.common.swob import HTTPOk, HTTPNoContent, str_to_wsgi
|
22
21
|
from swift.common.utils import Timestamp
|
@@ -71,25 +70,43 @@ def get_response_headers(broker):
|
|
71
70
|
|
72
71
|
|
73
72
|
def account_listing_response(account, req, response_content_type, broker=None,
|
74
|
-
limit=
|
75
|
-
|
73
|
+
limit=constraints.ACCOUNT_LISTING_LIMIT,
|
74
|
+
marker='', end_marker='', prefix='', delimiter='',
|
75
|
+
reverse=False):
|
76
76
|
if broker is None:
|
77
77
|
broker = FakeAccountBroker()
|
78
78
|
|
79
79
|
resp_headers = get_response_headers(broker)
|
80
80
|
|
81
81
|
account_list = broker.list_containers_iter(limit, marker, end_marker,
|
82
|
-
prefix, delimiter, reverse
|
82
|
+
prefix, delimiter, reverse,
|
83
|
+
req.allow_reserved_names)
|
83
84
|
data = []
|
84
|
-
for (name, object_count, bytes_used, put_timestamp,
|
85
|
+
for (name, object_count, bytes_used, put_timestamp,
|
86
|
+
storage_policy_index, is_subdir) \
|
85
87
|
in account_list:
|
86
|
-
name_ = name.decode('utf8') if six.PY2 else name
|
87
88
|
if is_subdir:
|
88
|
-
data.append({'subdir':
|
89
|
+
data.append({'subdir': name})
|
89
90
|
else:
|
90
|
-
|
91
|
-
|
92
|
-
|
91
|
+
container = {
|
92
|
+
'name': name,
|
93
|
+
'count': object_count,
|
94
|
+
'bytes': bytes_used,
|
95
|
+
'last_modified': Timestamp(put_timestamp).isoformat}
|
96
|
+
# Add the container's storage policy to the response, unless
|
97
|
+
# storage_policy_index was not found in POLICIES, which means
|
98
|
+
# the storage policy is missing from the Swift configuration
|
99
|
+
# or otherwise could not be determined.
|
100
|
+
#
|
101
|
+
# The storage policy should always be returned when
|
102
|
+
# everything is configured correctly, but clients are
|
103
|
+
# expected to be able to handle this case regardless,
|
104
|
+
# if only to support older versions of swift.
|
105
|
+
if storage_policy_index in POLICIES:
|
106
|
+
container['storage_policy'] = (
|
107
|
+
POLICIES[storage_policy_index].name
|
108
|
+
)
|
109
|
+
data.append(container)
|
93
110
|
if response_content_type.endswith('/xml'):
|
94
111
|
account_list = listing_formats.account_to_xml(data, account)
|
95
112
|
ret = HTTPOk(body=account_list, request=req, headers=resp_headers)
|
@@ -1,4 +1,4 @@
|
|
1
|
-
|
1
|
+
#!/usr/bin/env python
|
2
2
|
# Copyright (c) 2010-2012 OpenStack Foundation
|
3
3
|
#
|
4
4
|
# Licensed under the Apache License, Version 2.0 (the "License");
|
@@ -14,20 +14,19 @@
|
|
14
14
|
# See the License for the specific language governing permissions and
|
15
15
|
# limitations under the License.
|
16
16
|
|
17
|
-
from __future__ import print_function
|
18
17
|
import os
|
19
18
|
import sys
|
20
|
-
from hashlib import md5
|
21
19
|
import getopt
|
22
20
|
from itertools import chain
|
23
21
|
|
24
22
|
import json
|
25
23
|
from eventlet.greenpool import GreenPool
|
26
24
|
from eventlet.event import Event
|
27
|
-
from
|
25
|
+
from urllib.parse import quote
|
28
26
|
|
29
27
|
from swift.common.ring import Ring
|
30
28
|
from swift.common.utils import split_path
|
29
|
+
from swift.common.utils.base import md5
|
31
30
|
from swift.common.bufferedhttp import http_connect
|
32
31
|
|
33
32
|
|
@@ -91,7 +90,7 @@ class Auditor(object):
|
|
91
90
|
conn = http_connect(node['ip'], node['port'],
|
92
91
|
node['device'], part, 'GET', path, {})
|
93
92
|
resp = conn.getresponse()
|
94
|
-
calc_hash = md5()
|
93
|
+
calc_hash = md5(usedforsecurity=False)
|
95
94
|
chunk = True
|
96
95
|
while chunk:
|
97
96
|
chunk = resp.read(8192)
|
@@ -100,15 +99,15 @@ class Auditor(object):
|
|
100
99
|
if resp.status // 100 != 2:
|
101
100
|
self.object_not_found += 1
|
102
101
|
consistent = False
|
103
|
-
print(' Bad status GETting object "%s" on %s/%s'
|
104
|
-
% (
|
102
|
+
print(' Bad status %s GETting object "%s" on %s/%s'
|
103
|
+
% (resp.status, path,
|
104
|
+
node['ip'], node['device']))
|
105
105
|
continue
|
106
106
|
if resp.getheader('ETag').strip('"') != calc_hash:
|
107
107
|
self.object_checksum_mismatch += 1
|
108
108
|
consistent = False
|
109
109
|
print(' MD5 does not match etag for "%s" on %s/%s'
|
110
110
|
% (path, node['ip'], node['device']))
|
111
|
-
etags.append((resp.getheader('ETag'), node))
|
112
111
|
else:
|
113
112
|
conn = http_connect(node['ip'], node['port'],
|
114
113
|
node['device'], part, 'HEAD',
|
@@ -117,9 +116,16 @@ class Auditor(object):
|
|
117
116
|
if resp.status // 100 != 2:
|
118
117
|
self.object_not_found += 1
|
119
118
|
consistent = False
|
120
|
-
print(' Bad status HEADing object "%s" on %s/%s'
|
121
|
-
% (
|
119
|
+
print(' Bad status %s HEADing object "%s" on %s/%s'
|
120
|
+
% (resp.status, path,
|
121
|
+
node['ip'], node['device']))
|
122
122
|
continue
|
123
|
+
|
124
|
+
override_etag = resp.getheader(
|
125
|
+
'X-Object-Sysmeta-Container-Update-Override-Etag')
|
126
|
+
if override_etag:
|
127
|
+
etags.append((override_etag, node))
|
128
|
+
else:
|
123
129
|
etags.append((resp.getheader('ETag'), node))
|
124
130
|
except Exception:
|
125
131
|
self.object_exceptions += 1
|
@@ -252,14 +258,14 @@ class Auditor(object):
|
|
252
258
|
self.account_not_found += 1
|
253
259
|
consistent = False
|
254
260
|
print(" Bad status GETting account '%s' "
|
255
|
-
" from %
|
261
|
+
" from %s:%s" %
|
256
262
|
(account, node['ip'], node['device']))
|
257
263
|
break
|
258
264
|
results = json.loads(resp.read())
|
259
265
|
except Exception:
|
260
266
|
self.account_exceptions += 1
|
261
267
|
consistent = False
|
262
|
-
print(" Exception GETting account '%s' on %
|
268
|
+
print(" Exception GETting account '%s' on %s:%s" %
|
263
269
|
(account, node['ip'], node['device']))
|
264
270
|
break
|
265
271
|
if node_id not in responses:
|
@@ -352,7 +358,7 @@ class Auditor(object):
|
|
352
358
|
_print_stat("MD5 Mismatch", self.object_checksum_mismatch)
|
353
359
|
|
354
360
|
|
355
|
-
|
361
|
+
def main():
|
356
362
|
try:
|
357
363
|
optlist, args = getopt.getopt(sys.argv[1:], 'c:r:e:d')
|
358
364
|
except getopt.GetoptError as err:
|
@@ -377,3 +383,7 @@ if __name__ == '__main__':
|
|
377
383
|
auditor.audit(*split_path(path, 1, 3, True))
|
378
384
|
auditor.wait()
|
379
385
|
auditor.print_stats()
|
386
|
+
|
387
|
+
|
388
|
+
if __name__ == '__main__':
|
389
|
+
main()
|
@@ -1,4 +1,4 @@
|
|
1
|
-
|
1
|
+
#!/usr/bin/env python
|
2
2
|
# Licensed under the Apache License, Version 2.0 (the "License");
|
3
3
|
# you may not use this file except in compliance with the License.
|
4
4
|
# You may obtain a copy of the License at
|
@@ -12,7 +12,6 @@
|
|
12
12
|
# See the License for the specific language governing permissions and
|
13
13
|
# limitations under the License.
|
14
14
|
|
15
|
-
from __future__ import print_function
|
16
15
|
import optparse
|
17
16
|
import os
|
18
17
|
import sys
|
@@ -86,5 +85,6 @@ def main():
|
|
86
85
|
print('# %s = %s' % (k, v))
|
87
86
|
print()
|
88
87
|
|
88
|
+
|
89
89
|
if __name__ == "__main__":
|
90
90
|
sys.exit(main())
|
swift/cli/container_deleter.py
CHANGED
@@ -28,7 +28,6 @@ import argparse
|
|
28
28
|
import io
|
29
29
|
import itertools
|
30
30
|
import json
|
31
|
-
import six
|
32
31
|
import time
|
33
32
|
|
34
33
|
from swift.common.internal_client import InternalClient
|
@@ -50,17 +49,11 @@ def make_delete_jobs(account, container, objects, timestamp):
|
|
50
49
|
:returns: list of dicts appropriate for an UPDATE request to an
|
51
50
|
expiring-object queue
|
52
51
|
'''
|
53
|
-
if six.PY2:
|
54
|
-
if isinstance(account, str):
|
55
|
-
account = account.decode('utf8')
|
56
|
-
if isinstance(container, str):
|
57
|
-
container = container.decode('utf8')
|
58
52
|
return [
|
59
53
|
{
|
60
54
|
'name': build_task_obj(
|
61
55
|
timestamp, account, container,
|
62
|
-
obj
|
63
|
-
else obj),
|
56
|
+
obj, high_precision=True),
|
64
57
|
'deleted': 0,
|
65
58
|
'created_at': timestamp.internal,
|
66
59
|
'etag': MD5_OF_EMPTY_STRING,
|
@@ -133,7 +126,7 @@ def mark_for_deletion(swift, account, container, marker, end_marker,
|
|
133
126
|
return enqueue_deletes()
|
134
127
|
|
135
128
|
|
136
|
-
def main():
|
129
|
+
def main(args=None):
|
137
130
|
parser = argparse.ArgumentParser(
|
138
131
|
description=__doc__,
|
139
132
|
formatter_class=argparse.RawTextHelpFormatter)
|
@@ -156,10 +149,11 @@ def main():
|
|
156
149
|
parser.add_argument(
|
157
150
|
'--timestamp', type=Timestamp, default=Timestamp.now(),
|
158
151
|
help='delete all objects as of this time (default: now)')
|
159
|
-
args = parser.parse_args()
|
152
|
+
args = parser.parse_args(args)
|
160
153
|
|
161
154
|
swift = InternalClient(
|
162
|
-
args.config, 'Swift Container Deleter', args.request_tries
|
155
|
+
args.config, 'Swift Container Deleter', args.request_tries,
|
156
|
+
global_conf={'log_name': 'container-deleter-ic'})
|
163
157
|
for deleted, marker in mark_for_deletion(
|
164
158
|
swift, args.account, args.container,
|
165
159
|
args.marker, args.end_marker, args.prefix, args.timestamp):
|
@@ -1,4 +1,4 @@
|
|
1
|
-
|
1
|
+
#!/usr/bin/env python
|
2
2
|
# Copyright (c) 2010-2012 OpenStack Foundation
|
3
3
|
#
|
4
4
|
# Licensed under the Apache License, Version 2.0 (the "License");
|
@@ -13,7 +13,6 @@
|
|
13
13
|
# implied.
|
14
14
|
# See the License for the specific language governing permissions and
|
15
15
|
# limitations under the License.
|
16
|
-
from __future__ import print_function
|
17
16
|
|
18
17
|
import io
|
19
18
|
import traceback
|
@@ -23,9 +22,7 @@ from time import time
|
|
23
22
|
|
24
23
|
from eventlet import GreenPool, patcher, sleep
|
25
24
|
from eventlet.pools import Pool
|
26
|
-
import
|
27
|
-
from six.moves import range
|
28
|
-
from six.moves.configparser import ConfigParser
|
25
|
+
from configparser import ConfigParser
|
29
26
|
|
30
27
|
from swift.common.internal_client import SimpleClient
|
31
28
|
from swift.common.ring import Ring
|
@@ -53,7 +50,7 @@ def put_object(connpool, container, obj, report):
|
|
53
50
|
global retries_done
|
54
51
|
try:
|
55
52
|
with connpool.item() as conn:
|
56
|
-
data = io.BytesIO(obj
|
53
|
+
data = io.BytesIO(obj.encode('utf8'))
|
57
54
|
conn.put_object(container, obj, data,
|
58
55
|
headers={'x-object-meta-dispersion': obj})
|
59
56
|
retries_done += conn.attempts - 1
|
@@ -81,7 +78,7 @@ def report(success):
|
|
81
78
|
stdout.flush()
|
82
79
|
|
83
80
|
|
84
|
-
|
81
|
+
def main():
|
85
82
|
global begun, created, item_type, next_report, need_to_create, retries_done
|
86
83
|
patcher.monkey_patch()
|
87
84
|
try:
|
@@ -281,3 +278,7 @@ Usage: %%prog [options] [conf_file]
|
|
281
278
|
print('\r\x1B[KTotal object coverage is now %.2f%%.' %
|
282
279
|
((float(obj_coverage) / object_ring.partition_count * 100)))
|
283
280
|
stdout.flush()
|
281
|
+
|
282
|
+
|
283
|
+
if __name__ == '__main__':
|
284
|
+
main()
|
swift/cli/dispersion_report.py
CHANGED
@@ -14,10 +14,9 @@
|
|
14
14
|
# See the License for the specific language governing permissions and
|
15
15
|
# limitations under the License.
|
16
16
|
|
17
|
-
from __future__ import print_function
|
18
17
|
import json
|
19
18
|
from collections import defaultdict
|
20
|
-
from
|
19
|
+
from configparser import ConfigParser
|
21
20
|
from optparse import OptionParser
|
22
21
|
from sys import exit, stdout, stderr
|
23
22
|
from time import time
|
@@ -26,14 +25,11 @@ from eventlet import GreenPool, hubs, patcher, Timeout
|
|
26
25
|
from eventlet.pools import Pool
|
27
26
|
|
28
27
|
from swift.common import direct_client
|
29
|
-
try:
|
30
|
-
from swiftclient import get_auth
|
31
|
-
except ImportError:
|
32
|
-
from swift.common.internal_client import get_auth
|
33
28
|
from swift.common.internal_client import SimpleClient
|
34
29
|
from swift.common.ring import Ring
|
35
30
|
from swift.common.exceptions import ClientException
|
36
|
-
from swift.common.utils import compute_eta, get_time_units,
|
31
|
+
from swift.common.utils import compute_eta, get_time_units, \
|
32
|
+
config_true_value, node_to_string
|
37
33
|
from swift.common.storage_policy import POLICIES
|
38
34
|
|
39
35
|
|
@@ -93,7 +89,7 @@ def container_dispersion_report(coropool, connpool, account, container_ring,
|
|
93
89
|
def direct(container, part, nodes):
|
94
90
|
found_count = 0
|
95
91
|
for node in nodes:
|
96
|
-
error_log = get_error_log(
|
92
|
+
error_log = get_error_log(node_to_string(node))
|
97
93
|
try:
|
98
94
|
attempts, _junk = direct_client.retry(
|
99
95
|
direct_client.direct_head_container, node, part, account,
|
@@ -205,7 +201,7 @@ def object_dispersion_report(coropool, connpool, account, object_ring,
|
|
205
201
|
def direct(obj, part, nodes):
|
206
202
|
found_count = 0
|
207
203
|
for node in nodes:
|
208
|
-
error_log = get_error_log(
|
204
|
+
error_log = get_error_log(node_to_string(node))
|
209
205
|
try:
|
210
206
|
attempts, _junk = direct_client.retry(
|
211
207
|
direct_client.direct_head_object, node, part, account,
|
@@ -365,6 +361,11 @@ Usage: %%prog [options] [conf_file]
|
|
365
361
|
|
366
362
|
|
367
363
|
def generate_report(conf, policy_name=None):
|
364
|
+
try:
|
365
|
+
# Delay importing so urllib3 will import monkey-patched modules
|
366
|
+
from swiftclient import get_auth
|
367
|
+
except ImportError:
|
368
|
+
from swift.common.internal_client import get_auth
|
368
369
|
global json_output
|
369
370
|
json_output = config_true_value(conf.get('dump_json', 'no'))
|
370
371
|
if policy_name is None:
|