2
* simple-channel-dispatch-operation.c - a simple channel dispatch operation
5
* Copyright © 2010 Collabora Ltd. <http://www.collabora.co.uk/>
7
* Copying and distribution of this file, with or without modification,
8
* are permitted in any medium without royalty provided the copyright
9
* notice and this notice are preserved.
12
#include "simple-channel-dispatch-operation.h"
14
#include <telepathy-glib/channel.h>
15
#include <telepathy-glib/dbus.h>
16
#include <telepathy-glib/defs.h>
17
#include <telepathy-glib/enums.h>
18
#include <telepathy-glib/gtypes.h>
19
#include <telepathy-glib/interfaces.h>
20
#include <telepathy-glib/util.h>
21
#include <telepathy-glib/svc-generic.h>
22
#include <telepathy-glib/svc-channel-dispatch-operation.h>
24
static void channel_dispatch_operation_iface_init (gpointer, gpointer);
26
G_DEFINE_TYPE_WITH_CODE (SimpleChannelDispatchOperation,
27
simple_channel_dispatch_operation,
29
G_IMPLEMENT_INTERFACE (TP_TYPE_SVC_CHANNEL_DISPATCH_OPERATION,
30
channel_dispatch_operation_iface_init);
31
G_IMPLEMENT_INTERFACE (TP_TYPE_SVC_DBUS_PROPERTIES,
32
tp_dbus_properties_mixin_iface_init)
35
/* TP_IFACE_CHANNEL_DISPATCH_OPERATION is implied */
36
static const char *CHANNEL_DISPATCH_OPERATION_INTERFACES[] = { NULL };
38
static const gchar *CHANNEL_DISPATCH_OPERATION_POSSIBLE_HANDLERS[] = {
39
TP_CLIENT_BUS_NAME_BASE ".Badger", NULL, };
48
PROP_POSSIBLE_HANDLERS,
51
struct _SimpleChannelDispatchOperationPrivate
55
/* Array of TpChannel */
60
simple_channel_dispatch_operation_handle_with (
61
TpSvcChannelDispatchOperation *iface,
63
DBusGMethodInvocation *context)
65
if (!tp_strdiff (handler, "FAIL"))
67
GError error = { TP_ERRORS, TP_ERROR_INVALID_ARGUMENT, "Nope" };
69
dbus_g_method_return_error (context, &error);
73
dbus_g_method_return (context);
77
simple_channel_dispatch_operation_claim (
78
TpSvcChannelDispatchOperation *iface,
79
DBusGMethodInvocation *context)
81
dbus_g_method_return (context);
85
channel_dispatch_operation_iface_init (gpointer klass,
86
gpointer unused G_GNUC_UNUSED)
88
#define IMPLEMENT(x) tp_svc_channel_dispatch_operation_implement_##x (\
89
klass, simple_channel_dispatch_operation_##x)
90
IMPLEMENT(handle_with);
97
simple_channel_dispatch_operation_init (SimpleChannelDispatchOperation *self)
99
self->priv = G_TYPE_INSTANCE_GET_PRIVATE (self, SIMPLE_TYPE_CHANNEL_DISPATCH_OPERATION,
100
SimpleChannelDispatchOperationPrivate);
102
self->priv->channels = g_ptr_array_new_with_free_func (
103
(GDestroyNotify) g_object_unref);
107
simple_channel_dispatch_operation_get_property (GObject *object,
112
SimpleChannelDispatchOperation *self = SIMPLE_CHANNEL_DISPATCH_OPERATION (
115
switch (property_id) {
116
case PROP_INTERFACES:
117
g_value_set_boxed (value, CHANNEL_DISPATCH_OPERATION_INTERFACES);
121
g_value_set_boxed (value, self->priv->account_path);
124
case PROP_CONNECTION:
125
g_value_set_boxed (value, self->priv->conn_path);
130
GPtrArray *arr = g_ptr_array_new ();
133
for (i = 0; i < self->priv->channels->len; i++)
135
TpChannel *channel = g_ptr_array_index (self->priv->channels, i);
137
g_ptr_array_add (arr,
138
tp_value_array_build (2,
139
DBUS_TYPE_G_OBJECT_PATH, tp_proxy_get_object_path (channel),
140
TP_HASH_TYPE_STRING_VARIANT_MAP,
141
tp_channel_borrow_immutable_properties (channel),
145
g_value_take_boxed (value, arr);
149
case PROP_POSSIBLE_HANDLERS:
150
g_value_set_boxed (value, CHANNEL_DISPATCH_OPERATION_POSSIBLE_HANDLERS);
154
G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, spec);
160
simple_channel_dispatch_operation_finalize (GObject *object)
162
SimpleChannelDispatchOperation *self = SIMPLE_CHANNEL_DISPATCH_OPERATION (
164
void (*finalize) (GObject *) =
165
G_OBJECT_CLASS (simple_channel_dispatch_operation_parent_class)->finalize;
167
g_free (self->priv->conn_path);
168
g_free (self->priv->account_path);
169
g_ptr_array_free (self->priv->channels, TRUE);
171
if (finalize != NULL)
176
* This class currently only provides the minimum for
177
* tp_channel_dispatch_operation_prepare to succeed. This turns out to be only a working
178
* Properties.GetAll().
181
simple_channel_dispatch_operation_class_init (SimpleChannelDispatchOperationClass *klass)
183
GObjectClass *object_class = (GObjectClass *) klass;
184
GParamSpec *param_spec;
186
static TpDBusPropertiesMixinPropImpl a_props[] = {
187
{ "Interfaces", "interfaces", NULL },
188
{ "Connection", "connection", NULL },
189
{ "Account", "account", NULL },
190
{ "Channels", "channels", NULL },
191
{ "PossibleHandlers", "possible-handlers", NULL },
195
static TpDBusPropertiesMixinIfaceImpl prop_interfaces[] = {
196
{ TP_IFACE_CHANNEL_DISPATCH_OPERATION,
197
tp_dbus_properties_mixin_getter_gobject_properties,
204
g_type_class_add_private (klass, sizeof (SimpleChannelDispatchOperationPrivate));
205
object_class->get_property = simple_channel_dispatch_operation_get_property;
206
object_class->finalize = simple_channel_dispatch_operation_finalize;
208
param_spec = g_param_spec_boxed ("interfaces", "Extra D-Bus interfaces",
209
"In this case we only implement ChannelDispatchOperation, so none.",
211
G_PARAM_READABLE | G_PARAM_STATIC_STRINGS);
212
g_object_class_install_property (object_class, PROP_INTERFACES, param_spec);
214
param_spec = g_param_spec_boxed ("connection", "connection path",
216
DBUS_TYPE_G_OBJECT_PATH,
217
G_PARAM_READABLE | G_PARAM_STATIC_STRINGS);
218
g_object_class_install_property (object_class, PROP_CONNECTION, param_spec);
220
param_spec = g_param_spec_boxed ("account", "account path",
222
DBUS_TYPE_G_OBJECT_PATH,
223
G_PARAM_READABLE | G_PARAM_STATIC_STRINGS);
224
g_object_class_install_property (object_class, PROP_ACCOUNT, param_spec);
226
param_spec = g_param_spec_boxed ("channels", "channel paths",
228
TP_ARRAY_TYPE_CHANNEL_DETAILS_LIST,
229
G_PARAM_READABLE | G_PARAM_STATIC_STRINGS);
230
g_object_class_install_property (object_class, PROP_CHANNELS, param_spec);
232
param_spec = g_param_spec_boxed ("possible-handlers", "possible handlers",
235
G_PARAM_READABLE | G_PARAM_STATIC_STRINGS);
236
g_object_class_install_property (object_class, PROP_POSSIBLE_HANDLERS,
239
klass->dbus_props_class.interfaces = prop_interfaces;
240
tp_dbus_properties_mixin_class_init (object_class,
241
G_STRUCT_OFFSET (SimpleChannelDispatchOperationClass, dbus_props_class));
245
simple_channel_dispatch_operation_set_conn_path (
246
SimpleChannelDispatchOperation *self,
247
const gchar *conn_path)
249
self->priv->conn_path = g_strdup (conn_path);
253
simple_channel_dispatch_operation_add_channel (
254
SimpleChannelDispatchOperation *self,
257
g_ptr_array_add (self->priv->channels, g_object_ref (chan));
261
simple_channel_dispatch_operation_lost_channel (
262
SimpleChannelDispatchOperation *self,
265
const gchar *path = tp_proxy_get_object_path (chan);
267
g_ptr_array_remove (self->priv->channels, chan);
269
tp_svc_channel_dispatch_operation_emit_channel_lost (self, path,
270
TP_ERROR_STR_NOT_AVAILABLE, "Badger");
272
if (self->priv->channels->len == 0)
274
/* We removed the last channel; fire Finished */
275
tp_svc_channel_dispatch_operation_emit_finished (self);
280
simple_channel_dispatch_operation_set_account_path (
281
SimpleChannelDispatchOperation *self,
282
const gchar *account_path)
284
self->priv->account_path = g_strdup (account_path);