-
-
Notifications
You must be signed in to change notification settings - Fork 2.9k
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
Import errors in a try/except ImportError
block should be allowed
#1393
Comments
Yup. (Can you shut it up using `# type: ignore`?)
|
Yes, |
This is also the case with attribute access in try/except block, not only imports, e.g.: try:
foo = sys._MEIPASS
except AttributeError:
foo = '.' causes mypy to fail with |
We encountered this in Twine with I made a repository to reproduce the errors and try out some fixes: https://github.com/bhrutledge/mypy-importlib-metadata. That's currently passing, but the commit history has more details. |
The change is likely due to a change in typeshed (adding |
@ethanhs Thanks! I didn't know that mypy would use |
This approach is less desirable than using the try/except pattern. In particular, one must (a) import sys, (b) parse/compare sys.version_info, and (c) encode availability of module features to their various versions (which may not be a simple Is the implication of this recommendation that |
A workaround is needed because of a missing mypy feature. I don't know when the feature might be implemented, though. |
Perhaps a naive question: If mypy recognized a "try/except ImportError", could it set the type of the module object to something like |
@The-Compiler sadly that probably wouldn't work, as you want to make sure the same module is used throughout. We would probably want something closer to a type variable I believe. |
I just ran into the same thing today with this: try:
from typing import TypeAlias
except ImportError:
from typing_extensions import TypeAlias Since I have this in my pyproject.toml (rather not add an extra dependency when not necessary): [tool.poetry.dev-dependencies]
# ...
typing-extensions = {version = "^4.1.1", python = "<3.10"}
|
I've encountered this as well. From Adam Johnson's blog post, his workaround is to set a boolean flag: try:
import markdown
HAVE_MARKDOWN = True
except ImportError:
HAVE_MARKDOWN = False
def something():
...
if HAVE_MARKDOWN:
... In fact, @Michael0x2a on this SO post couples the above approach with the Alternatively, @cjerdonek has developed a nice workaround.
@The-Compiler No, I don't think it's naive at all. In fact, I believe @JukkaL hinted at this. However, @ethanhs might be right: I believe (emphasis on "believe") the root of the issue is that @JukkaL Can you confirm? AddendumBelow are gists of Adam Johnson's failed attempt and @cjerdonek's working workaround: |
MyPy can't handle a Pythonic try-except import: python/mypy#1393 We could put # type: ignore[attr-defined] except then whichever branch actually passed on the currently installed version of the module would fail due to having an apparently-unneeded ignore.
* Use a vg-like system toa void needing a Kubernetes docker builder * Specify inline caching correctly * Drop extra import * Fix the wandering typedef two ways * Fix it only one way MyPy can't handle a Pythonic try-except import: python/mypy#1393 We could put # type: ignore[attr-defined] except then whichever branch actually passed on the currently installed version of the module would fail due to having an apparently-unneeded ignore. * Manually force out busted stubs package
I'm going to close this issue. I don't think type checkers should do the fully general thing of ignore type errors in See also #1153 (comment) / #8823 (comment) |
I agree that mypy definitely shouldn't support checked exceptions in general, but Even if the decision is that we shouldn't implement any special-casing here, in order to remain consistent about never understanding any exception handling, I still think we could add a better error message to point users towards what they should do instead. This is one of the most popular feature requests on the issue tracker, and I think that's evidence that this is a real problem that users are facing. |
This issue was opened in 2016 and there's a lot that has changed since then. In particular, I fixed the most common case of this a couple months ago: where a conditional import redefines a symbol with exactly the same structural type. I think in #13969, but some other PRs were involved as well Like I mention in the comment I link to, the issue is about providing guarantees about the rest of the code. I'm happy to leave issues open if we can tweak an error message, but I'm not seeing many additional things to implement that are a good combination of viable and sound, so a broad issue like this isn't super actionable. The main workable thing I can think of is doing something for |
As the original issue author, I agree that a lot has changed. I no longer really need this, because the main case where it came up for me was in code that needed support for Python 2 and 3 simultaneously. I still have a few places with lingering |
Python 2 may be no longer relevant, but |
In most cases, guarding your typing imports with |
That doesn't work for anything examining the types at runtime, and also for types used outside annotations (such as class definitions, decorators, typevarlike definitions, etc). |
**Pull Request Checklist** - [ ] Fixes #<!--issue number goes here--> - [ ] Tests added - [ ] Documentation/examples added - [X] [Good commit messages](https://cbea.ms/git-commit/) and/or PR title **Description of PR** Currently, conditional imports that depend on Python version are using `try/except ImportError` to import from `typing_extensions` on older Python versions. This is not natively supported by typecheckers, forcing use of error suppression, and losing potential validation of downstream code. (Additionally, pyright is erroneously flagging a lot of code that uses `Annotated` with "Call expression not allowed in type expression, making it harder to spot real issues in VSCode.) This PR refactors these conditional imports to use the recommended `if sys.version_info >= (3, minor):` pattern instead. See also: [mypy issue comment](python/mypy#1393 (comment)), [pyright issue comment](microsoft/pyright#4160 (comment)) Signed-off-by: Alice Purcell <alicederyn@gmail.com>
When this pattern is checked in py2 mode (or really any pre-3.5 version)
it raises an error
tornado/gen.py:118: error: Module has no attribute 'isawaitable'
. Instead, mypy should recognize that this is within a try/except block that catches theImportError
and choose the alternate path instead.This falls under the umbrella of #1297 but I couldn't find an exact match for this issue.
The text was updated successfully, but these errors were encountered: