我正在使用入口点开发带有插件的 slack 机器人。我想在运行时动态添加一个插件。
我有一个具有这种结构的项目:
+ ~/my_project_dir/
+ my_projects_python_code/
+ plugins/
- plugin1.py
- plugin2.py
- ...
- pluginN.py
- setup.py
- venv/
- install.sh
我的 setup.py
文件如下所示:
from setuptools import setup, find_packages
setup(
name="My_Project_plugins",
version="1.0",
packages=['plugins'],
entry_points="""
[my_project.plugins]
plugin1 = plugins.plugin1:plugin1_class
plugin2 = plugins.plugin2:plugin2_class
...
pluginN = plugins.pluginN:pluginN_class
"""
)
运行 sudo install.sh
执行以下操作:
将所需文件复制到
/usr/share/my_project_dir/
在
/usr/share/my_project_dir/venv/bin/activate
激活virtualenv
运行:
python setup.py develop
这按预期工作并正确设置了我的入口点,以便我可以通过机器人使用它们。
但我希望能够将插件添加到 setup.py
并能够在机器人运行时使用它。所以我想添加一行:pluginN+1 = plugins.pluginN+1:pluginN+1_class
并让 pluginN+1 可用。
我尝试/学到的东西:
在
/usr/share/my_project_dir/venv/bin/activate
之后,我打开一个 Python 交互式 shell 并遍历pkg_resources.iter_entry_points()
,它列出了从 setup.py 的初始状态加载的所有内容(即 plugin1 到 pluginN)如果我向
setup.py
添加一行并运行sudo python setup.py develop
并使用相同的 Python shell 再次迭代,它不会选择新插件,但如果我退出 shell 并重新打开它,就会选择新插件。我注意到当我安装机器人时,部分输出显示:
复制 My_Project_plugins-1.0-py2.7.egg 到/usr/share/my_project-dir/venv/lib/python2.7/site-packages
当我
cd/usr/share/my_project_dir/
时,激活我的 virtualenv,并从 shell 运行setup.py
它说:创建/usr/local/lib/python2.7/dist-packages/My_Project-plugins.egg-link(链接到 .) My_Project-plugins 1.0 已经是 easy-install.pth 中的激活版本
最佳答案
为了测试目的,我需要做一些类似的事情来加载一个虚拟插件。这与您的用例略有不同,因为我特别试图避免需要在包中定义入口点(因为它只是测试代码)。
我发现我可以动态地将条目插入到 pkg_resources 数据结构中,如下所示:
import pkg_resources
# Create the fake entry point definition
ep = pkg_resources.EntryPoint.parse('dummy = dummy_module:DummyPlugin')
# Create a fake distribution to insert into the global working_set
d = pkg_resources.Distribution()
# Add the mapping to the fake EntryPoint
d._ep_map = {'namespace': {'dummy': ep}}
# Add the fake distribution to the global working_set
pkg_resources.working_set.add(d, 'dummy')
这在运行时添加了一个名为“dummy”的入口点到“namespace”,这将是“dummy_module.py”中的类“DummyPlugin”。
这是通过使用 setuptools 文档和对象上的 dir() 来根据需要获取更多信息来确定的。
文档在这里:http://setuptools.readthedocs.io/en/latest/pkg_resources.html
您可能会特别关注 http://setuptools.readthedocs.io/en/latest/pkg_resources.html#locating-plugins如果您需要做的就是加载您刚刚存储到本地文件系统的插件。
关于python - 如何动态添加和加载入口点?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/40514205/