在脚本中包含python库
我的系统管理员不允许全局安装python包。 我正在编写一个脚本,人们将调用它来为他们执行某些操作。我正在编写的脚本需要某些库,如在脚本中包含python库,python,Python,我的系统管理员不允许全局安装python包。 我正在编写一个脚本,人们将调用它来为他们执行某些操作。我正在编写的脚本需要某些库,如sqlalchemy和coloredlogs。但是,我可以在任何本地文件夹中安装python libs。i、 e不是站点包 如何将libs安装在与脚本相同的文件夹中,以便脚本能够访问它们 我的文件夹层次结构是这样的 script_to_invoke.py scriptpack/ bin/ coloredlogs coloredl
sqlalchemy
和coloredlogs
。但是,我可以在任何本地文件夹中安装python libs。i、 e不是站点包
如何将libs安装在与脚本相同的文件夹中,以便脚本能够访问它们
我的文件夹层次结构是这样的
script_to_invoke.py
scriptpack/
bin/
coloredlogs
coloredlogs.egg
...
utils/
util1.py
util2.py
(所示的所有文件夹都有一个\uuuu init\uuuu.py
)
到目前为止,我所尝试的: 在
script\u to\u invoke.py中,我使用
from scriptpack.utils invoke util1 # no problem here
from scriptpack.bin import coloredlogs # fails to find the import
我查看了一些其他的SO答案,但我不确定如何将它们与我的问题关联起来。您可以使用--user
标志将这些软件包安装在非全局位置(通常位于~/.local/lib/python
),例如:
pip install --user sqlalchemy coloredlogs
这样,您就不必担心更改导入的工作方式,而且您仍然遵守系统管理员的策略。我明白了
必须指导Python查找.egg
文件
这可以通过以下两种方式实现:
在解释器启动之前编辑PYTHONPATH
var(或)
将鸡蛋的完整路径附加到sys路径
代码如下:
import sys
for entry in [<list of full path to egg files in bin dir>]:
sys.path.append(str(entry))
# Proceed with local imports
导入系统
在[]中输入:
sys.path.append(str(条目))
#进行本地进口
如果您想试试的话。这样做会生成一个充当Python脚本的zip文件,但可以包含大量的嵌入式包。实现这一目标的步骤如下:
testapp
)\uuuu main\uuuu.py
,并将其放入该文件夹中pip
,使用--target=/path/to/testapp
python3-mzipapp testapp-p='/usr/bin/env python3'
(提供shebang行是可选的;没有它,用户将需要使用python3 testapp.pyz
运行包,而使用shebag,他们只需执行/testapp.pyz
)$ mkdir testapp
$ echo -e '#!/usr/bin/python3\nimport sqlalchemy\nprint(sqlalchemy)' > __main__.py
$ pip3 install --target=./testapp sqlalchemy
$ python3 -mzipapp testapp -p='/usr/bin/env python3'
$ ./testapp.pyz
<module 'sqlalchemy' from './testapp.pyz/sqlalchemy/__init__.py'>
但是调用我的脚本的人将无法访问这些库?您可以添加一个枚举依赖项的
requirements.txt
文件,并且在安装说明中请注意,用户应该运行pip INSTALL--user-r requirements.txt
。这是一个相当标准的工作流。不幸的是,要求用户安装也不是一个选项。我必须将LIB与我的程序捆绑在一起:(没有coloredlogs.py
但是coloredlogs.egg
是的,当我运行easy\u install
并将coloredlogs安装到bin文件夹时,它只安装了一个coloredlogs
和一个coloredlogs.egg
文件。这就是为什么从scriptpack.bin导入coloredlogs
失败的原因好的,那我该怎么解决呢?easy\u install
似乎没有将.py
文件放在文件夹中。将coloredlogs
更改为coloredlogs.py
这是一个非常脆弱的解决方案(尤其是PYTHONPATH
一个)。在其他问题中,修改PYTHONPATH
会同时影响Python 2和Python 3,并且如果所讨论的模块与这两个模块的源代码不完全兼容(这很少见),您将确保给定的模块只适用于一个主要的Python版本。专用的打包解决方案是一个更好的主意。除了导致python2/3不兼容之外,在这个用例中,您是否还看到了其他问题?目标用户有脚本的路径,只需调用它,无需担心更改路径等。Mo通常情况下,与正确的解决方案相比,很难维护。在随机目录中更新鸡蛋包不会从pip
支持中获得太多好处(如果有的话)(需要在目录中进行更新,并且可能需要手动编辑要加载到脚本中的鸡蛋列表),将支持文件放在用户目录中,但要使其全局可访问,需要仔细注意权限,这会导致意外故障(如果您意外地从主目录根目录中删除全局读取/遍历权限,则所有内容都会突然中断)还有更彻底的解决方案,甚至不需要用户安装Python(cx\u-freeze
,py2exe
,等等),但由于您似乎知道他们肯定会提供Python,zipapp
捆绑了解释器之外的所有东西,这在文件大小上节省了很多。作为记录,如果您不想命名主脚本\uuuu main\uuuuuuuuuuuuuuupy
,那么zipapp
文档将包括定义入口点(按模块和函数名)因此,您可以保留原始脚本名称,并让zipapp
生成调用它的骨架\uuu main\uuuu.py
。我将对此进行探讨,谢谢!!我们的系统没有python3,这还能工作吗?@SrinivasSuresh:zipapp
模块仅随python3.5及更高版本提供,但它可以使zipapp适用于任何版本的PythonPython(使用zipapp
模块以正确的格式构建zip,但不需要运行它)。从技术上讲,您甚至根本不需要zipapp
模块(您可以用zipapp
的方法手动创建必要的zip文件),但这使它变得简单多了。
$ du -s -h testapp*
13M testapp
8.1M testapp.pyz