2to3 says "No changes needed", then "files that need to be modified"
Asked Answered
S

2

14

I run 2to3 -f all -f idioms -f buffer -f set_literal -f ws_comma foo.py

Output:

RefactoringTool: No changes to foo.py
RefactoringTool: Files that need to be modified:
RefactoringTool: foo.py

Contents of foo.py:

print("Hi")

How do I interpret this output?

Smug answered 25/10, 2016 at 12:39 Comment(0)
M
8

The modification is triggered by the unicode fixer. This fixer will interpret the content of every string literals, and tries to re-escape the invalid Unicode sequences, and remove the u/U string prefix:

def transform(self, node, results):
    ...
    elif node.type == token.STRING:
        # 1. Replace the invalid \u sequences.
        val = node.value
        if not self.unicode_literals and val[0] in '\'"' and '\\' in val:
            val = r'\\'.join([
                v.replace('\\u', r'\\u').replace('\\U', r'\\U')
                for v in val.split(r'\\')
            ])

        # 2. Strip the leading `u` in u"...."
        if val[0] in 'uU':
            val = val[1:]

        # 3. If the whole string is the same, return the original node.
        if val == node.value:
            return node   # <--------------

        # 4. Otherwise, create a new node.
        new = node.clone()
        new.value = val
        return new

For some unknown reason (bug?), even if the original node is returned in step 3, lib2to3 still interpreted that as the token tree being changed, so it says "Files that need to be modified". However, the actual source code is the same, so there are "No changes to foo.py".

If step 3 returns None instead, it will truly say "No files need to be modified".

The affected files will just be rewritten with the original input. So the bug is harmless.

Megacycle answered 25/10, 2016 at 13:1 Comment(0)
L
8

According to Steven D'Aprano, this is a bug and the second line of text in your output should be interpreted as:

Files that include something that a fixer cares about, whether or not it gets modified.

In your case, the foo.py code is perfectly compatible with Python 3 and no changes are needed as the first line of your output states.

Lachesis answered 25/10, 2016 at 12:54 Comment(2)
By "something that the fixer cares about"... what does that mean? Do I have to care?Smug
@JETM To clarify, it means the file was inspected, not that changes are neededLachesis
M
8

The modification is triggered by the unicode fixer. This fixer will interpret the content of every string literals, and tries to re-escape the invalid Unicode sequences, and remove the u/U string prefix:

def transform(self, node, results):
    ...
    elif node.type == token.STRING:
        # 1. Replace the invalid \u sequences.
        val = node.value
        if not self.unicode_literals and val[0] in '\'"' and '\\' in val:
            val = r'\\'.join([
                v.replace('\\u', r'\\u').replace('\\U', r'\\U')
                for v in val.split(r'\\')
            ])

        # 2. Strip the leading `u` in u"...."
        if val[0] in 'uU':
            val = val[1:]

        # 3. If the whole string is the same, return the original node.
        if val == node.value:
            return node   # <--------------

        # 4. Otherwise, create a new node.
        new = node.clone()
        new.value = val
        return new

For some unknown reason (bug?), even if the original node is returned in step 3, lib2to3 still interpreted that as the token tree being changed, so it says "Files that need to be modified". However, the actual source code is the same, so there are "No changes to foo.py".

If step 3 returns None instead, it will truly say "No files need to be modified".

The affected files will just be rewritten with the original input. So the bug is harmless.

Megacycle answered 25/10, 2016 at 13:1 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.