[PDNCF] Python 3.12 compatibility 69/308169/3 accepted/tizen/unified/20240320.151957
authoryh106.jung <yh106.jung@samsung.com>
Tue, 19 Mar 2024 03:39:56 +0000 (20:39 -0700)
committerDae-Hyun Ko <dhyuna.ko@samsung.com>
Wed, 20 Mar 2024 05:14:25 +0000 (05:14 +0000)
This patch chery-picks upstream patches for Python 3.12 comaptibility
issue[1].

References:
https://chromium-review.googlesource.com/c/chromium/src/+/4976171 /
https://chromium-review.googlesource.com/c/chromium/src/+/4983816 /
https://chromium-review.googlesource.com/c/chromium/src/+/4988601 /
https://chromium-review.googlesource.com/c/chromium/src/+/5094673 /
https://chromium-review.googlesource.com/c/catapult/+/4979965 /
https://chromium-review.googlesource.com/c/catapult/+/5092950 /
https://chromium-review.googlesource.com/c/catapult/+/5092511 /

[1] https://issues.chromium.org/issues/40283283

Change-Id: Ic5d1ec7417c8db946201883329beb67ac474679b
Signed-off-by: yh106.jung <yh106.jung@samsung.com>
18 files changed:
build/util/generate_wrapper.py
build/util/lastchange.py
chrome/installer/linux/debian/package_version_interval.py
components/policy/tools/template_writers/writers/doc_writer.py
remoting/tools/verify_resources.py
third_party/catapult/AUTHORS
third_party/catapult/common/py_vulcanize/py_vulcanize/html_generation_controller.py
third_party/catapult/common/py_vulcanize/py_vulcanize/js_utils.py
third_party/catapult/common/py_vulcanize/py_vulcanize/parse_html_deps.py
third_party/catapult/common/py_vulcanize/py_vulcanize/style_sheet.py
third_party/catapult/devil/devil/utils/markdown.py
third_party/catapult/third_party/six/CHANGES
third_party/catapult/third_party/six/PKG-INFO
third_party/catapult/third_party/six/README
third_party/catapult/third_party/six/README.chromium
third_party/catapult/third_party/six/six.egg-info/PKG-INFO
third_party/catapult/third_party/six/six.py
tools/metrics/common/models.py

index b45f5f3..c106bd3 100755 (executable)
@@ -40,7 +40,7 @@ SCRIPT_TEMPLATES = {
 }
 
 
-PY_TEMPLATE = textwrap.dedent("""\
+PY_TEMPLATE = textwrap.dedent(r"""
     import os
     import re
     import shlex
index 98a6360..0a91178 100755 (executable)
@@ -314,8 +314,8 @@ def main(argv=None):
   if args.print_only:
     print(revision_string)
   else:
-    lastchange_year = datetime.datetime.utcfromtimestamp(
-        version_info.timestamp).year
+    lastchange_year = datetime.datetime.fromtimestamp(
+        version_info.timestamp, datetime.timezone.utc).year
     contents_lines = [
         "LASTCHANGE=%s" % revision_string,
         "LASTCHANGE_YEAR=%s" % lastchange_year,
index 4b751ba..9f50fd9 100755 (executable)
@@ -130,13 +130,13 @@ def parse_dep(dep):
   Returns:
       A PackageVersionInterval.
   """
-  package_name_regex = '[a-z][a-z0-9\+\-\.]+'
+  package_name_regex = r'[a-z][a-z0-9\+\-\.]+'
   match = re.match('^(%s)$' % package_name_regex, dep)
   if match:
     return PackageVersionInterval(dep, match.group(1),
         PackageVersionIntervalEndpoint(True, None, None),
         PackageVersionIntervalEndpoint(True, None, None))
-  match = re.match('^(%s) \(([\>\=\<]+) ([\~0-9A-Za-z\+\-\.\:]+)\)$' %
+  match = re.match(r'^(%s) \(([\>\=\<]+) ([\~0-9A-Za-z\+\-\.\:]+)\)$' %
                    package_name_regex, dep)
   if match:
     (start, end) = version_interval_endpoints_from_exp(
@@ -147,7 +147,7 @@ def parse_dep(dep):
 
 
 def parse_interval_set(deps):
-  """Parses a disjunction of package version requirements.
+  r"""Parses a disjunction of package version requirements.
 
   Args:
       deps: A string of the format
index b975de0..2f96919 100755 (executable)
@@ -354,7 +354,7 @@ class DocWriter(xml_formatted_writer.XMLFormattedWriter):
     self.AddText(element, '%s: %s' % (policy['name'], example))
 
   def _AddDictionaryExample(self, parent, policy):
-    '''Adds the example value of a 'dict' or 'external' policy to a DOM node.
+    r'''Adds the example value of a 'dict' or 'external' policy to a DOM node.
 
     Example output:
     <dl>
index 7534464..a6062ae 100755 (executable)
@@ -41,139 +41,140 @@ prefix /*i18n-content*/
 """
 
 def LoadTagsFromGrd(filename):
-  xml = minidom.parse(filename)
-  android_tags = []
-  other_tags = []
-  msgs_and_structs = xml.getElementsByTagName("message")
-  msgs_and_structs.extend(xml.getElementsByTagName("structure"))
-  for res in msgs_and_structs:
-    name = res.getAttribute("name")
-    if not name or not name.startswith("IDS_"):
-      raise Exception("Tag name doesn't start with IDS_: %s" % name)
-    name = name[4:]
-    if 'android_java' in res.getAttribute('formatter_data'):
-      android_tags.append(name)
-    else:
-      other_tags.append(name)
-  return android_tags, other_tags
+    xml = minidom.parse(filename)
+    android_tags = []
+    other_tags = []
+    msgs_and_structs = xml.getElementsByTagName("message")
+    msgs_and_structs.extend(xml.getElementsByTagName("structure"))
+    for res in msgs_and_structs:
+        name = res.getAttribute("name")
+        if not name or not name.startswith("IDS_"):
+            raise Exception("Tag name doesn't start with IDS_: %s" % name)
+        name = name[4:]
+        if 'android_java' in res.getAttribute('formatter_data'):
+            android_tags.append(name)
+        else:
+            other_tags.append(name)
+    return android_tags, other_tags
 
 
 def ExtractTagFromLine(file_type, line):
-  """Extract a tag from a line of HTML, C++, JS or JSON."""
-  if file_type == "html":
-    # HTML-style (tags)
-    m = re.search('i18n-content=[\'"]([^\'"]*)[\'"]', line)
-    if m: return m.group(1)
-    # HTML-style (titles)
-    m = re.search('i18n-title=[\'"]([^\'"]*)[\'"]', line)
-    if m: return m.group(1)
-    # HTML-style (substitutions)
-    m = re.search('i18n-value-name-[1-9]=[\'"]([^\'"]*)[\'"]', line)
-    if m: return m.group(1)
-  elif file_type == 'js':
-    # Javascript style
-    m = re.search('/\*i18n-content\*/[\'"]([^\`"]*)[\'"]', line)
-    if m: return m.group(1)
-  elif file_type == 'cc' or file_type == 'mm':
-    # C++ style
-    m = re.search('IDS_([A-Z0-9_]*)', line)
-    if m: return m.group(1)
-    m = re.search('/\*i18n-content\*/["]([^\`"]*)["]', line)
-    if m: return m.group(1)
-  elif file_type == 'json.jinja2':
-    # Manifest style
-    m = re.search('__MSG_(.*)__', line)
-    if m: return m.group(1)
-  elif file_type == 'jinja2':
-    # Jinja2 template file
-    m = re.search('\{\%\s+trans\s+\%\}([A-Z0-9_]+)\{\%\s+endtrans\s+\%\}', line)
-    if m: return m.group(1)
-  return None
+    """Extract a tag from a line of HTML, C++, JS or JSON."""
+    if file_type == "html":
+        # HTML-style (tags)
+        m = re.search(r'i18n-content=[\'"]([^\'"]*)[\'"]', line)
+        if m: return m.group(1)
+        # HTML-style (titles)
+        m = re.search(r'i18n-title=[\'"]([^\'"]*)[\'"]', line)
+        if m: return m.group(1)
+        # HTML-style (substitutions)
+        m = re.search(r'i18n-value-name-[1-9]=[\'"]([^\'"]*)[\'"]', line)
+        if m: return m.group(1)
+    elif file_type == 'js':
+        # Javascript style
+        m = re.search(r'/\*i18n-content\*/[\'"]([^\`"]*)[\'"]', line)
+        if m: return m.group(1)
+    elif file_type == 'cc' or file_type == 'mm':
+        # C++ style
+        m = re.search(r'IDS_([A-Z0-9_]*)', line)
+        if m: return m.group(1)
+        m = re.search(r'/\*i18n-content\*/["]([^\`"]*)["]', line)
+        if m: return m.group(1)
+    elif file_type == 'json.jinja2':
+        # Manifest style
+        m = re.search(r'__MSG_(.*)__', line)
+        if m: return m.group(1)
+    elif file_type == 'jinja2':
+        # Jinja2 template file
+        m = re.search(r'\{\%\s+trans\s+\%\}([A-Z0-9_]+)\{\%\s+endtrans\s+\%\}',
+                      line)
+        if m: return m.group(1)
+    return None
 
 
 def VerifyFile(filename, messages, used_tags):
-  """
+    """
   Parse |filename|, looking for tags and report any that are not included in
   |messages|. Return True if all tags are present and correct, or False if
   any are missing.
   """
 
-  base_name, file_type = os.path.splitext(filename)
-  file_type = file_type[1:]
-  if file_type == 'jinja2' and base_name.endswith('.json'):
-    file_type = 'json.jinja2'
-  if file_type not in ['js', 'cc', 'html', 'json.jinja2', 'jinja2', 'mm']:
-    raise Exception("Unknown file type: %s" % file_type)
-
-  result = True
-  matches = False
-  f = open(filename, 'r')
-  lines = f.readlines()
-  for i in range(0, len(lines)):
-    tag = ExtractTagFromLine(file_type, lines[i])
-    if tag:
-      tag = tag.upper()
-      used_tags.add(tag)
-      matches = True
-      if not tag in messages:
-        result = False
-        print('%s/%s:%d: error: Undefined tag: %s' %
-            (os.getcwd(), filename, i + 1, tag))
-  f.close()
-  return result
+    base_name, file_type = os.path.splitext(filename)
+    file_type = file_type[1:]
+    if file_type == 'jinja2' and base_name.endswith('.json'):
+        file_type = 'json.jinja2'
+    if file_type not in ['js', 'cc', 'html', 'json.jinja2', 'jinja2', 'mm']:
+        raise Exception("Unknown file type: %s" % file_type)
+
+    result = True
+    matches = False
+    f = open(filename, 'r')
+    lines = f.readlines()
+    for i in range(0, len(lines)):
+        tag = ExtractTagFromLine(file_type, lines[i])
+        if tag:
+            tag = tag.upper()
+            used_tags.add(tag)
+            matches = True
+            if not tag in messages:
+                result = False
+                print('%s/%s:%d: error: Undefined tag: %s' %
+                    (os.getcwd(), filename, i + 1, tag))
+    f.close()
+    return result
 
 
 def main():
-  parser = optparse.OptionParser(
-      usage='Usage: %prog [options...] [source_file...]')
-  parser.add_option('-t', '--touch', dest='touch',
-                    help='File to touch when finished.')
-  parser.add_option('-r', '--grd', dest='grd', action='append',
-                    help='grd file')
-  parser.add_option('--strict', dest='strict', action='store_true',
-                    help='Use strict verification checks.')
-
-  options, args = parser.parse_args()
-  if not options.touch:
-    print('-t is not specified.')
-    return 1
-  if len(options.grd) == 0 or len(args) == 0:
-    print('At least one GRD file needs to be specified.')
-    return 1
-
-  all_resources = []
-  non_android_resources = []
-  for f in options.grd:
-    android_tags, other_tags = LoadTagsFromGrd(f)
-    all_resources.extend(android_tags + other_tags)
-    non_android_resources.extend(other_tags)
-
-  used_tags = set([])
-  exit_code = 0
-  for f in args:
-    if not VerifyFile(f, all_resources, used_tags):
-      exit_code = 1
-
-  if options.strict:
-    warnings = False
-    # Determining if a resource is being used in the Android app is tricky
-    # because it requires annotating and parsing Android XML layout files.
-    # For now, exclude Android strings from this check.
-    for tag in non_android_resources:
-      if tag not in used_tags:
-        print('%s/%s:0: warning: %s is defined but not used' %
-            (os.getcwd(), sys.argv[2], tag))
-        warnings = True
-    if warnings:
-      print(WARNING_MESSAGE)
-
-  if exit_code == 0:
-    f = open(options.touch, 'a')
-    f.close()
-    os.utime(options.touch, None)
-
-  return exit_code
+    parser = optparse.OptionParser(
+        usage='Usage: %prog [options...] [source_file...]')
+    parser.add_option('-t', '--touch', dest='touch',
+                      help='File to touch when finished.')
+    parser.add_option('-r', '--grd', dest='grd', action='append',
+                      help='grd file')
+    parser.add_option('--strict', dest='strict', action='store_true',
+                      help='Use strict verification checks.')
+
+    options, args = parser.parse_args()
+    if not options.touch:
+        print('-t is not specified.')
+        return 1
+    if len(options.grd) == 0 or len(args) == 0:
+        print('At least one GRD file needs to be specified.')
+        return 1
+
+    all_resources = []
+    non_android_resources = []
+    for f in options.grd:
+        android_tags, other_tags = LoadTagsFromGrd(f)
+        all_resources.extend(android_tags + other_tags)
+        non_android_resources.extend(other_tags)
+
+    used_tags = set([])
+    exit_code = 0
+    for f in args:
+        if not VerifyFile(f, all_resources, used_tags):
+            exit_code = 1
+
+    if options.strict:
+        warnings = False
+        # Determining if a resource is being used in the Android app is tricky
+        # because it requires annotating and parsing Android XML layout files.
+        # For now, exclude Android strings from this check.
+        for tag in non_android_resources:
+            if tag not in used_tags:
+                print('%s/%s:0: warning: %s is defined but not used' %
+                    (os.getcwd(), sys.argv[2], tag))
+                warnings = True
+        if warnings:
+            print(WARNING_MESSAGE)
+
+    if exit_code == 0:
+        f = open(options.touch, 'a')
+        f.close()
+        os.utime(options.touch, None)
+
+    return exit_code
 
 
 if __name__ == '__main__':
-  sys.exit(main())
+    sys.exit(main())
index 0c1e00f..21e6d09 100644 (file)
@@ -9,6 +9,7 @@
 # See python fnmatch module documentation for more information.
 
 Anton Zub <azb.0x7dc@gmail.com>
+Ho Cheung <uioptt24@gmail.com>
 Jincheol Jo <jincheol.jo@navercorp.com>
 Kris Selden <kris.selden@gmail.com>
 Maciek Weksej <maciek.weksej@gmail.com>
index 991652c..d10537a 100644 (file)
@@ -18,7 +18,7 @@ class HTMLGenerationController(object):
 
   def GetHTMLForInlineStylesheet(self, contents):
     if self.current_module is None:
-      if re.search('url\(.+\)', contents):
+      if re.search(r'url\(.+\)', contents):
         raise Exception(
             'Default HTMLGenerationController cannot handle inline style urls')
       return contents
index 6e6ca9d..c03187c 100644 (file)
@@ -4,4 +4,4 @@
 
 
 def EscapeJSIfNeeded(js):
-  return js.replace('</script>', '<\/script>')
+  return js.replace('</script>', r'<\/script>')
index 9c46267..19d7ef6 100644 (file)
@@ -293,6 +293,6 @@ class HTMLModuleParser():
       html = ''
     else:
       if html.find('< /script>') != -1:
-        raise Exception('Escape script tags with <\/script>')
+        raise Exception(r'Escape script tags with <\/script>')
 
     return HTMLModuleParserResults(html)
index 2ffc4cc..7a0fdc3 100644 (file)
@@ -60,7 +60,7 @@ class ParsedStyleSheet(object):
       return 'url(data:image/%s;base64,%s)' % (ext[1:], data.decode('utf-8'))
 
     # I'm assuming we only have url()'s associated with images
-    return re.sub('url\((?P<quote>"|\'|)(?P<url>[^"\'()]*)(?P=quote)\)',
+    return re.sub(r'url\((?P<quote>"|\'|)(?P<url>[^"\'()]*)(?P=quote)\)',
                   InlineUrl, self.contents)
 
   def AppendDirectlyDependentFilenamesTo(self, dependent_filenames):
@@ -72,7 +72,7 @@ class ParsedStyleSheet(object):
       raise Exception('@imports are not supported')
 
     matches = re.findall(
-        'url\((?:["|\']?)([^"\'()]*)(?:["|\']?)\)',
+        r'url\((?:["|\']?)([^"\'()]*)(?:["|\']?)\)',
         self.contents)
 
     def resolve_url(url):
index bb21701..edca74d 100755 (executable)
@@ -6,7 +6,7 @@
 from __future__ import print_function
 
 import argparse
-import imp
+import importlib.util
 import os
 import re
 import sys
@@ -170,9 +170,11 @@ def load_module_from_path(module_path):
     if module:
       d = module.__path__
       full_module_name += '.'
-    r = imp.find_module(package_name, d)
-    full_module_name += package_name
-    module = imp.load_module(full_module_name, *r)
+    spec = importlib.util.find_spec(full_module_name + package_name, d)
+    if spec:
+      module = importlib.util.module_from_spec(spec)
+      spec.loader.exec_module(module)
+      full_module_name += package_name
   return module
 
 
index ad4cbaa..f3bf6a4 100644 (file)
@@ -3,6 +3,12 @@ Changelog for six
 
 This file lists the changes in each six version.
 
+1.16.0
+------
+
+- Pull request #343, issue #341, pull request #349: Port _SixMetaPathImporter to
+  Python 3.10.
+
 1.15.0
 ------
 
@@ -100,7 +106,7 @@ This file lists the changes in each six version.
 
 - Issue #98: Fix `six.moves` race condition in multi-threaded code.
 
-- Pull request #51: Add `six.view(keys|values|itmes)`, which provide dictionary
+- Pull request #51: Add `six.view(keys|values|items)`, which provide dictionary
   views on Python 2.7+.
 
 - Issue #112: `six.moves.reload_module` now uses the importlib module on
@@ -227,7 +233,7 @@ This file lists the changes in each six version.
 - Issue #40: Add import mapping for the Python 2 gdbm module.
 
 - Issue #35: On Python versions less than 2.7, print_ now encodes unicode
-  strings when outputing to standard streams. (Python 2.7 handles this
+  strings when outputting to standard streams. (Python 2.7 handles this
   automatically.)
 
 1.4.1
index 75aba67..1e57620 100644 (file)
@@ -1,6 +1,6 @@
 Metadata-Version: 1.2
 Name: six
-Version: 1.15.0
+Version: 1.16.0
 Summary: Python 2 and 3 compatibility utilities
 Home-page: https://github.com/benjaminp/six
 Author: Benjamin Peterson
index ee628a9..560a773 100644 (file)
@@ -1,16 +1,7 @@
-Six is a Python 2 and 3 compatibility library.  It provides utility functions
-for smoothing over the differences between the Python versions with the goal of
-writing Python code that is compatible on both Python versions.  See the
-documentation for more information on what is provided.
+Six is a Python 2 and 3 compatibility library. It provides utility functions for smoothing over the differences between the Python versions with the goal of writing Python code that is compatible on both Python versions. See the documentation for more information on what is provided.
 
-Six supports every Python version since 2.6.  It is contained in only one Python
-file, so it can be easily copied into your project. (The copyright and license
-notice must be retained.)
+Six supports Python 2.7 and 3.3+. It is contained in only one Python file, so it can be easily copied into your project. (The copyright and license notice must be retained.)
 
-Online documentation is at https://pythonhosted.org/six/.
+Online documentation is at https://six.readthedocs.io/.
 
-Bugs can be reported to https://bitbucket.org/gutworth/six.  The code can also
-be found there.
-
-For questions about six or porting in general, email the python-porting mailing
-list: https://mail.python.org/mailman/listinfo/python-porting
+Bugs can be reported to https://github.com/benjaminp/six. The code can also be found there.
\ No newline at end of file
index 6f7a9cb..3021912 100644 (file)
@@ -1,7 +1,7 @@
 Name: six
 URL: https://pypi.org/project/six/
-Version: 1.15.0
-Date: 2021-03-02
+Version: 1.16.0
+Date: 2021-05-05
 License: MIT
 License File: LICENSE
 Security Critical: no
index 75aba67..1e57620 100644 (file)
@@ -1,6 +1,6 @@
 Metadata-Version: 1.2
 Name: six
-Version: 1.15.0
+Version: 1.16.0
 Summary: Python 2 and 3 compatibility utilities
 Home-page: https://github.com/benjaminp/six
 Author: Benjamin Peterson
index 83f6978..4e15675 100644 (file)
@@ -29,7 +29,7 @@ import sys
 import types
 
 __author__ = "Benjamin Peterson <benjamin@python.org>"
-__version__ = "1.15.0"
+__version__ = "1.16.0"
 
 
 # Useful for very coarse version differentiation.
@@ -71,6 +71,11 @@ else:
             MAXSIZE = int((1 << 63) - 1)
         del X
 
+if PY34:
+    from importlib.util import spec_from_loader
+else:
+    spec_from_loader = None
+
 
 def _add_doc(func, doc):
     """Add documentation to a function."""
@@ -186,6 +191,11 @@ class _SixMetaPathImporter(object):
             return self
         return None
 
+    def find_spec(self, fullname, path, target=None):
+        if fullname in self.known_modules:
+            return spec_from_loader(fullname, self)
+        return None
+
     def __get_module(self, fullname):
         try:
             return self.known_modules[fullname]
@@ -223,6 +233,12 @@ class _SixMetaPathImporter(object):
         return None
     get_source = get_code  # same as get_code
 
+    def create_module(self, spec):
+        return self.load_module(spec.name)
+
+    def exec_module(self, module):
+        pass
+
 _importer = _SixMetaPathImporter(__name__)
 
 
index d06f8a8..d31afbe 100644 (file)
@@ -257,7 +257,7 @@ class ChildType(object):
 
 
 class ObjectNodeType(NodeType):
-  """A complex node type that has attributes or other nodes as children.
+  r"""A complex node type that has attributes or other nodes as children.
 
   Unmarshalls nodes to objects.
 
@@ -268,7 +268,7 @@ class ObjectNodeType(NodeType):
         attributes, when serializing objects to XML. The "regex" can be None
         to do no validation, otherwise the attribute must match that pattern.
     text_attribute: An attribute stored in the text content of the node.
-    children: A list of ChildTypes describing the objects children.
+    children: A list of ChildTypes describing the objects' children.
 
   Raises:
     ValueError: Attributes contains duplicate definitions.