pylint-dev / pylint

It's not just a linter that annoys you!
https://pylint.readthedocs.io/en/latest/
GNU General Public License v2.0
5.27k stars 1.13k forks source link

False positive import-error #3984

Open sam-s opened 3 years ago

sam-s commented 3 years ago

Steps to reproduce

in an empty directory:

  1. file a.py:
    def a():
    print("a")
  2. file b.py
    import a
    print(a.a())
  3. empty file __init__.py

Current behavior

pylint b.py
b.py:1: [E0401(import-error), ] Unable to import 'a'

Expected behavior

no diagnostics

Important note

if you remove __init__.py, the import-error disappears.

pylint --version output

pylint 2.6.0
astroid 2.4.2
Python 3.9.1 (default, Dec 10 2020, 10:36:35)
[Clang 12.0.0 (clang-1200.0.32.27)]
bvobart commented 3 years ago

Love how minimal this example is, I've been able to reproduce this behaviour exactly, including that the false positive import-error disappears after removing __init__.py

I'm doing research on static code analysis in machine learning code, where I run Pylint on a number of Python ML projects (after installing their requirements in a virtualenv). While this currently only includes 8 projects so far, Pylint reports each one of those as having several import-errors. I've noticed that most of those are imports from local files not being resolved correctly, even though they do indeed exist on the filesystem.

$ pylint --version
pylint 2.6.0
astroid 2.4.2
Python 3.8.6 (default, Sep 30 2020, 04:00:38) 
[GCC 10.2.0]
hippo91 commented 3 years ago

@sam-s thanks for your report. I can reproduce it.

jacobtylerwalls commented 2 years ago

I'm seeing this fixed in astroid 2.12. Let's add this test case to pylint.

DanielNoord commented 2 years ago

@jacobtylerwalls Is this still the case? 🚀

jacobtylerwalls commented 2 years ago

No, I was probably testing in a directory on sys.path, and we now know that's been polluting our test results.

Failing test for unittest_lint.py:


def test_import_sibling_module_from_explicit_package(initialized_linter: PyLinter) -> None:
    linter = initialized_linter
    with tempdir() as tmpdir:
        create_files(["siblingone.py", "siblingtwo.py", "__init__.py"], tmpdir)
        with open("siblingone.py", "w", encoding="utf-8") as f:
            f.write(
                """\"\"\"This module contains siblingone().\"\"\"
def siblingone():
    print("siblingone")
"""
            )
        with open("siblingtwo.py", "w", encoding="utf-8") as f:
            f.write(
                """\"\"\"This module imports siblingone().\"\"\"
import siblingone
print(siblingone.siblingone())
"""
            )
        linter.check(["siblingtwo"])
        assert not linter.stats.by_msg
vuongphamaioz commented 1 year ago

Hi,

I am still facing this issue with latest pylint version. pylint --version output:

pylint 2.16.2
astroid 2.14.2
Python 3.10.4 (main, Feb 15 2023, 15:33:42) [GCC 9.4.0]
vuongphamaioz commented 1 year ago

I found 2 solutions for this issue. For those who suffer from this issue like me:

  1. from . import a

    Explanation: As I understand, when we create __init__.py file, the directory which contains this file becomes a package/ module. So we need to import this as module importing syntax.

  2. Add to pylint args: init-hook="import sys; import os; sys.path.append(os.path.abspath('.'));" Explanation: Add the system path of the directory which contains a.py to pylint.

If your code structure is more complicated, modify an appropriate path value. Hope it helps!

honglei commented 1 year ago

issue remain in

pylint 2.17.4
astroid 2.15.5
Python 3.11.4 (tags/v3.11.4:d2340ef, Jun  7 2023, 05:45:37) [MSC v.1934 64 bit (AMD64)]
R0Y2 commented 4 weeks ago

For those who still facing this issue and have a similar structure like below

.
├── src
│    │ 
│    └─ pkgs
│         ├── __init__.py
│         ├── mod1.py
│         └── mod2.py  (import mod1)
│    ...   
├── pyproject.toml
└── .pylintrc

Try to add source-roots in your .pylintrc

[MAIN]
source-roots = src/pkgs

It's working in

pylint 3.2.7
astroid 3.2.4
Python 3.11.9 (main, Apr 19 2024, 16:39:34) [GCC 11.2.0]