s3_cmd_bin 0.0.1
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.
- data/.gitignore +17 -0
- data/Gemfile +3 -0
- data/LICENSE.txt +22 -0
- data/README.md +28 -0
- data/Rakefile +1 -0
- data/lib/s3_cmd_bin/version.rb +3 -0
- data/lib/s3_cmd_bin.rb +15 -0
- data/resources/ChangeLog +1462 -0
- data/resources/INSTALL +97 -0
- data/resources/LICENSE +339 -0
- data/resources/MANIFEST.in +2 -0
- data/resources/Makefile +4 -0
- data/resources/NEWS +234 -0
- data/resources/README +342 -0
- data/resources/S3/ACL.py +224 -0
- data/resources/S3/ACL.pyc +0 -0
- data/resources/S3/AccessLog.py +92 -0
- data/resources/S3/AccessLog.pyc +0 -0
- data/resources/S3/BidirMap.py +42 -0
- data/resources/S3/BidirMap.pyc +0 -0
- data/resources/S3/CloudFront.py +773 -0
- data/resources/S3/CloudFront.pyc +0 -0
- data/resources/S3/Config.py +294 -0
- data/resources/S3/Config.pyc +0 -0
- data/resources/S3/ConnMan.py +71 -0
- data/resources/S3/ConnMan.pyc +0 -0
- data/resources/S3/Exceptions.py +88 -0
- data/resources/S3/Exceptions.pyc +0 -0
- data/resources/S3/FileDict.py +53 -0
- data/resources/S3/FileDict.pyc +0 -0
- data/resources/S3/FileLists.py +517 -0
- data/resources/S3/FileLists.pyc +0 -0
- data/resources/S3/HashCache.py +53 -0
- data/resources/S3/HashCache.pyc +0 -0
- data/resources/S3/MultiPart.py +137 -0
- data/resources/S3/MultiPart.pyc +0 -0
- data/resources/S3/PkgInfo.py +14 -0
- data/resources/S3/PkgInfo.pyc +0 -0
- data/resources/S3/Progress.py +173 -0
- data/resources/S3/Progress.pyc +0 -0
- data/resources/S3/S3.py +979 -0
- data/resources/S3/S3.pyc +0 -0
- data/resources/S3/S3Uri.py +223 -0
- data/resources/S3/S3Uri.pyc +0 -0
- data/resources/S3/SimpleDB.py +178 -0
- data/resources/S3/SortedDict.py +66 -0
- data/resources/S3/SortedDict.pyc +0 -0
- data/resources/S3/Utils.py +462 -0
- data/resources/S3/Utils.pyc +0 -0
- data/resources/S3/__init__.py +0 -0
- data/resources/S3/__init__.pyc +0 -0
- data/resources/TODO +52 -0
- data/resources/artwork/AtomicClockRadio.ttf +0 -0
- data/resources/artwork/TypeRa.ttf +0 -0
- data/resources/artwork/site-top-full-size.xcf +0 -0
- data/resources/artwork/site-top-label-download.png +0 -0
- data/resources/artwork/site-top-label-s3cmd.png +0 -0
- data/resources/artwork/site-top-label-s3sync.png +0 -0
- data/resources/artwork/site-top-s3tools-logo.png +0 -0
- data/resources/artwork/site-top.jpg +0 -0
- data/resources/artwork/site-top.png +0 -0
- data/resources/artwork/site-top.xcf +0 -0
- data/resources/format-manpage.pl +196 -0
- data/resources/magic +63 -0
- data/resources/run-tests.py +537 -0
- data/resources/s3cmd +2116 -0
- data/resources/s3cmd.1 +435 -0
- data/resources/s3db +55 -0
- data/resources/setup.cfg +2 -0
- data/resources/setup.py +80 -0
- data/resources/testsuite.tar.gz +0 -0
- data/resources/upload-to-sf.sh +7 -0
- data/s3_cmd_bin.gemspec +23 -0
- metadata +152 -0
@@ -0,0 +1,537 @@
|
|
1
|
+
#!/usr/bin/env python
|
2
|
+
# -*- coding=utf-8 -*-
|
3
|
+
|
4
|
+
## Amazon S3cmd - testsuite
|
5
|
+
## Author: Michal Ludvig <michal@logix.cz>
|
6
|
+
## http://www.logix.cz/michal
|
7
|
+
## License: GPL Version 2
|
8
|
+
|
9
|
+
import sys
|
10
|
+
import os
|
11
|
+
import re
|
12
|
+
from subprocess import Popen, PIPE, STDOUT
|
13
|
+
import locale
|
14
|
+
import pwd
|
15
|
+
|
16
|
+
count_pass = 0
|
17
|
+
count_fail = 0
|
18
|
+
count_skip = 0
|
19
|
+
|
20
|
+
test_counter = 0
|
21
|
+
run_tests = []
|
22
|
+
exclude_tests = []
|
23
|
+
|
24
|
+
verbose = False
|
25
|
+
|
26
|
+
if os.name == "posix":
|
27
|
+
have_wget = True
|
28
|
+
elif os.name == "nt":
|
29
|
+
have_wget = False
|
30
|
+
else:
|
31
|
+
print "Unknown platform: %s" % os.name
|
32
|
+
sys.exit(1)
|
33
|
+
|
34
|
+
## Unpack testsuite/ directory
|
35
|
+
if not os.path.isdir('testsuite') and os.path.isfile('testsuite.tar.gz'):
|
36
|
+
os.system("tar -xz -f testsuite.tar.gz")
|
37
|
+
if not os.path.isdir('testsuite'):
|
38
|
+
print "Something went wrong while unpacking testsuite.tar.gz"
|
39
|
+
sys.exit(1)
|
40
|
+
|
41
|
+
os.system("tar -xf testsuite/checksum.tar -C testsuite")
|
42
|
+
if not os.path.isfile('testsuite/checksum/cksum33.txt'):
|
43
|
+
print "Something went wrong while unpacking testsuite/checkum.tar"
|
44
|
+
sys.exit(1)
|
45
|
+
|
46
|
+
## Fix up permissions for permission-denied tests
|
47
|
+
os.chmod("testsuite/permission-tests/permission-denied-dir", 0444)
|
48
|
+
os.chmod("testsuite/permission-tests/permission-denied.txt", 0000)
|
49
|
+
|
50
|
+
## Patterns for Unicode tests
|
51
|
+
patterns = {}
|
52
|
+
patterns['UTF-8'] = u"ŪņЇЌœđЗ/☺ unicode € rocks ™"
|
53
|
+
patterns['GBK'] = u"12月31日/1-特色條目"
|
54
|
+
|
55
|
+
encoding = locale.getpreferredencoding()
|
56
|
+
if not encoding:
|
57
|
+
print "Guessing current system encoding failed. Consider setting $LANG variable."
|
58
|
+
sys.exit(1)
|
59
|
+
else:
|
60
|
+
print "System encoding: " + encoding
|
61
|
+
|
62
|
+
have_encoding = os.path.isdir('testsuite/encodings/' + encoding)
|
63
|
+
if not have_encoding and os.path.isfile('testsuite/encodings/%s.tar.gz' % encoding):
|
64
|
+
os.system("tar xvz -C testsuite/encodings -f testsuite/encodings/%s.tar.gz" % encoding)
|
65
|
+
have_encoding = os.path.isdir('testsuite/encodings/' + encoding)
|
66
|
+
|
67
|
+
if have_encoding:
|
68
|
+
#enc_base_remote = "%s/xyz/%s/" % (pbucket(1), encoding)
|
69
|
+
enc_pattern = patterns[encoding]
|
70
|
+
else:
|
71
|
+
print encoding + " specific files not found."
|
72
|
+
|
73
|
+
if not os.path.isdir('testsuite/crappy-file-name'):
|
74
|
+
os.system("tar xvz -C testsuite -f testsuite/crappy-file-name.tar.gz")
|
75
|
+
# TODO: also unpack if the tarball is newer than the directory timestamp
|
76
|
+
# for instance when a new version was pulled from SVN.
|
77
|
+
|
78
|
+
def test(label, cmd_args = [], retcode = 0, must_find = [], must_not_find = [], must_find_re = [], must_not_find_re = []):
|
79
|
+
def command_output():
|
80
|
+
print "----"
|
81
|
+
print " ".join([arg.find(" ")>=0 and "'%s'" % arg or arg for arg in cmd_args])
|
82
|
+
print "----"
|
83
|
+
print stdout
|
84
|
+
print "----"
|
85
|
+
|
86
|
+
def failure(message = ""):
|
87
|
+
global count_fail
|
88
|
+
if message:
|
89
|
+
message = " (%r)" % message
|
90
|
+
print "\x1b[31;1mFAIL%s\x1b[0m" % (message)
|
91
|
+
count_fail += 1
|
92
|
+
command_output()
|
93
|
+
#return 1
|
94
|
+
sys.exit(1)
|
95
|
+
def success(message = ""):
|
96
|
+
global count_pass
|
97
|
+
if message:
|
98
|
+
message = " (%r)" % message
|
99
|
+
print "\x1b[32;1mOK\x1b[0m%s" % (message)
|
100
|
+
count_pass += 1
|
101
|
+
if verbose:
|
102
|
+
command_output()
|
103
|
+
return 0
|
104
|
+
def skip(message = ""):
|
105
|
+
global count_skip
|
106
|
+
if message:
|
107
|
+
message = " (%r)" % message
|
108
|
+
print "\x1b[33;1mSKIP\x1b[0m%s" % (message)
|
109
|
+
count_skip += 1
|
110
|
+
return 0
|
111
|
+
def compile_list(_list, regexps = False):
|
112
|
+
if regexps == False:
|
113
|
+
_list = [re.escape(item.encode(encoding, "replace")) for item in _list]
|
114
|
+
|
115
|
+
return [re.compile(item, re.MULTILINE) for item in _list]
|
116
|
+
|
117
|
+
global test_counter
|
118
|
+
test_counter += 1
|
119
|
+
print ("%3d %s " % (test_counter, label)).ljust(30, "."),
|
120
|
+
sys.stdout.flush()
|
121
|
+
|
122
|
+
if run_tests.count(test_counter) == 0 or exclude_tests.count(test_counter) > 0:
|
123
|
+
return skip()
|
124
|
+
|
125
|
+
if not cmd_args:
|
126
|
+
return skip()
|
127
|
+
|
128
|
+
p = Popen(cmd_args, stdout = PIPE, stderr = STDOUT, universal_newlines = True)
|
129
|
+
stdout, stderr = p.communicate()
|
130
|
+
if retcode != p.returncode:
|
131
|
+
return failure("retcode: %d, expected: %d" % (p.returncode, retcode))
|
132
|
+
|
133
|
+
if type(must_find) not in [ list, tuple ]: must_find = [must_find]
|
134
|
+
if type(must_find_re) not in [ list, tuple ]: must_find_re = [must_find_re]
|
135
|
+
if type(must_not_find) not in [ list, tuple ]: must_not_find = [must_not_find]
|
136
|
+
if type(must_not_find_re) not in [ list, tuple ]: must_not_find_re = [must_not_find_re]
|
137
|
+
|
138
|
+
find_list = []
|
139
|
+
find_list.extend(compile_list(must_find))
|
140
|
+
find_list.extend(compile_list(must_find_re, regexps = True))
|
141
|
+
find_list_patterns = []
|
142
|
+
find_list_patterns.extend(must_find)
|
143
|
+
find_list_patterns.extend(must_find_re)
|
144
|
+
|
145
|
+
not_find_list = []
|
146
|
+
not_find_list.extend(compile_list(must_not_find))
|
147
|
+
not_find_list.extend(compile_list(must_not_find_re, regexps = True))
|
148
|
+
not_find_list_patterns = []
|
149
|
+
not_find_list_patterns.extend(must_not_find)
|
150
|
+
not_find_list_patterns.extend(must_not_find_re)
|
151
|
+
|
152
|
+
for index in range(len(find_list)):
|
153
|
+
match = find_list[index].search(stdout)
|
154
|
+
if not match:
|
155
|
+
return failure("pattern not found: %s" % find_list_patterns[index])
|
156
|
+
for index in range(len(not_find_list)):
|
157
|
+
match = not_find_list[index].search(stdout)
|
158
|
+
if match:
|
159
|
+
return failure("pattern found: %s (match: %s)" % (not_find_list_patterns[index], match.group(0)))
|
160
|
+
|
161
|
+
return success()
|
162
|
+
|
163
|
+
def test_s3cmd(label, cmd_args = [], **kwargs):
|
164
|
+
if not cmd_args[0].endswith("s3cmd"):
|
165
|
+
cmd_args.insert(0, "python")
|
166
|
+
cmd_args.insert(1, "s3cmd")
|
167
|
+
|
168
|
+
return test(label, cmd_args, **kwargs)
|
169
|
+
|
170
|
+
def test_mkdir(label, dir_name):
|
171
|
+
if os.name in ("posix", "nt"):
|
172
|
+
cmd = ['mkdir', '-p']
|
173
|
+
else:
|
174
|
+
print "Unknown platform: %s" % os.name
|
175
|
+
sys.exit(1)
|
176
|
+
cmd.append(dir_name)
|
177
|
+
return test(label, cmd)
|
178
|
+
|
179
|
+
def test_rmdir(label, dir_name):
|
180
|
+
if os.path.isdir(dir_name):
|
181
|
+
if os.name == "posix":
|
182
|
+
cmd = ['rm', '-rf']
|
183
|
+
elif os.name == "nt":
|
184
|
+
cmd = ['rmdir', '/s/q']
|
185
|
+
else:
|
186
|
+
print "Unknown platform: %s" % os.name
|
187
|
+
sys.exit(1)
|
188
|
+
cmd.append(dir_name)
|
189
|
+
return test(label, cmd)
|
190
|
+
else:
|
191
|
+
return test(label, [])
|
192
|
+
|
193
|
+
def test_flushdir(label, dir_name):
|
194
|
+
test_rmdir(label + "(rm)", dir_name)
|
195
|
+
return test_mkdir(label + "(mk)", dir_name)
|
196
|
+
|
197
|
+
def test_copy(label, src_file, dst_file):
|
198
|
+
if os.name == "posix":
|
199
|
+
cmd = ['cp', '-f']
|
200
|
+
elif os.name == "nt":
|
201
|
+
cmd = ['copy']
|
202
|
+
else:
|
203
|
+
print "Unknown platform: %s" % os.name
|
204
|
+
sys.exit(1)
|
205
|
+
cmd.append(src_file)
|
206
|
+
cmd.append(dst_file)
|
207
|
+
return test(label, cmd)
|
208
|
+
|
209
|
+
try:
|
210
|
+
pwd = pwd.getpwuid(os.getuid())
|
211
|
+
bucket_prefix = "%s.%s-" % (pwd.pw_name, pwd.pw_uid)
|
212
|
+
except:
|
213
|
+
bucket_prefix = ''
|
214
|
+
print "Using bucket prefix: '%s'" % bucket_prefix
|
215
|
+
|
216
|
+
argv = sys.argv[1:]
|
217
|
+
while argv:
|
218
|
+
arg = argv.pop(0)
|
219
|
+
if arg.startswith('--bucket-prefix='):
|
220
|
+
print "Usage: '--bucket-prefix PREFIX', not '--bucket-prefix=PREFIX'"
|
221
|
+
sys.exit(0)
|
222
|
+
if arg in ("-h", "--help"):
|
223
|
+
print "%s A B K..O -N" % sys.argv[0]
|
224
|
+
print "Run tests number A, B and K through to O, except for N"
|
225
|
+
sys.exit(0)
|
226
|
+
if arg in ("-l", "--list"):
|
227
|
+
exclude_tests = range(0, 999)
|
228
|
+
break
|
229
|
+
if arg in ("-v", "--verbose"):
|
230
|
+
verbose = True
|
231
|
+
continue
|
232
|
+
if arg in ("-p", "--bucket-prefix"):
|
233
|
+
try:
|
234
|
+
bucket_prefix = argv.pop(0)
|
235
|
+
except IndexError:
|
236
|
+
print "Bucket prefix option must explicitly supply a bucket name prefix"
|
237
|
+
sys.exit(0)
|
238
|
+
continue
|
239
|
+
if arg.find("..") >= 0:
|
240
|
+
range_idx = arg.find("..")
|
241
|
+
range_start = arg[:range_idx] or 0
|
242
|
+
range_end = arg[range_idx+2:] or 999
|
243
|
+
run_tests.extend(range(int(range_start), int(range_end) + 1))
|
244
|
+
elif arg.startswith("-"):
|
245
|
+
exclude_tests.append(int(arg[1:]))
|
246
|
+
else:
|
247
|
+
run_tests.append(int(arg))
|
248
|
+
|
249
|
+
if not run_tests:
|
250
|
+
run_tests = range(0, 999)
|
251
|
+
|
252
|
+
# helper functions for generating bucket names
|
253
|
+
def bucket(tail):
|
254
|
+
'''Test bucket name'''
|
255
|
+
label = 'autotest'
|
256
|
+
if str(tail) == '3':
|
257
|
+
label = 'Autotest'
|
258
|
+
return '%ss3cmd-%s-%s' % (bucket_prefix, label, tail)
|
259
|
+
|
260
|
+
def pbucket(tail):
|
261
|
+
'''Like bucket(), but prepends "s3://" for you'''
|
262
|
+
return 's3://' + bucket(tail)
|
263
|
+
|
264
|
+
## ====== Remove test buckets
|
265
|
+
test_s3cmd("Remove test buckets", ['rb', '-r', pbucket(1), pbucket(2), pbucket(3)],
|
266
|
+
must_find = [ "Bucket '%s/' removed" % pbucket(1),
|
267
|
+
"Bucket '%s/' removed" % pbucket(2),
|
268
|
+
"Bucket '%s/' removed" % pbucket(3) ])
|
269
|
+
|
270
|
+
|
271
|
+
## ====== Create one bucket (EU)
|
272
|
+
test_s3cmd("Create one bucket (EU)", ['mb', '--bucket-location=EU', pbucket(1)],
|
273
|
+
must_find = "Bucket '%s/' created" % pbucket(1))
|
274
|
+
|
275
|
+
|
276
|
+
|
277
|
+
## ====== Create multiple buckets
|
278
|
+
test_s3cmd("Create multiple buckets", ['mb', pbucket(2), pbucket(3)],
|
279
|
+
must_find = [ "Bucket '%s/' created" % pbucket(2), "Bucket '%s/' created" % pbucket(3)])
|
280
|
+
|
281
|
+
|
282
|
+
## ====== Invalid bucket name
|
283
|
+
test_s3cmd("Invalid bucket name", ["mb", "--bucket-location=EU", pbucket('EU')],
|
284
|
+
retcode = 1,
|
285
|
+
must_find = "ERROR: Parameter problem: Bucket name '%s' contains disallowed character" % bucket('EU'),
|
286
|
+
must_not_find_re = "Bucket.*created")
|
287
|
+
|
288
|
+
|
289
|
+
## ====== Buckets list
|
290
|
+
test_s3cmd("Buckets list", ["ls"],
|
291
|
+
must_find = [ "autotest-1", "autotest-2", "Autotest-3" ], must_not_find_re = "autotest-EU")
|
292
|
+
|
293
|
+
|
294
|
+
## ====== Sync to S3
|
295
|
+
test_s3cmd("Sync to S3", ['sync', 'testsuite/', pbucket(1) + '/xyz/', '--exclude', 'demo/*', '--exclude', '*.png', '--no-encrypt', '--exclude-from', 'testsuite/exclude.encodings' ],
|
296
|
+
must_find = [ "WARNING: 32 non-printable characters replaced in: crappy-file-name/non-printables ^A^B^C^D^E^F^G^H^I^J^K^L^M^N^O^P^Q^R^S^T^U^V^W^X^Y^Z^[^\^]^^^_^? +-[\]^<>%%\"'#{}`&?.end",
|
297
|
+
"WARNING: File can not be uploaded: testsuite/permission-tests/permission-denied.txt: Permission denied",
|
298
|
+
"stored as '%s/xyz/crappy-file-name/non-printables ^A^B^C^D^E^F^G^H^I^J^K^L^M^N^O^P^Q^R^S^T^U^V^W^X^Y^Z^[^\^]^^^_^? +-[\\]^<>%%%%\"'#{}`&?.end'" % pbucket(1) ],
|
299
|
+
must_not_find_re = [ "demo/", "\.png$", "permission-denied-dir" ])
|
300
|
+
|
301
|
+
if have_encoding:
|
302
|
+
## ====== Sync UTF-8 / GBK / ... to S3
|
303
|
+
test_s3cmd("Sync %s to S3" % encoding, ['sync', 'testsuite/encodings/' + encoding, '%s/xyz/encodings/' % pbucket(1), '--exclude', 'demo/*', '--no-encrypt' ],
|
304
|
+
must_find = [ u"File 'testsuite/encodings/%(encoding)s/%(pattern)s' stored as '%(pbucket)s/xyz/encodings/%(encoding)s/%(pattern)s'" % { 'encoding' : encoding, 'pattern' : enc_pattern , 'pbucket' : pbucket(1)} ])
|
305
|
+
|
306
|
+
|
307
|
+
## ====== List bucket content
|
308
|
+
test_s3cmd("List bucket content", ['ls', '%s/xyz/' % pbucket(1) ],
|
309
|
+
must_find_re = [ u"DIR %s/xyz/binary/$" % pbucket(1) , u"DIR %s/xyz/etc/$" % pbucket(1) ],
|
310
|
+
must_not_find = [ u"random-crap.md5", u"/demo" ])
|
311
|
+
|
312
|
+
|
313
|
+
## ====== List bucket recursive
|
314
|
+
must_find = [ u"%s/xyz/binary/random-crap.md5" % pbucket(1) ]
|
315
|
+
if have_encoding:
|
316
|
+
must_find.append(u"%(pbucket)s/xyz/encodings/%(encoding)s/%(pattern)s" % { 'encoding' : encoding, 'pattern' : enc_pattern, 'pbucket' : pbucket(1) })
|
317
|
+
|
318
|
+
test_s3cmd("List bucket recursive", ['ls', '--recursive', pbucket(1)],
|
319
|
+
must_find = must_find,
|
320
|
+
must_not_find = [ "logo.png" ])
|
321
|
+
|
322
|
+
## ====== FIXME
|
323
|
+
# test_s3cmd("Recursive put", ['put', '--recursive', 'testsuite/etc', '%s/xyz/' % pbucket(1) ])
|
324
|
+
|
325
|
+
|
326
|
+
## ====== Clean up local destination dir
|
327
|
+
test_flushdir("Clean testsuite-out/", "testsuite-out")
|
328
|
+
|
329
|
+
|
330
|
+
## ====== Sync from S3
|
331
|
+
must_find = [ "File '%s/xyz/binary/random-crap.md5' stored as 'testsuite-out/xyz/binary/random-crap.md5'" % pbucket(1) ]
|
332
|
+
if have_encoding:
|
333
|
+
must_find.append(u"File '%(pbucket)s/xyz/encodings/%(encoding)s/%(pattern)s' stored as 'testsuite-out/xyz/encodings/%(encoding)s/%(pattern)s' " % { 'encoding' : encoding, 'pattern' : enc_pattern, 'pbucket' : pbucket(1) })
|
334
|
+
test_s3cmd("Sync from S3", ['sync', '%s/xyz' % pbucket(1), 'testsuite-out'],
|
335
|
+
must_find = must_find)
|
336
|
+
|
337
|
+
|
338
|
+
## ====== Remove 'demo' directory
|
339
|
+
test_rmdir("Remove 'dir-test/'", "testsuite-out/xyz/dir-test/")
|
340
|
+
|
341
|
+
|
342
|
+
## ====== Create dir with name of a file
|
343
|
+
test_mkdir("Create file-dir dir", "testsuite-out/xyz/dir-test/file-dir")
|
344
|
+
|
345
|
+
|
346
|
+
## ====== Skip dst dirs
|
347
|
+
test_s3cmd("Skip over dir", ['sync', '%s/xyz' % pbucket(1), 'testsuite-out'],
|
348
|
+
must_find = "WARNING: testsuite-out/xyz/dir-test/file-dir is a directory - skipping over")
|
349
|
+
|
350
|
+
|
351
|
+
## ====== Clean up local destination dir
|
352
|
+
test_flushdir("Clean testsuite-out/", "testsuite-out")
|
353
|
+
|
354
|
+
|
355
|
+
## ====== Put public, guess MIME
|
356
|
+
test_s3cmd("Put public, guess MIME", ['put', '--guess-mime-type', '--acl-public', 'testsuite/etc/logo.png', '%s/xyz/etc/logo.png' % pbucket(1)],
|
357
|
+
must_find = [ "stored as '%s/xyz/etc/logo.png'" % pbucket(1) ])
|
358
|
+
|
359
|
+
|
360
|
+
## ====== Retrieve from URL
|
361
|
+
if have_wget:
|
362
|
+
test("Retrieve from URL", ['wget', '-O', 'testsuite-out/logo.png', 'http://%s.s3.amazonaws.com/xyz/etc/logo.png' % bucket(1)],
|
363
|
+
must_find_re = [ 'logo.png.*saved \[22059/22059\]' ])
|
364
|
+
|
365
|
+
|
366
|
+
## ====== Change ACL to Private
|
367
|
+
test_s3cmd("Change ACL to Private", ['setacl', '--acl-private', '%s/xyz/etc/l*.png' % pbucket(1)],
|
368
|
+
must_find = [ "logo.png: ACL set to Private" ])
|
369
|
+
|
370
|
+
|
371
|
+
## ====== Verify Private ACL
|
372
|
+
if have_wget:
|
373
|
+
test("Verify Private ACL", ['wget', '-O', 'testsuite-out/logo.png', 'http://%s.s3.amazonaws.com/xyz/etc/logo.png' % bucket(1)],
|
374
|
+
retcode = 8,
|
375
|
+
must_find_re = [ 'ERROR 403: Forbidden' ])
|
376
|
+
|
377
|
+
|
378
|
+
## ====== Change ACL to Public
|
379
|
+
test_s3cmd("Change ACL to Public", ['setacl', '--acl-public', '--recursive', '%s/xyz/etc/' % pbucket(1) , '-v'],
|
380
|
+
must_find = [ "logo.png: ACL set to Public" ])
|
381
|
+
|
382
|
+
|
383
|
+
## ====== Verify Public ACL
|
384
|
+
if have_wget:
|
385
|
+
test("Verify Public ACL", ['wget', '-O', 'testsuite-out/logo.png', 'http://%s.s3.amazonaws.com/xyz/etc/logo.png' % bucket(1)],
|
386
|
+
must_find_re = [ 'logo.png.*saved \[22059/22059\]' ])
|
387
|
+
|
388
|
+
|
389
|
+
## ====== Sync more to S3
|
390
|
+
test_s3cmd("Sync more to S3", ['sync', 'testsuite/', 's3://%s/xyz/' % bucket(1), '--no-encrypt' ],
|
391
|
+
must_find = [ "File 'testsuite/demo/some-file.xml' stored as '%s/xyz/demo/some-file.xml' " % pbucket(1) ],
|
392
|
+
must_not_find = [ "File 'testsuite/etc/linked.png' stored as '%s/xyz/etc/linked.png" % pbucket(1) ])
|
393
|
+
|
394
|
+
|
395
|
+
## ====== Don't check MD5 sum on Sync
|
396
|
+
test_copy("Change file cksum1.txt", "testsuite/checksum/cksum2.txt", "testsuite/checksum/cksum1.txt")
|
397
|
+
test_copy("Change file cksum33.txt", "testsuite/checksum/cksum2.txt", "testsuite/checksum/cksum33.txt")
|
398
|
+
test_s3cmd("Don't check MD5", ['sync', 'testsuite/', 's3://%s/xyz/' % bucket(1), '--no-encrypt', '--no-check-md5'],
|
399
|
+
must_find = [ "cksum33.txt" ],
|
400
|
+
must_not_find = [ "cksum1.txt" ])
|
401
|
+
|
402
|
+
|
403
|
+
## ====== Check MD5 sum on Sync
|
404
|
+
test_s3cmd("Check MD5", ['sync', 'testsuite/', 's3://%s/xyz/' % bucket(1), '--no-encrypt', '--check-md5'],
|
405
|
+
must_find = [ "cksum1.txt" ])
|
406
|
+
|
407
|
+
|
408
|
+
## ====== Rename within S3
|
409
|
+
test_s3cmd("Rename within S3", ['mv', '%s/xyz/etc/logo.png' % pbucket(1), '%s/xyz/etc2/Logo.PNG' % pbucket(1)],
|
410
|
+
must_find = [ 'File %s/xyz/etc/logo.png moved to %s/xyz/etc2/Logo.PNG' % (pbucket(1), pbucket(1))])
|
411
|
+
|
412
|
+
|
413
|
+
## ====== Rename (NoSuchKey)
|
414
|
+
test_s3cmd("Rename (NoSuchKey)", ['mv', '%s/xyz/etc/logo.png' % pbucket(1), '%s/xyz/etc2/Logo.PNG' % pbucket(1)],
|
415
|
+
retcode = 1,
|
416
|
+
must_find_re = [ 'ERROR:.*NoSuchKey' ],
|
417
|
+
must_not_find = [ 'File %s/xyz/etc/logo.png moved to %s/xyz/etc2/Logo.PNG' % (pbucket(1), pbucket(1)) ])
|
418
|
+
|
419
|
+
|
420
|
+
## ====== Sync more from S3
|
421
|
+
test_s3cmd("Sync more from S3", ['sync', '--delete-removed', '%s/xyz' % pbucket(1), 'testsuite-out'],
|
422
|
+
must_find = [ "deleted: testsuite-out/logo.png",
|
423
|
+
"File '%s/xyz/etc2/Logo.PNG' stored as 'testsuite-out/xyz/etc2/Logo.PNG' (22059 bytes" % pbucket(1),
|
424
|
+
"File '%s/xyz/demo/some-file.xml' stored as 'testsuite-out/xyz/demo/some-file.xml' " % pbucket(1) ],
|
425
|
+
must_not_find_re = [ "not-deleted.*etc/logo.png" ])
|
426
|
+
|
427
|
+
|
428
|
+
## ====== Make dst dir for get
|
429
|
+
test_rmdir("Remove dst dir for get", "testsuite-out")
|
430
|
+
|
431
|
+
|
432
|
+
## ====== Get multiple files
|
433
|
+
test_s3cmd("Get multiple files", ['get', '%s/xyz/etc2/Logo.PNG' % pbucket(1), '%s/xyz/etc/AtomicClockRadio.ttf' % pbucket(1), 'testsuite-out'],
|
434
|
+
retcode = 1,
|
435
|
+
must_find = [ 'Destination must be a directory or stdout when downloading multiple sources.' ])
|
436
|
+
|
437
|
+
|
438
|
+
## ====== Make dst dir for get
|
439
|
+
test_mkdir("Make dst dir for get", "testsuite-out")
|
440
|
+
|
441
|
+
|
442
|
+
## ====== Get multiple files
|
443
|
+
test_s3cmd("Get multiple files", ['get', '%s/xyz/etc2/Logo.PNG' % pbucket(1), '%s/xyz/etc/AtomicClockRadio.ttf' % pbucket(1), 'testsuite-out'],
|
444
|
+
must_find = [ u"saved as 'testsuite-out/Logo.PNG'", u"saved as 'testsuite-out/AtomicClockRadio.ttf'" ])
|
445
|
+
|
446
|
+
## ====== Upload files differing in capitalisation
|
447
|
+
test_s3cmd("blah.txt / Blah.txt", ['put', '-r', 'testsuite/blahBlah', pbucket(1)],
|
448
|
+
must_find = [ '%s/blahBlah/Blah.txt' % pbucket(1), '%s/blahBlah/blah.txt' % pbucket(1)])
|
449
|
+
|
450
|
+
## ====== Copy between buckets
|
451
|
+
test_s3cmd("Copy between buckets", ['cp', '%s/xyz/etc2/Logo.PNG' % pbucket(1), '%s/xyz/etc2/logo.png' % pbucket(3)],
|
452
|
+
must_find = [ "File %s/xyz/etc2/Logo.PNG copied to %s/xyz/etc2/logo.png" % (pbucket(1), pbucket(3)) ])
|
453
|
+
|
454
|
+
## ====== Recursive copy
|
455
|
+
test_s3cmd("Recursive copy, set ACL", ['cp', '-r', '--acl-public', '%s/xyz/' % pbucket(1), '%s/copy' % pbucket(2), '--exclude', 'demo/dir?/*.txt', '--exclude', 'non-printables*'],
|
456
|
+
must_find = [ "File %s/xyz/etc2/Logo.PNG copied to %s/copy/etc2/Logo.PNG" % (pbucket(1), pbucket(2)),
|
457
|
+
"File %s/xyz/blahBlah/Blah.txt copied to %s/copy/blahBlah/Blah.txt" % (pbucket(1), pbucket(2)),
|
458
|
+
"File %s/xyz/blahBlah/blah.txt copied to %s/copy/blahBlah/blah.txt" % (pbucket(1), pbucket(2)) ],
|
459
|
+
must_not_find = [ "demo/dir1/file1-1.txt" ])
|
460
|
+
|
461
|
+
## ====== Verify ACL and MIME type
|
462
|
+
test_s3cmd("Verify ACL and MIME type", ['info', '%s/copy/etc2/Logo.PNG' % pbucket(2) ],
|
463
|
+
must_find_re = [ "MIME type:.*image/png",
|
464
|
+
"ACL:.*\*anon\*: READ",
|
465
|
+
"URL:.*http://%s.s3.amazonaws.com/copy/etc2/Logo.PNG" % bucket(2) ])
|
466
|
+
|
467
|
+
## ====== Rename within S3
|
468
|
+
test_s3cmd("Rename within S3", ['mv', '%s/copy/etc2/Logo.PNG' % pbucket(2), '%s/copy/etc/logo.png' % pbucket(2)],
|
469
|
+
must_find = [ 'File %s/copy/etc2/Logo.PNG moved to %s/copy/etc/logo.png' % (pbucket(2), pbucket(2))])
|
470
|
+
|
471
|
+
## ====== Sync between buckets
|
472
|
+
test_s3cmd("Sync remote2remote", ['sync', '%s/xyz/' % pbucket(1), '%s/copy/' % pbucket(2), '--delete-removed', '--exclude', 'non-printables*'],
|
473
|
+
must_find = [ "File %s/xyz/demo/dir1/file1-1.txt copied to %s/copy/demo/dir1/file1-1.txt" % (pbucket(1), pbucket(2)),
|
474
|
+
"remote copy: etc/logo.png -> etc2/Logo.PNG",
|
475
|
+
"deleted: '%s/copy/etc/logo.png'" % pbucket(2) ],
|
476
|
+
must_not_find = [ "blah.txt" ])
|
477
|
+
|
478
|
+
## ====== Don't Put symbolic link
|
479
|
+
test_s3cmd("Don't put symbolic links", ['put', 'testsuite/etc/linked1.png', 's3://%s/xyz/' % bucket(1),],
|
480
|
+
must_not_find_re = [ "linked1.png"])
|
481
|
+
|
482
|
+
## ====== Put symbolic link
|
483
|
+
test_s3cmd("Put symbolic links", ['put', 'testsuite/etc/linked1.png', 's3://%s/xyz/' % bucket(1),'--follow-symlinks' ],
|
484
|
+
must_find = [ "File 'testsuite/etc/linked1.png' stored as '%s/xyz/linked1.png'" % pbucket(1)])
|
485
|
+
|
486
|
+
## ====== Sync symbolic links
|
487
|
+
test_s3cmd("Sync symbolic links", ['sync', 'testsuite/', 's3://%s/xyz/' % bucket(1), '--no-encrypt', '--follow-symlinks' ],
|
488
|
+
must_find = ["remote copy: etc2/Logo.PNG -> etc/linked.png"],
|
489
|
+
# Don't want to recursively copy linked directories!
|
490
|
+
must_not_find_re = ["etc/more/linked-dir/more/give-me-more.txt",
|
491
|
+
"etc/brokenlink.png"],
|
492
|
+
)
|
493
|
+
|
494
|
+
## ====== Multi source move
|
495
|
+
test_s3cmd("Multi-source move", ['mv', '-r', '%s/copy/blahBlah/Blah.txt' % pbucket(2), '%s/copy/etc/' % pbucket(2), '%s/moved/' % pbucket(2)],
|
496
|
+
must_find = [ "File %s/copy/blahBlah/Blah.txt moved to %s/moved/Blah.txt" % (pbucket(2), pbucket(2)),
|
497
|
+
"File %s/copy/etc/AtomicClockRadio.ttf moved to %s/moved/AtomicClockRadio.ttf" % (pbucket(2), pbucket(2)),
|
498
|
+
"File %s/copy/etc/TypeRa.ttf moved to %s/moved/TypeRa.ttf" % (pbucket(2), pbucket(2)) ],
|
499
|
+
must_not_find = [ "blah.txt" ])
|
500
|
+
|
501
|
+
## ====== Verify move
|
502
|
+
test_s3cmd("Verify move", ['ls', '-r', pbucket(2)],
|
503
|
+
must_find = [ "%s/moved/Blah.txt" % pbucket(2),
|
504
|
+
"%s/moved/AtomicClockRadio.ttf" % pbucket(2),
|
505
|
+
"%s/moved/TypeRa.ttf" % pbucket(2),
|
506
|
+
"%s/copy/blahBlah/blah.txt" % pbucket(2) ],
|
507
|
+
must_not_find = [ "%s/copy/blahBlah/Blah.txt" % pbucket(2),
|
508
|
+
"%s/copy/etc/AtomicClockRadio.ttf" % pbucket(2),
|
509
|
+
"%s/copy/etc/TypeRa.ttf" % pbucket(2) ])
|
510
|
+
|
511
|
+
## ====== Simple delete
|
512
|
+
test_s3cmd("Simple delete", ['del', '%s/xyz/etc2/Logo.PNG' % pbucket(1)],
|
513
|
+
must_find = [ "File %s/xyz/etc2/Logo.PNG deleted" % pbucket(1) ])
|
514
|
+
|
515
|
+
|
516
|
+
## ====== Recursive delete
|
517
|
+
test_s3cmd("Recursive delete", ['del', '--recursive', '--exclude', 'Atomic*', '%s/xyz/etc' % pbucket(1)],
|
518
|
+
must_find = [ "File %s/xyz/etc/TypeRa.ttf deleted" % pbucket(1) ],
|
519
|
+
must_find_re = [ "File .*/etc/logo.png deleted" ],
|
520
|
+
must_not_find = [ "AtomicClockRadio.ttf" ])
|
521
|
+
|
522
|
+
## ====== Recursive delete all
|
523
|
+
test_s3cmd("Recursive delete all", ['del', '--recursive', '--force', pbucket(1)],
|
524
|
+
must_find_re = [ "File .*binary/random-crap deleted" ])
|
525
|
+
|
526
|
+
|
527
|
+
## ====== Remove empty bucket
|
528
|
+
test_s3cmd("Remove empty bucket", ['rb', pbucket(1)],
|
529
|
+
must_find = [ "Bucket '%s/' removed" % pbucket(1) ])
|
530
|
+
|
531
|
+
|
532
|
+
## ====== Remove remaining buckets
|
533
|
+
test_s3cmd("Remove remaining buckets", ['rb', '--recursive', pbucket(2), pbucket(3)],
|
534
|
+
must_find = [ "Bucket '%s/' removed" % pbucket(2),
|
535
|
+
"Bucket '%s/' removed" % pbucket(3) ])
|
536
|
+
|
537
|
+
# vim:et:ts=4:sts=4:ai
|