ruby-dbus 0.21.0 → 0.22.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/NEWS.md +17 -0
- data/VERSION +1 -1
- data/lib/dbus/auth.rb +1 -3
- data/lib/dbus/bus.rb +42 -6
- data/lib/dbus/platform.rb +26 -0
- data/lib/dbus/proxy_object.rb +3 -2
- data/lib/dbus/xml.rb +8 -2
- data/lib/dbus.rb +1 -3
- data/ruby-dbus.gemspec +4 -3
- data/spec/bus_and_xml_backend_spec.rb +3 -1
- data/spec/platform_spec.rb +14 -0
- data/spec/session_bus_spec.rb +33 -0
- data/spec/signal_spec.rb +10 -0
- data/spec/tools/dbus-launch-simple +5 -5
- data/spec/tools/dbus-limited-session.conf +7 -0
- metadata +8 -9
- data/examples/gdbus/gdbus +0 -264
- data/examples/gdbus/gdbus.glade +0 -98
- data/examples/gdbus/launch.sh +0 -4
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 6fb99aaae181360df50b490a74425d252d5d78d6c2cbfb72d6b1fad72a35defd
|
4
|
+
data.tar.gz: 7443efcea3624c95617b8375c7e71986f6746c3b9a81f658f0b26c427e0b424d
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: cc10425266793eb1f7e712aabc0a685b76f3467212a72346df3f382186cd5a05f0cc4124f1056e7c2cc5b64a54d376b5b038812063347a870ab86e72275f67c7
|
7
|
+
data.tar.gz: 2e7eedd8c235788121ab59412b5a9dec2841b1b8e738790b2405ebd69c3b284df9261f06545b0bab93990b6daed3188d7872afbfb219dc867ff8fc0119481e68
|
data/NEWS.md
CHANGED
@@ -2,6 +2,23 @@
|
|
2
2
|
|
3
3
|
## Unreleased
|
4
4
|
|
5
|
+
## Ruby D-Bus 0.22.0 - 2023-05-08
|
6
|
+
|
7
|
+
Features:
|
8
|
+
* Enable using nokogiri without rexml (by Dominik Andreas Schorpp, [#132][])
|
9
|
+
|
10
|
+
Bug fixes:
|
11
|
+
* Respect DBUS_SYSTEM_BUS_ADDRESS environment variable.
|
12
|
+
|
13
|
+
Other:
|
14
|
+
* For NameRequestError, mention who is the other owner.
|
15
|
+
* Session bus autolaunch still does not work, but: don't try launchd except
|
16
|
+
on macOS, and improve the error message.
|
17
|
+
* examples/gdbus split off to its own repository,
|
18
|
+
https://github.com/mvidner/dbus-gui-gtk
|
19
|
+
|
20
|
+
[#132]: https://github.com/mvidner/ruby-dbus/pull/132
|
21
|
+
|
5
22
|
## Ruby D-Bus 0.21.0 - 2023-04-08
|
6
23
|
|
7
24
|
Features:
|
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
0.
|
1
|
+
0.22.0
|
data/lib/dbus/auth.rb
CHANGED
@@ -8,8 +8,6 @@
|
|
8
8
|
# License, version 2.1 as published by the Free Software Foundation.
|
9
9
|
# See the file "COPYING" for the exact licensing terms.
|
10
10
|
|
11
|
-
require "rbconfig"
|
12
|
-
|
13
11
|
module DBus
|
14
12
|
# Exception raised when authentication fails somehow.
|
15
13
|
class AuthenticationFailed < StandardError
|
@@ -183,7 +181,7 @@ module DBus
|
|
183
181
|
# that may carry credentials.
|
184
182
|
# @return [void]
|
185
183
|
def send_nul_byte
|
186
|
-
if
|
184
|
+
if Platform.freebsd?
|
187
185
|
@socket.sendmsg(0.chr, 0, nil, [:SOCKET, :SCM_CREDS, ""])
|
188
186
|
else
|
189
187
|
@socket.write(0.chr)
|
data/lib/dbus/bus.rb
CHANGED
@@ -318,10 +318,13 @@ module DBus
|
|
318
318
|
<node>
|
319
319
|
<interface name="org.freedesktop.DBus.Introspectable">
|
320
320
|
<method name="Introspect">
|
321
|
-
<arg
|
321
|
+
<arg direction="out" type="s"/>
|
322
322
|
</method>
|
323
323
|
</interface>
|
324
324
|
<interface name="org.freedesktop.DBus">
|
325
|
+
<method name="Hello">
|
326
|
+
<arg direction="out" type="s"/>
|
327
|
+
</method>
|
325
328
|
<method name="RequestName">
|
326
329
|
<arg direction="in" type="s"/>
|
327
330
|
<arg direction="in" type="u"/>
|
@@ -336,8 +339,8 @@ module DBus
|
|
336
339
|
<arg direction="in" type="u"/>
|
337
340
|
<arg direction="out" type="u"/>
|
338
341
|
</method>
|
339
|
-
<method name="
|
340
|
-
<arg direction="
|
342
|
+
<method name="UpdateActivationEnvironment">
|
343
|
+
<arg direction="in" type="a{ss}"/>
|
341
344
|
</method>
|
342
345
|
<method name="NameHasOwner">
|
343
346
|
<arg direction="in" type="s"/>
|
@@ -371,12 +374,29 @@ module DBus
|
|
371
374
|
<arg direction="in" type="s"/>
|
372
375
|
<arg direction="out" type="u"/>
|
373
376
|
</method>
|
377
|
+
<method name="GetAdtAuditSessionData">
|
378
|
+
<arg direction="in" type="s"/>
|
379
|
+
<arg direction="out" type="ay"/>
|
380
|
+
</method>
|
374
381
|
<method name="GetConnectionSELinuxSecurityContext">
|
375
382
|
<arg direction="in" type="s"/>
|
376
383
|
<arg direction="out" type="ay"/>
|
377
384
|
</method>
|
378
385
|
<method name="ReloadConfig">
|
379
386
|
</method>
|
387
|
+
<method name="GetId">
|
388
|
+
<arg direction="out" type="s"/>
|
389
|
+
</method>
|
390
|
+
<method name="GetConnectionCredentials">
|
391
|
+
<arg direction="in" type="s"/>
|
392
|
+
<arg direction="out" type="a{sv}"/>
|
393
|
+
</method>
|
394
|
+
<property name="Features" type="as" access="read">
|
395
|
+
<annotation name="org.freedesktop.DBus.Property.EmitsChangedSignal" value="const"/>
|
396
|
+
</property>
|
397
|
+
<property name="Interfaces" type="as" access="read">
|
398
|
+
<annotation name="org.freedesktop.DBus.Property.EmitsChangedSignal" value="const"/>
|
399
|
+
</property>
|
380
400
|
<signal name="NameOwnerChanged">
|
381
401
|
<arg type="s"/>
|
382
402
|
<arg type="s"/>
|
@@ -480,7 +500,15 @@ module DBus
|
|
480
500
|
proxy.RequestName(name, NAME_FLAG_REPLACE_EXISTING) do |rmsg, r|
|
481
501
|
# check and report errors first
|
482
502
|
raise rmsg if rmsg.is_a?(Error)
|
483
|
-
|
503
|
+
|
504
|
+
details = if r == REQUEST_NAME_REPLY_IN_QUEUE
|
505
|
+
other = proxy.GetNameOwner(name).first
|
506
|
+
other_creds = proxy.GetConnectionCredentials(other).first
|
507
|
+
"already owned by #{other}, #{other_creds.inspect}"
|
508
|
+
else
|
509
|
+
"error code #{r}"
|
510
|
+
end
|
511
|
+
raise NameRequestError, "Could not request #{name}, #{details}" unless r == REQUEST_NAME_REPLY_PRIMARY_OWNER
|
484
512
|
end
|
485
513
|
@service = Service.new(name, self)
|
486
514
|
@service
|
@@ -702,7 +730,8 @@ module DBus
|
|
702
730
|
def self.session_bus_address
|
703
731
|
ENV["DBUS_SESSION_BUS_ADDRESS"] ||
|
704
732
|
address_from_file ||
|
705
|
-
"launchd:env=DBUS_LAUNCHD_SESSION_BUS_SOCKET"
|
733
|
+
("launchd:env=DBUS_LAUNCHD_SESSION_BUS_SOCKET" if Platform.macos?) ||
|
734
|
+
(raise NotImplementedError, "Cannot find session bus; sorry, haven't figured out autolaunch yet")
|
706
735
|
end
|
707
736
|
|
708
737
|
def self.address_from_file
|
@@ -732,6 +761,9 @@ module DBus
|
|
732
761
|
include Singleton
|
733
762
|
end
|
734
763
|
|
764
|
+
# Default socket name for the system bus.
|
765
|
+
SYSTEM_BUS_ADDRESS = "unix:path=/var/run/dbus/system_bus_socket"
|
766
|
+
|
735
767
|
# = D-Bus system bus class
|
736
768
|
#
|
737
769
|
# The system bus is a system-wide bus mostly used for global or
|
@@ -742,9 +774,13 @@ module DBus
|
|
742
774
|
class ASystemBus < Connection
|
743
775
|
# Get the default system bus.
|
744
776
|
def initialize
|
745
|
-
super(
|
777
|
+
super(self.class.system_bus_address)
|
746
778
|
send_hello
|
747
779
|
end
|
780
|
+
|
781
|
+
def self.system_bus_address
|
782
|
+
ENV["DBUS_SYSTEM_BUS_ADDRESS"] || SYSTEM_BUS_ADDRESS
|
783
|
+
end
|
748
784
|
end
|
749
785
|
|
750
786
|
# = D-Bus remote (TCP) bus class
|
@@ -0,0 +1,26 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
# This file is part of the ruby-dbus project
|
4
|
+
# Copyright (C) 2023 Martin Vidner
|
5
|
+
#
|
6
|
+
# This library is free software; you can redistribute it and/or
|
7
|
+
# modify it under the terms of the GNU Lesser General Public
|
8
|
+
# License, version 2.1 as published by the Free Software Foundation.
|
9
|
+
# See the file "COPYING" for the exact licensing terms.
|
10
|
+
|
11
|
+
require "rbconfig"
|
12
|
+
|
13
|
+
module DBus
|
14
|
+
# Platform detection
|
15
|
+
module Platform
|
16
|
+
module_function
|
17
|
+
|
18
|
+
def freebsd?
|
19
|
+
RbConfig::CONFIG["target_os"] =~ /freebsd/
|
20
|
+
end
|
21
|
+
|
22
|
+
def macos?
|
23
|
+
RbConfig::CONFIG["target_os"] =~ /darwin/
|
24
|
+
end
|
25
|
+
end
|
26
|
+
end
|
data/lib/dbus/proxy_object.rb
CHANGED
@@ -126,8 +126,9 @@ module DBus
|
|
126
126
|
# It uses _default_iface_ which must have been set.
|
127
127
|
# @return [void]
|
128
128
|
def on_signal(name, &block)
|
129
|
-
|
130
|
-
|
129
|
+
unless @default_iface && has_iface?(@default_iface)
|
130
|
+
raise NoMethodError, "undefined signal `#{name}' for DBus interface `#{@default_iface}' on object `#{@path}'"
|
131
|
+
end
|
131
132
|
|
132
133
|
@interfaces[@default_iface].on_signal(name, &block)
|
133
134
|
end
|
data/lib/dbus/xml.rb
CHANGED
@@ -11,11 +11,17 @@
|
|
11
11
|
# License, version 2.1 as published by the Free Software Foundation.
|
12
12
|
# See the file "COPYING" for the exact licensing terms.
|
13
13
|
|
14
|
-
#
|
15
|
-
|
14
|
+
# Our gemspec says rexml is needed and nokogiri is optional
|
15
|
+
# but in fact either will do
|
16
|
+
|
16
17
|
begin
|
17
18
|
require "nokogiri"
|
18
19
|
rescue LoadError
|
20
|
+
begin
|
21
|
+
require "rexml/document"
|
22
|
+
rescue LoadError
|
23
|
+
raise LoadError, "cannot load nokogiri OR rexml/document"
|
24
|
+
end
|
19
25
|
end
|
20
26
|
|
21
27
|
module DBus
|
data/lib/dbus.rb
CHANGED
@@ -41,6 +41,7 @@ require_relative "dbus/message_queue"
|
|
41
41
|
require_relative "dbus/object"
|
42
42
|
require_relative "dbus/object_manager"
|
43
43
|
require_relative "dbus/object_path"
|
44
|
+
require_relative "dbus/platform"
|
44
45
|
require_relative "dbus/proxy_object"
|
45
46
|
require_relative "dbus/proxy_object_factory"
|
46
47
|
require_relative "dbus/proxy_object_interface"
|
@@ -53,9 +54,6 @@ require "socket"
|
|
53
54
|
#
|
54
55
|
# Module containing all the D-Bus modules and classes.
|
55
56
|
module DBus
|
56
|
-
# Default socket name for the system bus.
|
57
|
-
SYSTEM_BUS_ADDRESS = "unix:path=/var/run/dbus/system_bus_socket"
|
58
|
-
|
59
57
|
# Comparing symbols is faster than strings
|
60
58
|
# @return [:little,:big]
|
61
59
|
HOST_ENDIANNESS = RawMessage.endianness(HOST_END)
|
data/ruby-dbus.gemspec
CHANGED
@@ -22,9 +22,10 @@ GEMSPEC = Gem::Specification.new do |s|
|
|
22
22
|
|
23
23
|
s.required_ruby_version = ">= 2.4.0"
|
24
24
|
|
25
|
-
|
26
|
-
|
27
|
-
#
|
25
|
+
# Either of rexml and nokogiri is required
|
26
|
+
# but AFAIK gemspec cannot express that.
|
27
|
+
# Nokogiri is recommended as rexml is dead slow.
|
28
|
+
s.add_runtime_dependency "rexml"
|
28
29
|
# s.add_runtime_dependency "nokogiri"
|
29
30
|
|
30
31
|
s.add_development_dependency "packaging_rake_tasks"
|
@@ -0,0 +1,14 @@
|
|
1
|
+
#!/usr/bin/env rspec
|
2
|
+
# frozen_string_literal: true
|
3
|
+
|
4
|
+
require_relative "spec_helper"
|
5
|
+
require "dbus"
|
6
|
+
|
7
|
+
describe DBus::Platform do
|
8
|
+
describe ".macos?" do
|
9
|
+
# code coverage chasing, as other tests mock it out
|
10
|
+
it "doesn't crash" do
|
11
|
+
expect { described_class.macos? }.to_not raise_error
|
12
|
+
end
|
13
|
+
end
|
14
|
+
end
|
data/spec/session_bus_spec.rb
CHANGED
@@ -4,6 +4,23 @@
|
|
4
4
|
require_relative "spec_helper"
|
5
5
|
require "dbus"
|
6
6
|
|
7
|
+
describe DBus::ASystemBus do
|
8
|
+
describe "#initialize" do
|
9
|
+
it "will use DBUS_SYSTEM_BUS_ADDRESS or the well known address" do
|
10
|
+
expect(ENV)
|
11
|
+
.to receive(:[])
|
12
|
+
.with("DBUS_SYSTEM_BUS_ADDRESS")
|
13
|
+
.and_return(nil)
|
14
|
+
expect(DBus::MessageQueue)
|
15
|
+
.to receive(:new)
|
16
|
+
.with("unix:path=/var/run/dbus/system_bus_socket")
|
17
|
+
expect_any_instance_of(described_class).to receive(:send_hello)
|
18
|
+
|
19
|
+
described_class.new
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
23
|
+
|
7
24
|
describe DBus::ASessionBus do
|
8
25
|
subject(:dbus_session_bus_address) { "unix:abstract=/tmp/dbus-foo,guid=123" }
|
9
26
|
|
@@ -18,6 +35,22 @@ describe DBus::ASessionBus do
|
|
18
35
|
ENV["DBUS_SESSION_BUS_ADDRESS"] = dbus_session_bus_address
|
19
36
|
expect(DBus::ASessionBus.session_bus_address).to eq(dbus_session_bus_address)
|
20
37
|
end
|
38
|
+
|
39
|
+
it "uses launchd on macOS when ENV and file fail" do
|
40
|
+
ENV["DBUS_SESSION_BUS_ADDRESS"] = nil
|
41
|
+
expect(described_class).to receive(:address_from_file).and_return(nil)
|
42
|
+
expect(DBus::Platform).to receive(:macos?).and_return(true)
|
43
|
+
|
44
|
+
expect(described_class.session_bus_address).to start_with "launchd:"
|
45
|
+
end
|
46
|
+
|
47
|
+
it "raises a readable exception when all addresses fail" do
|
48
|
+
ENV["DBUS_SESSION_BUS_ADDRESS"] = nil
|
49
|
+
expect(described_class).to receive(:address_from_file).and_return(nil)
|
50
|
+
expect(DBus::Platform).to receive(:macos?).and_return(false)
|
51
|
+
|
52
|
+
expect { described_class.session_bus_address }.to raise_error(NotImplementedError, /Cannot find session bus/)
|
53
|
+
end
|
21
54
|
end
|
22
55
|
|
23
56
|
describe "#address_from_file" do
|
data/spec/signal_spec.rb
CHANGED
@@ -103,4 +103,14 @@ describe "SignalHandlerTest" do
|
|
103
103
|
it "tests removing a nonexistent rule" do
|
104
104
|
@obj.on_signal "DoesNotExist"
|
105
105
|
end
|
106
|
+
|
107
|
+
describe DBus::ProxyObject do
|
108
|
+
describe "#on_signal" do
|
109
|
+
it "raises a descriptive error when the default_iface is wrong" do
|
110
|
+
@obj.default_iface = "org.ruby.NoSuchInterface"
|
111
|
+
expect { @obj.on_signal("Foo") {} }
|
112
|
+
.to raise_error(NoMethodError, /undefined signal.*interface `org.ruby.NoSuchInterface'/)
|
113
|
+
end
|
114
|
+
end
|
115
|
+
end
|
106
116
|
end
|
@@ -16,9 +16,9 @@ my_dbus_launch () {
|
|
16
16
|
# wait for the daemon to print the info
|
17
17
|
TRIES=0
|
18
18
|
while [ ! -s $AF -o ! -s $PF ]; do
|
19
|
-
|
20
|
-
|
21
|
-
|
19
|
+
sleep 0.1
|
20
|
+
TRIES=`expr $TRIES + 1`
|
21
|
+
if [ $TRIES -gt 100 ]; then echo "dbus-daemon failed?"; exit 1; fi
|
22
22
|
done
|
23
23
|
DBUS_SESSION_BUS_PID=$(cat $PF)
|
24
24
|
export DBUS_SESSION_BUS_ADDRESS=$(cat $AF)
|
@@ -26,10 +26,10 @@ my_dbus_launch () {
|
|
26
26
|
# dbus-monitor &
|
27
27
|
}
|
28
28
|
|
29
|
-
my_dbus_launch
|
30
|
-
|
31
29
|
# Clean up at exit.
|
32
30
|
trap "kill \$KILLS; rm -rf \$RM_FILES" EXIT TERM INT
|
33
31
|
|
32
|
+
my_dbus_launch
|
33
|
+
|
34
34
|
# run the payload; the return value is passed on
|
35
35
|
"$@"
|
@@ -21,7 +21,14 @@
|
|
21
21
|
<allow_anonymous/>
|
22
22
|
-->
|
23
23
|
|
24
|
+
<!-- Give clients a variety of addresses to connect to -->
|
24
25
|
<listen>unix:tmpdir=/tmp</listen>
|
26
|
+
<listen>unix:dir=/tmp</listen>
|
27
|
+
<!-- runtime will happily steal the actual session bus! -->
|
28
|
+
<!--
|
29
|
+
<listen>unix:runtime=yes</listen>
|
30
|
+
-->
|
31
|
+
<listen>tcp:host=%3a%3a1,family=ipv6</listen>
|
25
32
|
<listen>tcp:host=127.0.0.1</listen>
|
26
33
|
|
27
34
|
<standard_session_servicedirs />
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: ruby-dbus
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.22.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Ruby DBus Team
|
8
|
-
autorequire:
|
8
|
+
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2023-
|
11
|
+
date: 2023-05-08 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: rexml
|
@@ -124,9 +124,6 @@ files:
|
|
124
124
|
- doc/Tutorial.md
|
125
125
|
- examples/doc/README.md
|
126
126
|
- examples/doc/_extract_examples
|
127
|
-
- examples/gdbus/gdbus
|
128
|
-
- examples/gdbus/gdbus.glade
|
129
|
-
- examples/gdbus/launch.sh
|
130
127
|
- examples/no-introspect/nm-test.rb
|
131
128
|
- examples/no-introspect/tracker-test.rb
|
132
129
|
- examples/rhythmbox/playpause.rb
|
@@ -157,6 +154,7 @@ files:
|
|
157
154
|
- lib/dbus/object.rb
|
158
155
|
- lib/dbus/object_manager.rb
|
159
156
|
- lib/dbus/object_path.rb
|
157
|
+
- lib/dbus/platform.rb
|
160
158
|
- lib/dbus/proxy_object.rb
|
161
159
|
- lib/dbus/proxy_object_factory.rb
|
162
160
|
- lib/dbus/proxy_object_interface.rb
|
@@ -186,6 +184,7 @@ files:
|
|
186
184
|
- spec/object_spec.rb
|
187
185
|
- spec/packet_marshaller_spec.rb
|
188
186
|
- spec/packet_unmarshaller_spec.rb
|
187
|
+
- spec/platform_spec.rb
|
189
188
|
- spec/property_spec.rb
|
190
189
|
- spec/proxy_object_interface_spec.rb
|
191
190
|
- spec/proxy_object_spec.rb
|
@@ -211,7 +210,7 @@ homepage: https://github.com/mvidner/ruby-dbus
|
|
211
210
|
licenses:
|
212
211
|
- LGPL-2.1
|
213
212
|
metadata: {}
|
214
|
-
post_install_message:
|
213
|
+
post_install_message:
|
215
214
|
rdoc_options: []
|
216
215
|
require_paths:
|
217
216
|
- lib
|
@@ -226,8 +225,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
226
225
|
- !ruby/object:Gem::Version
|
227
226
|
version: '0'
|
228
227
|
requirements: []
|
229
|
-
rubygems_version: 3.3.
|
230
|
-
signing_key:
|
228
|
+
rubygems_version: 3.3.26
|
229
|
+
signing_key:
|
231
230
|
specification_version: 4
|
232
231
|
summary: Ruby module for interaction with D-Bus
|
233
232
|
test_files: []
|
data/examples/gdbus/gdbus
DELETED
@@ -1,264 +0,0 @@
|
|
1
|
-
#!/usr/bin/env ruby
|
2
|
-
# frozen_string_literal: true
|
3
|
-
|
4
|
-
#
|
5
|
-
# This is a quite complex example using internal lower level API.
|
6
|
-
# Not a good starting point, but might be usefull if you want to do tricky
|
7
|
-
# stuff.
|
8
|
-
# -- Arnaud
|
9
|
-
|
10
|
-
require "dbus"
|
11
|
-
require "gtk2"
|
12
|
-
|
13
|
-
ENABLE_SYSTEM = false
|
14
|
-
|
15
|
-
class MethodCallWindow
|
16
|
-
def initialize(pwindow, intf, meth)
|
17
|
-
@intf = intf
|
18
|
-
@meth = meth
|
19
|
-
@entries = []
|
20
|
-
@dialog = Gtk::Dialog.new(meth.name, pwindow,
|
21
|
-
Gtk::Dialog::MODAL | Gtk::Dialog::NO_SEPARATOR,
|
22
|
-
[Gtk::Stock::OK, Gtk::Dialog::RESPONSE_OK],
|
23
|
-
[Gtk::Stock::CANCEL, Gtk::Dialog::RESPONSE_CANCEL])
|
24
|
-
|
25
|
-
@meth.params.each do |param|
|
26
|
-
shbox = Gtk::HBox.new(true, 0)
|
27
|
-
label = Gtk::Label.new("#{param[0]} (#{param[1]})")
|
28
|
-
input = Gtk::Entry.new
|
29
|
-
@entries << input
|
30
|
-
shbox.pack_start(label, true, true, 0)
|
31
|
-
shbox.pack_start(input, true, true, 0)
|
32
|
-
@dialog.vbox.pack_start(shbox, true, true, 0)
|
33
|
-
@dialog.vbox.show_all
|
34
|
-
end
|
35
|
-
end
|
36
|
-
|
37
|
-
def run
|
38
|
-
on_ok if @dialog.run == Gtk::Dialog::RESPONSE_OK
|
39
|
-
@dialog.destroy
|
40
|
-
end
|
41
|
-
|
42
|
-
def on_ok
|
43
|
-
bus = @intf.object.bus
|
44
|
-
m = DBus::Message.new(DBus::Message::METHOD_CALL)
|
45
|
-
m.path = @intf.object.path
|
46
|
-
m.interface = @intf.name
|
47
|
-
m.destination = @intf.object.destination
|
48
|
-
m.member = @meth.name
|
49
|
-
m.sender = bus.unique_name
|
50
|
-
@meth.params.each_with_index do |param, idx|
|
51
|
-
entry = @entries[idx]
|
52
|
-
data = nil
|
53
|
-
case param[1]
|
54
|
-
when "u", "i"
|
55
|
-
data = entry.text.to_i
|
56
|
-
when "s"
|
57
|
-
data = entry.text
|
58
|
-
when /^a/
|
59
|
-
begin
|
60
|
-
data = eval(entry.text)
|
61
|
-
rescue
|
62
|
-
puts "Incorrect data: #{data}"
|
63
|
-
end
|
64
|
-
end
|
65
|
-
m.add_param(param[1], data)
|
66
|
-
end
|
67
|
-
bus.send_sync_or_async(m) do |retm|
|
68
|
-
if retm.is_a?(DBus::Error)
|
69
|
-
puts "Error: #{retm.inspect}"
|
70
|
-
else
|
71
|
-
puts "Method #{m.member} returns: #{retm.params.inspect}"
|
72
|
-
end
|
73
|
-
end
|
74
|
-
end
|
75
|
-
end
|
76
|
-
|
77
|
-
class DBusUI
|
78
|
-
def initialize
|
79
|
-
@glade = Gtk::Builder.new
|
80
|
-
@glade << "gdbus.glade"
|
81
|
-
|
82
|
-
@sessiontreeview = @glade.get_object("sessiontreeview")
|
83
|
-
setup_treeview_renderer(@sessiontreeview, "D-Bus Objects")
|
84
|
-
@sessiontreeview.selection.signal_connect("changed") do |selection|
|
85
|
-
on_treeview_selection_changed(selection)
|
86
|
-
end
|
87
|
-
|
88
|
-
@systemtreeview = @glade.get_object("systemtreeview")
|
89
|
-
setup_treeview_renderer(@systemtreeview, "D-Bus Objects")
|
90
|
-
@systemtreeview.selection.signal_connect("changed") do |selection|
|
91
|
-
on_treeview_selection_changed(selection)
|
92
|
-
end
|
93
|
-
|
94
|
-
@methsigtreeview = @glade.get_object("methsigtreeview")
|
95
|
-
# ierk
|
96
|
-
setup_methodview_renderer(@methsigtreeview)
|
97
|
-
@methsigtreeview.signal_connect("row-activated") do |view, path, column|
|
98
|
-
on_method_activated(view, path, column)
|
99
|
-
end
|
100
|
-
|
101
|
-
@window = @glade.get_object("window1")
|
102
|
-
@window.show_all
|
103
|
-
start_buses
|
104
|
-
end
|
105
|
-
|
106
|
-
def beautify_method(meth)
|
107
|
-
# Damn, this need to be rewritten :p
|
108
|
-
s = "#{meth.name}("
|
109
|
-
case meth
|
110
|
-
when DBus::Method
|
111
|
-
s += (meth.params.collect { |a| "in #{a[0]}:#{a[1]}" } +
|
112
|
-
meth.rets.collect { |a| "out #{a[0]}:#{a[1]}" }).join(", ")
|
113
|
-
when DBus::Signal
|
114
|
-
s += (meth.params.collect { |a| "in #{a[0]}:#{a[1]}" }).join(", ")
|
115
|
-
end
|
116
|
-
s += ")"
|
117
|
-
s
|
118
|
-
end
|
119
|
-
|
120
|
-
def on_treeview_selection_changed(selection)
|
121
|
-
selected = selection.selected
|
122
|
-
model = Gtk::ListStore.new(String, String, DBus::Method,
|
123
|
-
DBus::ProxyObjectInterface)
|
124
|
-
@methsigtreeview.model = model
|
125
|
-
return unless selected
|
126
|
-
|
127
|
-
intf = selected[1]
|
128
|
-
return unless intf
|
129
|
-
|
130
|
-
intf.methods.keys.sort.each do |mi|
|
131
|
-
m = intf.methods[mi]
|
132
|
-
subiter = model.append
|
133
|
-
subiter[0] = beautify_method(m)
|
134
|
-
subiter[1] = "M"
|
135
|
-
subiter[2] = m
|
136
|
-
subiter[3] = intf
|
137
|
-
end
|
138
|
-
intf.signals.keys.sort.each do |mi|
|
139
|
-
m = intf.signals[mi]
|
140
|
-
subiter = model.append
|
141
|
-
subiter[0] = beautify_method(m)
|
142
|
-
subiter[1] = "S"
|
143
|
-
subiter[2] = m
|
144
|
-
subiter[3] = intf
|
145
|
-
end
|
146
|
-
end
|
147
|
-
|
148
|
-
def on_method_activated(view, path, _column)
|
149
|
-
name = view.model.get_iter(path)[0]
|
150
|
-
puts "Clicked on: #{name.inspect}"
|
151
|
-
type = view.model.get_iter(path)[1]
|
152
|
-
case type
|
153
|
-
when "M"
|
154
|
-
method = view.model.get_iter(path)[2]
|
155
|
-
intf = view.model.get_iter(path)[3]
|
156
|
-
MethodCallWindow.new(@window, intf, method).run
|
157
|
-
when "S"
|
158
|
-
signal = view.model.get_iter(path)[2]
|
159
|
-
intf = view.model.get_iter(path)[3]
|
160
|
-
mr = DBus::MatchRule.new.from_signal(intf, signal)
|
161
|
-
puts "*** Registering matchrule: #{mr} ***"
|
162
|
-
intf.object.bus.add_match(mr) do |sig|
|
163
|
-
puts "Got #{sig.member}(#{sig.params.join(",")})"
|
164
|
-
end
|
165
|
-
end
|
166
|
-
end
|
167
|
-
|
168
|
-
def on_sessiontreeview_row_activated(view, path, _column)
|
169
|
-
name = view.model.get_iter(path)[0]
|
170
|
-
puts "Clicked on: #{name.inspect}"
|
171
|
-
end
|
172
|
-
|
173
|
-
def on_window_delete_event(_window, _event)
|
174
|
-
Gtk.main_quit
|
175
|
-
end
|
176
|
-
|
177
|
-
def setup_methodview_renderer(treeview)
|
178
|
-
renderer = Gtk::CellRendererText.new
|
179
|
-
_col_offset = treeview.insert_column(-1, "T", renderer, "text" => 1)
|
180
|
-
col_offset = treeview.insert_column(-1, "Name", renderer, "text" => 0)
|
181
|
-
column = treeview.get_column(col_offset - 1)
|
182
|
-
column.clickable = true
|
183
|
-
end
|
184
|
-
|
185
|
-
def setup_treeview_renderer(treeview, str)
|
186
|
-
renderer = Gtk::CellRendererText.new
|
187
|
-
col_offset = treeview.insert_column(-1, str, renderer, "text" => 0)
|
188
|
-
column = treeview.get_column(col_offset - 1)
|
189
|
-
column.clickable = true
|
190
|
-
end
|
191
|
-
|
192
|
-
def process_input(bus)
|
193
|
-
# THIS is the bad ass loop
|
194
|
-
# we should return to the glib main loop from time to time. Anyone with a
|
195
|
-
# proper way to handle it ?
|
196
|
-
bus.update_buffer
|
197
|
-
bus.messages.each do |msg|
|
198
|
-
bus.process(msg)
|
199
|
-
end
|
200
|
-
end
|
201
|
-
|
202
|
-
def start_buses
|
203
|
-
# call glibize to get dbus messages from the glib mainloop
|
204
|
-
DBus::SessionBus.instance.glibize
|
205
|
-
DBus::SystemBus.instance.glibize if ENABLE_SYSTEM
|
206
|
-
|
207
|
-
DBus::SessionBus.instance.proxy.ListNames do |_msg, names|
|
208
|
-
fill_treeview(DBus::SessionBus.instance, @sessiontreeview, names)
|
209
|
-
end
|
210
|
-
|
211
|
-
return unless ENABLE_SYSTEM
|
212
|
-
|
213
|
-
DBus::SystemBus.instance.proxy.ListNames do |_msg, names|
|
214
|
-
fill_treeview(DBus::SystemBus.instance, @systemtreeview, names)
|
215
|
-
end
|
216
|
-
end
|
217
|
-
|
218
|
-
def walk_node(model, iter, node)
|
219
|
-
node.each_pair do |key, val|
|
220
|
-
subiter = model.append(iter)
|
221
|
-
subiter[0] = key
|
222
|
-
walk_node(model, subiter, val)
|
223
|
-
end
|
224
|
-
|
225
|
-
return if node.object.nil?
|
226
|
-
|
227
|
-
node.object.interfaces.sort.each do |ifname|
|
228
|
-
subiter = model.append(iter)
|
229
|
-
subiter[0] = ifname
|
230
|
-
subiter[1] = node.object[ifname]
|
231
|
-
end
|
232
|
-
end
|
233
|
-
|
234
|
-
def introspect_services(model, bus)
|
235
|
-
el = @introspect_array.shift
|
236
|
-
if el !~ /^:/
|
237
|
-
iter = model.append(nil)
|
238
|
-
iter[0] = el
|
239
|
-
puts "introspecting: #{el}"
|
240
|
-
begin
|
241
|
-
service = bus.service(el).introspect
|
242
|
-
walk_node(model, iter, service.root)
|
243
|
-
rescue Exception => e
|
244
|
-
puts "DBus Error:"
|
245
|
-
puts e.backtrace.join("\n")
|
246
|
-
end
|
247
|
-
end
|
248
|
-
|
249
|
-
!@introspect_array.empty?
|
250
|
-
end
|
251
|
-
|
252
|
-
def fill_treeview(bus, treeview, array)
|
253
|
-
model = Gtk::TreeStore.new(String, DBus::ProxyObjectInterface)
|
254
|
-
treeview.model = model
|
255
|
-
@introspect_array = array.sort
|
256
|
-
Gtk.idle_add { introspect_services(model, bus) }
|
257
|
-
end
|
258
|
-
|
259
|
-
def main
|
260
|
-
Gtk.main
|
261
|
-
end
|
262
|
-
end
|
263
|
-
|
264
|
-
DBusUI.new.main
|
data/examples/gdbus/gdbus.glade
DELETED
@@ -1,98 +0,0 @@
|
|
1
|
-
<?xml version="1.0" encoding="UTF-8"?>
|
2
|
-
<interface>
|
3
|
-
<!-- interface-requires gtk+ 2.6 -->
|
4
|
-
<!-- interface-naming-policy toplevel-contextual -->
|
5
|
-
<object class="GtkWindow" id="window1">
|
6
|
-
<property name="visible">True</property>
|
7
|
-
<property name="can_focus">False</property>
|
8
|
-
<property name="title" translatable="yes">GD-Bus</property>
|
9
|
-
<property name="default_width">500</property>
|
10
|
-
<property name="default_height">400</property>
|
11
|
-
<signal name="delete-event" handler="on_window_delete_event" swapped="no"/>
|
12
|
-
<child>
|
13
|
-
<object class="GtkHPaned" id="hpaned1">
|
14
|
-
<property name="visible">True</property>
|
15
|
-
<property name="can_focus">True</property>
|
16
|
-
<child>
|
17
|
-
<object class="GtkNotebook" id="notebook1">
|
18
|
-
<property name="visible">True</property>
|
19
|
-
<property name="can_focus">True</property>
|
20
|
-
<child>
|
21
|
-
<object class="GtkScrolledWindow" id="scrolledwindow3">
|
22
|
-
<property name="visible">True</property>
|
23
|
-
<property name="can_focus">True</property>
|
24
|
-
<property name="shadow_type">in</property>
|
25
|
-
<child>
|
26
|
-
<object class="GtkTreeView" id="sessiontreeview">
|
27
|
-
<property name="visible">True</property>
|
28
|
-
<property name="can_focus">True</property>
|
29
|
-
<signal name="row-activated" handler="on_sessiontreeview_row_activated" swapped="no"/>
|
30
|
-
</object>
|
31
|
-
</child>
|
32
|
-
</object>
|
33
|
-
</child>
|
34
|
-
<child type="tab">
|
35
|
-
<object class="GtkLabel" id="label1">
|
36
|
-
<property name="visible">True</property>
|
37
|
-
<property name="can_focus">False</property>
|
38
|
-
<property name="label" translatable="yes">Session</property>
|
39
|
-
</object>
|
40
|
-
<packing>
|
41
|
-
<property name="tab_fill">False</property>
|
42
|
-
</packing>
|
43
|
-
</child>
|
44
|
-
<child>
|
45
|
-
<object class="GtkScrolledWindow" id="scrolledwindow5">
|
46
|
-
<property name="visible">True</property>
|
47
|
-
<property name="can_focus">True</property>
|
48
|
-
<property name="shadow_type">in</property>
|
49
|
-
<child>
|
50
|
-
<object class="GtkTreeView" id="systemtreeview">
|
51
|
-
<property name="visible">True</property>
|
52
|
-
<property name="can_focus">True</property>
|
53
|
-
</object>
|
54
|
-
</child>
|
55
|
-
</object>
|
56
|
-
<packing>
|
57
|
-
<property name="position">1</property>
|
58
|
-
</packing>
|
59
|
-
</child>
|
60
|
-
<child type="tab">
|
61
|
-
<object class="GtkLabel" id="label2">
|
62
|
-
<property name="visible">True</property>
|
63
|
-
<property name="can_focus">False</property>
|
64
|
-
<property name="label" translatable="yes">System</property>
|
65
|
-
</object>
|
66
|
-
<packing>
|
67
|
-
<property name="position">1</property>
|
68
|
-
<property name="tab_fill">False</property>
|
69
|
-
</packing>
|
70
|
-
</child>
|
71
|
-
</object>
|
72
|
-
<packing>
|
73
|
-
<property name="resize">False</property>
|
74
|
-
<property name="shrink">True</property>
|
75
|
-
</packing>
|
76
|
-
</child>
|
77
|
-
<child>
|
78
|
-
<object class="GtkScrolledWindow" id="scrolledwindow4">
|
79
|
-
<property name="visible">True</property>
|
80
|
-
<property name="can_focus">True</property>
|
81
|
-
<property name="shadow_type">in</property>
|
82
|
-
<child>
|
83
|
-
<object class="GtkTreeView" id="methsigtreeview">
|
84
|
-
<property name="visible">True</property>
|
85
|
-
<property name="can_focus">True</property>
|
86
|
-
<signal name="row-activated" handler="on_method_activated" swapped="no"/>
|
87
|
-
</object>
|
88
|
-
</child>
|
89
|
-
</object>
|
90
|
-
<packing>
|
91
|
-
<property name="resize">False</property>
|
92
|
-
<property name="shrink">True</property>
|
93
|
-
</packing>
|
94
|
-
</child>
|
95
|
-
</object>
|
96
|
-
</child>
|
97
|
-
</object>
|
98
|
-
</interface>
|
data/examples/gdbus/launch.sh
DELETED