Browse code

* s3cmd: Reworked internal handling of unicode vs encoded filenames. Should replace unknown characters with '?' instead of baling out. * run-tests.py: Display system encoding in use.

git-svn-id: https://s3tools.svn.sourceforge.net/svnroot/s3tools/s3cmd/trunk@320 830e0280-6d2a-0410-9c65-932aecc39d9d

Michal Ludvig authored on 2008/12/31 13:55:32
Showing 3 changed files
... ...
@@ -1,5 +1,11 @@
1 1
 2008-12-31  Michal Ludvig  <michal@logix.cz>
2 2
 
3
+	* s3cmd: Reworked internal handling of unicode vs encoded filenames.
4
+	  Should replace unknown characters with '?' instead of baling out.
5
+
6
+2008-12-31  Michal Ludvig  <michal@logix.cz>
7
+
8
+	* run-tests.py: Display system encoding in use.
3 9
 	* s3cmd: Print a nice error message when --exclude-from
4 10
 	  file is not readable.
5 11
 	* S3/PkgInfo.py: Bumped up version to 0.9.9-pre4
... ...
@@ -37,16 +37,19 @@ encoding = locale.getpreferredencoding()
37 37
 if not encoding:
38 38
 	print "Guessing current system encoding failed. Consider setting $LANG variable."
39 39
 	sys.exit(1)
40
+else:
41
+	print "System encoding: " + encoding
40 42
 
41 43
 have_encoding = os.path.isdir('testsuite/encodings/' + encoding)
42 44
 if not have_encoding and os.path.isfile('testsuite/encodings/%s.tar.gz' % encoding):
43
-	os.system("tar xvz -C testsuite/encodings -f testsuite/encodings/UTF-8.tar.gz")
45
+	os.system("tar xvz -C testsuite/encodings -f testsuite/encodings/%s.tar.gz" % encoding)
44 46
 	have_encoding = os.path.isdir('testsuite/encodings/' + encoding)
45 47
 
46 48
 if have_encoding:
47 49
 	enc_base_remote = "s3://s3cmd-autotest-1/xyz/%s/" % encoding
48 50
 	enc_pattern = patterns[encoding]
49
-	print "System encoding: " + encoding
51
+else:
52
+	print encoding + " specific files not found."
50 53
 
51 54
 def test(label, cmd_args = [], retcode = 0, must_find = [], must_not_find = [], must_find_re = [], must_not_find_re = []):
52 55
 	def failure(message = ""):
... ...
@@ -259,7 +262,7 @@ if have_wget:
259 259
 
260 260
 
261 261
 ## ====== Sync more to S3
262
-test_s3cmd("Sync more to S3", ['sync', 'testsuite', 's3://s3cmd-autotest-1/xyz/', '--exclude', '*.png', '--no-encrypt', '--exclude-from', 'testsuite/exclude.encodings' ])
262
+test_s3cmd("Sync more to S3", ['sync', 'testsuite', 's3://s3cmd-autotest-1/xyz/', '--no-encrypt' ])
263 263
 
264 264
 
265 265
 ## ====== Rename within S3
... ...
@@ -341,7 +341,8 @@ def cmd_object_get(args):
341 341
 	for item in remote_keys:
342 342
 		seq += 1
343 343
 		uri = item['remote_uri']
344
-		destination = item['local_filename']
344
+		## Encode / Decode destination with "replace" to make sure it's compatible with current encoding
345
+		destination = unicodise_safe(item['local_filename'])
345 346
 		seq_label = "[%d of %d]" % (seq, total_count)
346 347
 
347 348
 		start_position = 0
... ...
@@ -478,7 +479,7 @@ def cmd_info(args):
478 478
 
479 479
 def _get_filelist_local(local_uri):
480 480
 	info(u"Compiling list of local files...")
481
-	local_path = local_uri.path()
481
+	local_path = deunicodise(local_uri.path())
482 482
 	if os.path.isdir(local_path):
483 483
 		loc_base = os.path.join(local_path, "")
484 484
 		filelist = os.walk(local_path)
... ...
@@ -497,9 +498,10 @@ def _get_filelist_local(local_uri):
497 497
 				## Synchronize symlinks... one day
498 498
 				## for now skip over
499 499
 				continue
500
-			file = full_name[loc_base_len:]
500
+			file = unicodise(full_name[loc_base_len:])
501 501
 			sr = os.stat_result(os.lstat(full_name))
502 502
 			loc_list[file] = {
503
+				'full_name_unicoded' : unicodise(full_name),
503 504
 				'full_name' : full_name,
504 505
 				'size' : sr.st_size, 
505 506
 				'mtime' : sr.st_mtime,
... ...
@@ -757,6 +759,7 @@ def cmd_sync_local2remote(src, dst):
757 757
 	def _build_attr_header(src):
758 758
 		import pwd, grp
759 759
 		attrs = {}
760
+		src = deunicodise(src)
760 761
 		st = os.stat_result(os.stat(src))
761 762
 		for attr in cfg.preserve_attrs_list:
762 763
 			if attr == 'uname':
... ...
@@ -823,17 +826,17 @@ def cmd_sync_local2remote(src, dst):
823 823
 	file_list.sort()
824 824
 	for file in file_list:
825 825
 		seq += 1
826
-		src = loc_list[file]['full_name']
826
+		src = loc_list[file]
827 827
 		uri = S3Uri(dst_base + file)
828 828
 		seq_label = "[%d of %d]" % (seq, total_count)
829 829
 		attr_header = None
830 830
 		if cfg.preserve_attrs:
831
-			attr_header = _build_attr_header(src)
831
+			attr_header = _build_attr_header(src['full_name'])
832 832
 			debug(attr_header)
833 833
 		try:
834
-			response = s3.object_put(src, uri, attr_header, extra_label = seq_label)
834
+			response = s3.object_put(src['full_name'], uri, attr_header, extra_label = seq_label)
835 835
 		except S3UploadError, e:
836
-			error(u"%s: upload failed too many times. Skipping that file." % src)
836
+			error(u"%s: upload failed too many times. Skipping that file." % src['full_name_unicode'])
837 837
 			continue
838 838
 		except InvalidFileError, e:
839 839
 			warning(u"File can not be uploaded: %s" % e)