python-3.x - 如何选择和使用 python3 dbus 库来替换 dbus-send 调用

标签 python-3.x linux dbus

使用ubuntu 20.10

我想编写一个 python 脚本来处理此 shell 命令的输出:

dbus-send --print-reply --dest=org.gnome.SessionManager /org/gnome/SessionManager org.gnome.SessionManager.GetInhibitors

我对 dbus 编码一无所知。首先我希望有一个好的 python 库。

我了解到这个明显规范的库:“dbus-python 是一个遗留 API,使用已弃用的 dbus-glib 库构建,并且涉及大量类型猜测(尽管“显式优于隐式”和“抵制猜测的诱惑”)(来自 https://wiki.python.org/moin/DbusExamples )

图书馆https://pypi.org/project/dbus-next/ promise 纯 Python 实现:“零依赖和纯 Python 3”。 上面提到的 wiki 页面上没有提到它,但它看起来像是一个健康的项目。 然而,纯Python方法似乎需要我使用asyncio版本。我认为这对于我的需求来说太过分了。

我尝试使用dasbus,但无法安装必要的库,至少在虚拟环境中无法安装。 尽管安装了系统包 python3-gi,但我收到错误“没有名为 gi 的模块”,并且尝试安装 PyGObject 失败,因为“找不到包‘cairo’”......以及错误:pycairo 的构建轮失败。

所以在这一点上,我有一个旧的且不推荐的库,一个具有依赖困难的库和一个似乎迫使我使用 asyncio 的库。

我现在明白为什么我尝试用 python 重写的 php 脚本会执行 shell 命令并处理丑陋的输出。

除此之外,我想我已经解决了以下几点:

我需要 session 总线

“路径”是“/org/gnome/SessionManager” “接口(interface)”是 org.gnome.SessionManager 我想“调用”“成员”GetInhibitors

我发现 async 有点矫枉过正,因为这是一个 shell 脚本,但如果这是我避免 C 依赖的唯一方法,我会处理它。

我应该使用哪个库?

最佳答案

首先,如何使用两个流行的、易于安装的、仅限 Python 的 MIT 许可包来实现您想要的功能

吉普车

以下是如何使用 jeepney 来完成任务:

from jeepney import DBusAddress, new_method_call
from jeepney.io.blocking import open_dbus_connection

proxy = DBusAddress('/org/gnome/SessionManager',
                            bus_name='org.gnome.SessionManager',
                            interface='org.gnome.SessionManager')

connection = open_dbus_connection(bus='SESSION')

msg = new_method_call(proxy, 'GetInhibitors')

reply = connection.send_and_get_reply(msg)
print(reply.body[0])

dbus-下一个

以下是如何在 dbus-next 中完成相同的操作。我不是异步方面的专家,但即使您的代码是非异步(同步),这似乎也有效:

import asyncio
from dbus_next.aio import MessageBus
from dbus_next.message import Message

async def main():
    bus = await MessageBus().connect()
    msg = Message(destination='org.gnome.SessionManager',
        path='/org/gnome/SessionManager',
        interface='org.gnome.SessionManager',
        member='GetInhibitors')
    return await bus.call(msg)
    

reply = asyncio.run(main())
print(reply.body[0])

我有哪些选择?

有很多选择。其中有些易于安装,有些则不然。

“难以”安装的软件包

我通过运行 python -m pip install <packagename> 测试了可安装性在新的虚拟环境中,在新的 Ubuntu 22.04 安装中。这些软件包未安装(因为它们有额外的依赖项):

  • dbus-python它依赖于原始的 dbus 实现和 libdbus。
  • pydbus ,它依赖于 PyGObject (又名。具有导入名称 gi 的 PyGI )。安装,但在运行时引发异常,因为缺少 gi模块。
  • dasbus ,它依赖于 PyGObject,基本上是(已废弃的)pydbus 项目的延续。安装,但在运行时引发异常,因为缺少 gi模块。
  • pystemd它为 libsystemd 提供 Cython 包装器。

易于安装的软件包

  • jeepney ,这是纯Python,使用 socket 的零依赖实现标准库模块。它也获得了麻省理工学院的许可。 (docs)
  • dbus-next (你已经找到了),是另一个纯Python,使用 socket 的零依赖实现。标准库模块。也就是说,当您使用 async dbus_next.aio 子包中的 MessageBus 时(dbus_next.glib 部分中的 MessageBus 需要 PyGObject)。 Dbus-next 已获得 MIT 许可。 (docs)
  • sdbus它依赖于 libsystemd。这不是纯Python,但在存储库中有一些C 文件。不确定安装是否总是轻松的:)它已获得 LGPL-2.1 和 GPL-2.0 的许可。
  • dbussy较小的项目,基本上是 ctypes 包装器 libdbus-1.so.3 (并且它要求在系统上可用)。这个共享库基本上是每个运行 dbus-daemon(并使用 dbus)的系统的一部分。有些人不喜欢 libdbus(线程问题?至少互联网是这么说的)。 LGPL-2.1 已获得许可。
  • pysdbus一个小项目,如 dbussy,但取决于共享库的可用性 libsystemd.so.0在系统上。这应该在任何运行 systemd 的系统中都可用(它构成了大多数流行的发行版)。 LGPL-2.1 已获得许可。

其中,当今

  • jeepney 每天的下载量约为 850000 次
  • dbus-next 约 1250 次下载/天
  • sdbus 大约 100 次下载/天
  • dbussy 20/天

并且 pysdbus 未在 PyPI 中列出。所以吉普尼似乎确实是最受欢迎的选择,也许是因为安装方便。是not optimized for speed , 尽管。话虽如此,上述代码示例在多次运行时,使用 jeepney 大约需要 2 毫秒,使用 dbus-next 大约需要 3 毫秒。


  • 还有txdbus这实际上仅适用于twisted(它甚至安装twis​​ted作为依赖项)。
  • 或许还值得一提的是,Ubuntu 22.04 安装附带 jeepney , dbus (python-dbus) 和 gi (PyGObject)已安装。但这对虚拟环境或应该作为依赖项(在 venv 内)安装的项目没有帮助。

关于python-3.x - 如何选择和使用 python3 dbus 库来替换 dbus-send 调用,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/66916580/

相关文章:

c++ - 如何在不使用mutex、semorphore、spinLock、futex的情况下实现线程同步?

python - 使用 pydbus 库通过 session 总线发送信号

python - Dbus.Array(从 python 读取 pidgin 消息)

python - 作为子流程倒计时的函数

python - 从数据库查询输出创建 JSON 字符串

python - Python3读写.txt文件

linux - 创建具有特定数量的零的新文件的最快方法

c# - 从公共(public)服务器上的 PHP 页面向 C# 发送数据/命令

linux - 将密码安全地传递给另一个程序(单独的 shell/dbus)

python-3.x - 为什么这个 VAE 实现有时会添加 sigmoid 运算?