mirror of
				https://github.com/python/cpython.git
				synced 2025-11-03 23:21:29 +00:00 
			
		
		
		
	svn+ssh://pythondev@svn.python.org/sandbox/trunk/2to3/lib2to3 ........ r67427 | benjamin.peterson | 2008-11-28 16:07:41 -0600 (Fri, 28 Nov 2008) | 1 line fix spelling in comment ........ r67431 | benjamin.peterson | 2008-11-28 17:14:08 -0600 (Fri, 28 Nov 2008) | 1 line add a scripts directory; move things to it ........ r67433 | benjamin.peterson | 2008-11-28 17:18:48 -0600 (Fri, 28 Nov 2008) | 1 line run svneol.py ........ r67435 | benjamin.peterson | 2008-11-28 17:25:03 -0600 (Fri, 28 Nov 2008) | 1 line rename pre/post_order_mapping to pre/post_order_heads ........ r67630 | alexandre.vassalotti | 2008-12-06 21:51:56 -0600 (Sat, 06 Dec 2008) | 2 lines Fix typo in the urllib2.HTTPDigestAuthHandler fixer. ........ r67652 | armin.ronacher | 2008-12-07 15:39:43 -0600 (Sun, 07 Dec 2008) | 5 lines Added a fixer that cleans up a tuple argument to isinstance after the tokens in it were fixed. This is mainly used to remove double occurrences of tokens as a leftover of the long -> int / unicode -> str conversion. ........ r67656 | armin.ronacher | 2008-12-07 16:54:16 -0600 (Sun, 07 Dec 2008) | 3 lines Added missing copyright fo 2to3 fix_isinstance. ........ r67657 | armin.ronacher | 2008-12-07 18:29:35 -0600 (Sun, 07 Dec 2008) | 3 lines 2to3: intern and reduce fixes now add the imports if missing. Because that is a common task the fixer_util module now has a function "touch_import" that adds imports if missing. ........ r67674 | benjamin.peterson | 2008-12-08 19:58:11 -0600 (Mon, 08 Dec 2008) | 1 line copy permission bits when making backup files #4602 ........ r67675 | benjamin.peterson | 2008-12-08 19:59:11 -0600 (Mon, 08 Dec 2008) | 1 line add forgotten import ........ r67678 | benjamin.peterson | 2008-12-08 20:08:30 -0600 (Mon, 08 Dec 2008) | 1 line fix #4602 for real ........ r67679 | armin.ronacher | 2008-12-09 00:54:03 -0600 (Tue, 09 Dec 2008) | 3 lines Removed redudant code from the 2to3 long fixer. This fixes #4590. ........ r67705 | benjamin.peterson | 2008-12-11 13:04:08 -0600 (Thu, 11 Dec 2008) | 1 line put trailers after a range call after the list() ........ r67706 | benjamin.peterson | 2008-12-11 13:17:57 -0600 (Thu, 11 Dec 2008) | 1 line add html related modules to the fix_imports mapping ........ r67716 | benjamin.peterson | 2008-12-11 22:16:47 -0600 (Thu, 11 Dec 2008) | 1 line consolidate tests ........ r67723 | benjamin.peterson | 2008-12-12 19:49:31 -0600 (Fri, 12 Dec 2008) | 1 line fix name ........ r67765 | benjamin.peterson | 2008-12-14 14:05:05 -0600 (Sun, 14 Dec 2008) | 1 line run fix_isinstance after fix_long and fix_unicode ........ r67766 | benjamin.peterson | 2008-12-14 14:13:05 -0600 (Sun, 14 Dec 2008) | 1 line use run_order instead of order ........ r67767 | benjamin.peterson | 2008-12-14 14:28:12 -0600 (Sun, 14 Dec 2008) | 1 line don't retain parenthesis if there is only one item left ........ r67768 | benjamin.peterson | 2008-12-14 14:32:30 -0600 (Sun, 14 Dec 2008) | 1 line use insert_child() ........ r67769 | benjamin.peterson | 2008-12-14 14:59:10 -0600 (Sun, 14 Dec 2008) | 1 line parenthesize doesn't belong in pygram or FixerBase ........ r67770 | alexandre.vassalotti | 2008-12-14 15:15:36 -0600 (Sun, 14 Dec 2008) | 2 lines Fix typo: html.paser -> html.parser. ........ r67771 | benjamin.peterson | 2008-12-14 15:22:09 -0600 (Sun, 14 Dec 2008) | 1 line altering .children needs to call changed() ........ r67774 | benjamin.peterson | 2008-12-14 15:55:38 -0600 (Sun, 14 Dec 2008) | 1 line employ an evil hack to fix multiple names in the same import statement ........ r67776 | benjamin.peterson | 2008-12-14 16:22:38 -0600 (Sun, 14 Dec 2008) | 1 line make a common mixin class for Test_imports and friends ........ r67778 | alexandre.vassalotti | 2008-12-14 17:48:20 -0600 (Sun, 14 Dec 2008) | 2 lines Make fix_imports refactor multiple imports as. ........
		
			
				
	
	
		
			177 lines
		
	
	
	
		
			7.1 KiB
		
	
	
	
		
			Python
		
	
	
	
	
	
			
		
		
	
	
			177 lines
		
	
	
	
		
			7.1 KiB
		
	
	
	
		
			Python
		
	
	
	
	
	
"""Fix changes imports of urllib which are now incompatible.
 | 
						|
   This is rather similar to fix_imports, but because of the more
 | 
						|
   complex nature of the fixing for urllib, it has its own fixer.
 | 
						|
"""
 | 
						|
# Author: Nick Edds
 | 
						|
 | 
						|
# Local imports
 | 
						|
from .fix_imports import alternates, FixImports
 | 
						|
from .. import fixer_base
 | 
						|
from ..fixer_util import Name, Comma, FromImport, Newline, attr_chain
 | 
						|
 | 
						|
MAPPING = {'urllib':  [
 | 
						|
                ('urllib.request',
 | 
						|
                    ['URLOpener', 'FancyURLOpener', 'urlretrieve',
 | 
						|
                     '_urlopener', 'urlcleanup']),
 | 
						|
                ('urllib.parse',
 | 
						|
                    ['quote', 'quote_plus', 'unquote', 'unquote_plus',
 | 
						|
                     'urlencode', 'pahtname2url', 'url2pathname']),
 | 
						|
                ('urllib.error',
 | 
						|
                    ['ContentTooShortError'])],
 | 
						|
           'urllib2' : [
 | 
						|
                ('urllib.request',
 | 
						|
                    ['urlopen', 'install_opener', 'build_opener',
 | 
						|
                     'Request', 'OpenerDirector', 'BaseHandler',
 | 
						|
                     'HTTPDefaultErrorHandler', 'HTTPRedirectHandler',
 | 
						|
                     'HTTPCookieProcessor', 'ProxyHandler',
 | 
						|
                     'HTTPPasswordMgr',
 | 
						|
                     'HTTPPasswordMgrWithDefaultRealm',
 | 
						|
                     'AbstractBasicAuthHandler',
 | 
						|
                     'HTTPBasicAuthHandler', 'ProxyBasicAuthHandler',
 | 
						|
                     'AbstractDigestAuthHandler',
 | 
						|
                     'HTTPDigestAuthHandler', 'ProxyDigestAuthHandler',
 | 
						|
                     'HTTPHandler', 'HTTPSHandler', 'FileHandler',
 | 
						|
                     'FTPHandler', 'CacheFTPHandler',
 | 
						|
                     'UnknownHandler']),
 | 
						|
                ('urllib.error',
 | 
						|
                    ['URLError', 'HTTPError'])],
 | 
						|
}
 | 
						|
 | 
						|
 | 
						|
# def alternates(members):
 | 
						|
#     return "(" + "|".join(map(repr, members)) + ")"
 | 
						|
 | 
						|
 | 
						|
def build_pattern():
 | 
						|
    bare = set()
 | 
						|
    for old_module, changes in MAPPING.items():
 | 
						|
        for change in changes:
 | 
						|
            new_module, members = change
 | 
						|
            members = alternates(members)
 | 
						|
            yield """import_name< 'import' (module=%r
 | 
						|
                                  | dotted_as_names< any* module=%r any* >) >
 | 
						|
                  """ % (old_module, old_module)
 | 
						|
            yield """import_from< 'from' mod_member=%r 'import'
 | 
						|
                       ( member=%s | import_as_name< member=%s 'as' any > |
 | 
						|
                         import_as_names< members=any*  >) >
 | 
						|
                  """ % (old_module, members, members)
 | 
						|
            yield """import_from< 'from' module_star=%r 'import' star='*' >
 | 
						|
                  """ % old_module
 | 
						|
            yield """import_name< 'import'
 | 
						|
                                  dotted_as_name< module_as=%r 'as' any > >
 | 
						|
                  """ % old_module
 | 
						|
            yield """power< module_dot=%r trailer< '.' member=%s > any* >
 | 
						|
                  """ % (old_module, members)
 | 
						|
 | 
						|
 | 
						|
class FixUrllib(FixImports):
 | 
						|
 | 
						|
    def build_pattern(self):
 | 
						|
        return "|".join(build_pattern())
 | 
						|
 | 
						|
    def transform_import(self, node, results):
 | 
						|
        """Transform for the basic import case. Replaces the old
 | 
						|
           import name with a comma separated list of its
 | 
						|
           replacements.
 | 
						|
        """
 | 
						|
        import_mod = results.get('module')
 | 
						|
        pref = import_mod.get_prefix()
 | 
						|
 | 
						|
        names = []
 | 
						|
 | 
						|
        # create a Node list of the replacement modules
 | 
						|
        for name in MAPPING[import_mod.value][:-1]:
 | 
						|
            names.extend([Name(name[0], prefix=pref), Comma()])
 | 
						|
        names.append(Name(MAPPING[import_mod.value][-1][0], prefix=pref))
 | 
						|
        import_mod.replace(names)
 | 
						|
 | 
						|
    def transform_member(self, node, results):
 | 
						|
        """Transform for imports of specific module elements. Replaces
 | 
						|
           the module to be imported from with the appropriate new
 | 
						|
           module.
 | 
						|
        """
 | 
						|
        mod_member = results.get('mod_member')
 | 
						|
        pref = mod_member.get_prefix()
 | 
						|
        member = results.get('member')
 | 
						|
 | 
						|
        # Simple case with only a single member being imported
 | 
						|
        if member:
 | 
						|
            # this may be a list of length one, or just a node
 | 
						|
            if isinstance(member, list):
 | 
						|
                member = member[0]
 | 
						|
            new_name = None
 | 
						|
            for change in MAPPING[mod_member.value]:
 | 
						|
                if member.value in change[1]:
 | 
						|
                    new_name = change[0]
 | 
						|
                    break
 | 
						|
            if new_name:
 | 
						|
                mod_member.replace(Name(new_name, prefix=pref))
 | 
						|
            else:
 | 
						|
                self.cannot_convert(node,
 | 
						|
                                    'This is an invalid module element')
 | 
						|
 | 
						|
        # Multiple members being imported
 | 
						|
        else:
 | 
						|
            # a dictionary for replacements, order matters
 | 
						|
            modules = []
 | 
						|
            mod_dict = {}
 | 
						|
            members = results.get('members')
 | 
						|
            for member in members:
 | 
						|
                member = member.value
 | 
						|
                # we only care about the actual members
 | 
						|
                if member != ',':
 | 
						|
                    for change in MAPPING[mod_member.value]:
 | 
						|
                        if member in change[1]:
 | 
						|
                            if change[0] in mod_dict:
 | 
						|
                                mod_dict[change[0]].append(member)
 | 
						|
                            else:
 | 
						|
                                mod_dict[change[0]] = [member]
 | 
						|
                                modules.append(change[0])
 | 
						|
 | 
						|
            new_nodes = []
 | 
						|
            for module in modules:
 | 
						|
                elts = mod_dict[module]
 | 
						|
                names = []
 | 
						|
                for elt in elts[:-1]:
 | 
						|
                    names.extend([Name(elt, prefix=pref), Comma()])
 | 
						|
                names.append(Name(elts[-1], prefix=pref))
 | 
						|
                new_nodes.append(FromImport(module, names))
 | 
						|
            if new_nodes:
 | 
						|
                nodes = []
 | 
						|
                for new_node in new_nodes[:-1]:
 | 
						|
                    nodes.extend([new_node, Newline()])
 | 
						|
                nodes.append(new_nodes[-1])
 | 
						|
                node.replace(nodes)
 | 
						|
            else:
 | 
						|
                self.cannot_convert(node, 'All module elements are invalid')
 | 
						|
 | 
						|
    def transform_dot(self, node, results):
 | 
						|
        """Transform for calls to module members in code."""
 | 
						|
        module_dot = results.get('module_dot')
 | 
						|
        member = results.get('member')
 | 
						|
        # this may be a list of length one, or just a node
 | 
						|
        if isinstance(member, list):
 | 
						|
            member = member[0]
 | 
						|
        new_name = None
 | 
						|
        for change in MAPPING[module_dot.value]:
 | 
						|
            if member.value in change[1]:
 | 
						|
                new_name = change[0]
 | 
						|
                break
 | 
						|
        if new_name:
 | 
						|
            module_dot.replace(Name(new_name,
 | 
						|
                                    prefix=module_dot.get_prefix()))
 | 
						|
        else:
 | 
						|
            self.cannot_convert(node, 'This is an invalid module element')
 | 
						|
 | 
						|
    def transform(self, node, results):
 | 
						|
        if results.get('module'):
 | 
						|
            self.transform_import(node, results)
 | 
						|
        elif results.get('mod_member'):
 | 
						|
            self.transform_member(node, results)
 | 
						|
        elif results.get('module_dot'):
 | 
						|
            self.transform_dot(node, results)
 | 
						|
        # Renaming and star imports are not supported for these modules.
 | 
						|
        elif results.get('module_star'):
 | 
						|
            self.cannot_convert(node, 'Cannot handle star imports.')
 | 
						|
        elif results.get('module_as'):
 | 
						|
            self.cannot_convert(node, 'This module is now multiple modules')
 |