在virtualenv中,我还能做些什么来解决一个包没有在python中导入,而在ipython中导入的问题?

2024-09-30 04:41:37 发布

您现在位置:Python中文网/ 问答频道 /正文

我是一个Python爱好者,他决定认真地创建一些我自己的可重用包。在

我的问题概要:

  1. 调用python test_dummy.py无法导入包eforest。一个强求被抛出。在
  2. import eforest在python解释器和ipython解释器中都不抛出异常。在
  3. ipython解释器中调用run test_dummy.py不会引发异常。在
  4. 所有的案子都是在虚拟机里运行的。在

virtualenv和我的问题无关。我发布了一个新问题:script that adds packages to sys.path import as expected when run from ipython but throw exception when the script is run from python

类似的问题在Can't import package from virtualenv

我阅读了关于virtualenvvirtualenvwrapper的文档,并将它们都安装在带有python2.7.6的ubuntu14.04.1lts系统上。在

我创建了一个虚拟版:

mkvirtualenv module_troubleshooting -a . -r requirements.txt

我的requirements.txt文件包含:

^{pr2}$

我用workon module_troubleshooting激活了我的virtualenv

我的虚拟机处于活动状态:(module_troubleshooting)dmmmd@ubuntuG5:

我从virtualenvwrapper文档中了解到,我可以向系统路径通过add2virtualenv命令。在

使用add2virtualenv我添加了我创建的非常简单的包。我验证了pth文件确实包含了这些包。在

^{3}$

我运行ipython来看看是否可以导入这些包。我可以。没有错误。检查ipython中的sys.path,发现上述路径是存在的。在

为了我自己的启发,我制作了下面的模块叫做测试_假人.py公司名称:

import browser
import display
import singleton
import eforest

我在ipython中运行了以下命令:run test_dummy.py。在

ipython中没有例外。在

然后,我退出ipython并运行以下命令,以确保没有调用全局python,并查看python是否会运行脚本:/home/dmmmd/.virtualenvs/module_troubleshooting/bin/python test_dummy.py

Traceback (most recent call last):
    File "tests/test_dummy.py", line 4, in <module>
import eforest
ImportError: No module named eforest

其他三个包browser、display和singleton按预期导入,异常在import eforest处引发

起初,我推测eforest可能包含一些异常。因此,我运行了/home/dmmmd/.virtualenvs/module_troubleshooting/bin/python,在导入eforest时得到了预期的提示,没有导入错误:

Python 2.7.6 (default, Mar 22 2014, 22:57:26)
[GCC 4.8.2] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>> import eforest
>>> print eforest
<module 'eforest' from 'eforest/__init__.pyc'>
>>>

所以我推断系统路径对于ipython和python可能不同。我救了系统路径对于python,将其编辑为以下内容,以便可以导入来自sys.path的列表:

/home/dmmmd/.virtualenvs/module_troubleshooting/bin/python -c "import sys; print sys.path" > path.py

我编辑过路径.py因此from path import path将是来自调用/home/dmmmd/.virtualenvs/module_troubleshooting/bin/python的列表sys.path。在

然后我运行ipython并输入以下命令:

In [1]: from path import path

In [2]: path # this is the sys.path from calling /home/dmmmd/.virtualenvs/module_troubleshooting/bin/python
Out[2]:
['',
 '/home/dmmmd/development/python/singleton',
 '/home/dmmmd/development/python/eforest',
 '/home/dmmmd/development/python/dummy',
 '/home/dmmmd/development/python/display',
 '/home/dmmmd/development/python/browser',
 '/home/dmmmd/.virtualenvs/module_troubleshooting/lib/python2.7',
 '/home/dmmmd/.virtualenvs/module_troubleshooting/lib/python2.7/plat-powerpc-linux-gnu',
 '/home/dmmmd/.virtualenvs/module_troubleshooting/lib/python2.7/lib-tk',
 '/home/dmmmd/.virtualenvs/module_troubleshooting/lib/python2.7/lib-old',
 '/home/dmmmd/.virtualenvs/module_troubleshooting/lib/python2.7/lib-dynload',
 '/usr/lib/python2.7',
 '/usr/lib/python2.7/plat-powerpc-linux-gnu',
 '/usr/lib/python2.7/lib-tk',
 '/home/dmmmd/.virtualenvs/module_troubleshooting/local/lib/python2.7/site-packages',
 '/home/dmmmd/.virtualenvs/module_troubleshooting/lib/python2.7/site-packages']

为了查看ipython的sys.path是否不同,我键入了:

In [5]: import sys

In [6]: len(sys.path)
Out[6]: 19

In [7]: len(path)
Out[7]: 16

In [8]: [item for item in sys.path if item not in path]
Out[8]:
['/home/dmmmd/.virtualenvs/module_troubleshooting/bin',
 '/home/dmmmd/.virtualenvs/module_troubleshooting/local/lib/python2.7/site-packages/IPython/extensions',
 '/home/dmmmd/.ipython']

ipython的最后两项系统路径与ipython相关。另一个不同的项目是'/home/dmmmd/.virtualenvs/module_troubleshooting/bin'。在

有谁能提供任何其他故障排除建议或向我解释如何在系统路径在ipython中,当调用run test_dummy.py时,允许eforest在ipython中按预期导入?在

eforest包:

eforest/
├── CustomElementFilters.py
├── CustomEtrees.py
├── CustomEtrees.pyc
├── __init__.py
└── __init__.pyc

同样,eforest在ipython中按预期导入,并使用python解释器,但当脚本作为参数传递给/home/dmmmd/.virtualenvs/module_troubleshooting/bin/python test_dummy.py时,它不会导入。在

我认为eforest与其他包不同的唯一可能的例外是它导入了lxml。lxml是否可以依赖于在系统路径?在

如有任何故障排除建议,我们将不胜感激。我第一次注意到这个问题是在我使用py.测试. 我以为这和py.测试,但事实证明,我编写的测试脚本也没有与python一起运行。我决定停下来看看能不能得到一些帮助。在

排除了virtualenv作为问题来源

我用python test_dummy.py运行以下脚本,virtuenv已停用。在

import sys
import os
HOME = os.path.expanduser('~')
PYTHON = os.path.join(HOME, 'development/my_python')
PACKAGES = [
    'browser',
    'display',
    'singleton',
    'eforest'
]
for package in PACKAGES:
    package = os.path.join(PYTHON, package)
    if os.path.exists(package) is True:
        if package not in sys.path:
            print "loading package '{0}'".format(package)
            sys.path.append(package)
        else:
            print "package '{0}' already in sys.path".format(package)
    else:
        raise
import browser
import display
import singleton
import eforest

使用virtualenv停用eforest是唯一不通过运行python test_dummy.py命令导入的包。在

结果:

Traceback (most recent call last):
  File "my_django/automated_browsing/tests/test_dummy.py", line 16, in <module>
import eforest
ImportError: No module named eforest

Tags: pathpytestimportpackagehomelibipython
1条回答
网友
1楼 · 发布于 2024-09-30 04:41:37

我找到了一个解决方案,尽管该解决方案不能解决这样一个问题:当使用python test_dummy.py运行脚本时,为什么以adhoc方式添加到sys.path的某些包路径没有被导入。在

我最初在尝试使用时遇到了这个问题py.测试. In the py.test documentation I saw this tip关于“使用virutalenv、pip和可编辑模式管理您的项目”。我忽略了它,因为我认为它对于我的Python知识水平来说太高级了。在

在读了“creating your own python project”之后,我决定试试这个技巧

在pwd中,我用以下代码创建了一个setup.py文件:

from setuptools import setup, find_packages

setup(name='import_troubleshooting', version='1.0')
packages = find_packages(exclude=[
    'my_django',
    'fake*',
    'tests*'
])

然后,我在命令行执行了以下代码:

^{pr2}$

然后,我执行了以下代码,得到了预期的结果:

$ python tests/test_dummy.py
# output    
package '/home/dmmmd/development/my_python/browser' already in sys.path
package '/home/dmmmd/development/my_python/display' already in sys.path
package '/home/dmmmd/development/my_python/singleton' already in sys.path
loading package '/home/dmmmd/development/my_python/test_a'
loading package '/home/dmmmd/development/my_python/hello_world'
loading 'browser'
loading 'display'
loading 'singleton'
loading 'test_a'
loading 'hello_world.hello'
Hello, world!

这些都不能解释为什么我不能以一种特殊的方式添加包路径。不过,我很高兴了解了python的安装和打包。当从test_dummy.py调用时,test_dummy.py脚本现在按预期运行。在

我现在很困惑,为什么运行test_dummy.py脚本时其中三个包已经在sys.path中:

package '/home/dmmmd/development/my_python/browser' already in sys.path
package '/home/dmmmd/development/my_python/display' already in sys.path
package '/home/dmmmd/development/my_python/singleton' already in sys.path

我不记得我做过什么会将这些添加到sys.path的事情,但这是可能的,因为我已经做了各种教程。它们不在sys.path中,也不在我没有运行我创建的setup.py的任何其他环境中。在

我的困惑是Python复杂性的症状,而不是原因!在

谢谢大家的意见。在

注意:这是一个新的virtualenv后python test_dummy.py的输出:

$ pip install -e .
# install output unremarkable
$ python tests/test_dummy.py
# output
loading package '/home/dmmmd/development/my_python/automated_browsing/browser'
loading package '/home/dmmmd/development/my_python/automated_browsing/display'
loading package '/home/dmmmd/development/my_python/automated_browsing/singleton'
loading package '/home/dmmmd/development/my_python/automated_browsing/hello_world'
loading package '/home/dmmmd/development/my_python/automated_browsing/test_a'
loading 'browser'
loading 'display'
loading 'singleton'
loading 'hello_world.hello'
Hello, world!
loading 'test_a'

相关问题 更多 >

    热门问题