source: trunk/doc/src/frameworks-technologies/dbus-adaptors.qdoc

Last change on this file was 846, checked in by Dmitry A. Kuminov, 14 years ago

trunk: Merged in qt 4.7.2 sources from branches/vendor/nokia/qt.

  • Property svn:eol-style set to native
File size: 19.9 KB
Line 
1/****************************************************************************
2**
3** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
4** All rights reserved.
5** Contact: Nokia Corporation (qt-info@nokia.com)
6**
7** This file is part of the documentation of the Qt Toolkit.
8**
9** $QT_BEGIN_LICENSE:FDL$
10** Commercial Usage
11** Licensees holding valid Qt Commercial licenses may use this file in
12** accordance with the Qt Commercial License Agreement provided with the
13** Software or, alternatively, in accordance with the terms contained in a
14** written agreement between you and Nokia.
15**
16** GNU Free Documentation License
17** Alternatively, this file may be used under the terms of the GNU Free
18** Documentation License version 1.3 as published by the Free Software
19** Foundation and appearing in the file included in the packaging of this
20** file.
21**
22** If you have questions regarding the use of this file, please contact
23** Nokia at qt-info@nokia.com.
24** $QT_END_LICENSE$
25**
26****************************************************************************/
27
28/*!
29 \page usingadaptors.html
30 \title Using QtDBus Adaptors
31 \brief How to create and use DBus adaptors in Qt.
32
33 \ingroup best-practices
34
35 Adaptors are special classes that are attached to any QObject-derived class
36 and provide the interface to the external world using D-Bus. Adaptors are
37 intended to be lightweight classes whose main purpose is to relay calls to
38 and from the real object, possibly validating or converting the input from
39 the external world and, thus, protecting the real object.
40
41 Unlike multiple inheritance, adaptors can be added at any time to any object
42 (but not removed), which allows for greater flexibility when exporting
43 existing classes. Another advantage of adaptors is to provide similar but not
44 identical functionality in methods of the same name in different interfaces,
45 a case which can be quite common when adding a new version of a standard
46 interface to an object.
47
48 In order to use an adaptor, one must create a class which inherits
49 QDBusAbstractAdaptor. Since that is a standard QObject-derived class, the
50 Q_OBJECT macro must appear in the declaration and the source file must be
51 processed with the \l {moc} tool. The class must also contain one
52 Q_CLASSINFO entry with the \c {"D-Bus Interface"} name, declaring which
53 interface it is exporting. Only one entry per class is supported.
54
55 Any public slot in the class will be accessible through the bus over messages
56 of the MethodCall type. (See \l {Declaring Slots in D-Bus Adaptors} for more
57 information). Signals in the class will be automatically relayed over D-Bus.
58 However, not all types are allowed signals or slots' parameter lists: see
59 \l {The QtDBus Type System} for more information.
60
61 Also, any property declared with Q_PROPERTY will be automatically exposed
62 over the Properties interface on D-Bus. Since the QObject property system
63 does not allow for non-readable properties, it is not possible to declare
64 write-only properties using adaptors.
65
66 More information:
67 \list
68 \o \l{Declaring Slots in D-Bus Adaptors}
69 \o \l{Declaring Signals in D-Bus Adaptors}
70 \o \l{The QtDBus Type System}
71 \o \l{D-Bus Adaptor Example}
72 \endlist
73
74 \sa QDBusAbstractAdaptor
75*/
76
77/*!
78 \page qdbusadaptorexample.html
79 \title D-Bus Adaptor Example
80
81 \previouspage The QtDBus Type System
82 \contentspage Using QtDBus Adaptors
83
84 The following example code shows how a D-Bus interface can be implemented
85 using an adaptor.
86
87 A sample usage of QDBusAbstractAdaptor is as follows:
88 \snippet doc/src/snippets/code/doc_src_qdbusadaptors.qdoc 0
89
90 The code above would create an interface that could be represented more or less in the following
91 canonical representation:
92 \snippet doc/src/snippets/code/doc_src_qdbusadaptors.qdoc 1
93
94 This adaptor could be used in the application's main function as follows
95 \snippet doc/src/snippets/code/doc_src_qdbusadaptors.qdoc 2
96
97 Break-down analysis:
98 \tableofcontents
99
100 \section1 The header
101
102 The header of the example is:
103 \snippet doc/src/snippets/code/doc_src_qdbusadaptors.qdoc 3
104
105 The code does the following:
106 \list
107 \o it declares the adaptor MainApplicationAdaptor, which descends from QDBusAbstractAdaptor
108 \o it declares the Qt meta-object data using the Q_OBJECT macro
109 \o it declares the name of the D-Bus interface it implements.
110 \endlist
111
112 \section1 The properties
113
114 The properties are declared as follows:
115 \snippet doc/src/snippets/code/doc_src_qdbusadaptors.qdoc 4
116
117 And are implemented as follows:
118 \snippet doc/src/snippets/code/doc_src_qdbusadaptors.qdoc 5
119
120 The code declares three properties: one of them is a read-write property called "caption" of
121 string type. The other two are read-only, also of the string type.
122
123 The properties organizationName and organizationDomain are simple relays of the app object's
124 organizationName and organizationDomain properties. However, the caption property requires
125 verifying if the application has a main window associated with it: if there isn't any, the
126 caption property is empty. Note how it is possible to access data defined in other objects
127 through the getter/setter functions.
128
129 \section1 The constructor
130
131 The constructor:
132 \snippet doc/src/snippets/code/doc_src_qdbusadaptors.qdoc 6
133
134 The constructor does the following:
135 \list
136 \o it initialises its base class (QDBusAbstractAdaptor) with the parent object it is related to.
137 \o it stores the app pointer in a member variable. Note that it would be possible to access the
138 same object using the QDBusAbstractAdaptor::object() function, but it would be necessary to
139 use \a static_cast<> to properly access the methods in QApplication that are not part of
140 QObject.
141 \o it connects the application's signal \a aboutToQuit to its own signal \a aboutToQuit.
142 \o it connects the application's signal \a focusChanged to a private slot to do some further
143 processing before emitting a D-Bus signal.
144 \endlist
145
146 Note that there is no destructor in the example. An eventual destructor could be used to emit
147 one last signal before the object is destroyed, for instance.
148
149 \section1 Slots/methods
150
151 The public slots in the example (which will be exported as D-Bus methods) are the following:
152 \snippet doc/src/snippets/code/doc_src_qdbusadaptors.qdoc 7
153
154 This snippet of code defines 4 methods with different properties each:
155 \list 1
156 \o \c quit: this method takes no parameters and is defined to be asynchronous. That is, callers
157 are expected to use "fire-and-forget" mechanism when calling this method, since it provides no
158 useful reply. This is represented in D-Bus by the use of the
159 org.freedesktop.DBus.Method.NoReply annotation. See \l Q_NOREPLY for more information on
160 asynchronous methods
161
162 \o \c reparseConfiguration: this simple method, with no input or output arguments simply relays
163 the call to the application's reparseConfiguration member function.
164
165 \o \c mainWindowObject: this method takes no input parameter, but returns one string output
166 argument, containing the path to the main window object (if the application has a main
167 window), or an empty string if it has no main window. Note that this method could have also
168 been written: void mainWindowObject(QString &path).
169
170 \o \c setSessionManagement: this method takes one input argument (a boolean) and, depending on
171 its value, it calls one function or another in the application.
172 \endlist
173
174 See also: \l Q_NOREPLY.
175
176 \section1 Signals
177
178 The signals in this example are defined as follows:
179 \snippet doc/src/snippets/code/doc_src_qdbusadaptors.qdoc 8
180
181 However, signal definition isn't enough: signals have to be emitted. One simple way of emitting
182 signals is to connect another signal to them, so that Qt's signal handling system chains them
183 automatically. This is what is done for the \a aboutToQuit signal.
184
185 When this is the case, one can use the QDBusAbstractAdaptor::setAutoRelaySignals to
186 automatically connect every signal from the real object to the adaptor.
187
188 When simple signal-to-signal connection isn't enough, one can use a private slot do do some
189 work. This is what was done for the mainWindowHasFocus signal:
190 \snippet doc/src/snippets/code/doc_src_qdbusadaptors.qdoc 9
191
192 This private slot (which will not be exported as a method via D-Bus) was connected to the
193 \c focusChanged signal in the adaptor's constructor. It is therefore able to shape the
194 application's signal into what the interface expects it to be.
195*/
196
197/*!
198 \page qdbusdeclaringslots.html
199 \title Declaring Slots in D-Bus Adaptors
200
201 \contentspage Using QtDBus Adaptors
202 \nextpage Declaring Signals in D-Bus Adaptors
203
204 Slots in D-Bus adaptors are declared just like normal, public slots, but their
205 parameters must follow certain rules (see \l{The QtDBus Type System} for more
206 information). Slots whose parameters do not follow those rules or that are not
207 public will not be accessible via D-Bus.
208
209 Slots can have one parameter of type \c{const QDBusMessage &}, which must
210 appear at the end of the input parameter list, before any output parameters.
211 This parameter, if present, will be initialized with a copy of the
212 current message being processed, which allows the callee to obtain
213 information about the caller, such as its connection name.
214
215 Slots can be of three kinds:
216 \list 1
217 \o Asynchronous
218 \o Input-only
219 \o Input-and-output
220 \endlist
221
222 \section1 Asynchronous Slots
223 Asynchronous slots are those that do not normally return any reply to the
224 caller. For that reason, they cannot take any output parameters. In most
225 cases, by the time the first line of the slot is run, the caller function
226 has already resumed working.
227
228 However, slots must not rely on that behavior. Scheduling and message-dispatching
229 issues could change the order in which the slot is run. Code intending to
230 synchronize with the caller should provide its own method of synchronization.
231
232 Asynchronous slots are marked by the keyword \l Q_NOREPLY in the method
233 signature, before the \c void return type and the slot name. (See the
234 \c quit() slot in the \l{D-Bus Adaptor Example}).
235
236 \section1 Input-Only Slots
237
238 Input-only slots are normal slots that take parameters passed by value or
239 by constant reference. However, unlike asynchronous slots, the caller is
240 usually waiting for completion of the callee before resuming operation.
241 Therefore, non-asynchronous slots should not block or should state it its
242 documentation that they may do so.
243
244 Input-only slots have no special marking in their signature, except that
245 they take only parameters passed by value or by constant reference.
246 Optionally, slots can take a QDBusMessage parameter as a last parameter,
247 which can be used to perform additional analysis of the method call message.
248
249 \section1 Input and Output Slots
250
251 Like input-only slots, input-and-output slots are those that the caller is
252 waiting for a reply. Unlike input-only ones, though, this reply will contain
253 data. Slots that output data may contain non-constant references and may
254 return a value as well. However, the output parameters must all appear at
255 the end of the argument list and may not have input arguments interleaved.
256 Optionally, a QDBusMessage argument may appear between the input and the
257 output arguments.
258
259 \section1 Automatic Replies
260
261 Method replies are generated automatically with the contents of the output
262 parameters (if there were any) by the QtDBus implementation. Slots need not
263 worry about constructing proper QDBusMessage objects and sending them over
264 the connection.
265
266 However, the possibility of doing so remains there. Should the slot find out
267 it needs to send a special reply or even an error, it can do so by using
268 QDBusMessage::createReply() or QDBusMessage::createErrorReply() on the
269 QDBusMessage parameter and send it with QDBusConnection::send(). The
270 QtDBus implementation will not generate any reply if the slot did so.
271
272 \warning When a caller places a method call and waits for a reply, it will
273 only wait for a limited amount of time. Slots intending to take a long time
274 to complete should make that fact clear in documentation so that callers
275 properly set higher timeouts.
276
277 \section1 Delayed Replies
278
279 In some circumstances, the called slot may not be able to process
280 the request immediately. This is frequently the case when the
281 request involves an I/O or networking operation which may block.
282
283 If this is the case, the slot should return control to the
284 application's main loop to avoid freezing the user interface, and
285 resume the process later. To accomplish this, it should make use
286 of the extra \c QDBusMessage parameter at the end of the input
287 parameter list and request a delayed reply.
288
289 We do this by writing a slot that stores the request data in a
290 persistent structure, indicating to the caller using
291 \l{QDBusMessage::setDelayedReply()}{QDBusMessage::setDelayedReply(true)}
292 that the response will be sent later.
293
294 \snippet doc/src/snippets/code/doc_src_qdbusadaptors.qdoc 10
295
296 The use of
297 \l{QDBusConnection::send()}{QDBusConnection::sessionBus().send(data->reply)}
298 is needed to explicitly inform the caller that the response will be delayed.
299 In this case, the return value is unimportant; we return an arbitrary value
300 to satisfy the compiler.
301
302 When the request is processed and a reply is available, it should be sent
303 using the \c QDBusMessage object that was obtained. In our example, the
304 reply code could be something as follows:
305
306 \snippet doc/src/snippets/code/doc_src_qdbusadaptors.qdoc 11
307
308 As can be seen in the example, when a delayed reply is in place,
309 the return value(s) from the slot will be ignored by QtDBus. They
310 are used only to determine the slot's signature when communicating
311 the adaptor's description to remote applications, or in case the
312 code in the slot decides not to use a delayed reply.
313
314 The delayed reply itself is requested from QtDBus by calling
315 QDBusMessage::reply() on the original message. It then becomes the
316 resposibility of the called code to eventually send a reply to the
317 caller.
318
319 \warning When a caller places a method call and waits for a reply, it will
320 only wait for a limited amount of time. Slots intending to take a long time
321 to complete should make that fact clear in documentation so that callers
322 properly set higher timeouts.
323
324 \sa {Using QtDBus Adaptors}, {Declaring Signals in D-Bus Adaptors},
325 {The QtDBus Type System}, QDBusConnection, QDBusMessage
326*/
327
328/*!
329 \page qdbusdeclaringsignals.html
330 \title Declaring Signals in D-Bus Adaptors
331
332 \previouspage Declaring Slots in D-Bus Adaptors
333 \contentspage Using QtDBus Adaptors
334 \nextpage The QtDBus Type System
335
336 Any signal in a class derived from QDBusAbstractAdaptor will be automatically
337 relayed into D-Bus, provided that the signal's parameters conform to certain
338 rules (see \l{The QtDBus Type System} for more information). No special code
339 is necessary to make this relay.
340
341 However, signals must still be emitted. The easiest way to emit an adaptor
342 signal is to connect another signal to it, so that Qt's signals and slots
343 mechanism automatically emits the adaptor signal, too. This can be done in
344 the adaptor's constructor, as has been done in the
345 \l{D-Bus Adaptor Example}{D-Bus Adaptor example}.
346
347 The QDBusAbstractAdaptor::setAutoRelaySignals() convenience function can also
348 be used to make and break connections between signals in the real object and
349 the corresponding signals in the adaptor. It will inspect the list of signals
350 in both classes and connect those whose parameters match exactly.
351
352 \sa {Using QtDBus Adaptors},
353 {Declaring Slots in D-Bus Adaptors},
354 {The QtDBus Type System}, QDBusAbstractAdaptor
355*/
356
357/*!
358 \page qdbustypesystem.html
359 \title The QtDBus Type System
360
361 \previouspage Declaring Signals in D-Bus Adaptors
362 \contentspage Using QtDBus Adaptors
363 \nextpage D-Bus Adaptor Example
364
365 D-Bus has an extensible type system based on a few primitives and
366 composition of the primitives in arrays and structures. QtDBus
367 implements the interface to that type system through the
368 QDBusArgument class, allowing user programs to send and receive
369 practically every C++ type over the bus.
370
371 \section1 Primitive Types
372
373 The primitive types are supported natively by QDBusArgument and
374 need no special customization to be sent or received. They are
375 listed below, along with the C++ class they relate to:
376
377 \table
378 \header
379 \o Qt type
380 \o D-Bus equivalent type
381 \row
382 \o uchar
383 \o BYTE
384 \row
385 \o bool
386 \o BOOLEAN
387 \row
388 \o short
389 \o INT16
390 \row
391 \o ushort
392 \o UINT16
393 \row
394 \o int
395 \o INT32
396 \row
397 \o uint
398 \o UINT32
399 \row
400 \o qlonglong
401 \o INT64
402 \row
403 \o qulonglong
404 \o UINT64
405 \row
406 \o double
407 \o DOUBLE
408 \row
409 \o QString
410 \o STRING
411 \row
412 \o QDBusVariant
413 \o VARIANT
414 \row
415 \o QDBusObjectPath
416 \o OBJECT_PATH
417 \row
418 \o QDBusSignature
419 \o SIGNATURE
420 \endtable
421
422 Aside from the primitive types, QDBusArgument also supports two
423 non-primitive types natively, due to their widespread use in Qt
424 applications: QStringList and QByteArray.
425
426 \section1 Compound Types
427
428 D-Bus specifies three types of aggregations of primitive types
429 that allow one to create compound types. They are \c ARRAY, \c
430 STRUCT and maps/dictionaries.
431
432 Arrays are sets of zero or more elements of the same type, while
433 structures are a set of a fixed number of elements, each of any
434 type. Maps or dictionaries are implemented as arrays of a pair of
435 elements, so there can be zero or more elements in one map.
436
437 \section1 Extending the Type System
438
439 In order to use one's own type with QtDBus, the type has to be
440 declared as a Qt meta-type with the Q_DECLARE_METATYPE() macro and
441 registered with the qDBusRegisterMetaType() function. The
442 streaming operators \c{operator>>} and \c{operator<<} will be
443 automatically found by the registration system.
444
445 QtDBus provides template specializations for arrays and maps for
446 use with Qt's \l{Container classes}{container classes}, such as
447 QMap and QList, so it is not necessary to write the streaming
448 operator functions for those. For other types, and specially for
449 types implementing structures, the operators have to be explicitly
450 implemented.
451
452 See the documentation for QDBusArgument for examples for
453 structures, arrays and maps.
454
455 \section1 The Type System in Use
456
457 All of the QtDBus types (primitives and user-defined alike) can be
458 used to send and receive messages of all types over the bus.
459
460 \warning You may not use any type that is not on the list above,
461 including \a typedefs to the types listed. This also includes
462 QList<QVariant> and QMap<QString,QVariant>.
463*/
464
465/*!
466 \macro Q_NOREPLY
467 \relates QDBusAbstractAdaptor
468 \since 4.2
469
470 The Q_NOREPLY macro can be used to mark a method to be called and not wait for it to finish
471 processing before returning from QDBusInterface::call(). The called method cannot return any
472 output arguments and, if it does, any such arguments will be discarded.
473
474 You can use this macro in your own adaptors by placing it before your method's return value
475 (which must be "void") in the class declaration, as shown in the example:
476 \snippet doc/src/snippets/code/doc_src_qdbusadaptors.qdoc 12
477
478 Its presence in the method implementation (outside the class declaration) is optional.
479
480 \sa {Using QtDBus Adaptors}
481*/
Note: See TracBrowser for help on using the repository browser.