使用 pythons Gio-Bindings 在 DBus 上注册对象



我正在研究现有C项目的Python克隆。C 项目连接到自定义 DBu,并在那里提供一个用于获取回调的对象。

我试图使用Python复制它,代码基本上可以归结为:

def vtable_method_call_cb(connection, sender, object_path, interface_name, method_name, parameters, invocation, user_data):
    print('vtable_method_call_cb: %s' % method_name)
connection = Gio.DBusConnection.new_for_address_sync(
    "unix:abstract=gstswitch",
    Gio.DBusConnectionFlags.AUTHENTICATION_CLIENT,
    None,
    None)
node_info = Gio.DBusNodeInfo.new_for_xml(introspection_xml)
vtable = Gio.DBusInterfaceVTable()
vtable.method_call(vtable_method_call_cb)
vtable.get_property(None)
vtable.set_property(None)
connection.register_object(
    "/info/duzy/gst/switch/SwitchUI",
    node_info.interfaces[0],
    vtable,
    None,
    None)

vtable.method_call调用中创建 vtable 时代码失败(但当我注释一个调用时,get_property失败)以下日志/回溯:

** (process:18062): WARNING **: Field method_call: Interface type 2 should have is_pointer set
Traceback (most recent call last):
  File "moo.py", line 69, in <module>
    vtable.method_call(vtable_method_call_cb)
RuntimeError: unable to get the value

我无法在 python 中找到使用 register_object() 的代码,所以我不确定 Gio 的这一部分是否应该可用,或者它是否不完整。

这当然不是你想听到的,但是你在GDBus Python绑定中遇到了一个4年前的错误,这使得无法在总线上注册对象。很久以前就提出了一个补丁,但每次看起来它真的要登陆时,一些 GNOME 开发人员发现了他/她不喜欢的东西,提出了一个新的补丁......在接下来的一年的大部分时间里,什么也没发生。这个循环已经发生了 3 次,我不知道是否有希望很快被打破......

基本上GNOME开发人员自己或多或少地建议人们使用dbus-python,直到这个问题最终得到解决,所以我想你应该去这里。

顺便说一句:我认为你的源代码是错误的(除了它不会以任何一种方式工作的事实)。要创建 VTable,您实际上会被写成这样的东西,我认为:

vtable = Gio.DBusInterfaceVTable()
vtable.method_call  = vtable_method_call_cb
vtable.get_property = None
vtable.set_property = None

但是由于绑定被破坏,您只是在这里交易了一个带有abort()的异常...... :-(

如果补丁实际上以当前形式进入python-gi,则vtable将被完全转储(是的!),connection.register_object调用将变为:

connection.register_object_with_closures(
    "/info/duzy/gst/switch/SwitchUI",
    node_info.interfaces[0],
    vtable_method_call_cb, # vtable.method_call
    None,                  # vtable.get_property
    None)                  # vtable.set_property

更新

看来这终于解决了!您现在可以使用以下g_dbus_connection_register_object_with_closures导出对象:

def vtable_method_call_cb(connection, sender, object_path, interface_name, method_name, parameters, invocation, user_data):
    print('vtable_method_call_cb: %s' % method_name)
connection = Gio.DBusConnection.new_for_address_sync(
    "unix:abstract=gstswitch",
    Gio.DBusConnectionFlags.AUTHENTICATION_CLIENT,
    None,
    None)
node_info = Gio.DBusNodeInfo.new_for_xml(introspection_xml)
connection.register_object(
    "/info/duzy/gst/switch/SwitchUI",
    node_info.interfaces[0],
    vtable_method_call_cb,
    None,
    None)

最新更新