]> git.ipfire.org Git - thirdparty/babel.git/commitdiff
Prefer setuptools imports to distutils imports
authorAarni Koskela <akx@iki.fi>
Wed, 23 Feb 2022 18:52:35 +0000 (20:52 +0200)
committerAarni Koskela <akx@iki.fi>
Fri, 8 Apr 2022 10:28:21 +0000 (13:28 +0300)
The non-conditional imports have been around for 6 to 17 years,
so they should be safe in conservative situations too.

Refs #824

babel/messages/frontend.py
setup.py
tests/messages/test_frontend.py

index 41b75cec7ecb9e589b842f0eddce2afee5b320d4..c71bc0d79993e1b8110a675af94556be8e54ce2b 100644 (file)
@@ -32,9 +32,23 @@ from babel.messages.extract import DEFAULT_KEYWORDS, DEFAULT_MAPPING, check_and_
 from babel.messages.mofile import write_mo
 from babel.messages.pofile import read_po, write_po
 from babel.util import LOCALTZ
-from distutils import log as distutils_log
-from distutils.cmd import Command as _Command
-from distutils.errors import DistutilsOptionError, DistutilsSetupError
+
+log = logging.getLogger('babel')
+
+try:
+    # See: https://setuptools.pypa.io/en/latest/deprecated/distutils-legacy.html
+    from setuptools import Command as _Command
+    distutils_log = log  # "distutils.log → (no replacement yet)"
+
+    try:
+        from setuptools.errors import OptionError, SetupError
+    except ImportError:  # Error aliases only added in setuptools 59 (2021-11).
+        OptionError = SetupError = Exception
+
+except ImportError:
+    from distutils import log as distutils_log
+    from distutils.cmd import Command as _Command
+    from distutils.errors import OptionError as OptionError, DistutilsSetupError as SetupError
 
 
 def listify_value(arg, split=None):
@@ -169,11 +183,9 @@ class compile_catalog(Command):
     def finalize_options(self):
         self.domain = listify_value(self.domain)
         if not self.input_file and not self.directory:
-            raise DistutilsOptionError('you must specify either the input file '
-                                       'or the base directory')
+            raise OptionError('you must specify either the input file or the base directory')
         if not self.output_file and not self.directory:
-            raise DistutilsOptionError('you must specify either the output file '
-                                       'or the base directory')
+            raise OptionError('you must specify either the output file or the base directory')
 
     def run(self):
         n_errors = 0
@@ -216,7 +228,7 @@ class compile_catalog(Command):
                                              domain + '.mo'))
 
         if not po_files:
-            raise DistutilsOptionError('no message catalogs found')
+            raise OptionError('no message catalogs found')
 
         catalogs_and_errors = {}
 
@@ -388,7 +400,7 @@ class extract_messages(Command):
             if not self.input_paths:
                 self.input_paths = self.input_dirs
             else:
-                raise DistutilsOptionError(
+                raise OptionError(
                     'input-dirs and input-paths are mutually exclusive'
                 )
 
@@ -402,22 +414,25 @@ class extract_messages(Command):
         self.keywords = keywords
 
         if not self.keywords:
-            raise DistutilsOptionError('you must specify new keywords if you '
-                                       'disable the default ones')
+            raise OptionError(
+                'you must specify new keywords if you disable the default ones'
+            )
 
         if not self.output_file:
-            raise DistutilsOptionError('no output file specified')
+            raise OptionError('no output file specified')
         if self.no_wrap and self.width:
-            raise DistutilsOptionError("'--no-wrap' and '--width' are mutually "
-                                       "exclusive")
+            raise OptionError(
+                "'--no-wrap' and '--width' are mutually exclusive"
+            )
         if not self.no_wrap and not self.width:
             self.width = 76
         elif self.width is not None:
             self.width = int(self.width)
 
         if self.sort_output and self.sort_by_file:
-            raise DistutilsOptionError("'--sort-output' and '--sort-by-file' "
-                                       "are mutually exclusive")
+            raise OptionError(
+                "'--sort-output' and '--sort-by-file' are mutually exclusive"
+            )
 
         if self.input_paths:
             if isinstance(self.input_paths, str):
@@ -431,11 +446,11 @@ class extract_messages(Command):
             self.input_paths = []
 
         if not self.input_paths:
-            raise DistutilsOptionError("no input files or directories specified")
+            raise OptionError("no input files or directories specified")
 
         for path in self.input_paths:
             if not os.path.exists(path):
-                raise DistutilsOptionError("Input path: %s does not exist" % path)
+                raise OptionError("Input path: %s does not exist" % path)
 
         self.add_comments = listify_value(self.add_comments or (), ",")
 
@@ -456,7 +471,6 @@ class extract_messages(Command):
         else:
             self.directory_filter = None
 
-
     def run(self):
         mappings = self._get_mappings()
         with open(self.output_file, 'wb') as outfile:
@@ -558,8 +572,10 @@ def check_message_extractors(dist, name, value):
     """
     assert name == 'message_extractors'
     if not isinstance(value, dict):
-        raise DistutilsSetupError('the value of the "message_extractors" '
-                                  'parameter must be a dictionary')
+        raise SetupError(
+            'the value of the "message_extractors" '
+            'parameter must be a dictionary'
+        )
 
 
 class init_catalog(Command):
@@ -609,18 +625,17 @@ class init_catalog(Command):
 
     def finalize_options(self):
         if not self.input_file:
-            raise DistutilsOptionError('you must specify the input file')
+            raise OptionError('you must specify the input file')
 
         if not self.locale:
-            raise DistutilsOptionError('you must provide a locale for the '
-                                       'new catalog')
+            raise OptionError('you must provide a locale for the new catalog')
         try:
             self._locale = Locale.parse(self.locale)
         except UnknownLocaleError as e:
-            raise DistutilsOptionError(e)
+            raise OptionError(e) from e
 
         if not self.output_file and not self.output_dir:
-            raise DistutilsOptionError('you must specify the output directory')
+            raise OptionError('you must specify the output directory')
         if not self.output_file:
             self.output_file = os.path.join(self.output_dir, self.locale,
                                             'LC_MESSAGES', self.domain + '.po')
@@ -628,8 +643,7 @@ class init_catalog(Command):
         if not os.path.exists(os.path.dirname(self.output_file)):
             os.makedirs(os.path.dirname(self.output_file))
         if self.no_wrap and self.width:
-            raise DistutilsOptionError("'--no-wrap' and '--width' are mutually "
-                                       "exclusive")
+            raise OptionError("'--no-wrap' and '--width' are mutually exclusive")
         if not self.no_wrap and not self.width:
             self.width = 76
         elif self.width is not None:
@@ -723,28 +737,28 @@ class update_catalog(Command):
 
     def finalize_options(self):
         if not self.input_file:
-            raise DistutilsOptionError('you must specify the input file')
+            raise OptionError('you must specify the input file')
         if not self.output_file and not self.output_dir:
-            raise DistutilsOptionError('you must specify the output file or '
-                                       'directory')
+            raise OptionError('you must specify the output file or directory')
         if self.output_file and not self.locale:
-            raise DistutilsOptionError('you must specify the locale')
+            raise OptionError('you must specify the locale')
 
         if self.init_missing:
             if not self.locale:
-                raise DistutilsOptionError('you must specify the locale for '
-                                           'the init-missing option to work')
+                raise OptionError(
+                    'you must specify the locale for '
+                    'the init-missing option to work'
+                )
 
             try:
                 self._locale = Locale.parse(self.locale)
             except UnknownLocaleError as e:
-                raise DistutilsOptionError(e)
+                raise OptionError(e) from e
         else:
             self._locale = None
 
         if self.no_wrap and self.width:
-            raise DistutilsOptionError("'--no-wrap' and '--width' are mutually "
-                                       "exclusive")
+            raise OptionError("'--no-wrap' and '--width' are mutually exclusive")
         if not self.no_wrap and not self.width:
             self.width = 76
         elif self.width is not None:
@@ -771,7 +785,7 @@ class update_catalog(Command):
             po_files.append((self.locale, self.output_file))
 
         if not po_files:
-            raise DistutilsOptionError('no message catalogs found')
+            raise OptionError('no message catalogs found')
 
         domain = self.domain
         if not domain:
@@ -910,7 +924,7 @@ class CommandLineInterface(object):
         return cmdinst.run()
 
     def _configure_logging(self, loglevel):
-        self.log = logging.getLogger('babel')
+        self.log = log
         self.log.setLevel(loglevel)
         # Don't add a new handler for every instance initialization (#227), this
         # would cause duplicated output when the CommandLineInterface as an
@@ -976,7 +990,7 @@ class CommandLineInterface(object):
 
         try:
             cmdinst.ensure_finalized()
-        except DistutilsOptionError as err:
+        except OptionError as err:
             parser.error(str(err))
 
         return cmdinst
index 9a4af2313128d23e12958256a0e2e9b8639258e9..e036bbdc08008041d2bfb634bd0b2a8204f5f722 100755 (executable)
--- a/setup.py
+++ b/setup.py
@@ -2,9 +2,8 @@
 
 import subprocess
 import sys
-from distutils.cmd import Command
 
-from setuptools import setup
+from setuptools import setup, Command
 
 try:
     from babel import __version__
index 2dc53306cace36b849dd707e8f67daa28cfdb218..ba78f502c5b56037fe3078f90d39df3f83e6c14c 100644 (file)
 # individuals. For the exact contribution history, see the revision
 # history and logs, available at http://babel.edgewall.org/log/.
 import shlex
-from freezegun import freeze_time
 from datetime import datetime
-from distutils.dist import Distribution
-from distutils.errors import DistutilsOptionError
-from distutils.log import _global_log
+from freezegun import freeze_time
 from io import StringIO
+from setuptools import Distribution
 import logging
 import os
 import shutil
@@ -29,7 +27,7 @@ import pytest
 from babel import __version__ as VERSION
 from babel.dates import format_datetime
 from babel.messages import frontend, Catalog
-from babel.messages.frontend import CommandLineInterface, extract_messages, update_catalog
+from babel.messages.frontend import CommandLineInterface, extract_messages, update_catalog, OptionError
 from babel.util import LOCALTZ
 from babel.messages.pofile import read_po, write_po
 
@@ -49,7 +47,6 @@ class CompileCatalogTestCase(unittest.TestCase):
     def setUp(self):
         self.olddir = os.getcwd()
         os.chdir(data_dir)
-        _global_log.threshold = 5  # shut up distutils logging
 
         self.dist = Distribution(dict(
             name='TestProject',
@@ -65,12 +62,12 @@ class CompileCatalogTestCase(unittest.TestCase):
     def test_no_directory_or_output_file_specified(self):
         self.cmd.locale = 'en_US'
         self.cmd.input_file = 'dummy'
-        self.assertRaises(DistutilsOptionError, self.cmd.finalize_options)
+        self.assertRaises(OptionError, self.cmd.finalize_options)
 
     def test_no_directory_or_input_file_specified(self):
         self.cmd.locale = 'en_US'
         self.cmd.output_file = 'dummy'
-        self.assertRaises(DistutilsOptionError, self.cmd.finalize_options)
+        self.assertRaises(OptionError, self.cmd.finalize_options)
 
 
 class ExtractMessagesTestCase(unittest.TestCase):
@@ -78,7 +75,6 @@ class ExtractMessagesTestCase(unittest.TestCase):
     def setUp(self):
         self.olddir = os.getcwd()
         os.chdir(data_dir)
-        _global_log.threshold = 5  # shut up distutils logging
 
         self.dist = Distribution(dict(
             name='TestProject',
@@ -100,21 +96,21 @@ class ExtractMessagesTestCase(unittest.TestCase):
     def test_neither_default_nor_custom_keywords(self):
         self.cmd.output_file = 'dummy'
         self.cmd.no_default_keywords = True
-        self.assertRaises(DistutilsOptionError, self.cmd.finalize_options)
+        self.assertRaises(OptionError, self.cmd.finalize_options)
 
     def test_no_output_file_specified(self):
-        self.assertRaises(DistutilsOptionError, self.cmd.finalize_options)
+        self.assertRaises(OptionError, self.cmd.finalize_options)
 
     def test_both_sort_output_and_sort_by_file(self):
         self.cmd.output_file = 'dummy'
         self.cmd.sort_output = True
         self.cmd.sort_by_file = True
-        self.assertRaises(DistutilsOptionError, self.cmd.finalize_options)
+        self.assertRaises(OptionError, self.cmd.finalize_options)
 
     def test_invalid_file_or_dir_input_path(self):
         self.cmd.input_paths = 'nonexistent_path'
         self.cmd.output_file = 'dummy'
-        self.assertRaises(DistutilsOptionError, self.cmd.finalize_options)
+        self.assertRaises(OptionError, self.cmd.finalize_options)
 
     def test_input_paths_is_treated_as_list(self):
         self.cmd.input_paths = data_dir
@@ -146,7 +142,7 @@ class ExtractMessagesTestCase(unittest.TestCase):
         self.cmd.input_dirs = this_dir
         self.cmd.input_paths = this_dir
         self.cmd.output_file = pot_file
-        self.assertRaises(DistutilsOptionError, self.cmd.finalize_options)
+        self.assertRaises(OptionError, self.cmd.finalize_options)
 
     @freeze_time("1994-11-11")
     def test_extraction_with_default_mapping(self):
@@ -354,7 +350,6 @@ class InitCatalogTestCase(unittest.TestCase):
     def setUp(self):
         self.olddir = os.getcwd()
         os.chdir(data_dir)
-        _global_log.threshold = 5  # shut up distutils logging
 
         self.dist = Distribution(dict(
             name='TestProject',
@@ -375,12 +370,12 @@ class InitCatalogTestCase(unittest.TestCase):
     def test_no_input_file(self):
         self.cmd.locale = 'en_US'
         self.cmd.output_file = 'dummy'
-        self.assertRaises(DistutilsOptionError, self.cmd.finalize_options)
+        self.assertRaises(OptionError, self.cmd.finalize_options)
 
     def test_no_locale(self):
         self.cmd.input_file = 'dummy'
         self.cmd.output_file = 'dummy'
-        self.assertRaises(DistutilsOptionError, self.cmd.finalize_options)
+        self.assertRaises(OptionError, self.cmd.finalize_options)
 
     @freeze_time("1994-11-11")
     def test_with_output_dir(self):