Add api for cloudprovider object manager
Julius Härtl
6 years ago
0 | /* cloudprovider.c | |
1 | * | |
2 | * Copyright (C) 2015 Carlos Soriano <csoriano@gnome.org> | |
3 | * Copyright (C) 2017 Julius Haertl <jus@bitgrid.net> | |
4 | * | |
5 | * This file is free software; you can redistribute it and/or modify it | |
6 | * under the terms of the GNU Lesser General Public License as | |
7 | * published by the Free Software Foundation; either version 3 of the | |
8 | * License, or (at your option) any later version. | |
9 | * | |
10 | * This file is distributed in the hope that it will be useful, but | |
11 | * WITHOUT ANY WARRANTY; without even the implied warranty of | |
12 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | |
13 | * Lesser General Public License for more details. | |
14 | * | |
15 | * You should have received a copy of the GNU General Public License | |
16 | * along with this program. If not, see <http://www.gnu.org/licenses/>. | |
17 | */ | |
18 | ||
19 | #include "cloudprovider.h" | |
20 | #include "cloudprovider-generated.h" | |
21 | ||
22 | ||
23 | typedef struct | |
24 | { | |
25 | GDBusConnection *bus; | |
26 | GDBusObjectManagerServer *manager; | |
27 | gchar *bus_name; | |
28 | gchar *object_path; | |
29 | GCancellable *cancellable; | |
30 | } CloudProviderPrivate; | |
31 | ||
32 | G_DEFINE_TYPE_WITH_PRIVATE (CloudProvider, cloud_provider, G_TYPE_OBJECT) | |
33 | ||
34 | enum { | |
35 | CHANGED, | |
36 | READY, | |
37 | LAST_SIGNAL | |
38 | }; | |
39 | ||
40 | static guint gSignals [LAST_SIGNAL]; | |
41 | ||
42 | void | |
43 | cloud_provider_export_account(CloudProvider* cloud_provider, | |
44 | gchar *account_name, | |
45 | CloudProviderAccount1 *account) | |
46 | { | |
47 | CloudProviderPrivate *priv = cloud_provider_get_instance_private(cloud_provider); | |
48 | CloudProviderObjectSkeleton *object; | |
49 | gchar *object_path = g_strconcat (priv->object_path, "/", account_name, NULL); | |
50 | g_print("%s\n", object_path); | |
51 | object = cloud_provider_object_skeleton_new(object_path); | |
52 | cloud_provider_object_skeleton_set_account1(object, account); | |
53 | g_dbus_object_manager_server_export (priv->manager, | |
54 | G_DBUS_OBJECT_SKELETON(object)); | |
55 | g_free(object_path); | |
56 | } | |
57 | ||
58 | void | |
59 | cloud_provider_unexport_account(CloudProvider* cloud_provider, | |
60 | gchar *account_name) | |
61 | { | |
62 | CloudProviderPrivate *priv = cloud_provider_get_instance_private(cloud_provider); | |
63 | gchar *object_path = g_strconcat (priv->object_path, "/", account_name, NULL); | |
64 | g_dbus_object_manager_server_unexport (priv->manager, object_path); | |
65 | g_free (object_path); | |
66 | } | |
67 | ||
68 | guint | |
69 | cloud_provider_export_menu(CloudProvider* cloud_provider, | |
70 | gchar *account_name, | |
71 | GMenuModel *model) | |
72 | { | |
73 | CloudProviderPrivate *priv = cloud_provider_get_instance_private(cloud_provider); | |
74 | gchar *object_path = g_strconcat(priv->object_path, "/", account_name, NULL); | |
75 | GError *error = NULL; | |
76 | g_print ("Exporting menus on the bus...\n"); | |
77 | guint export_id = g_dbus_connection_export_menu_model (priv->bus, object_path, model, &error); | |
78 | if (!export_id) | |
79 | { | |
80 | g_warning ("Menu export failed: %s", error->message); | |
81 | return 0; | |
82 | } | |
83 | return export_id; | |
84 | } | |
85 | ||
86 | guint | |
87 | cloud_provider_export_actions(CloudProvider* cloud_provider, | |
88 | gchar *account_name, | |
89 | GActionGroup *action_group) | |
90 | { | |
91 | CloudProviderPrivate *priv = cloud_provider_get_instance_private(cloud_provider); | |
92 | gchar *object_path = g_strconcat(priv->object_path, "/", account_name, NULL); | |
93 | GError *error = NULL; | |
94 | guint export_id = g_dbus_connection_export_action_group (priv->bus, object_path, action_group, &error); | |
95 | g_print ("Exporting actions on the bus...\n"); | |
96 | if (!export_id) | |
97 | { | |
98 | g_warning ("Action export failed: %s", error->message); | |
99 | return 0; | |
100 | } | |
101 | return export_id; | |
102 | } | |
103 | ||
104 | void | |
105 | cloud_provider_export_objects(CloudProvider* cloud_provider) | |
106 | { | |
107 | CloudProviderPrivate *priv = cloud_provider_get_instance_private(cloud_provider); | |
108 | g_dbus_object_manager_server_set_connection (priv->manager, priv->bus); | |
109 | } | |
110 | ||
111 | void | |
112 | cloud_provider_emit_changed (CloudProvider *cloud_provider, gchar *account_name) | |
113 | { | |
114 | CloudProviderPrivate *priv = cloud_provider_get_instance_private(cloud_provider); | |
115 | gchar *object_path = g_strconcat(priv->object_path, "/", account_name, NULL); | |
116 | g_dbus_connection_emit_signal (priv->bus, | |
117 | NULL, | |
118 | object_path, | |
119 | "org.freedesktop.CloudProvider.Account1", | |
120 | "CloudProviderChanged", | |
121 | NULL, | |
122 | NULL /*error*/); | |
123 | g_free (object_path); | |
124 | } | |
125 | CloudProvider* | |
126 | cloud_provider_new (GDBusConnection *bus, | |
127 | const gchar *bus_name, | |
128 | const gchar *object_path) | |
129 | { | |
130 | CloudProvider *self; | |
131 | CloudProviderPrivate *priv; | |
132 | ||
133 | self = g_object_new (TYPE_CLOUD_PROVIDER, NULL); | |
134 | priv = cloud_provider_get_instance_private (self); | |
135 | ||
136 | priv->bus_name = g_strdup (bus_name); | |
137 | priv->object_path = g_strdup (object_path); | |
138 | priv->bus = bus; | |
139 | priv->cancellable = g_cancellable_new (); | |
140 | priv->manager = g_dbus_object_manager_server_new (object_path); | |
141 | ||
142 | return self; | |
143 | } | |
144 | ||
145 | static void | |
146 | cloud_provider_finalize (GObject *object) | |
147 | { | |
148 | CloudProvider *self = (CloudProvider *)object; | |
149 | CloudProviderPrivate *priv = cloud_provider_get_instance_private (self); | |
150 | ||
151 | g_cancellable_cancel (priv->cancellable); | |
152 | g_clear_object (&priv->cancellable); | |
153 | g_clear_object (&priv->bus); | |
154 | g_free (priv->bus_name); | |
155 | g_free (priv->object_path); | |
156 | ||
157 | G_OBJECT_CLASS (cloud_provider_parent_class)->finalize (object); | |
158 | } | |
159 | ||
160 | static void | |
161 | cloud_provider_class_init (CloudProviderClass *klass) | |
162 | { | |
163 | GObjectClass *object_class = G_OBJECT_CLASS (klass); | |
164 | ||
165 | object_class->finalize = cloud_provider_finalize; | |
166 | ||
167 | gSignals [CHANGED] = | |
168 | g_signal_new ("changed", | |
169 | G_TYPE_FROM_CLASS (klass), | |
170 | G_SIGNAL_RUN_LAST, | |
171 | 0, | |
172 | NULL, | |
173 | NULL, | |
174 | g_cclosure_marshal_generic, | |
175 | G_TYPE_NONE, | |
176 | 0); | |
177 | gSignals [READY] = | |
178 | g_signal_new ("ready", | |
179 | G_TYPE_FROM_CLASS (klass), | |
180 | G_SIGNAL_RUN_LAST, | |
181 | 0, | |
182 | NULL, | |
183 | NULL, | |
184 | g_cclosure_marshal_generic, | |
185 | G_TYPE_NONE, | |
186 | 0); | |
187 | } | |
188 | ||
189 | static void | |
190 | cloud_provider_init (CloudProvider *self) | |
191 | { | |
192 | } |
0 | /* cloudprovider.h | |
1 | * | |
2 | * Copyright (C) 2017 Julius Haertl <jus@bitgrid.net> | |
3 | * | |
4 | * This file is free software; you can redistribute it and/or modify it | |
5 | * under the terms of the GNU Lesser General Public License as | |
6 | * published by the Free Software Foundation; either version 3 of the | |
7 | * License, or (at your option) any later version. | |
8 | * | |
9 | * This file is distributed in the hope that it will be useful, but | |
10 | * WITHOUT ANY WARRANTY; without even the implied warranty of | |
11 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | |
12 | * Lesser General Public License for more details. | |
13 | * | |
14 | * You should have received a copy of the GNU General Public License | |
15 | * along with this program. If not, see <http://www.gnu.org/licenses/>. | |
16 | */ | |
17 | ||
18 | #ifndef CLOUD_PROVIDER_H | |
19 | #define CLOUD_PROVIDER_H | |
20 | ||
21 | #include <gio/gio.h> | |
22 | #include "cloudprovider-generated.h" | |
23 | ||
24 | G_BEGIN_DECLS | |
25 | ||
26 | #define TYPE_CLOUD_PROVIDER (cloud_provider_get_type()) | |
27 | #define CLOUD_PROVIDER(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), TYPE_CLOUD_PROVIDER, CloudProvider)) | |
28 | #define CLOUD_PROVIDER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), TYPE_CLOUD_PROVIDER, CloudProviderClass)) | |
29 | #define IS_CLOUD_PROVIDER(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), TYPE_CLOUD_PROVIDER)) | |
30 | #define IS_CLOUD_PROVIDER_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), TYPE_CLOUD_PROVIDER)) | |
31 | #define CLOUD_PROVIDER_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), TYPE_CLOUD_PROVIDER, CloudProviderClass)) | |
32 | ||
33 | typedef struct _CloudProvider CloudProvider; | |
34 | typedef struct _CloudProviderClass CloudProviderClass; | |
35 | ||
36 | ||
37 | struct _CloudProviderClass | |
38 | { | |
39 | GObjectClass parent_class; | |
40 | }; | |
41 | ||
42 | struct _CloudProvider | |
43 | { | |
44 | GObject parent_instance; | |
45 | }; | |
46 | ||
47 | ||
48 | ||
49 | void | |
50 | cloud_provider_export_account (CloudProvider* cloud_provider, | |
51 | gchar *account_name, | |
52 | CloudProviderAccount1 *account); | |
53 | void | |
54 | cloud_provider_unexport_account (CloudProvider* cloud_provider, | |
55 | gchar *account_name); | |
56 | guint | |
57 | cloud_provider_export_menu (CloudProvider* cloud_provider, | |
58 | gchar *account_name, | |
59 | GMenuModel *model); | |
60 | guint | |
61 | cloud_provider_export_actions(CloudProvider* cloud_provider, | |
62 | gchar *account_name, | |
63 | GActionGroup *action_group); | |
64 | void | |
65 | cloud_provider_export_objects (CloudProvider* cloud_provider); | |
66 | ||
67 | void | |
68 | cloud_provider_emit_changed (CloudProvider *cloud_provider, gchar *account_name); | |
69 | ||
70 | CloudProvider* | |
71 | cloud_provider_new (GDBusConnection *bus, | |
72 | const gchar *bus_name, | |
73 | const gchar *object_path); | |
74 | ||
75 | G_END_DECLS | |
76 | ||
77 | ||
78 | #endif /* CLOUD_PROVIDER_H */ |
1 | 1 | #include <cloudprovidermanager.h> |
2 | 2 | |
3 | 3 | gint |
4 | main (gint argc, | |
5 | gchar *argv[]) | |
4 | main (gint argc, gchar *argv[]) | |
6 | 5 | { |
7 | 6 | GMainLoop *loop = g_main_loop_new(NULL, FALSE); |
8 | 7 | CloudProviderManager *manager = cloud_provider_manager_dup_singleton (); |
9 | 8 | g_main_loop_run(loop); |
10 | 9 | g_free(manager); |
11 | 10 | g_free(loop); |
12 | ||
13 | 11 | return 0; |
14 | 12 | } |
1 | 1 | 'cloudprovidermanager.h', |
2 | 2 | 'cloudproviderproxy.h', |
3 | 3 | 'cloudproviders.h', |
4 | 'cloudprovider.h', | |
4 | 5 | 'cloudprovider-generated.h', |
5 | 6 | 'cloudprovidermanager-generated.h' |
6 | 7 | ] |
9 | 10 | 'cloudprovidermanager.c', |
10 | 11 | 'cloudproviderproxy.c', |
11 | 12 | 'cloudproviders.c', |
13 | 'cloudprovider.c', | |
12 | 14 | ] |
13 | 15 | |
14 | 16 | libcloudproviders_deps = [glib, gio, gio_unix] |
0 | 0 | #include <glib.h> |
1 | 1 | #include <stdlib.h> |
2 | 2 | #include <gio/gio.h> |
3 | #include <cloudprovider.h> | |
3 | 4 | #include <cloudproviderproxy.h> |
5 | ||
4 | 6 | |
5 | 7 | #define TIMEOUT 800 |
6 | 8 | #define COUNT_PLACEHOLDER_ACCOUNTS 3 |
9 | #define TEST_CLOUD_PROVIDER_BUS_NAME "org.freedesktop.CloudProviderServerExample" | |
10 | #define TEST_CLOUD_PROVIDER_OBJECT_PATH "/org/freedesktop/CloudProviderServerExample" | |
7 | 11 | |
8 | 12 | typedef struct _TestCloudProviderClass TestCloudProviderClass; |
9 | 13 | typedef struct _TestCloudProvider TestCloudProvider; |
23 | 27 | gchar *path; |
24 | 28 | guint timeout_handler; |
25 | 29 | GDBusConnection *connection; |
30 | CloudProvider *cloud_provider; | |
26 | 31 | GDBusObjectManagerServer *manager; |
27 | 32 | }; |
28 | 33 | |
206 | 211 | return G_ACTION_GROUP (group); |
207 | 212 | } |
208 | 213 | |
209 | static void | |
210 | export_menu (GDBusConnection *bus, | |
211 | gchar *object_path) | |
212 | { | |
213 | GMenuModel *model; | |
214 | GActionGroup *action_group; | |
215 | GError *error = NULL; | |
216 | ||
217 | model = get_model (); | |
218 | action_group = get_action_group (); | |
219 | ||
220 | g_print ("Exporting menus on the bus...\n"); | |
221 | if (!g_dbus_connection_export_menu_model (bus, object_path, model, &error)) | |
222 | { | |
223 | g_warning ("Menu export failed: %s", error->message); | |
224 | exit (1); | |
225 | } | |
226 | g_print ("Exporting actions on the bus...\n"); | |
227 | if (!g_dbus_connection_export_action_group (bus, object_path, action_group, &error)) | |
228 | { | |
229 | g_warning ("Action export failed: %s", error->message); | |
230 | exit (1); | |
231 | } | |
232 | } | |
233 | ||
234 | ||
235 | 214 | static gboolean |
236 | 215 | change_random_cloud_provider_state (gpointer user_data) |
237 | 216 | { |
247 | 226 | CLOUD_PROVIDER_STATUS_IDLE, |
248 | 227 | CLOUD_PROVIDER_STATUS_ERROR + 1); |
249 | 228 | |
250 | account_object_name = g_strdup_printf ("/org/freedesktop/CloudProviderServerExample/%03d", | |
251 | account_id); | |
252 | ||
229 | account_object_name = g_strdup_printf ("MyCloud%d", account_id); | |
230 | g_print ("Change status of %03d to %d\n", account_id, new_status); | |
253 | 231 | test_cloud_provider_set_status (cloud_provider, new_status); |
254 | ||
255 | g_print ("Change status of %03d to %d\n", account_id, new_status); | |
256 | ||
257 | g_dbus_connection_emit_signal (cloud_provider->connection, | |
258 | NULL, | |
259 | account_object_name, | |
260 | "org.freedesktop.CloudProvider.Account1", | |
261 | "CloudProviderChanged", | |
262 | NULL, | |
263 | NULL /*error*/); | |
232 | cloud_provider_emit_changed (cloud_provider->cloud_provider, account_object_name); | |
264 | 233 | return TRUE; |
265 | 234 | } |
266 | 235 | |
312 | 281 | { |
313 | 282 | TestCloudProvider *self = user_data; |
314 | 283 | guint n; |
315 | CloudProviderObjectSkeleton *object; | |
284 | ||
316 | 285 | self->connection = connection; |
286 | self->cloud_provider = cloud_provider_new(self->connection, | |
287 | TEST_CLOUD_PROVIDER_BUS_NAME, | |
288 | TEST_CLOUD_PROVIDER_OBJECT_PATH); | |
317 | 289 | |
318 | 290 | g_debug ("Registering cloud provider server 'MyCloud'\n"); |
319 | 291 | |
320 | self->manager = g_dbus_object_manager_server_new ("/org/freedesktop/CloudProviderServerExample"); | |
321 | 292 | // export multiple accounts as DBus objects to the bus |
322 | 293 | for (n = 0; n < COUNT_PLACEHOLDER_ACCOUNTS; n++) |
323 | 294 | { |
324 | ||
325 | gchar *account_object_name; | |
326 | gchar *account_name; | |
327 | ||
328 | account_object_name = g_strdup_printf ("/org/freedesktop/CloudProviderServerExample/%03d", n); | |
329 | account_name = g_strdup_printf ("MyCloud %d", n); | |
330 | object = cloud_provider_object_skeleton_new(account_object_name); | |
331 | ||
332 | CloudProviderAccount1 *cloud_provider = cloud_provider_account1_skeleton_new(); | |
333 | g_signal_connect(cloud_provider, "handle_get_name", G_CALLBACK (on_get_name), account_name); | |
334 | g_signal_connect(cloud_provider, "handle_get_icon", G_CALLBACK (on_get_icon), self); | |
335 | g_signal_connect(cloud_provider, "handle_get_path", G_CALLBACK (on_get_path), self); | |
336 | g_signal_connect(cloud_provider, "handle_get_status", G_CALLBACK (on_get_status), self); | |
337 | cloud_provider_object_skeleton_set_account1(object, cloud_provider); | |
338 | g_dbus_object_manager_server_export (self->manager, G_DBUS_OBJECT_SKELETON(object)); | |
339 | ||
340 | export_menu (connection, account_object_name); | |
295 | gchar *account_object_name = g_strdup_printf ("MyCloud%d", n); | |
296 | gchar *account_name = g_strdup_printf ("MyCloud %d", n); | |
297 | ||
298 | CloudProviderAccount1 *cloud_provider_account = cloud_provider_account1_skeleton_new(); | |
299 | g_signal_connect(cloud_provider_account, "handle_get_name", G_CALLBACK (on_get_name), account_name); | |
300 | g_signal_connect(cloud_provider_account, "handle_get_icon", G_CALLBACK (on_get_icon), self); | |
301 | g_signal_connect(cloud_provider_account, "handle_get_path", G_CALLBACK (on_get_path), self); | |
302 | g_signal_connect(cloud_provider_account, "handle_get_status", G_CALLBACK (on_get_status), self); | |
303 | ||
304 | cloud_provider_export_account(self->cloud_provider, account_object_name, cloud_provider_account); | |
305 | cloud_provider_export_menu (self->cloud_provider, account_object_name, get_model ()); | |
306 | cloud_provider_export_actions (self->cloud_provider, account_object_name, get_action_group ()); | |
341 | 307 | |
342 | 308 | g_free(account_object_name); |
343 | 309 | } |
344 | g_dbus_object_manager_server_set_connection (self->manager, connection); | |
310 | ||
311 | cloud_provider_export_objects (self->cloud_provider); | |
345 | 312 | |
346 | 313 | return; |
347 | ||
348 | ||
349 | 314 | } |
350 | 315 | |
351 | 316 | static void |
378 | 343 | test_cloud_provider = g_object_new (test_cloud_provider_get_type (), NULL); |
379 | 344 | |
380 | 345 | owner_id = g_bus_own_name (G_BUS_TYPE_SESSION, |
381 | "org.freedesktop.CloudProviderServerExample", | |
346 | TEST_CLOUD_PROVIDER_BUS_NAME, | |
382 | 347 | G_BUS_NAME_OWNER_FLAGS_NONE, |
383 | 348 | on_bus_acquired, |
384 | 349 | on_name_acquired, |