From db22fdc20dc93a3e1d8a084f8847d16d4bcaad55 Mon Sep 17 00:00:00 2001
From: david-sarah <david-sarah@jacaranda.org>
Date: Tue, 9 Aug 2011 20:15:58 -0700
Subject: [PATCH] Factor out methods dealing with non-ASCII directories and
 filenames from test_drop_upload.py into common_util.py. refs #1429, #1472

---
 src/allmydata/test/common_util.py      | 30 +++++++++++++++++-
 src/allmydata/test/test_drop_upload.py | 42 +++-----------------------
 2 files changed, 34 insertions(+), 38 deletions(-)

diff --git a/src/allmydata/test/common_util.py b/src/allmydata/test/common_util.py
index 4ccae7b2..70a07245 100644
--- a/src/allmydata/test/common_util.py
+++ b/src/allmydata/test/common_util.py
@@ -1,9 +1,13 @@
-import os, signal, time
+import os, signal, sys, time
 from random import randrange
 
 from twisted.internet import reactor, defer
 from twisted.python import failure
 
+from allmydata.util import fileutil, log
+from allmydata.util.encodingutil import unicode_platform, get_filesystem_encoding
+
+
 def insecurerandstr(n):
     return ''.join(map(chr, map(randrange, [0]*n, [256]*n)))
 
@@ -32,6 +36,30 @@ class ReallyEqualMixin:
         self.failUnlessEqual(type(a), type(b), msg="a :: %r, b :: %r, %r" % (a, b, msg))
 
 
+class NonASCIIPathMixin:
+    def mkdir_nonascii(self, dirpath):
+        # Kludge to work around the fact that buildbot can't remove a directory tree that has
+        # any non-ASCII directory names on Windows. (#1472)
+        if sys.platform == "win32":
+            def _cleanup():
+                try:
+                    fileutil.rm_dir(dirpath)
+                finally:
+                    log.err("We were unable to delete a non-ASCII directory %r created by the test. "
+                            "This is liable to cause failures on future builds." % (dirpath,))
+            self.addCleanup(self._cleanup_nonascii, dirpath)
+        os.mkdir(dirpath)
+
+    def unicode_or_fallback(self, unicode_name, fallback_name):
+        if unicode_platform():
+            return unicode_name
+        try:
+            unicode_name.encode(get_filesystem_encoding())
+            return unicode_name
+        except UnicodeEncodeError:
+            return fallback_name
+
+
 class SignalMixin:
     # This class is necessary for any code which wants to use Processes
     # outside the usual reactor.run() environment. It is copied from
diff --git a/src/allmydata/test/test_drop_upload.py b/src/allmydata/test/test_drop_upload.py
index 30cbe1cb..4f3007d8 100644
--- a/src/allmydata/test/test_drop_upload.py
+++ b/src/allmydata/test/test_drop_upload.py
@@ -11,53 +11,26 @@ from allmydata.util import fileutil, fake_inotify
 from allmydata.util.encodingutil import get_filesystem_encoding
 from allmydata.util.consumer import download_to_data
 from allmydata.test.no_network import GridTestMixin
-from allmydata.test.common_util import ReallyEqualMixin
+from allmydata.test.common_util import ReallyEqualMixin, NonASCIIPathMixin
 from allmydata.test.common import ShouldFailMixin
 
 from allmydata.frontends.drop_upload import DropUploader
 
 
-class DropUploadTestMixin(GridTestMixin, ShouldFailMixin, ReallyEqualMixin):
+class DropUploadTestMixin(GridTestMixin, ShouldFailMixin, ReallyEqualMixin, NonASCIIPathMixin):
     """
     These tests will be run both with a mock notifier, and (on platforms that support it)
     with the real INotify.
     """
 
-    def setUp(self):
-        GridTestMixin.setUp(self)
-        self.nonascii_dirs = []
-
-    def tearDown(self):
-        try:
-            GridTestMixin.tearDown(self)
-        finally:
-            # kludge to work around the fact that buildbot can't remove a directory tree that has any non-ASCII directory names
-            if sys.platform == "win32":
-                for dirpath in self.nonascii_dirs:
-                    try:
-                        fileutil.rm_dir(dirpath)
-                    finally:
-                        log.err("We were unable to delete a non-ASCII directory %r created by the test. "
-                                "This is liable to cause failures on future builds." % (dirpath,))
-
-    def _mkdir_nonascii(self, dirpath):
-        self.nonascii_dirs.append(dirpath)
-        os.mkdir(dirpath)
-
     def _get_count(self, name):
         return self.stats_provider.get_stats()["counters"].get(name, 0)
 
     def _test(self):
         self.uploader = None
         self.set_up_grid()
-        dirname_u = u"loc\u0101l_dir"
-        if sys.platform != "win32":
-            try:
-                u"loc\u0101l_dir".encode(get_filesystem_encoding())
-            except UnicodeEncodeError:
-                dirname_u = u"local_dir"
-        self.local_dir = os.path.join(self.basedir, dirname_u)
-        self._mkdir_nonascii(self.local_dir)
+        self.local_dir = os.path.join(self.basedir, self.unicode_or_fallback(u"loc\u0101l_dir", u"local_dir"))
+        self.mkdir_nonascii(self.local_dir)
 
         self.client = self.g.clients[0]
         self.stats_provider = self.client.stats_provider
@@ -85,12 +58,7 @@ class DropUploadTestMixin(GridTestMixin, ShouldFailMixin, ReallyEqualMixin):
         d.addCallback(lambda ign: os.mkdir(os.path.join(self.local_dir, u"directory")))
 
         # Write something longer, and also try to test a Unicode name if the fs can represent it.
-        name_u = u"l\u00F8ng"
-        if sys.platform != "win32":
-            try:
-                u"l\u00F8ng".encode(get_filesystem_encoding())
-            except UnicodeEncodeError:
-                name_u = u"long"
+        name_u = self.unicode_or_fallback(u"l\u00F8ng", u"long")
         d.addCallback(lambda ign: self._test_file(name_u, "test"*100))
 
         # TODO: test that causes an upload failure.
-- 
2.45.2