1 /* GLib testing framework examples and tests
3 * Copyright © 2013 Red Hat, Inc.
4 * Copyright © 2015, 2017, 2018 Endless Mobile, Inc.
6 * SPDX-License-Identifier: LGPL-2.1-or-later
8 * This library is free software; you can redistribute it and/or
9 * modify it under the terms of the GNU Lesser General Public
10 * License as published by the Free Software Foundation; either
11 * version 2.1 of the License, or (at your option) any later version.
13 * This library is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 * Lesser General Public License for more details.
18 * You should have received a copy of the GNU Lesser General
19 * Public License along with this library; if not, see <http://www.gnu.org/licenses/>.
25 #if defined (G_OS_UNIX) && !defined (__APPLE__)
26 #include <gio/gdesktopappinfo.h>
31 gchar *applications_dir;
35 setup (Fixture *fixture,
36 gconstpointer user_data)
38 fixture->applications_dir = g_build_filename (g_get_user_data_dir (), "applications", NULL);
39 g_assert_no_errno (g_mkdir_with_parents (fixture->applications_dir, 0755));
41 g_test_message ("Using data directory: %s", g_get_user_data_dir ());
45 teardown (Fixture *fixture,
46 gconstpointer user_data)
48 g_assert_no_errno (g_rmdir (fixture->applications_dir));
49 g_clear_pointer (&fixture->applications_dir, g_free);
52 #if defined (G_OS_UNIX) && !defined (__APPLE__)
54 create_app (gpointer data)
56 const gchar *path = data;
58 const gchar *contents =
65 g_file_set_contents (path, contents, -1, &error);
66 g_assert_no_error (error);
68 return G_SOURCE_REMOVE;
72 delete_app (gpointer data)
74 const gchar *path = data;
80 changed_cb (GAppInfoMonitor *monitor,
83 gboolean *changed_fired = user_data;
85 *changed_fired = TRUE;
86 g_main_context_wakeup (g_main_context_get_thread_default ());
90 timeout_cb (gpointer user_data)
92 gboolean *timed_out = user_data;
94 g_assert (!timed_out);
96 g_main_context_wakeup (g_main_context_get_thread_default ());
98 return G_SOURCE_REMOVE;
100 #endif /* defined (G_OS_UNIX) && !defined (__APPLE__) */
103 test_app_monitor (Fixture *fixture,
104 gconstpointer user_data)
106 #if defined (G_OS_UNIX) && !defined (__APPLE__)
108 GAppInfoMonitor *monitor;
109 GMainContext *context = NULL; /* use the global default main context */
110 GSource *timeout_source = NULL;
111 GDesktopAppInfo *app = NULL;
112 gboolean changed_fired = FALSE;
113 gboolean timed_out = FALSE;
115 app_path = g_build_filename (fixture->applications_dir, "app.desktop", NULL);
117 /* FIXME: this shouldn't be required */
118 g_list_free_full (g_app_info_get_all (), g_object_unref);
120 /* Create an app monitor and check that its ::changed signal is emitted when
121 * a new app is installed. */
122 monitor = g_app_info_monitor_get ();
124 g_signal_connect (monitor, "changed", G_CALLBACK (changed_cb), &changed_fired);
126 g_idle_add (create_app, app_path);
127 timeout_source = g_timeout_source_new_seconds (3);
128 g_source_set_callback (timeout_source, timeout_cb, &timed_out, NULL);
129 g_source_attach (timeout_source, NULL);
131 while (!changed_fired && !timed_out)
132 g_main_context_iteration (context, TRUE);
134 g_assert_true (changed_fired);
135 changed_fired = FALSE;
137 g_source_destroy (timeout_source);
138 g_clear_pointer (&timeout_source, g_source_unref);
140 /* Check that the app is now queryable. This has the side-effect of re-arming
141 * the #GAppInfoMonitor::changed signal for the next part of the test. */
142 app = g_desktop_app_info_new ("app.desktop");
143 g_assert_nonnull (app);
144 g_clear_object (&app);
146 /* Now check that ::changed is emitted when an app is uninstalled. */
147 timeout_source = g_timeout_source_new_seconds (3);
148 g_source_set_callback (timeout_source, timeout_cb, &timed_out, NULL);
149 g_source_attach (timeout_source, NULL);
151 delete_app (app_path);
153 while (!changed_fired && !timed_out)
154 g_main_context_iteration (context, TRUE);
156 g_assert_true (changed_fired);
158 g_source_destroy (timeout_source);
159 g_clear_pointer (&timeout_source, g_source_unref);
162 g_object_unref (monitor);
165 #elif defined (__APPLE__)
166 g_test_skip (".desktop monitor on macos");
167 #else /* if !(defined (G_OS_UNIX) && !defined (__APPLE__)) */
168 g_test_skip (".desktop monitor on win32");
169 #endif /* !(defined (G_OS_UNIX) && !defined (__APPLE__)) */
173 main (int argc, char *argv[])
175 g_test_init (&argc, &argv, G_TEST_OPTION_ISOLATE_DIRS, NULL);
177 g_test_add ("/monitor/app", Fixture, NULL, setup, test_app_monitor, teardown);
179 return g_test_run ();