问题:PyLint“无法导入”错误-如何设置PYTHONPATH?

我正在Windows的Wing IDE中运行PyLint。我的项目中有一个子目录(程序包),在程序包中,我从顶层(即)导入模块。

__init__.py
myapp.py
one.py
subdir\
    __init__.py
    two.py

two.py我的内部import one,这在运行时效果很好,因为顶层目录(从中myapp.py运行)位于Python路径中。但是,当我在two.py上运行PyLint时,出现了一个错误:

F0401: Unable to import 'one'

我该如何解决?

I’m running PyLint from inside Wing IDE on Windows. I have a sub-directory (package) in my project and inside the package I import a module from the top level, ie.

__init__.py
myapp.py
one.py
subdir\
    __init__.py
    two.py

Inside two.py I have import one and this works fine at runtime, because the top-level directory (from which myapp.py is run) is in the Python path. However, when I run PyLint on two.py it gives me an error:

F0401: Unable to import 'one'

How do I fix this?


回答 0

我知道有两个选择。

一,更改PYTHONPATH环境变量,使其包含模块上方的目录。

或者,编辑~/.pylintrc以包括模块上方的目录,如下所示:

[MASTER]
init-hook='import sys; sys.path.append("/path/to/root")'

(或者在其他版本的pylint中,init-hook要求您将[General]更改为[MASTER])

这两个选项都应该起作用。

希望有帮助。

There are two options I’m aware of.

One, change the PYTHONPATH environment variable to include the directory above your module.

Alternatively, edit ~/.pylintrc to include the directory above your module, like this:

[MASTER]
init-hook='import sys; sys.path.append("/path/to/root")'

(Or in other version of pylint, the init-hook requires you to change [General] to [MASTER])

Both of these options ought to work.

Hope that helps.


回答 1

更改路径的解决方案init-hook很好,但是我不喜欢必须在此处添加绝对路径的事实,因此,我无法在项目开发人员之间共享此pylintrc文件。这种使用相对路径指向pylintrc文件的解决方案对我来说效果更好:

[MASTER]
init-hook="from pylint.config import find_pylintrc; import os, sys; sys.path.append(os.path.dirname(find_pylintrc()))"

请注意,pylint.config.PYLINTRC该值也存在,并且具有与相同的值find_pylintrc()

The solution to alter path in init-hook is good, but I dislike the fact that I had to add absolute path there, as result I can not share this pylintrc file among the developers of the project. This solution using relative path to pylintrc file works better for me:

[MASTER]
init-hook="from pylint.config import find_pylintrc; import os, sys; sys.path.append(os.path.dirname(find_pylintrc()))"

Note that pylint.config.PYLINTRC also exists and has the same value as find_pylintrc().


回答 2

1)sys.path是一个列表。

2)问题有时是sys.path不是您的virtualenv.path,并且您想在virtualenv中使用pylint

3)像这样说,使用init-hook(注意’和’pylint的解析是严格的)

[Master]
init-hook='sys.path = ["/path/myapps/bin/", "/path/to/myapps/lib/python3.3/site-packages/", ... many paths here])'

要么

[Master]
init-hook='sys.path = list(); sys.path.append("/path/to/foo")'

..和

pylint --rcfile /path/to/pylintrc /path/to/module.py

1) sys.path is a list.

2) The problem is sometimes the sys.path is not your virtualenv.path and you want to use pylint in your virtualenv

3) So like said, use init-hook (pay attention in ‘ and ” the parse of pylint is strict)

[Master]
init-hook='sys.path = ["/path/myapps/bin/", "/path/to/myapps/lib/python3.3/site-packages/", ... many paths here])'

or

[Master]
init-hook='sys.path = list(); sys.path.append("/path/to/foo")'

.. and

pylint --rcfile /path/to/pylintrc /path/to/module.py

回答 3

可以通过在venv下配置pylint路径来解决该问题:$ cat .vscode / settings.json

{
    "python.pythonPath": "venv/bin/python",
    "python.linting.pylintPath": "venv/bin/pylint"
}

The problem can be solved by configuring pylint path under venv: $ cat .vscode/settings.json

{
    "python.pythonPath": "venv/bin/python",
    "python.linting.pylintPath": "venv/bin/pylint"
}

回答 4

您是否__init__.py在两个目录中都有一个空文件来让python知道dirs是模块?

当您不在文件夹中运行时(例如,虽然不是我使用过的pylint),其基本轮廓是:

topdir\
  __init__.py
  functions_etc.py
  subdir\
    __init__.py
    other_functions.py

这是怎样的Python解释器知道不参考当前目录中的模块,因此,如果pylint的是从自身的绝对路径运行它就能访问functions_etc.pytopdir.functions_etctopdir.subdir.other_functions,只要topdir是对的PYTHONPATH

更新:如果问题不在于__init__.py文件,也许只是尝试将模块复制或移动到c:\Python26\Lib\site-packages-这是放置其他软件包的常见位置,并且肯定会在pythonpath上。如果您知道如何执行Windows符号链接或等效链接(我不知道!),则可以这样做。这里还有更多选项:http://docs.python.org/install/index.html,包括在开发代码的用户级目录后附加sys.path的选项,但实际上,我通常只是象征性地链接我将本地开发目录复制到站点软件包-将其复制具有相同的效果。

Do you have an empty __init__.py file in both directories to let python know that the dirs are modules?

The basic outline when you are not running from within the folder (ie maybe from pylint’s, though I haven’t used that) is:

topdir\
  __init__.py
  functions_etc.py
  subdir\
    __init__.py
    other_functions.py

This is how the python interpreter is aware of the module without reference to the current directory, so if pylint is running from its own absolute path it will be able to access functions_etc.py as topdir.functions_etc or topdir.subdir.other_functions, provided topdir is on the PYTHONPATH.

UPDATE: If the problem is not the __init__.py file, maybe just try copying or moving your module to c:\Python26\Lib\site-packages — that is a common place to put additional packages, and will definitely be on your pythonpath. If you know how to do Windows symbolic links or the equivalent (I don’t!), you could do that instead. There are many more options here: http://docs.python.org/install/index.html, including the option of appending sys.path with the user-level directory of your development code, but in practice I usually just symbolically link my local development dir to site-packages – copying it over has the same effect.


回答 5

我在此页面上找到的关于此问题的一般答案请不要打开,网站显示错误

创建.pylintrc并添加

[MASTER]
init-hook="from pylint.config import find_pylintrc;
import os, sys; sys.path.append(os.path.dirname(find_pylintrc()))"

general answer for this question I found on this page PLEASE NOT OPEN, SITE IS BUGED

create .pylintrc and add

[MASTER]
init-hook="from pylint.config import find_pylintrc;
import os, sys; sys.path.append(os.path.dirname(find_pylintrc()))"

回答 6

我不知道它如何与WingIDE一起使用,但是对于将PyLint与Geany一起使用,我将外部命令设置为:

PYTHONPATH=${PYTHONPATH}:$(dirname %d) pylint --output-format=parseable --reports=n "%f"

其中%f是文件名,%d是路径。可能对某人有用:)

I don’t know how it works with WingIDE, but for using PyLint with Geany, I set my external command to:

PYTHONPATH=${PYTHONPATH}:$(dirname %d) pylint --output-format=parseable --reports=n "%f"

where %f is the filename, and %d is the path. Might be useful for someone :)


回答 7

我必须更新系统PYTHONPATH变量以添加我的App Engine路径。就我而言,我只需要编辑~/.bashrc文件并添加以下行:

export PYTHONPATH=$PYTHONPATH:/path/to/google_appengine_folder

实际上,我尝试设置第init-hook一个,但这不能在我的代码库中始终解决此问题(不确定原因)。一旦将其添加到系统路径中(一般来说可能是一个好主意),我的问题就消失了。

I had to update the system PYTHONPATH variable to add my App Engine path. In my case I just had to edit my ~/.bashrc file and add the following line:

export PYTHONPATH=$PYTHONPATH:/path/to/google_appengine_folder

In fact, I tried setting the init-hook first but this did not resolve the issue consistently across my code base (not sure why). Once I added it to the system path (probably a good idea in general) my issues went away.


回答 8

我刚刚发现的一种解决方法是实际上只对整个软件包运行PyLint,而不是对单个文件运行。不知何故,它设法找到了导入的模块。

One workaround that I only just discovered is to actually just run PyLint for the entire package, rather than a single file. Somehow, it manages to find imported module then.


回答 9

尝试

if __name__ == '__main__':
    from [whatever the name of your package is] import one
else:
    import one

请注意,在Python 3中,else子句中该部分的语法为

from .. import one

再三考虑,这可能无法解决您的特定问题。我误解了这个问题,并认为two.py已作为主要模块运行,但事实并非如此。考虑到Python 2.6(不absolute_import从导入__future__)和Python 3.x处理导入的方式的差异,我认为对于Python 2.6无需这样做。

不过,如果最终您确实切换到Python 3,并计划将模块既用作包模块又用作包内的独立脚本,那么最好保留以下内容:

if __name__ == '__main__':
    from [whatever the name of your package is] import one   # assuming the package is in the current working directory or a subdirectory of PYTHONPATH
else:
    from .. import one

心里。

编辑:现在为您的实际问题提供可能的解决方案。从包含one模块的目录中运行PyLint (也许通过命令行),或者在运行PyLint时将以下代码放在某个位置:

import os

olddir = os.getcwd()
os.chdir([path_of_directory_containing_module_one])
import one
os.chdir(olddir)

基本上,作为摆弄PYTHONPATH的替代方法,只需确保当前工作目录是one.py执行导入时包含的目录。

(查看Brian的答案,您可能会将先前的代码分配给init_hook,但是如果您打算这样做,则可以简单地对其进行附加sys.path操作,这比我的解决方案要优雅得多。)

Try

if __name__ == '__main__':
    from [whatever the name of your package is] import one
else:
    import one

Note that in Python 3, the syntax for the part in the else clause would be

from .. import one

On second thought, this probably won’t fix your specific problem. I misunderstood the question and thought that two.py was being run as the main module, but that is not the case. And considering the differences in the way Python 2.6 (without importing absolute_import from __future__) and Python 3.x handle imports, you wouldn’t need to do this for Python 2.6 anyway, I don’t think.

Still, if you do eventually switch to Python 3 and plan on using a module as both a package module and as a standalone script inside the package, it may be a good idea to keep something like

if __name__ == '__main__':
    from [whatever the name of your package is] import one   # assuming the package is in the current working directory or a subdirectory of PYTHONPATH
else:
    from .. import one

in mind.

EDIT: And now for a possible solution to your actual problem. Either run PyLint from the directory containing your one module (via the command line, perhaps), or put the following code somewhere when running PyLint:

import os

olddir = os.getcwd()
os.chdir([path_of_directory_containing_module_one])
import one
os.chdir(olddir)

Basically, as an alternative to fiddling with PYTHONPATH, just make sure the current working directory is the directory containing one.py when you do the import.

(Looking at Brian’s answer, you could probably assign the previous code to init_hook, but if you’re going to do that then you could simply do the appending to sys.path that he does, which is slightly more elegant than my solution.)


回答 10

关键是在sys.path不考虑env变量的情况下将项目目录添加到其中。

对于使用VSCode的人,如果您的项目有基本目录,这是一种单线解决方案:

[MASTER]
init-hook='base_dir="my_spider"; import sys,os,re; _re=re.search(r".+\/" + base_dir, os.getcwd()); project_dir = _re.group() if _re else os.path.join(os.getcwd(), base_dir); sys.path.append(project_dir)'

让我解释一下:

  • re.search(r".+\/" + base_dir, os.getcwd()).group():根据编辑文件查找基本目录

  • os.path.join(os.getcwd(), base_dir):添加cwdsys.path满足命令行环境


仅供参考,这是我的.pylintrc:

https://gist.github.com/chuyik/f0ffc41a6948b6c87c7160151ffe8c2f

The key is to add your project directory to sys.path without considering about the env variable.

For someone who use VSCode, here’s a one-line solution for you if there’s a base directory of your project:

[MASTER]
init-hook='base_dir="my_spider"; import sys,os,re; _re=re.search(r".+\/" + base_dir, os.getcwd()); project_dir = _re.group() if _re else os.path.join(os.getcwd(), base_dir); sys.path.append(project_dir)'

Let me explain it a little bit:

  • re.search(r".+\/" + base_dir, os.getcwd()).group(): find base directory according to the editing file

  • os.path.join(os.getcwd(), base_dir): add cwd to sys.path to meet command line environment


FYI, here’s my .pylintrc:

https://gist.github.com/chuyik/f0ffc41a6948b6c87c7160151ffe8c2f


回答 11

我遇到了同样的问题,并通过在virtualenv中安装pylint,然后将.pylintrc文件添加到我的项目目录中并在文件中添加以下内容来修复了该问题:

[Master]
init-hook='sys.path = list(); sys.path.append("./Lib/site-packages/")'

I had this same issue and fixed it by installing pylint in my virtualenv and then adding a .pylintrc file to my project directory with the following in the file:

[Master]
init-hook='sys.path = list(); sys.path.append("./Lib/site-packages/")'

回答 12

也许通过在PYTHONPATH内手动附加目录?

sys.path.append(dirname)

Maybe by manually appending the dir inside the PYTHONPATH?

sys.path.append(dirname)

回答 13

我遇到了同样的问题,因为我找不到答案,所以我希望这可以帮助任何有类似问题的人。

我用飞配epylint。基本上我所做的就是添加一个dired-mode-hook,以检查dired目录是否为python软件包目录。如果是,我将其添加到PYTHONPATH。就我而言,如果目录包含名为“ setup.py”的文件,则我认为该目录是python软件包。

;;;;;;;;;;;;;;;;;
;; PYTHON PATH ;;
;;;;;;;;;;;;;;;;;

(defun python-expand-path ()
  "Append a directory to the PYTHONPATH."
  (interactive
   (let ((string (read-directory-name 
          "Python package directory: " 
          nil 
          'my-history)))
     (setenv "PYTHONPATH" (concat (expand-file-name string)
                  (getenv ":PYTHONPATH"))))))

(defun pythonpath-dired-mode-hook ()
  (let ((setup_py (concat default-directory "setup.py"))
    (directory (expand-file-name default-directory)))
    ;;   (if (file-exists-p setup_py)
    (if (is-python-package-directory directory)
    (let ((pythonpath (concat (getenv "PYTHONPATH") ":" 
                  (expand-file-name directory))))
      (setenv "PYTHONPATH" pythonpath)
      (message (concat "PYTHONPATH=" (getenv "PYTHONPATH")))))))

(defun is-python-package-directory (directory)
  (let ((setup_py (concat directory "setup.py")))
    (file-exists-p setup_py)))

(add-hook 'dired-mode-hook 'pythonpath-dired-mode-hook)

希望这可以帮助。

I had the same problem and since i could not find a answer I hope this can help anyone with a similar problem.

I use flymake with epylint. Basically what i did was add a dired-mode-hook that check if the dired directory is a python package directory. If it is I add it to the PYTHONPATH. In my case I consider a directory to be a python package if it contains a file named “setup.py”.

;;;;;;;;;;;;;;;;;
;; PYTHON PATH ;;
;;;;;;;;;;;;;;;;;

(defun python-expand-path ()
  "Append a directory to the PYTHONPATH."
  (interactive
   (let ((string (read-directory-name 
          "Python package directory: " 
          nil 
          'my-history)))
     (setenv "PYTHONPATH" (concat (expand-file-name string)
                  (getenv ":PYTHONPATH"))))))

(defun pythonpath-dired-mode-hook ()
  (let ((setup_py (concat default-directory "setup.py"))
    (directory (expand-file-name default-directory)))
    ;;   (if (file-exists-p setup_py)
    (if (is-python-package-directory directory)
    (let ((pythonpath (concat (getenv "PYTHONPATH") ":" 
                  (expand-file-name directory))))
      (setenv "PYTHONPATH" pythonpath)
      (message (concat "PYTHONPATH=" (getenv "PYTHONPATH")))))))

(defun is-python-package-directory (directory)
  (let ((setup_py (concat directory "setup.py")))
    (file-exists-p setup_py)))

(add-hook 'dired-mode-hook 'pythonpath-dired-mode-hook)

Hope this helps.


回答 14

如果有人在寻找一种方法来将Pylint作为PyCharm中的外部工具运行并使其与他们的虚拟环境一起工作(为什么我要问这个问题),那么我将通过以下方式解决它:

  1. 在PyCharm>首选项>工具>外部工具中,添加或编辑pylint的项目。
  2. 在“编辑工具”对话框的“工具设置”中,将“程序”设置为使用python解释器目录中的pylint: $PyInterpreterDirectory$/pylint
  3. 在“参数”字段中设置其他参数,例如: --rcfile=$ProjectFileDir$/pylintrc -r n $FileDir$
  4. 将工作目录设置为 $FileDir$

现在,使用pylint作为外部工具,可以在使用公共配置文件选择的任何目录上运行pylint,并使用为项目配置的任何解释器(大概是您的virtualenv解释器)。

In case anybody is looking for a way to run pylint as an external tool in PyCharm and have it work with their virtual environments (why I came to this question), here’s how I solved it:

  1. In PyCharm > Preferences > Tools > External Tools, Add or Edit an item for pylint.
  2. In the Tool Settings of the Edit Tool dialog, set Program to use pylint from the python interpreter directory: $PyInterpreterDirectory$/pylint
  3. Set your other parameters in the Parameters field, like: --rcfile=$ProjectFileDir$/pylintrc -r n $FileDir$
  4. Set your working directory to $FileDir$

Now using pylint as an external tool will run pylint on whatever directory you have selected using a common config file and use whatever interpreter is configured for your project (which presumably is your virtualenv interpreter).


回答 15

这是一个老问题,但是没有可接受的答案,所以我建议这样做:将two.py中的import语句更改为:

from .. import one

在我当前的环境(Python 3.6,使用pylint 2.3.1的VSCode)中,这清除了标记的语句。

This is an old question but has no accepted answer, so I’ll suggest this: change the import statement in two.py to read:

from .. import one

In my current environment (Python 3.6, VSCode using pylint 2.3.1) this clears the flagged statement.


回答 16

我找到了一个不错的答案。编辑您的pylintrc并在master中添加以下内容

init-hook="import imp, os; from pylint.config import find_pylintrc; imp.load_source('import_hook', os.path.join(os.path.dirname(find_pylintrc()), 'import_hook.py'))"

I found a nice answer. Edit your pylintrc and add the following in master

init-hook="import imp, os; from pylint.config import find_pylintrc; imp.load_source('import_hook', os.path.join(os.path.dirname(find_pylintrc()), 'import_hook.py'))"

回答 17

安装Python时,可以设置路径。如果已经定义了路径,那么您可以在VS Code中进行操作,按Ctrl + Shift + P并键入Python:选择“解释器”并选择Python的更新版本。请点击此链接以获取更多信息,https://code.visualstudio.com/docs/python/environments

When you install Python, you can set up the path. If path is already defined then what you can do is within VS Code, hit Ctrl+Shift+P and type Python: Select Interpreter and select updated version of Python. Follow this link for more information, https://code.visualstudio.com/docs/python/environments


回答 18

如果使用vscode,请确保您的软件包目录不在_pychache__目录中。

if you using vscode,make sure your package directory is out of the _pychache__ directory.


回答 19

如果您在Linux中使用Cython,则解决了删除module.cpython-XXm-X-linux-gnu.so项目目标目录中的文件的问题。

If you are using Cython in Linux, I resolved removing module.cpython-XXm-X-linux-gnu.so files in my project target directory.


回答 20

只需在.vscode / settings.json文件中添加此代码

,“ python.linting.pylintPath”:“ venv / bin / pylint”

这将通知pylint的位置(这是python的错误检查器)

just add this code in .vscode/settings.json file

,”python.linting.pylintPath”: “venv/bin/pylint”

This will notify the location of pylint(which is an error checker for python)


回答 21

您好,我能够从其他目录导入软件包。我只是做了以下事情:注意:我正在使用VScode

创建Python软件包的步骤使用Python软件包确实非常简单。您需要做的只是:

创建一个目录,并为其指定软件包的名称。将类放进去。在目录中创建一个初始化 .py文件

例如:您有一个名为Framework的文件夹,其中保存了所有自定义类,您的工作是在名为Framework的文件夹内创建一个init .py文件。

在导入时,您需要以这种方式导入->

从Framework导入库

因此E0401错误消失了,Framework是您刚在其中创建init .py 的文件夹,而base是您要自定义的模块,您需要将其导入并在该模块上工作,希望它能有所帮助!!!

Hello i was able to import the packages from different directory. I just did the following: Note: I am using VScode

Steps to Create a Python Package Working with Python packages is really simple. All you need to do is:

Create a directory and give it your package’s name. Put your classes in it. Create a init.py file in the directory

For example: you have a folder called Framework where you are keeping all the custom classes there and your job is to just create a init.py file inside the folder named Framework.

And while importing you need to import in this fashion—>

from Framework import base

so the E0401 error disappears Framework is the folder where you just created init.py and base is your custom module which you are required to import into and work upon Hope it helps!!!!


声明:本站所有文章,如无特殊说明或标注,均为本站原创发布。任何个人或组织,在未征得本站同意时,禁止复制、盗用、采集、发布本站内容到任何网站、书籍等各类媒体平台。如若本站内容侵犯了原著者的合法权益,可联系我们进行处理。