PYTHONPATH与sys.path
另一位开发者和我不同意应该使用PYTHONPATH还是sys.path来允许Python在用户(例如,开发)目录中find一个Python包。
我们有一个典型的目录结构的Python项目:
Project setup.py package __init__.py lib.py script.py
在script.py中,我们需要import package.lib
。 当软件包安装在站点包中时,script.py可以findpackage.lib
。
但是,从用户目录进行工作时,还需要做其他事情。 我的解决scheme是设置我的PYTHONPATH包括“〜/项目”。 另一个开发者想把这行代码放在script.py的开头:
sys.path.append(os.path.dirname(os.path.dirname(os.path.abspath(__file__))))
所以Python可以findpackage.lib
的本地副本。
我认为这是一个坏主意,因为这条线只对开发者或从本地副本运行的人有用,但我不能给出一个很好的理由,为什么这是一个坏主意。
我们应该使用PYTOHNPATH,sys.path,还是罚款?
如果修改path的唯一原因是从工作树开始工作,那么您应该使用安装工具为您设置环境。 virtualenv非常stream行,如果你使用的是setuptools,你可以简单地运行setup.py develop
,在你当前的Python安装中半安装工作树。
我讨厌PYTHONPATH。 我发现它很脆弱,很烦人,以每个用户为基础(尤其是守护进程用户),并随着项目文件夹的移动而跟踪。 我宁愿在独立项目的调用脚本中设置sys.path
。
但是sys.path.append
不是这样做的。 你可以很容易得到重复的,它不会整理.pth
文件。 更好(更可读): site.addsitedir
。
而script.py
通常不会是更适合的地方,因为它在你想要在path上提供的包里面 。 库模块肯定不会碰到sys.path
本身。 相反,你通常会在包之外有一个hashbanged脚本,用于实例化和运行应用程序,而且在这个简单的包装脚本中,你会放置像sys.path
-frobbing这样的部署细节。
一般来说,我会考虑设置一个环境variables(比如PYTHONPATH)是一个糟糕的做法。 虽然这可能是罚款一个closuresdebugging,但使用此作为
定期的做法可能不是一个好主意。
环境variables的使用会导致某些情况,如“对我有用”
否则会报告代码库中的问题。 也可能有一些与testing环境相同的做法,导致像某些特定的开发者可以正常运行的testing,但是当某个testing开始时可能会失败。
除了已经提到的许多其他原因之外,还可以指出硬编码
sys.path.append(os.path.dirname(os.path.dirname(os.path.abspath(__file__))))
是脆弱的,因为它假定script.py的位置 – 它只会在script.py位于Project / package中时才起作用。 如果用户决定在任何地方移动/复制/符号链接script.py(几乎),它将会中断。
我认为,在这种情况下使用PYTHONPATH是一个更好的事情,主要是因为它没有引入(可疑的)不必要的代码。
毕竟,如果你想到了,你的用户不需要这个sys.path
,因为你的软件包将被安装到site-packages中,因为你将使用一个打包系统。
如果用户select从“本地副本”运行,就像你所说的那样,那么我已经注意到,通常的做法是声明,如果在站点包之外使用包,则需要手动将包添加到PYTHONPATH中。