Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

F823 (undefined local) triggered by a double import #6029

Closed
ajkerrigan opened this issue Jul 24, 2023 · 4 comments
Closed

F823 (undefined local) triggered by a double import #6029

ajkerrigan opened this issue Jul 24, 2023 · 4 comments
Assignees

Comments

@ajkerrigan
Copy link

ajkerrigan commented Jul 24, 2023

First, thanks for ruff! It rocks and I love it 😍 .

I ran across a minor issue recently and wanted to document it here in case other folks do too. I'm not sure if it's an intentional change or not...

Moving from version 0.0.278 to 0.0.279 I noticed F823 Local variable 'sys' referenced before assignment occurring in a new situation. If you import a module twice, this rule flags references in between the two imports. For example:

double_import.py

import sys


def main():
    print(sys.argv)

    try:
        3 / 0
    except ZeroDivisionError:
        import sys

        sys.exit(1)
ruff double_import.py
double_import.py:5:11: F823 Local variable `sys` referenced before assignment
Found 1 error.

It does feel right to call out the double import sys as unnecessary here, but F823 seems misleading. Is this change intentional?

I didn't see an obvious answer in the 0.0.279 changelog though there are a couple changes that seem possibly relevant. Will update here if I find anything useful. The change that seems most relevant at a glance (to my untrained eye anyway) is bcec2f0.

@charliermarsh
Copy link
Member

Thanks! Looks like a bug.

@ajkerrigan ajkerrigan changed the title F823 triggered by a double import F823 (undefined local) triggered by a double import Jul 24, 2023
@charliermarsh
Copy link
Member

Or, this may actually be correct? I'm not 100% sure. Python does error with an early unbound access:

Traceback (most recent call last):
  File "/Users/crmarsh/workspace/ruff/foo.py", line 22, in <module>
    main()
  File "/Users/crmarsh/workspace/ruff/foo.py", line 5, in main
    print(sys.argv)
          ^^^
UnboundLocalError: cannot access local variable 'sys' where it is not associated with a value

So in that case, F823 feels correct to me.

@ajkerrigan
Copy link
Author

Ha, you're right 😅 ! I could have seen it either way since it does feel wrong and worth yelling about one way or the other.

My first thought was looking at flake8 which runs clean on this file. But pylint yells all around the issue 😁

double_import.py:11:8: W0621: Redefining name 'sys' from outer scope (line 1) (redefined-outer-name)
double_import.py:6:10: E0601: Using variable 'sys' before assignment (used-before-assignment)
double_import.py:11:8: W0404: Reimport 'sys' (imported line 1) (reimported)
double_import.py:11:8: C0415: Import outside toplevel (sys) (import-outside-toplevel)
double_import.py:1:0: W0611: Unused import sys (unused-import)

This is also a good reminder to not just lint your minimal example but also try, you know... running it 😆 .

Thanks for the follow-up!

@charliermarsh
Copy link
Member

I had the same reaction as you, I actually thought that code was fine! I'm gonna add some test cases so that we're at least explicit about this.

charliermarsh added a commit that referenced this issue Jul 24, 2023
Making some behavior explicit / codified. See:
#6029.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants