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

Don't complain about code that catches ImportErrors #676

Closed
JukkaL opened this issue May 16, 2015 · 8 comments
Closed

Don't complain about code that catches ImportErrors #676

JukkaL opened this issue May 16, 2015 · 8 comments
Labels

Comments

@JukkaL
Copy link
Collaborator

JukkaL commented May 16, 2015

Conder this example from @benhoyt's scandir (https://github.com/benhoyt/scandir):

# Use the built-in version of scandir/walk if possible, otherwise
# use the scandir module version
try:
    from os import scandir, walk
except ImportError:
    from scandir import scandir, walk

Code like this is pretty common in Python modules that want to be backward compatible with older Python versions.

If mypy doesn't know about the scandir module (which is not in the std lib), mypy will complain about the code (note that os.scandir is Python 3.5 only, and isn't included in mypy stubs quite yet). However, I argue that the code is fine if the try block doesn't generate errors, since the except block will not be reached (unless some module is missing, but mypy assumes that all modules with a stub are available).

Here is a more formal rule:

Don't report errors for an except ImportError block if the corresponding try block only contains import statements and all the imported modules and names in the try block can be resolved.

Another related issue is code that imports a potentially non-existent module in a try block and falls back to a stdlib module in an except block. Not sure whether we should also ignore errors in the try block if the except block has no issues. Contrived example:

try:
    from scandir import scandir, walk
except ImportError:
    from os import scandir, walk

Should mypy report an error for the above code if no stub or implementation for scandir is available?

@gvanrossum
Copy link
Member

There are tons of variations on this pattern though... Some code might import a 3rd party module in preference of a stdlib one... Maybe there are assignments following the import, or in the except block some variables are set to None, or a flag is set to False, ...

@NYKevin
Copy link

NYKevin commented Sep 22, 2015

If you want to be really crazy, it would be nice to support something like this:

In __init__.py (of whatever package):

import sys
try:
    from . import _cFoo as foo
except ImportError:
    from . import _foo as foo
sys.modules[__name__ + '.foo'] = foo

But maybe that's asking a bit much. For my use case, I wrote out a separate foo.pyi file even though there is no foo.py file. That's legal, right?

@o11c
Copy link
Contributor

o11c commented Sep 22, 2015

You can also use type: ignore

@JukkaL
Copy link
Collaborator Author

JukkaL commented Oct 7, 2015

Yeah, you can always add a stub file even if there is no corresnponding .py file. If a stub exists, mypy trusts it.

@JukkaL
Copy link
Collaborator Author

JukkaL commented Oct 18, 2015

Adding 'priority' as this seems to be a very common problem when migrating existing code. We still don't have a clear understanding of how exactly we should fix this, however.

@ddfisher ddfisher added this to the Future milestone Mar 2, 2016
@ddfisher
Copy link
Collaborator

ddfisher commented Mar 2, 2016

#1107 will happen first; is more important for now.

@gnprice gnprice removed the priority label Mar 2, 2016
@gvanrossum gvanrossum removed this from the Future milestone Mar 29, 2017
@OJFord
Copy link

OJFord commented Nov 25, 2017

A similar pattern:

try:
    from foo import bar
except ImportError:
    pass
else:
    # do something with bar

Here mypy will treat bar: Any rather than whatever it actually is, even if we have stubs for it.

@JukkaL JukkaL added the false-positive mypy gave an error on correct code label May 17, 2018
@JukkaL
Copy link
Collaborator Author

JukkaL commented Jan 28, 2020

This seems too difficult to support in a general enough fashion. Using # type: ignore seems like a reasonable compromise and it already works.

@JukkaL JukkaL closed this as completed Jan 28, 2020
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

7 participants