[Python-checkins] distutils2: Making sure the code works on all Python versions.

tarek.ziade python-checkins at python.org
Sun Jul 4 11:16:45 CEST 2010


tarek.ziade pushed f696d39e9e86 to distutils2:

http://hg.python.org/distutils2/rev/f696d39e9e86
changeset:   256:f696d39e9e86
tag:         tip
user:        Tarek Ziade <tarek at ziade.org>
date:        Sun Jul 04 11:16:37 2010 +0200
summary:     Making sure the code works on all Python versions.
files:       src/distutils2/command/build_py.py, src/distutils2/tests/support.py, src/distutils2/tests/test_Mixin2to3.py, src/distutils2/tests/test_util.py, src/distutils2/util.py

diff --git a/src/distutils2/command/build_py.py b/src/distutils2/command/build_py.py
--- a/src/distutils2/command/build_py.py
+++ b/src/distutils2/command/build_py.py
@@ -28,14 +28,14 @@
 
 class Mixin2to3(_KLASS):
     """ The base class which can be used for refactoring. When run under
-    Python 3.0, the run_2to3 method provided by Mixin2to3 is overridden. 
-    When run on Python 2.x, it merely creates a class which overrides run_2to3, 
-    yet does nothing in particular with it. 
+    Python 3.0, the run_2to3 method provided by Mixin2to3 is overridden.
+    When run on Python 2.x, it merely creates a class which overrides run_2to3,
+    yet does nothing in particular with it.
     """
     if _CONVERT:
         def _run_2to3(self, files, doctests=[]):
             """ Takes a list of files and doctests, and performs conversion
-            on those. 
+            on those.
               - First, the files which contain the code(`files`) are converted.
               - Second, the doctests in `files` are converted.
               - Thirdly, the doctests in `doctests` are converted.
@@ -53,7 +53,7 @@
             # 1. User has specified the 'convert_2to3_doctests' option. So, we
             #    can expect that the list 'doctests' is not empty.
             # 2. The default is allow distutils2 to allow conversion of text files
-            #    containing doctests. It is set as 
+            #    containing doctests. It is set as
             #    distutils2.run_2to3_on_doctests
 
             if doctests != [] and distutils2.run_2to3_on_doctests:
@@ -258,8 +258,8 @@
             if os.path.isfile(init_py):
                 return init_py
             else:
-                log.warn(("package init file '%s' not found " +
-                          "(or not a regular file)"), init_py)
+                logging.warning(("package init file '%s' not found " +
+                                 "(or not a regular file)"), init_py)
 
         # Either not in a package at all (__init__.py not expected), or
         # __init__.py doesn't exist -- so don't return the filename.
@@ -267,7 +267,8 @@
 
     def check_module(self, module, module_file):
         if not os.path.isfile(module_file):
-            log.warn("file %s (for module %s) not found", module_file, module)
+            logging.warning("file %s (for module %s) not found",
+                            module_file, module)
             return False
         else:
             return True
diff --git a/src/distutils2/tests/support.py b/src/distutils2/tests/support.py
--- a/src/distutils2/tests/support.py
+++ b/src/distutils2/tests/support.py
@@ -64,12 +64,22 @@
     def setUp(self):
         super(TempdirManager, self).setUp()
         self.tempdirs = []
+        self.tempfiles = []
 
     def tearDown(self):
         super(TempdirManager, self).tearDown()
         while self.tempdirs:
             d = self.tempdirs.pop()
             shutil.rmtree(d, os.name in ('nt', 'cygwin'))
+        for file_ in self.tempfiles:
+            if os.path.exists(file_):
+                os.remove(file_)
+
+    def mktempfile(self):
+        """Create a temporary file that will be cleaned up."""
+        tempfile_ = tempfile.NamedTemporaryFile()
+        self.tempfiles.append(tempfile_.name)
+        return tempfile_
 
     def mkdtemp(self):
         """Create a temporary directory that will be cleaned up.
diff --git a/src/distutils2/tests/test_Mixin2to3.py b/src/distutils2/tests/test_Mixin2to3.py
--- a/src/distutils2/tests/test_Mixin2to3.py
+++ b/src/distutils2/tests/test_Mixin2to3.py
@@ -1,32 +1,37 @@
 """Tests for distutils.command.build_py."""
+import sys
+import tempfile
 
-import tempfile
 import distutils2
 from distutils2.tests import support
 from distutils2.tests.support import unittest
 from distutils2.command.build_py import Mixin2to3
 
-class Mixin2to3TestCase(unittest.TestCase):
+
+class Mixin2to3TestCase(support.TempdirManager, unittest.TestCase):
+
+    @unittest.skipUnless(sys.version > '2.6', 'Need >= 2.6')
     def test_convert_code_only(self):
         # used to check if code gets converted properly.
         code_content = "print 'test'\n"
-        code_handle = tempfile.NamedTemporaryFile(delete=True)
+        code_handle = self.mktempfile()
         code_name = code_handle.name
 
         code_handle.write(code_content)
         code_handle.flush()
 
-        mixin2to3 = Mixin2to3() 
+        mixin2to3 = Mixin2to3()
         mixin2to3._run_2to3([code_name])
         converted_code_content = "print('test')\n"
         new_code_content = "".join(open(code_name).readlines())
 
         self.assertEquals(new_code_content, converted_code_content)
 
+    @unittest.skipUnless(sys.version > '2.6', 'Need >= 2.6')
     def test_doctests_only(self):
         # used to check if doctests gets converted properly.
         doctest_content = '"""\n>>> print test\ntest\n"""\nprint test\n\n'
-        doctest_handle = tempfile.NamedTemporaryFile(delete=True)
+        doctest_handle = self.mktempfile()
         doctest_name = doctest_handle.name
 
         doctest_handle.write(doctest_content)
@@ -35,7 +40,9 @@
         mixin2to3 = Mixin2to3()
         mixin2to3._run_2to3([doctest_name])
 
-        converted_doctest_content = '"""\n>>> print(test)\ntest\n"""\nprint(test)\n\n\n'
+        converted_doctest_content = ['"""', '>>> print(test)', 'test', '"""',
+                                     'print(test)', '', '', '']
+        converted_doctest_content = '\n'.join(converted_doctest_content)
         new_doctest_content = "".join(open(doctest_name).readlines())
 
         self.assertEquals(new_doctest_content, converted_doctest_content)
diff --git a/src/distutils2/tests/test_util.py b/src/distutils2/tests/test_util.py
--- a/src/distutils2/tests/test_util.py
+++ b/src/distutils2/tests/test_util.py
@@ -296,10 +296,11 @@
         res = find_packages([root], ['pkg1.pkg2'])
         self.assertEqual(set(res), set(['pkg1', 'pkg5', 'pkg1.pkg3', 'pkg1.pkg3.pkg6']))
 
+    @unittest.skipUnless(sys.version > '2.6', 'Need Python 2.6 or more')
     def test_run_2to3_on_code(self):
         content = "print 'test'"
         converted_content = "print('test')"
-        file_handle = tempfile.NamedTemporaryFile(delete=True)
+        file_handle = self.mktempfile()
         file_name = file_handle.name
         file_handle.write(content)
         file_handle.flush()
@@ -310,11 +311,12 @@
         file_handle.close()
         self.assertEquals(new_content, converted_content)
 
+    @unittest.skipUnless(sys.version > '2.6', 'Need Python 2.6 or more')
     def test_run_2to3_on_doctests(self):
         # to check if text files containing doctests only get converted.
         content = ">>> print 'test'\ntest\n"
         converted_content = ">>> print('test')\ntest\n\n"
-        file_handle = tempfile.NamedTemporaryFile(delete=True)
+        file_handle = self.mktempfile()
         file_name = file_handle.name
         file_handle.write(content)
         file_handle.flush()
diff --git a/src/distutils2/util.py b/src/distutils2/util.py
--- a/src/distutils2/util.py
+++ b/src/distutils2/util.py
@@ -5,7 +5,10 @@
 
 __revision__ = "$Id: util.py 77761 2010-01-26 22:46:15Z tarek.ziade $"
 
-import sys, os, string, re
+import sys
+import os
+import string
+import re
 from copy import copy
 from fnmatch import fnmatchcase
 
@@ -17,6 +20,7 @@
 
 _PLATFORM = None
 
+
 def newer(source, target):
     """Tells if the target is newer than the source.
 
@@ -37,6 +41,7 @@
 
     return os.stat(source).st_mtime > os.stat(target).st_mtime
 
+
 def get_platform():
     """Return a string that identifies the current platform.
 
@@ -48,6 +53,7 @@
         _PLATFORM = _sysconfig.get_platform()
     return _PLATFORM
 
+
 def set_platform(identifier):
     """Sets the platform string identifier returned by get_platform().
 
@@ -57,6 +63,7 @@
     global _PLATFORM
     _PLATFORM = identifier
 
+
 def convert_path(pathname):
     """Return 'pathname' as a name that will work on the native filesystem.
 
@@ -125,6 +132,7 @@
 
 _environ_checked = 0
 
+
 def check_environ():
     """Ensure that 'os.environ' has all the environment variables needed.
 
@@ -147,6 +155,7 @@
 
     _environ_checked = 1
 
+
 def subst_vars(s, local_vars):
     """Perform shell/Perl-style variable substitution on 'string'.
 
@@ -158,7 +167,8 @@
     variables not found in either 'local_vars' or 'os.environ'.
     """
     check_environ()
-    def _subst (match, local_vars=local_vars):
+
+    def _subst(match, local_vars=local_vars):
         var_name = match.group(1)
         if var_name in local_vars:
             return str(local_vars[var_name])
@@ -170,6 +180,7 @@
     except KeyError, var:
         raise ValueError("invalid variable '$%s'" % var)
 
+
 def grok_environment_error(exc, prefix="error: "):
     """Generate a useful error message from an EnvironmentError.
 
@@ -196,12 +207,14 @@
 # Needed by 'split_quoted()'
 _wordchars_re = _squote_re = _dquote_re = None
 
+
 def _init_regex():
     global _wordchars_re, _squote_re, _dquote_re
     _wordchars_re = re.compile(r'[^\\\'\"%s ]*' % string.whitespace)
     _squote_re = re.compile(r"'(?:[^'\\]|\\.)*'")
     _dquote_re = re.compile(r'"(?:[^"\\]|\\.)*"')
 
+
 def split_quoted(s):
     """Split a string up according to Unix shell-like rules for quotes and
     backslashes.
@@ -217,7 +230,8 @@
     # This is a nice algorithm for splitting up a single string, since it
     # doesn't require character-by-character examination.  It was a little
     # bit of a brain-bender to get it working right, though...
-    if _wordchars_re is None: _init_regex()
+    if _wordchars_re is None:
+        _init_regex()
 
     s = s.strip()
     words = []
@@ -237,8 +251,8 @@
 
         elif s[end] == '\\':            # preserve whatever is being escaped;
                                         # will become part of the current word
-            s = s[:end] + s[end+1:]
-            pos = end+1
+            s = s[:end] + s[end + 1:]
+            pos = end + 1
 
         else:
             if s[end] == "'":           # slurp singly-quoted string
@@ -253,7 +267,7 @@
                 raise ValueError("bad string (mismatched %s quotes?)" % s[end])
 
             (beg, end) = m.span()
-            s = s[:beg] + s[beg+1:end-1] + s[end:]
+            s = s[:beg] + s[beg + 1:end - 1] + s[end:]
             pos = m.end() - 2
 
         if pos >= len(s):
@@ -296,7 +310,7 @@
     elif val in ('n', 'no', 'f', 'false', 'off', '0'):
         return 0
     else:
-        raise ValueError, "invalid truth value %r" % (val,)
+        raise ValueError("invalid truth value %r" % (val,))
 
 
 def byte_compile(py_files, optimize=0, force=0, prefix=None, base_dir=None,
@@ -450,7 +464,9 @@
     return sep.join(lines)
 
 _RE_VERSION = re.compile('(\d+\.\d+(\.\d+)*)')
-_MAC_OS_X_LD_VERSION = re.compile('^@\(#\)PROGRAM:ld  PROJECT:ld64-((\d+)(\.\d+)*)')
+_MAC_OS_X_LD_VERSION = re.compile('^@\(#\)PROGRAM:ld  '
+                                  'PROJECT:ld64-((\d+)(\.\d+)*)')
+
 
 def _find_ld_version():
     """Finds the ld version. The version scheme differs under Mac OSX."""
@@ -459,6 +475,7 @@
     else:
         return _find_exe_version('ld -v')
 
+
 def _find_exe_version(cmd, pattern=_RE_VERSION):
     """Find the version of an executable by running `cmd` in the shell.
 
@@ -488,6 +505,7 @@
         return None
     return result.group(1)
 
+
 def get_compiler_versions():
     """Returns a tuple providing the versions of gcc, ld and dllwrap
 
@@ -499,6 +517,7 @@
     dllwrap = _find_exe_version('dllwrap --version')
     return gcc, ld, dllwrap
 
+
 def newer_group(sources, target, missing='error'):
     """Return true if 'target' is out-of-date with respect to any file
     listed in 'sources'.
@@ -538,6 +557,7 @@
 
     return False
 
+
 def write_file(filename, contents):
     """Create a file with the specified name and write 'contents' (a
     sequence of strings without line terminators) to it.
@@ -549,12 +569,14 @@
     finally:
         f.close()
 
+
 def _is_package(path):
     """Returns True if path is a package (a dir with an __init__ file."""
     if not os.path.isdir(path):
         return False
     return os.path.isfile(os.path.join(path, '__init__.py'))
 
+
 def _under(path, root):
     path = path.split(os.sep)
     root = root.split(os.sep)
@@ -565,12 +587,14 @@
             return False
     return True
 
+
 def _package_name(root_path, path):
     """Returns a dotted package name, given a subpath."""
     if not _under(path, root_path):
         raise ValueError('"%s" is not a subpath of "%s"' % (path, root_path))
     return path[len(root_path) + 1:].replace(os.sep, '.')
 
+
 def find_packages(paths=('.',), exclude=()):
     """Return a list all Python packages found recursively within
     directories 'paths'
@@ -585,6 +609,7 @@
     """
     packages = []
     discarded = []
+
     def _discarded(path):
         for discard in discarded:
             if _under(path, discard):
@@ -619,12 +644,12 @@
 
 # utility functions for 2to3 support
 
-def run_2to3(files, doctests_only=False, fixer_names=None, options=None, 
+def run_2to3(files, doctests_only=False, fixer_names=None, options=None,
                                                             explicit=None):
     """ Wrapper function around the refactor() class which
-	performs the conversions on a list of python files.
-	Invoke 2to3 on a list of Python files. The files should all come 
-	from the build area, as the modification is done in-place."""
+    performs the conversions on a list of python files.
+    Invoke 2to3 on a list of Python files. The files should all come
+    from the build area, as the modification is done in-place."""
 
     if not files:
         return
@@ -642,6 +667,7 @@
     else:
         r.refactor(files, write=True)
 
+
 class Mixin2to3:
     """ Wrapper class for commands that run 2to3.
     To configure 2to3, setup scripts may either change
@@ -660,4 +686,5 @@
 
     def run_2to3(self, files, doctests_only=False):
         """ Issues a call to util.run_2to3. """
-        return run_2to3(files, doctests_only, self.fixer_names, self.options, self.explicit)
+        return run_2to3(files, doctests_only, self.fixer_names,
+                        self.options, self.explicit)

--
Repository URL: http://hg.python.org/distutils2


More information about the Python-checkins mailing list