package-update-indicator-7/pui-get-updates.c010064400017500001750000000152441331741420000177120ustar00gbergber/* * Copyright (C) 2018 Guido Berhoerster * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files (the * "Software"), to deal in the Software without restriction, including * without limitation the rights to use, copy, modify, merge, publish, * distribute, sublicense, and/or sell copies of the Software, and to * permit persons to whom the Software is furnished to do so, subject to * the following conditions: * * The above copyright notice and this permission notice shall be included * in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ #include "pui-get-updates.h" typedef struct { PkControl *pk_control; PkTask *pk_task; guint refresh_interval; } PuiGetUpdates; GQuark pui_get_updates_error_quark(void) { return (g_quark_from_static_string("pui-get-updates-error-quark")); } static void on_get_updates_finished(GObject *source_object, GAsyncResult *async_result, gpointer user_data) { GTask *task = user_data; PuiGetUpdates *get_updates; PkResults *results = NULL; PkError *pk_error = NULL; GError *error = NULL; gint error_code; GPtrArray *package_list; get_updates = g_task_get_task_data(task); g_debug("get updates transaction finished"); results = pk_client_generic_finish(PK_CLIENT(get_updates->pk_task), async_result, &error); if (results == NULL) { /* pass the error on */ g_task_return_error(task, error); goto out; } pk_error = pk_results_get_error_code(results); if (pk_error != NULL) { /* transaction failed, return error */ g_debug("failed to refresh the cache: %s", pk_error_get_details(pk_error)); if (pk_error_get_code(pk_error) == PK_ERROR_ENUM_TRANSACTION_CANCELLED) { error_code = PUI_GET_UPDATES_ERROR_CANCELLED; } else { error_code = PUI_GET_UPDATES_ERROR_GET_UPDATES_FAILED; } error = g_error_new(PUI_GET_UPDATES_ERROR, error_code, "Failed to get package updates: %s", pk_error_get_details(pk_error)); g_task_return_error(task, error); g_object_unref(pk_error); goto out; } /* return results */ package_list = pk_results_get_package_array(results); g_assert(package_list != NULL); g_task_return_pointer(task, package_list, (GDestroyNotify)g_ptr_array_unref); out: if (results != NULL) { g_object_unref(results); } g_object_unref(task); } static void on_refresh_cache_finished(GObject *source_object, GAsyncResult *async_result, gpointer user_data) { GTask *task = user_data; PuiGetUpdates *get_updates; PkResults *results = NULL; PkClient *pk_client; GError *error = NULL; PkError *pk_error = NULL; gint error_code; get_updates = g_task_get_task_data(task); pk_client = PK_CLIENT(get_updates->pk_task); g_debug("refresh cache transaction finished"); results = pk_client_generic_finish(pk_client, async_result, &error); if (results == NULL) { g_task_return_error(task, error); goto out; } pk_error = pk_results_get_error_code(results); if (pk_error != NULL) { /* transaction failed, return error */ g_debug("failed to refresh the cache: %s", pk_error_get_details(pk_error)); if (pk_error_get_code(pk_error) == PK_ERROR_ENUM_TRANSACTION_CANCELLED) { error_code = PUI_GET_UPDATES_ERROR_CANCELLED; } else { error_code = PUI_GET_UPDATES_ERROR_REFRESH_FAILED; } error = g_error_new(PUI_GET_UPDATES_ERROR, error_code, "Failed to refresh the cache: %s", pk_error_get_details(pk_error)); g_task_return_error(task, error); g_object_unref(pk_error); goto out; } /* cache is up to date, get updates */ pk_client_get_updates_async(pk_client, pk_bitfield_value(PK_FILTER_ENUM_NONE), g_task_get_cancellable(task), NULL, NULL, on_get_updates_finished, task); out: if (results != NULL) { g_object_unref(results); } } static void on_get_time_since_refresh_finished(GObject *source_object, GAsyncResult *async_result, gpointer user_data) { GTask *task = user_data; PuiGetUpdates *get_updates; guint last_refresh; GError *error = NULL; PkClient *pk_client; get_updates = g_task_get_task_data(task); pk_client = PK_CLIENT(get_updates->pk_task); last_refresh = pk_control_get_time_since_action_finish(get_updates->pk_control, async_result, &error); if (last_refresh == 0) { g_task_return_error(task, error); g_object_unref(task); return; } g_debug("time since last cache refresh: %us", last_refresh); if (last_refresh > get_updates->refresh_interval) { /* cache is out of date, refresh first */ g_debug("refreshing the cache"); pk_client_refresh_cache_async(pk_client, FALSE, g_task_get_cancellable(task), NULL, NULL, on_refresh_cache_finished, task); } else { /* cache is up to date, get updates */ g_debug("getting updates"); pk_client_get_updates_async(pk_client, pk_bitfield_value(PK_FILTER_ENUM_NONE), g_task_get_cancellable(task), NULL, NULL, on_get_updates_finished, task); } } static void pui_get_updates_free(gpointer data) { PuiGetUpdates *get_updates = data; g_object_unref(get_updates->pk_control); g_object_unref(get_updates->pk_task); g_slice_free(PuiGetUpdates, data); } void pui_get_updates_async(PkControl *pk_control, guint refresh_interval, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data) { PuiGetUpdates *get_updates; GTask *task; PkClient *pk_client; get_updates = g_slice_new0(PuiGetUpdates); get_updates->pk_control = g_object_ref(pk_control); get_updates->pk_task = pk_task_new(); get_updates->refresh_interval = refresh_interval; pk_client = PK_CLIENT(get_updates->pk_task); pk_client_set_cache_age(pk_client, refresh_interval); pk_client_set_background(pk_client, TRUE); task = g_task_new(NULL, cancellable, callback, user_data); g_task_set_task_data(task, get_updates, pui_get_updates_free); /* check whether to refresh the cache before checking for updates */ g_debug("getting the time since the cache was last refreshed"); pk_control_get_time_since_action_async(pk_control, PK_ROLE_ENUM_REFRESH_CACHE, cancellable, on_get_time_since_refresh_finished, task); } GPtrArray * pui_get_updates_finish(GAsyncResult *result, GError **errorp) { return (g_task_propagate_pointer(G_TASK(result), errorp)); } package-update-indicator-7/pui-types.h.in010064400017500001750000000010371331765667600172720ustar00gbergber/*** BEGIN file-header ***/ #ifndef PUI_TYPES_H #define PUI_TYPES_H #include G_BEGIN_DECLS /*** END file-header ***/ /*** BEGIN file-production ***/ /* enumerations from "@filename@" */ /*** END file-production ***/ /*** BEGIN value-header ***/ #define @ENUMPREFIX@_TYPE_@ENUMSHORT@ (@enum_name@_get_type()) GType @enum_name@_get_type(void) G_GNUC_CONST; /*** END value-header ***/ /*** BEGIN file-tail ***/ gchar * pui_types_enum_to_string(GType, gint); G_END_DECLS #endif /* !PUI_TYPES_H */ /*** END file-tail ***/ package-update-indicator-7/pui-prefs-application.c010064400017500001750000000155201331741424000211110ustar00gbergber/* * Copyright (C) 2018 Guido Berhoerster * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files (the * "Software"), to deal in the Software without restriction, including * without limitation the rights to use, copy, modify, merge, publish, * distribute, sublicense, and/or sell copies of the Software, and to * permit persons to whom the Software is furnished to do so, subject to * the following conditions: * * The above copyright notice and this permission notice shall be included * in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ #include #include #include "pui-prefs-application.h" #include "pui-settings.h" #define COLUMN_REFRESH_INTERVAL 2 struct _PuiPrefsApplication { GtkApplication parent_instance; GSettings *settings; }; G_DEFINE_TYPE(PuiPrefsApplication, pui_prefs_application, GTK_TYPE_APPLICATION) static void pui_prefs_application_quit(GSimpleAction *, GVariant *, gpointer); static const GActionEntry pui_prefs_application_actions[] = { { "quit", pui_prefs_application_quit } }; static void pui_prefs_application_quit(GSimpleAction *simple, GVariant *parameter, gpointer user_data) { PuiPrefsApplication *self = user_data; g_application_quit(G_APPLICATION(self)); } static gboolean map_refresh_interval_to_index(GValue *value, GVariant *variant, gpointer user_data) { GtkTreeModel *tree_model = user_data; guint32 setting_interval; gint index; gboolean iter_continue; GtkTreeIter iter = { 0 }; GValue model_value = G_VALUE_INIT; guint model_interval; setting_interval = g_variant_get_uint32(variant); /* try to find a matching entry in the list */ for (iter_continue = gtk_tree_model_get_iter_first(tree_model, &iter), index = 0; iter_continue; iter_continue = gtk_tree_model_iter_next(tree_model, &iter), index++) { gtk_tree_model_get_value(tree_model, &iter, COLUMN_REFRESH_INTERVAL, &model_value); model_interval = g_value_get_uint(&model_value); g_value_unset(&model_value); if (setting_interval == model_interval) { g_debug("mapping refresh-interval %" G_GUINT32_FORMAT " to index %d", setting_interval, index); g_value_set_int(value, index); return (TRUE); } } g_debug("mapping refresh-interval %" G_GUINT32_FORMAT " to index -1", setting_interval); g_value_set_int(value, -1); return (TRUE); } static GVariant * map_index_to_refresh_interval(const GValue *value, const GVariantType *expected_type, gpointer user_data) { GtkTreeModel *tree_model = GTK_TREE_MODEL(user_data); gint index; GtkTreeIter iter = { 0 }; GValue model_value = G_VALUE_INIT; guint model_interval; index = g_value_get_int(value); if (!gtk_tree_model_iter_nth_child(tree_model, &iter, NULL, index)) { return (NULL); } gtk_tree_model_get_value(tree_model, &iter, COLUMN_REFRESH_INTERVAL, &model_value); model_interval = g_value_get_uint(&model_value); g_debug("mapping index %d to refresh-interval value %" G_GUINT32_FORMAT, index, model_interval); g_value_unset(&model_value); return (g_variant_new_uint32(model_interval)); } static void pui_prefs_application_startup(GApplication *application) { PuiPrefsApplication *self = PUI_PREFS_APPLICATION(application); GApplicationClass *application_class = G_APPLICATION_CLASS(pui_prefs_application_parent_class); GtkBuilder *builder; GtkWidget *window; GtkTreeModel *tree_model; GtkWidget *update_command_entry; GtkWidget *refresh_interval_combo_box; GtkWidget *use_mobile_check_button; application_class->startup(application); /* create actions */ g_action_map_add_action_entries(G_ACTION_MAP(self), pui_prefs_application_actions, G_N_ELEMENTS(pui_prefs_application_actions), self); /* get widgets from builder */ builder = gtk_builder_new_from_resource("/org/guido-berhoerster/code/" "package-update-indicator/preferences/pui-prefs-window.ui"); window = GTK_WIDGET(gtk_builder_get_object(builder, "window")); gtk_application_add_window(GTK_APPLICATION(self), GTK_WINDOW(window)); update_command_entry = GTK_WIDGET(gtk_builder_get_object(builder, "update-command")); refresh_interval_combo_box = GTK_WIDGET(gtk_builder_get_object(builder, "refresh-interval")); tree_model = gtk_combo_box_get_model(GTK_COMBO_BOX(refresh_interval_combo_box)); use_mobile_check_button = GTK_WIDGET(gtk_builder_get_object(builder, "use-mobile-connection")); /* bind settings to widgets */ self->settings = pui_settings_new(); g_settings_bind(self->settings, "update-command", update_command_entry, "text", G_SETTINGS_BIND_DEFAULT); g_settings_bind_with_mapping(self->settings, "refresh-interval", refresh_interval_combo_box, "active", G_SETTINGS_BIND_DEFAULT, map_refresh_interval_to_index, map_index_to_refresh_interval, tree_model, NULL); g_settings_bind(self->settings, "use-mobile-connection", use_mobile_check_button, "active", G_SETTINGS_BIND_DEFAULT); /* show window */ gtk_widget_show(window); gtk_window_present(GTK_WINDOW(window)); g_object_unref(builder); } static void pui_prefs_application_activate(GApplication *application) { GtkApplication *gtk_application = GTK_APPLICATION(application); GApplicationClass *application_class = G_APPLICATION_CLASS(pui_prefs_application_parent_class); /* raise window when activated */ gtk_window_present(gtk_application_get_active_window(gtk_application)); application_class->activate(application); } static void pui_prefs_application_dispose(GObject *object) { PuiPrefsApplication *self = PUI_PREFS_APPLICATION(object); if (self->settings != NULL) { g_clear_object(&self->settings); } G_OBJECT_CLASS(pui_prefs_application_parent_class)->dispose(object); } static void pui_prefs_application_class_init(PuiPrefsApplicationClass *klass) { GObjectClass *object_class = G_OBJECT_CLASS(klass); GApplicationClass *application_class = G_APPLICATION_CLASS(klass); object_class->dispose = pui_prefs_application_dispose; application_class->startup = pui_prefs_application_startup; application_class->activate = pui_prefs_application_activate; } static void pui_prefs_application_init(PuiPrefsApplication *self) { /* do nothing, implementation required */ } PuiPrefsApplication * pui_prefs_application_new(void) { return (g_object_new(PUI_TYPE_PREFS_APPLICATION, "application-id", APPLICATION_ID, NULL)); } package-update-indicator-7/deps.sed010064400017500001750000000012451331741420000161550ustar00gbergber/^[^:]\{1,\}:.*\\$/{ h s/\([^:]\{1,\}:\).*/\1/ x s/[^:]\{1,\}:// } /\\$/,/^$/bgen /\\$/,/[^\\]$/{ :gen s/[[:blank:]]*\\$// s/^[[:blank:]]*// G s/\(.*\)\n\(.*\)/\2 \1/ } /^[^:]\{1,\}:[[:blank:]]*$/d /^[^:]\{1,\}\.o:/{ s/[[:blank:]]*[^[:blank:]]\{1,\}\.[cC][[:blank:]]*/ /g s/[[:blank:]]*[^[:blank:]]\{1,\}\.[cC]$//g s/[[:blank:]]*[^[:blank:]]\{1,\}\.cc[[:blank:]]*/ /g s/[[:blank:]]*[^[:blank:]]\{1,\}\.cc$//g s/[[:blank:]]*[^[:blank:]]\{1,\}\.cpp[[:blank:]]*/ /g s/[[:blank:]]*[^[:blank:]]\{1,\}\.cpp$//g /^[^:]\{1,\}:[[:blank:]]*$/d s/^\([^:]\{1,\}\)\.o[[:blank:]]*:[[:blank:]]*\(.*\)/\1.d: $(wildcard \2)\ &/ } package-update-indicator-7/package-update-indicator.c010064400017500001750000000043721331741420000215220ustar00gbergber/* * Copyright (C) 2018 Guido Berhoerster * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files (the * "Software"), to deal in the Software without restriction, including * without limitation the rights to use, copy, modify, merge, publish, * distribute, sublicense, and/or sell copies of the Software, and to * permit persons to whom the Software is furnished to do so, subject to * the following conditions: * * The above copyright notice and this permission notice shall be included * in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ #include #include #include #include #include #include #include "pui-application.h" gboolean restart; int main(int argc, char *argv[]) { int status; gchar *program; PuiApplication *application; /* try to obtain the name of the executable for safe re-execution */ if (argv[0] == NULL) { g_error("unable to locate %s executable", PACKAGE); } if (argv[0][0] != '/') { program = g_find_program_in_path(argv[0]); if (program == NULL) { g_error("unable to locate %s executable", PACKAGE); } argv[0] = program; } bindtextdomain(GETTEXT_PACKAGE, PACKAGE_LOCALE_DIR); setlocale(LC_ALL, ""); bind_textdomain_codeset(GETTEXT_PACKAGE, "UTF-8"); textdomain(GETTEXT_PACKAGE); g_set_application_name(_("Package Update Indicator")); gtk_init(&argc, &argv); application = pui_application_new(); status = g_application_run(G_APPLICATION(application), argc, argv); g_object_unref(application); if (restart) { /* application restart requested */ if (execv(argv[0], argv) == -1) { g_error("exec: %s", g_strerror(errno)); } } exit(status); } package-update-indicator-7/pui-backend.c010064400017500001750000000572461375223147000171000ustar00gbergber/* * Copyright (C) 2018 Guido Berhoerster * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files (the * "Software"), to deal in the Software without restriction, including * without limitation the rights to use, copy, modify, merge, publish, * distribute, sublicense, and/or sell copies of the Software, and to * permit persons to whom the Software is furnished to do so, subject to * the following conditions: * * The above copyright notice and this permission notice shall be included * in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ #include #include #include #include #include #include #include #include #include #include "pui-common.h" #include "pui-backend.h" #include "pui-get-updates.h" #include "pui-types.h" #define LOW_BATTERY_THRESHOLD 10.0 /* % */ #define UPDATES_CHANGED_UNBLOCK_DELAY 4 /* s */ struct _PuiBackend { GObject parent_instance; PkControl *pk_control; GCancellable *cancellable; PkClient *pk_client; PkTransactionList *transaction_list; UpClient *up_client; UpDevice *up_device; gchar *proxy_http; gchar *proxy_https; gchar *proxy_ftp; gchar *proxy_socks; gchar *no_proxy; gchar *pac; gint64 last_check; PkNetworkEnum network_state; gboolean inhibited; gboolean is_battery_low; guint check_id; guint unblock_updates_changed_id; guint refresh_interval; gboolean use_mobile_connection; guint important_updates; guint normal_updates; PuiRestart restart_type; }; static void pui_backend_async_initable_iface_init(gpointer, gpointer); G_DEFINE_TYPE_WITH_CODE(PuiBackend, pui_backend, G_TYPE_OBJECT, G_IMPLEMENT_INTERFACE(G_TYPE_ASYNC_INITABLE, pui_backend_async_initable_iface_init)) enum { STATE_CHANGED, RESTART_REQUIRED, SIGNAL_LAST }; enum { PROP_0, PROP_IMPORTANT_UPDATES, PROP_NORMAL_UPDATES, PROP_RESTART_TYPE, PROP_REFRESH_INTERVAL, PROP_USE_MOBILE_CONNECTION, PROP_LAST }; static guint signals[SIGNAL_LAST] = { 0 }; static GParamSpec *properties[PROP_LAST] = { NULL }; static gboolean periodic_check(gpointer); static void on_updates_changed(PkControl *, gpointer); GQuark pui_backend_error_quark(void) { return (g_quark_from_static_string("pui-backend-error-quark")); } static void process_pk_package(gpointer data, gpointer user_data) { PkPackage *package = data; PuiBackend *self = user_data; PkInfoEnum type_info = pk_package_get_info(package); switch (type_info) { case PK_INFO_ENUM_LOW: /* FALLTHROUGH */ case PK_INFO_ENUM_ENHANCEMENT: /* FALLTHROUGH */ case PK_INFO_ENUM_NORMAL: self->normal_updates++; break; case PK_INFO_ENUM_BUGFIX: /* FALLTHROUGH */ case PK_INFO_ENUM_IMPORTANT: /* FALLTHROUGH */ case PK_INFO_ENUM_SECURITY: self->important_updates++; break; default: break; } } static gboolean unblock_updates_changed(gpointer user_data) { PuiBackend *self = user_data; g_signal_handlers_unblock_by_func(self->pk_control, on_updates_changed, self); self->unblock_updates_changed_id = 0; return (G_SOURCE_REMOVE); } static void on_get_updates_finished(GObject *source_object, GAsyncResult *async_result, gpointer user_data) { PuiBackend *self = user_data; GPtrArray *package_list = NULL; GError *error = NULL; guint prev_normal_updates = self->normal_updates; guint prev_important_updates = self->important_updates; package_list = pui_get_updates_finish(async_result, &error); if (package_list == NULL) { if (g_error_matches(error, G_IO_ERROR, G_IO_ERROR_CANCELLED) || g_error_matches(error, PUI_GET_UPDATES_ERROR, PUI_GET_UPDATES_ERROR_CANCELLED)) { /* cancelled */ g_debug("cancelled checking for updates"); } else { g_warning("failed to check for updates: %s", error->message); } g_error_free(error); goto out; } self->normal_updates = 0; self->important_updates = 0; g_ptr_array_foreach(package_list, process_pk_package, self); g_debug("normal updates: %u, important updates: %u", self->normal_updates, self->important_updates); if (self->normal_updates != prev_normal_updates) { g_object_notify_by_pspec(G_OBJECT(self), properties[PROP_NORMAL_UPDATES]); } if (self->important_updates != prev_important_updates) { g_object_notify_by_pspec(G_OBJECT(self), properties[PROP_IMPORTANT_UPDATES]); } if ((self->normal_updates != prev_normal_updates) || (self->important_updates != prev_important_updates)) { g_debug("emitting signal state-changed"); g_signal_emit(self, signals[STATE_CHANGED], 0); } /* last successful check */ self->last_check = g_get_monotonic_time(); out: g_clear_object(&self->cancellable); /* reschedule periodic check */ if (!self->inhibited) { self->check_id = g_timeout_add_seconds(PUI_CHECK_UPDATES_INTERVAL, periodic_check, self); } /* handle get-updates signals again after a short delay */ self->unblock_updates_changed_id = g_timeout_add_seconds(UPDATES_CHANGED_UNBLOCK_DELAY, unblock_updates_changed, self); if (package_list != NULL) { g_ptr_array_unref(package_list); } } static void run_check(PuiBackend *self, gboolean refresh_cache) { /* block any get-updates signals emitted when refreshing the cache */ if (self->unblock_updates_changed_id != 0) { /* still blocked */ g_source_remove(self->unblock_updates_changed_id); self->unblock_updates_changed_id = 0; } else { g_signal_handlers_block_by_func(self->pk_control, G_CALLBACK(on_updates_changed), self); } self->cancellable = g_cancellable_new(); pui_get_updates_async(self->pk_control, refresh_cache ? self->refresh_interval : G_MAXUINT, self->cancellable, on_get_updates_finished, self); /* next periodic check will be scheduled after completion */ self->check_id = 0; } static gboolean irregular_check(gpointer user_data) { PuiBackend *self = user_data; g_debug("running check"); run_check(self, FALSE); return (G_SOURCE_REMOVE); } static gboolean periodic_check(gpointer user_data) { PuiBackend *self = user_data; g_debug("running periodic check"); run_check(self, TRUE); return (G_SOURCE_REMOVE); } static void check_inhibit(PuiBackend *self) { gboolean is_offline; gboolean is_disallowed_mobile; gboolean inhibited; guint elapsed_time; guint remaining_time; is_offline = self->network_state == PK_NETWORK_ENUM_OFFLINE; is_disallowed_mobile = !self->use_mobile_connection && (self->network_state == PK_NETWORK_ENUM_MOBILE); inhibited = is_offline || is_disallowed_mobile || self->is_battery_low; if (self->inhibited == inhibited) { return; } self->inhibited = inhibited; if (inhibited) { /* cancel periodic checks */ if (self->check_id != 0) { g_source_remove(self->check_id); } /* cancel running operation */ if ((self->cancellable != NULL) && !g_cancellable_is_cancelled(self->cancellable)) { g_cancellable_cancel(self->cancellable); g_clear_object(&self->cancellable); } if (is_offline) { g_debug("perioidic checks inhibited: network offline"); } if (is_disallowed_mobile) { g_debug("perioidic checks inhibited: use of mobile " "connection not allowed"); } if (self->is_battery_low) { g_debug("perioidic checks inhibited: low battery"); } } else { if (self->last_check == 0) { /* first check after startup */ remaining_time = PUI_STARTUP_DELAY; g_debug("scheduled first check in: %ds", remaining_time); } else { /* schedule periodic checks when no longer inhibited */ elapsed_time = (g_get_monotonic_time() - self->last_check) / G_USEC_PER_SEC; /* * if more time than the check interval has passed * since the last check, schedule a check after a short * delay, otherwise wait until the interval has passed */ remaining_time = (elapsed_time < PUI_CHECK_UPDATES_INTERVAL) ? PUI_CHECK_UPDATES_INTERVAL - elapsed_time : PUI_STARTUP_DELAY; g_debug("perioidic checks no longer inhibited, " "time since last check: %ds, next check in: %ds", elapsed_time, remaining_time); } self->check_id = g_timeout_add_seconds(remaining_time, periodic_check, self); } } static void pui_backend_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { PuiBackend *self = PUI_BACKEND(object); switch (property_id) { case PROP_REFRESH_INTERVAL: self->refresh_interval = g_value_get_uint(value); g_debug("property \"refresh-interval\" set to %u", self->refresh_interval); break; case PROP_USE_MOBILE_CONNECTION: self->use_mobile_connection = g_value_get_boolean(value); g_debug("property \"use-mobile-connection\" set to %s", self->use_mobile_connection ? "true" : "false"); check_inhibit(self); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void pui_backend_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { PuiBackend *self = PUI_BACKEND(object); switch (property_id) { case PROP_IMPORTANT_UPDATES: g_value_set_uint(value, self->important_updates); break; case PROP_NORMAL_UPDATES: g_value_set_uint(value, self->normal_updates); break; case PROP_RESTART_TYPE: g_value_set_enum(value, self->restart_type); break; case PROP_REFRESH_INTERVAL: g_value_set_uint(value, self->refresh_interval); break; case PROP_USE_MOBILE_CONNECTION: g_value_set_boolean(value, self->use_mobile_connection); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void pui_backend_dispose(GObject *object) { PuiBackend *self = PUI_BACKEND(object); if (self->check_id != 0) { g_source_remove(self->check_id); self->check_id = 0; } if (self->unblock_updates_changed_id != 0) { g_source_remove(self->unblock_updates_changed_id); self->unblock_updates_changed_id = 0; } if (self->transaction_list != NULL) { g_clear_object(&self->transaction_list); } if (self->pk_client != NULL) { g_clear_object(&self->pk_client); } if (self->cancellable != NULL) { g_cancellable_cancel(self->cancellable); g_clear_object(&self->cancellable); } if (self->pk_control != NULL) { g_clear_object(&self->pk_control); } if (self->up_device != NULL) { g_clear_object(&self->up_device); } if (self->up_client != NULL) { g_clear_object(&self->up_client); } G_OBJECT_CLASS(pui_backend_parent_class)->dispose(object); } static void pui_backend_finalize(GObject *object) { PuiBackend *self = PUI_BACKEND(object); g_free(self->proxy_http); g_free(self->proxy_https); g_free(self->proxy_ftp); g_free(self->proxy_socks); g_free(self->no_proxy); g_free(self->pac); G_OBJECT_CLASS(pui_backend_parent_class)->finalize(object); } static void pui_backend_class_init(PuiBackendClass *klass) { GObjectClass *object_class = G_OBJECT_CLASS(klass); object_class->set_property = pui_backend_set_property; object_class->get_property = pui_backend_get_property; object_class->dispose = pui_backend_dispose; object_class->finalize = pui_backend_finalize; properties[PROP_IMPORTANT_UPDATES] = g_param_spec_uint("important-updates", "Important updates", "Number of available important updates", 0, G_MAXUINT, 0, G_PARAM_READABLE); properties[PROP_NORMAL_UPDATES] = g_param_spec_uint("normal-updates", "Normal updates", "Number of available normal updates", 0, G_MAXUINT, 0, G_PARAM_READABLE); properties[PROP_RESTART_TYPE] = g_param_spec_enum("restart-type", "Type of restart required", "The Type of restart required", PUI_TYPE_RESTART, PUI_RESTART_NONE, G_PARAM_READABLE); properties[PROP_REFRESH_INTERVAL] = g_param_spec_uint("refresh-interval", "Refresh interval", "Interval in seconds for refreshing the package cache", 0, G_MAXUINT, PUI_DEFAULT_REFRESH_INTERVAL, G_PARAM_READWRITE); properties[PROP_USE_MOBILE_CONNECTION] = g_param_spec_boolean("use-mobile-connection", "Whether to use a mobile connection", "Whether to use a mobile " "connection for refreshing the package cache", FALSE, G_PARAM_READWRITE); g_object_class_install_properties(object_class, PROP_LAST, properties); signals[STATE_CHANGED] = g_signal_new("state-changed", G_TYPE_FROM_CLASS(object_class), G_SIGNAL_RUN_LAST | G_SIGNAL_NO_RECURSE | G_SIGNAL_NO_HOOKS, 0, NULL, NULL, NULL, G_TYPE_NONE, 0); signals[RESTART_REQUIRED] = g_signal_new("restart-required", G_TYPE_FROM_CLASS(object_class), G_SIGNAL_RUN_LAST | G_SIGNAL_NO_RECURSE | G_SIGNAL_NO_HOOKS, 0, NULL, NULL, NULL, G_TYPE_NONE, 0); } static void pui_backend_init(PuiBackend *self) { self->pk_control = pk_control_new(); self->pk_client = pk_client_new(); self->inhibited = TRUE; self->up_client = up_client_new(); if (self->up_client) { self->up_device = up_client_get_display_device(self->up_client); } } static void on_get_properties_finished(GObject *object, GAsyncResult *result, gpointer user_data) { PkControl *control = PK_CONTROL(object); PuiBackend *self; GTask *task = user_data; GError *error = NULL; gchar *backend_name = NULL; PkBitfield roles = 0; gchar *roles_str = NULL; self = g_task_get_task_data(task); if (!pk_control_get_properties_finish(control, result, &error)) { g_task_return_error(task, error); goto out; } /* check whether the backend supports GetUpdates */ g_object_get(control, "backend-name", &backend_name, "roles", &roles, "network-state", &self->network_state, NULL); g_debug("backend: %s", backend_name); roles_str = pk_role_bitfield_to_string(roles); g_debug("roles: %s", roles_str); g_debug("network-state: %s", pk_network_enum_to_string(self->network_state)); if (!pk_bitfield_contain(roles, PK_ROLE_ENUM_GET_UPDATES)) { error = g_error_new(PUI_BACKEND_ERROR, PUI_BACKEND_ERROR_GET_UPDATES_NOT_IMPLEMENTED, "Getting updates is not implemented in the %s PackageKit " "backend", backend_name); g_task_return_error(task, error); goto out; } g_task_return_boolean(task, TRUE); out: g_free(roles_str); g_free(backend_name); g_object_unref(task); } static void on_notify_device_charge_percentage(UpDevice *device, GParamSpec *pspec, gpointer user_data) { PuiBackend *self = user_data; UpDeviceKind kind; gdouble percentage; g_object_get(device, "kind", &kind, "percentage", &percentage, NULL); if ((kind != UP_DEVICE_KIND_BATTERY) && (kind != UP_DEVICE_KIND_UPS)) { return; } g_debug("charge percentage changed: %.0f%%\n", percentage); if ((self->is_battery_low && (percentage > LOW_BATTERY_THRESHOLD)) || (!self->is_battery_low && (percentage < LOW_BATTERY_THRESHOLD))) { self->is_battery_low = !self->is_battery_low; check_inhibit(self); } } static void on_notify_network_state(PkControl *pk_control, GParamSpec *pspec, gpointer user_data) { PuiBackend *self = user_data; g_object_get(pk_control, "network-state", &self->network_state, NULL); g_debug("network state changed: %s", pk_network_enum_to_string(self->network_state)); check_inhibit(self); } static void on_updates_changed(PkControl *control, gpointer user_data) { PuiBackend *self = user_data; g_debug("package metatdata cache invalidated"); /* * schedule a check after a short delay so that a rapid succession of * signals is coalesced */ if (!self->inhibited) { if (self->check_id != 0) { g_source_remove(self->check_id); } self->check_id = g_timeout_add_seconds(PUI_UPDATES_CHANGED_DELAY, irregular_check, self); } } static void on_restart_schedule(PkControl *control, gpointer user_data) { PuiBackend *self = user_data; /* * do not restart package-update-indicator if a session or system * restart is required since that iformation would be lost across the * restart, rather keep running and risk errors when interacting with * a newer version of the PackageKit daemon */ if (self->restart_type > PUI_RESTART_NONE) { return; } g_debug("emitting signal restart-required"); g_signal_emit(self, signals[RESTART_REQUIRED], 0); } static void on_transaction_adopt_finish(GObject *source_object, GAsyncResult *result, gpointer user_data) { PuiBackend *self = user_data; PkClient *pk_client = PK_CLIENT(source_object); PkResults *results; GError *error = NULL; PkRestartEnum restart; results = pk_client_generic_finish(pk_client, result, &error); if (results == NULL) { g_warning("failed to get transaction results: %s", error->message); g_error_free(error); goto out; } /* check if transaction requires a restart */ restart = pk_results_get_require_restart_worst(results); switch (restart) { case PK_RESTART_ENUM_SESSION: /* FALLTHROUGH */ case PK_RESTART_ENUM_SECURITY_SESSION: if (self->restart_type < PUI_RESTART_SESSION) { self->restart_type = PUI_RESTART_SESSION; g_object_notify_by_pspec(G_OBJECT(self), properties[PROP_RESTART_TYPE]); g_signal_emit(self, signals[STATE_CHANGED], 0); } break; case PK_RESTART_ENUM_SYSTEM: /* FALLTHROUGH */ case PK_RESTART_ENUM_SECURITY_SYSTEM: if (self->restart_type < PUI_RESTART_SYSTEM) { self->restart_type = PUI_RESTART_SYSTEM; g_object_notify_by_pspec(G_OBJECT(self), properties[PROP_RESTART_TYPE]); g_signal_emit(self, signals[STATE_CHANGED], 0); } break; default: /* do nothing */ break; } g_debug("transaction finished, required restart: %s", pk_restart_enum_to_string(restart)); out: if (results != NULL) { g_object_unref(results); } } static void on_transaction_list_added(PkTransactionList *transaction_list, const gchar *transaction_id, gpointer user_data) { PuiBackend *self = user_data; /* adopt transaction in order to monitor it for restart requirements */ pk_client_adopt_async(self->pk_client, transaction_id, NULL, NULL, NULL, on_transaction_adopt_finish, user_data); } static void pui_backend_init_async(GAsyncInitable *initable, int io_priority, GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data) { PuiBackend *self = PUI_BACKEND(initable); GTask *task; task = g_task_new(G_OBJECT(initable), cancellable, callback, user_data); g_task_set_priority(task, io_priority); g_task_set_task_data(task, g_object_ref(self), (GDestroyNotify)g_object_unref); pk_control_get_properties_async(self->pk_control, cancellable, on_get_properties_finished, task); } static gboolean pui_backend_init_finish(GAsyncInitable *initable, GAsyncResult *result, GError **errorp) { PuiBackend *self = PUI_BACKEND(initable); GTask *task = G_TASK(result); UpDeviceKind kind; gdouble percentage; if (!g_task_propagate_boolean(task, errorp)) { return (FALSE); } if (self->up_device != NULL) { /* get the kind of device and charge percentage */ g_object_get(self->up_device, "kind", &kind, "percentage", &percentage, NULL); if ((kind == UP_DEVICE_KIND_BATTERY) || (kind == UP_DEVICE_KIND_UPS)) { self->is_battery_low = (percentage < LOW_BATTERY_THRESHOLD); } /* get notification if the charge percentage changes */ g_signal_connect(self->up_device, "notify::percentage", G_CALLBACK(on_notify_device_charge_percentage), self); } /* get notification when the network state changes */ g_signal_connect(self->pk_control, "notify::network-state", G_CALLBACK(on_notify_network_state), self); /* get notifications when the package metatdata cache is invalidated */ g_signal_connect(self->pk_control, "updates-changed", G_CALLBACK(on_updates_changed), self); /* get notifications when an application restart is required */ g_signal_connect(self->pk_control, "restart-schedule", G_CALLBACK(on_restart_schedule), self); /* get notifications when a transactions are added */ self->transaction_list = pk_transaction_list_new(); g_signal_connect(self->transaction_list, "added", G_CALLBACK(on_transaction_list_added), self); check_inhibit(self); return (TRUE); } static void pui_backend_async_initable_iface_init(gpointer g_iface, gpointer iface_data) { GAsyncInitableIface *iface = g_iface; iface->init_async = pui_backend_init_async; iface->init_finish = pui_backend_init_finish; } void pui_backend_new_async(GCancellable *cancellable, GAsyncReadyCallback callback, gpointer user_data) { g_async_initable_new_async(PUI_TYPE_BACKEND, G_PRIORITY_DEFAULT, cancellable, callback, user_data, NULL); } PuiBackend * pui_backend_new_finish(GAsyncResult *result, GError **errorp) { GObject *object; GObject *source_object; source_object = g_async_result_get_source_object(result); object = g_async_initable_new_finish(G_ASYNC_INITABLE(source_object), result, errorp); g_object_unref(source_object); return ((object != NULL) ? PUI_BACKEND(object) : NULL); } static void on_set_proxy_finished(GObject *source_object, GAsyncResult *result, gpointer user_data) { PuiBackend *self = user_data; GError *error = NULL; if (!pk_control_set_proxy_finish(self->pk_control, result, &error)) { g_warning("failed to set proxies: %s", error->message); g_error_free(error); } } static void on_polkit_permission_finished(GObject *source_object, GAsyncResult *result, gpointer user_data) { PuiBackend *self = user_data; GPermission *permission; GError *error = NULL; permission = polkit_permission_new_finish(result, &error); if (permission == NULL) { g_warning("failed to create PolKit permission for setting the " "network proxies: %s", error->message); g_error_free(error); return; } if (!g_permission_get_allowed(permission)) { /* setting the proxy requires authentication or is disallowed */ g_debug("setting the network proxy is not allowed"); return; } g_debug("setting HTTP proxy to \"%s\"", (self->proxy_http != NULL) ? self->proxy_http : "(null)"); g_debug("setting HTTPS proxy to \"%s\"", (self->proxy_https != NULL) ? self->proxy_https : "(null)"); g_debug("setting FTP proxy to \"%s\"", (self->proxy_ftp != NULL) ? self->proxy_ftp : "(null)"); g_debug("setting SOCKS proxy to \"%s\"", (self->proxy_socks != NULL) ? self->proxy_socks : "(null)"); g_debug("setting the list of download IPs which should not go through " "a proxy to \"%s\"", (self->no_proxy != NULL) ? self->no_proxy : "(null)"); g_debug("setting the PAC string to \"%s\"", (self->pac != NULL) ? self->pac : "(null)"); pk_control_set_proxy2_async(self->pk_control, self->proxy_http, self->proxy_https, self->proxy_ftp, self->proxy_socks, self->no_proxy, self->pac, NULL, on_set_proxy_finished, self); } void pui_backend_set_proxy(PuiBackend *self, const gchar *proxy_http, const gchar *proxy_https, const gchar *proxy_ftp, const gchar *proxy_socks, const gchar *no_proxy, const gchar *pac) { g_free(self->proxy_http); self->proxy_http = (proxy_http != NULL) ? g_strdup(proxy_http) : NULL; g_free(self->proxy_https); self->proxy_https = (proxy_https != NULL) ? g_strdup(proxy_https) : NULL; g_free(self->proxy_ftp); self->proxy_ftp = (proxy_ftp != NULL) ? g_strdup(proxy_ftp) : NULL; g_free(self->proxy_socks); self->proxy_socks = (proxy_socks != NULL) ? g_strdup(proxy_socks) : NULL; g_free(self->no_proxy); self->no_proxy = (no_proxy != NULL) ? g_strdup(no_proxy) : NULL; g_free(self->pac); self->pac = (pac != NULL) ? g_strdup(pac) : NULL; polkit_permission_new("org.freedesktop.packagekit." "system-network-proxy-configure", NULL, NULL, on_polkit_permission_finished, self); } package-update-indicator-7/package-update-indicator.1.xml010064400017500001750000000130531331741427600222500ustar00gbergber Guido Berhoerster guido+pui@berhoerster.name 19 June, 2018 package-update-indicator 1 User Commands package-update-indicator notify about available software updates package-update-indicator Description The package-update-indicator utility regularly checks for software updates and notifies the user about available updates using desktop notifications and either a status notifier icon or a system tray icon. Protocol-specific proxies specified through the corresponding environment variables will be used by PackagKit when refreshing metadata if the user is allowed to use the polkit action org.freedesktop.packagekit.system-network-proxy-configure without authentication. Options The following options are supported: Quit the running instance of package-update-indicator. Print the version number and exit. Environment Variables http_proxy Network proxy using the HTTP protcol. https_proxy Network proxy using the HTTPS protcol. ftp_proxy Network proxy using the FTP protcol. socks_proxy Network proxy using the SOCKS protcol. no_proxy Comma-separated list of host for which no proxy should be used. Exit Status The following exit values are returned: 0 Command successfully executed. 1 An unspecified error has occured. 2 Invalid command line options were specified. See Also package-update-indicator-prefs 1, polkit 8 org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in010064400017500001750000000005271340270273700327360ustar00gbergberpackage-update-indicator-7[Desktop Entry] Name=Package Update Indicator Preferences GenericName=Package Update Indicator Preferences Comment=Edit the Preferences for Package Update Indicator Keywords=updates;preferences; Icon=preferences-other Exec=package-update-indicator-prefs Terminal=false Type=Application Categories=Settings;PackageManager;GTK; NotShowIn=GNOME; package-update-indicator-7/pui-prefs.gresource.xml010064400017500001750000000003401331741424000211550ustar00gbergber pui-prefs-window.ui package-update-indicator-7/pui.gresource.xml010064400017500001750000000004031331741424000200400ustar00gbergber pui-menu.ui pui-about-dialog.ui package-update-indicator-7/pui-settings.c010064400017500001750000000033711331741424000173320ustar00gbergber/* * Copyright (C) 2018 Guido Berhoerster * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files (the * "Software"), to deal in the Software without restriction, including * without limitation the rights to use, copy, modify, merge, publish, * distribute, sublicense, and/or sell copies of the Software, and to * permit persons to whom the Software is furnished to do so, subject to * the following conditions: * * The above copyright notice and this permission notice shall be included * in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ #define G_SETTINGS_ENABLE_BACKEND #include #include "pui-settings.h" #define SETTINGS_ROOT_PATH \ "/org/guido-berhoerster/code/package-update-indicator/" #define SETTINGS_ROOT_GROUP "General" GSettings * pui_settings_new(void) { gchar *settings_filename; GSettingsBackend *settings_backend; settings_filename = g_build_filename(g_get_user_config_dir(), PACKAGE, PACKAGE ".conf", NULL); settings_backend = g_keyfile_settings_backend_new(settings_filename, SETTINGS_ROOT_PATH, SETTINGS_ROOT_GROUP); return (g_settings_new_with_backend(SETTINGS_SCHEMA_ID, settings_backend)); } package-update-indicator-7/Makefile010064400017500001750000000220651375473113300162040ustar00gbergber# # Copyright (C) 2018 Guido Berhoerster # # Permission is hereby granted, free of charge, to any person obtaining # a copy of this software and associated documentation files (the # "Software"), to deal in the Software without restriction, including # without limitation the rights to use, copy, modify, merge, publish, # distribute, sublicense, and/or sell copies of the Software, and to # permit persons to whom the Software is furnished to do so, subject to # the following conditions: # # The above copyright notice and this permission notice shall be included # in all copies or substantial portions of the Software. # # THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, # EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF # MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. # IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY # CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, # TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE # SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. # PACKAGE = package-update-indicator APPLICATION_ID = org.guido-berhoerster.code.package-update-indicator PREFS_APPLICATION_ID = org.guido-berhoerster.code.package-update-indicator.preferences VERSION = 7 DISTNAME = $(PACKAGE)-$(VERSION) AUTHOR = Guido Berhoerster BUG_ADDRESS = guido+pui@berhoerster.name # gcc, clang, icc, Sun/Solaris Studio CC := $(CC) -std=c99 COMPILE.c = $(CC) $(CFLAGS) $(XCFLAGS) $(CPPFLAGS) $(XCPPFLAGS) $(TARGET_ARCH) -c # gcc, clang, icc MAKEDEPEND.c = $(CC) -MM $(CFLAGS) $(XCFLAGS) $(CPPFLAGS) $(XCPPFLAGS) # Sun/Solaris Studio #MAKEDEPEND.c = $(CC) -xM1 $(CFLAGS) $(XCFLAGS) $(CPPFLAGS) $(XCPPFLAGS) # X makedepend #MAKEDEPEND.c = makedepend -f- -Y -- $(CFLAGS) $(XCFLAGS) $(CPPFLAGS) $(XCPPFLAGS) -- LINK.c = $(CC) $(CFLAGS) $(XCFLAGS) $(CPPFLAGS) $(XCPPFLAGS) $(LDFLAGS) $(XLDFLAGS) $(TARGET_ARCH) LINK.o = $(CC) $(LDFLAGS) $(XLDFLAGS) $(TARGET_ARCH) CP := cp INSTALL := install INSTALL.exec := $(INSTALL) -D -m 0755 INSTALL.data := $(INSTALL) -D -m 0644 INSTALL.link := $(CP) -f -P PAX := pax GZIP := gzip SED := sed GLIB_COMPILE_SCHEMAS := $(shell pkg-config --variable=glib_compile_schemas gio-2.0) GLIB_COMPILE_RESOURCES := $(shell pkg-config --variable=glib_compile_resources gio-2.0) GLIB_MKENUMS := $(shell pkg-config --variable=glib_mkenums glib-2.0) XSLTPROC := xsltproc DOCBOOK5_MANPAGES_STYLESHEET = http://docbook.sourceforge.net/release/xsl-ns/current/manpages/docbook.xsl DOCBOOK5_MANPAGES_FLAGS = --stringparam man.authors.section.enabled 0 \ --stringparam man.copyright.section.enabled 0 MSGFMT = msgfmt MSGMERGE = msgmerge XGETTEXT = xgettext XGETTEXT_OPTIONS = --copyright-holder "$(AUTHOR)" \ --package-name '$(PACKAGE)' \ --package-version '$(VERSION)' \ --msgid-bugs-address '$(BUG_ADDRESS)' \ --default-domain '$(PACKAGE)' \ --from-code UTF-8 \ --keyword=_ \ --keyword=N_ \ --keyword=C_:1c,2 \ --keyword=NC_:1c,2 \ --keyword=g_dngettext:2,3 \ --add-comments INDICATOR_LIB := $(or \ $(shell pkg-config --exists appindicator3-0.1 && \ printf '%s\\\n' appindicator3-0.1), \ $(shell pkg-config --exists ayatana-appindicator3-0.1 && \ printf '%s\\\n' ayatana-appindicator3-0.1), \ appindicator3-0.1) INDICATOR_FLAG := $(if $(findstring ayatana,$(INDICATOR_LIB)), \ -DHAVE_AYATANA_APPINDICATOR,) define generate-manpage-rule = %.$1: %.$(addsuffix .xml,$1) docbook-update-source-data.xsl $$(XSLTPROC) \ --xinclude \ --stringparam package $$(PACKAGE) \ --stringparam version $$(VERSION) \ docbook-update-source-data.xsl $$< | \ $$(XSLTPROC) \ --xinclude \ --output $$@ \ $$(DOCBOOK5_MANPAGES_FLAGS) \ $$(DOCBOOK5_MANPAGES_STYLESHEET) \ - endef DESTDIR ?= prefix ?= /usr/local bindir ?= $(prefix)/bin datadir ?= $(prefix)/share mandir ?= $(datadir)/man localedir ?= $(datadir)/locale sysconfdir ?= /etc xdgautostartdir ?= $(sysconfdir)/xdg/autostart xdgapplicationsdir ?= $(datadir)/applications OS_NAME := $(shell uname -s) OS_RELEASE := $(shell uname -r) $(PACKAGE)_OBJS = package-update-indicator.o \ pui-application.o \ pui-backend.o \ pui-get-updates.o \ pui-settings.o \ pui-types.o \ pui-resources.o $(PACKAGE)-prefs_OBJS = package-update-indicator-prefs.o \ pui-prefs-application.o \ pui-settings.o \ pui-prefs-resources.o OBJS = $($(PACKAGE)_OBJS) $($(PACKAGE)-prefs_OBJS) ENUM_DEPS = pui-backend.h \ pui-application.h ENUM_HEADER = pui-types.h ENUM_FILES = $(ENUM_HEADER) \ pui-types.c GSETTINGS_SCHEMAS = $(APPLICATION_ID).gschema.xml GRESOURCE_FILES = pui-prefs.gresource.xml AUTOSTART_FILE = $(APPLICATION_ID).desktop DESKTOP_FILES = $(PREFS_APPLICATION_ID).desktop LINGUAS := $(shell sed 's/\#.*//' po/LINGUAS) MOFILES := $(patsubst %,po/%.mo,$(LINGUAS)) POTFILES_IN := $(shell sed 's/\#.*//' po/POTFILES.in) POTFILE = po/$(PACKAGE).pot MANPAGES = $(PACKAGE).1 $(PACKAGE)-prefs.1 .DEFAULT_TARGET = all .PHONY: all pot update-po clean clobber dist install all: $(PACKAGE) $(PACKAGE)-prefs $(AUTOSTART_FILE) $(DESKTOP_FILES) $(MOFILES) $(MANPAGES) $(PACKAGE): XCPPFLAGS = -DPACKAGE=\"$(PACKAGE)\" \ -DAPPLICATION_ID=\"$(APPLICATION_ID)\" \ -DVERSION=\"$(VERSION)\" \ -DG_LOG_DOMAIN=\"$(PACKAGE)\" \ -DPACKAGE_LOCALE_DIR="\"$(localedir)\"" \ -DGETTEXT_PACKAGE=\"$(PACKAGE)\" \ -DSETTINGS_SCHEMA_ID=\"$(APPLICATION_ID)\" \ -DI_KNOW_THE_PACKAGEKIT_GLIB2_API_IS_SUBJECT_TO_CHANGE \ $(INDICATOR_FLAG) $(PACKAGE): XCFLAGS = $(shell pkg-config --cflags gtk+-3.0 \ $(INDICATOR_LIB) packagekit-glib2 \ polkit-gobject-1 upower-glib) $(PACKAGE): LDLIBS = $(shell pkg-config --libs gtk+-3.0 \ $(INDICATOR_LIB) packagekit-glib2 \ polkit-gobject-1 upower-glib) $(PACKAGE)-prefs: XCPPFLAGS = -DPACKAGE=\"$(PACKAGE)\" \ -DAPPLICATION_ID=\"$(PREFS_APPLICATION_ID)\" \ -DVERSION=\"$(VERSION)\" \ -DG_LOG_DOMAIN=\"$(PACKAGE)\" \ -DPACKAGE_LOCALE_DIR="\"$(localedir)\"" \ -DGETTEXT_PACKAGE=\"$(PACKAGE)\" \ -DSETTINGS_SCHEMA_ID=\"$(APPLICATION_ID)\" $(PACKAGE)-prefs: XCFLAGS = $(shell pkg-config --cflags gtk+-3.0) $(PACKAGE)-prefs: LDLIBS = $(shell pkg-config --libs gtk+-3.0) ifneq ($(findstring $(OS_NAME),FreeBSD DragonFly OpenBSD),) $(PACKAGE): XCPPFLAGS += -I/usr/local/include $(PACKAGE): XLDFLAGS += -L/usr/local/lib else ifeq ($(OS_NAME),NetBSD) $(PACKAGE): XCPPFLAGS += -I/usr/pkg/include $(PACKAGE): XLDFLAGS += -L/usr/pkg/lib endif ifeq ($(findstring $(OS_NAME),FreeBSD DragonFly NetBSD OpenBSD),) $(PACKAGE): XCPPFLAGS += -D_XOPEN_SOURCE=600 endif $(PACKAGE): $($(PACKAGE)_OBJS) $(LINK.o) $^ $(LDLIBS) -o $@ $(PACKAGE)-prefs: $($(PACKAGE)-prefs_OBJS) $(LINK.o) $^ $(LDLIBS) -o $@ $(OBJS): $(ENUM_HEADER) %-types.h: %-types.h.in $(ENUM_DEPS) $(GLIB_MKENUMS) --template $< >$@ $(filter-out $<,$^) %-types.c: %-types.c.in $(ENUM_DEPS) $(GLIB_MKENUMS) --template $< >$@ $(filter-out $<,$^) %-resources.c: %.gresource.xml $(GLIB_COMPILE_RESOURCES) --generate-dependencies $< | \ while read -r resource_file; do \ printf '%s: %s\n' $@ "$${resource_file}"; \ done $(GLIB_COMPILE_RESOURCES) --target=$@ --sourcedir=. --generate-source $< $(POTFILE): po/POTFILES.in $(POTFILES_IN) $(XGETTEXT) $(XGETTEXT_OPTIONS) --files-from $< --output $@ pot: $(POTFILE) update-po: $(POTFILE) for pofile in $(patsubst %.mo,%.po,$(MOFILES)); do \ $(MSGMERGE) --update --backup off $$pofile $<; \ done %.mo: %.po $(MSGFMT) --output $@ $< %.desktop: %.desktop.in $(MSGFMT) --desktop --keyword 'Keywords' --template $< -d po --output $@ $(foreach section,1 2 3 4 5 6 7 8 9,$(eval $(call generate-manpage-rule,$(section)))) %.o: %.c $(MAKEDEPEND.c) $< | $(SED) -f deps.sed >$*.d $(COMPILE.c) -o $@ $< install: all $(INSTALL.exec) $(PACKAGE) "$(DESTDIR)$(bindir)/$(PACKAGE)" $(INSTALL.exec) $(PACKAGE)-prefs \ "$(DESTDIR)$(bindir)/$(PACKAGE)-prefs" for schema in $(GSETTINGS_SCHEMAS); do \ $(INSTALL.data) $${schema} \ $(DESTDIR)$(datadir)/glib-2.0/schemas/$${schema}; \ done if [ -n "$(GSETTINGS_SCHEMAS)" ] && [ -z "$(DESTDIR)" ]; then \ $(GLIB_COMPILE_SCHEMAS) $(datadir)/glib-2.0/schemas; \ fi $(INSTALL.data) $(AUTOSTART_FILE) \ $(DESTDIR)$(xdgautostartdir)/$(AUTOSTART_FILE) for desktop_file in $(DESKTOP_FILES); do \ $(INSTALL.data) $${desktop_file} \ $(DESTDIR)$(xdgapplicationsdir)/$${desktop_file}; \ done for lang in $(LINGUAS); do \ $(INSTALL.data) po/$${lang}.mo \ $(DESTDIR)$(localedir)/$${lang}/LC_MESSAGES/$(PACKAGE).mo; \ done for manpage in $(MANPAGES); do \ $(INSTALL.data) $${manpage} \ "$(DESTDIR)$(mandir)/man$${manpage##*.}/$${manpage##*/}"; \ done clean: rm -f $(PACKAGE) $(OBJS) $(ENUM_FILES) $(AUTOSTART_FILE) \ $(DESKTOP_FILES) $(POTFILE) $(MOFILES) $(MANPAGES) clobber: clean rm -f $(patsubst %.o,%.d,$(OBJS)) dist: clobber $(PAX) -w -x ustar -s ',.*/\..*,,' -s ',./[^/]*\.tar\.gz,,' \ -s ',^\.$$,,' -s ',\./,$(DISTNAME)/,' . | \ $(GZIP) > $(DISTNAME).tar.gz -include local.mk -include $(patsubst %.o,%.d,$(OBJS)) -include $(patsubst %.gresource.xml,%.gresource.d,$(GRESOURCE_FILES)) package-update-indicator-7/pui-about-dialog.ui010064400017500001750000000035711331741424000202360ustar00gbergber False About Package Update Indicator system-software-update dialog Package Update Indicator Copyright © 2018 Guido Berhörster Notify about available software updates http://code.guido-berhoerster.org/projects/package-update-indicator/ Guido Berhörster Translator system-software-update True mit-x11 False vertical 2 False end False False 0 package-update-indicator-7/pui-menu.ui010064400017500001750000000025631331741424000166330ustar00gbergber True False True False app.install-updates _Install updates True True False app.preferences _Preferences… True True False app.about _About… True package-update-indicator-7/package-update-indicator-prefs.1.xml010064400017500001750000000073051331741424000233570ustar00gbergber Guido Berhoerster guido+pui@berhoerster.name 17 June, 2018 package-update-indicator-prefs 1 User Commands package-update-indicator-prefs edit preferences for package-update-indicator package-update-indicator-prefs Description The package-update-indicator-prefs utility can be used to edit the preferences for package-update-indicator. Preferences Cache refresh interval The interval in which package metadata is refreshed. Update installer command The command for installing updates. Use mobile connection Whether to use a mobile connection for refreshing the package cache. Exit Status The following exit values are returned: 0 Command successfully executed. 1 An unspecified error has occured. 2 Invalid command line options were specified. See Also package-update-indicator 1 package-update-indicator-7/pui-application.c010064400017500001750000000515031353444374200200070ustar00gbergber/* * Copyright (C) 2018 Guido Berhoerster * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files (the * "Software"), to deal in the Software without restriction, including * without limitation the rights to use, copy, modify, merge, publish, * distribute, sublicense, and/or sell copies of the Software, and to * permit persons to whom the Software is furnished to do so, subject to * the following conditions: * * The above copyright notice and this permission notice shall be included * in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ #include #include #ifndef HAVE_AYATANA_APPINDICATOR #include #else /* !HAVE_AYATANA_APPINDICATOR */ #include #endif /* !HAVE_AYATANA_APPINDICATOR */ #include #include #include "pui-application.h" #include "pui-backend.h" #include "pui-common.h" #include "pui-settings.h" #include "pui-types.h" struct _PuiApplication { GApplication parent_instance; GSettings *settings; GCancellable *cancellable; PuiBackend *backend; AppIndicator *indicator; GtkWidget *about_dialog; GIcon *icons[PUI_STATE_LAST]; PuiState state; gchar *update_command; gchar *error_message; }; G_DEFINE_TYPE(PuiApplication, pui_application, G_TYPE_APPLICATION) enum { PROP_0, PROP_UPDATE_COMMAND, PROP_LAST }; extern gboolean restart; static GParamSpec *properties[PROP_LAST] = { NULL }; static const gchar *icon_names[PUI_STATE_LAST] = { [PUI_STATE_INITIAL] = "system-software-update", [PUI_STATE_UP_TO_DATE] = "system-software-update", [PUI_STATE_NORMAL_UPDATES_AVAILABLE] = "software-update-available", [PUI_STATE_IMPORTANT_UPDATES_AVAILABLE] = "software-update-urgent", [PUI_STATE_SESSION_RESTART_REQUIRED] = "system-log-out", [PUI_STATE_SYSTEM_RESTART_REQUIRED] = "system-reboot", [PUI_STATE_ERROR] = "dialog-warning" }; static const GOptionEntry cmd_options[] = { { "debug", '\0', G_OPTION_FLAG_NONE, G_OPTION_ARG_NONE, NULL, N_("Enable debugging messages"), NULL }, { "quit", 'q', G_OPTION_FLAG_NONE, G_OPTION_ARG_NONE, NULL, N_("Quit running instance of Package Update Indicator"), NULL }, { "version", 'V', G_OPTION_FLAG_NONE, G_OPTION_ARG_NONE, NULL, N_("Print the version number and quit"), NULL }, { G_OPTION_REMAINING, 0, 0, G_OPTION_ARG_FILENAME_ARRAY, NULL, NULL, NULL }, { NULL } }; static void pui_application_show_about_dialog(GSimpleAction *, GVariant *, gpointer); static void pui_application_open_preferences(GSimpleAction *, GVariant *, gpointer); static void pui_application_quit(GSimpleAction *, GVariant *, gpointer); static void pui_application_install_updates(GSimpleAction *, GVariant *, gpointer); static const GActionEntry pui_application_actions[] = { { "about", pui_application_show_about_dialog }, { "preferences", pui_application_open_preferences }, { "quit", pui_application_quit }, { "install-updates", pui_application_install_updates } }; static gboolean program_exists(const gchar *command_line) { gboolean is_program_in_path; gchar **argv = NULL; gchar *program_path; if (!g_shell_parse_argv(command_line, NULL, &argv, NULL)) { return (FALSE); } program_path = g_find_program_in_path(argv[0]); is_program_in_path = (program_path != NULL) ? TRUE : FALSE; g_free(program_path); g_strfreev(argv); return (is_program_in_path); } static void pui_application_show_about_dialog(GSimpleAction *simple, GVariant *parameter, gpointer user_data) { PuiApplication *self = user_data; GtkBuilder *builder; if (self->about_dialog == NULL) { /* get dialog from builder */ builder = gtk_builder_new_from_resource("/org" "/guido-berhoerster/code/package-update-indicator" "/pui-about-dialog.ui"); self->about_dialog = GTK_WIDGET(gtk_builder_get_object(builder, "about-dialog")); g_object_unref(builder); } gtk_dialog_run(GTK_DIALOG(self->about_dialog)); gtk_widget_hide(self->about_dialog); } static void pui_application_open_preferences(GSimpleAction *simple, GVariant *parameter, gpointer user_data) { GDesktopAppInfo *prefs_app_info; GError *error = NULL; prefs_app_info = g_desktop_app_info_new("org.guido-berhoerster.code." "package-update-indicator.preferences.desktop"); if (prefs_app_info == NULL) { g_warning("desktop file \"org.guido-berhoerster.code." "package-update-indicator.preferences.desktop\" not found"); return; } if (!g_app_info_launch(G_APP_INFO(prefs_app_info), NULL, NULL, &error)) { g_warning("failed to launch preferences: %s", error->message); g_error_free(error); } } static void pui_application_quit(GSimpleAction *simple, GVariant *parameter, gpointer user_data) { PuiApplication *self = user_data; /* quit the GTK main loop if the about dialog is running */ if (self->about_dialog != NULL) { gtk_widget_hide(self->about_dialog); } g_application_quit(G_APPLICATION(self)); } static void pui_application_install_updates(GSimpleAction *simple, GVariant *parameter, gpointer user_data) { PuiApplication *self = user_data; GError *error = NULL; if (!g_spawn_command_line_async(self->update_command, &error)) { g_warning("failed to run update command: %s", error->message); g_error_free(error); } } static void update_ui(PuiApplication *self) { GSimpleAction *install_updates_action; guint important_updates = 0; guint normal_updates = 0; gchar *title = NULL; gchar *body = NULL; GApplication *application = G_APPLICATION(self); GNotification *notification = NULL; install_updates_action = G_SIMPLE_ACTION(g_action_map_lookup_action(G_ACTION_MAP(self), "install-updates")); if ((self->state == PUI_STATE_NORMAL_UPDATES_AVAILABLE) || (self->state == PUI_STATE_IMPORTANT_UPDATES_AVAILABLE)) { g_object_get(self->backend, "important-updates", &important_updates, "normal-updates", &normal_updates, NULL); } /* actions */ switch (self->state) { case PUI_STATE_INITIAL: /* FALLTHGROUGH */ case PUI_STATE_UP_TO_DATE: /* FALLTHGROUGH */ case PUI_STATE_SESSION_RESTART_REQUIRED: /* FALLTHGROUGH */ case PUI_STATE_SYSTEM_RESTART_REQUIRED: /* FALLTHGROUGH */ case PUI_STATE_ERROR: g_simple_action_set_enabled(install_updates_action, FALSE); break; case PUI_STATE_NORMAL_UPDATES_AVAILABLE: /* FALLTHROUGH */ case PUI_STATE_IMPORTANT_UPDATES_AVAILABLE: g_simple_action_set_enabled(install_updates_action, program_exists(self->update_command)); break; } /* title and body for indicator and notification */ switch (self->state) { case PUI_STATE_INITIAL: title = g_strdup(""); body = g_strdup(""); break; case PUI_STATE_UP_TO_DATE: title = g_strdup(_("Up to Date")); body = g_strdup(_("The system is up to date.")); break; case PUI_STATE_NORMAL_UPDATES_AVAILABLE: title = g_strdup(g_dngettext(NULL, "Software Update", "Software Updates", (gulong)normal_updates)); if (normal_updates == 1) { body = g_strdup(_("There is a software update " "available.")); } else { body = g_strdup_printf(_("There are %u " "software updates available."), normal_updates); } break; case PUI_STATE_IMPORTANT_UPDATES_AVAILABLE: title = g_strdup(g_dngettext(NULL, "Important Software Update", "Important Software Updates", (gulong)important_updates)); if ((normal_updates == 0) && (important_updates == 1)) { body = g_strdup(_("There is an important " "software update available.")); } else if ((normal_updates == 0) && (important_updates > 1)) { body = g_strdup_printf(_("There are %u " "important software updates available."), important_updates); } else if ((normal_updates > 0) && (important_updates == 1)) { body = g_strdup_printf(_("There are %u " "software updates available, " "one of them is important."), normal_updates + important_updates); } else { body = g_strdup_printf(_("There are %u " "software updates available, " "%u of them are important."), normal_updates + important_updates, important_updates); } break; case PUI_STATE_SESSION_RESTART_REQUIRED: title = g_strdup(_("Logout Required")); body = g_strdup(_("You need to log out and back in for the " "update to take effect.")); break; case PUI_STATE_SYSTEM_RESTART_REQUIRED: title = g_strdup(_("Restart Required")); body = g_strdup(_("The computer has to be restarted for the " "updates to take effect.")); break; case PUI_STATE_ERROR: title = g_strdup(self->error_message); break; } /* indicator */ switch (self->state) { case PUI_STATE_INITIAL: app_indicator_set_status(self->indicator, APP_INDICATOR_STATUS_PASSIVE); break; case PUI_STATE_UP_TO_DATE: /* FALLTHGROUGH */ case PUI_STATE_NORMAL_UPDATES_AVAILABLE: /* FALLTHGROUGH */ case PUI_STATE_IMPORTANT_UPDATES_AVAILABLE: /* FALLTHGROUGH */ case PUI_STATE_SESSION_RESTART_REQUIRED: /* FALLTHGROUGH */ case PUI_STATE_SYSTEM_RESTART_REQUIRED: /* FALLTHGROUGH */ case PUI_STATE_ERROR: app_indicator_set_status(self->indicator, APP_INDICATOR_STATUS_ACTIVE); break; } app_indicator_set_icon_full(self->indicator, icon_names[self->state], title); /* notification */ switch (self->state) { case PUI_STATE_INITIAL: /* FALLTHGROUGH */ case PUI_STATE_UP_TO_DATE: /* FALLTHGROUGH */ case PUI_STATE_ERROR: /* withdraw exisiting notification */ g_application_withdraw_notification(application, "package-updates-or-restart-required"); break; case PUI_STATE_NORMAL_UPDATES_AVAILABLE: /* FALLTHGROUGH */ case PUI_STATE_IMPORTANT_UPDATES_AVAILABLE: /* FALLTHGROUGH */ case PUI_STATE_SESSION_RESTART_REQUIRED: /* FALLTHGROUGH */ case PUI_STATE_SYSTEM_RESTART_REQUIRED: /* create notification */ notification = g_notification_new(title); g_notification_set_body(notification, body); g_notification_set_icon(notification, self->icons[self->state]); g_notification_set_priority(notification, G_NOTIFICATION_PRIORITY_NORMAL); if (g_action_get_enabled(G_ACTION(install_updates_action))) { g_notification_add_button(notification, _("Install Updates"), "app.install-updates"); } g_application_send_notification(application, "package-updates-or-restart-required", notification); break; } if (notification != NULL) { g_object_unref(notification); } g_debug("indicator icon: %s, notification title: \"%s\", " "notification body: \"%s\"", icon_names[self->state], title, body); g_free(body); g_free(title); } static void transition_state(PuiApplication *self) { PuiState state = self->state; PuiRestart restart_type; guint important_updates; guint normal_updates; gchar *old_state; gchar *new_state; switch (self->state) { case PUI_STATE_INITIAL: /* FALLTHROUGH */ case PUI_STATE_UP_TO_DATE: /* FALLTHROUGH */ case PUI_STATE_NORMAL_UPDATES_AVAILABLE: /* FALLTHROUGH */ case PUI_STATE_IMPORTANT_UPDATES_AVAILABLE: if (self->error_message != NULL) { state = PUI_STATE_ERROR; break; } g_object_get(self->backend, "restart-type", &restart_type, "important-updates", &important_updates, "normal-updates", &normal_updates, NULL); if (restart_type == PUI_RESTART_SESSION) { state = PUI_STATE_SESSION_RESTART_REQUIRED; } else if (restart_type == PUI_RESTART_SYSTEM) { state = PUI_STATE_SYSTEM_RESTART_REQUIRED; } else if (important_updates > 0) { state = PUI_STATE_IMPORTANT_UPDATES_AVAILABLE; } else if (normal_updates > 0) { state = PUI_STATE_NORMAL_UPDATES_AVAILABLE; } else { state = PUI_STATE_UP_TO_DATE; } break; case PUI_STATE_SESSION_RESTART_REQUIRED: g_object_get(self->backend, "restart-type", &restart_type, NULL); if (restart_type == PUI_RESTART_SYSTEM) { state = PUI_STATE_SYSTEM_RESTART_REQUIRED; } break; case PUI_STATE_SYSTEM_RESTART_REQUIRED: /* FALLTHROUGH */ case PUI_STATE_ERROR: break; } if (state != self->state) { old_state = pui_types_enum_to_string(PUI_TYPE_STATE, self->state); new_state = pui_types_enum_to_string(PUI_TYPE_STATE, state); g_debug("state %s -> %s", old_state, new_state); self->state = state; update_ui(self); g_free(new_state); g_free(old_state); } } static void on_backend_restart_required(PuiBackend *backend, gpointer user_data) { PuiApplication *self = user_data; restart = TRUE; g_action_group_activate_action(G_ACTION_GROUP(G_APPLICATION(self)), "quit", NULL); } static void on_backend_state_changed(PuiBackend *backend, gpointer user_data) { PuiApplication *self = user_data; transition_state(self); } static void on_pui_backend_finished(GObject *source_object, GAsyncResult *result, gpointer user_data) { PuiApplication *self = user_data; GError *error = NULL; self->backend = pui_backend_new_finish(result, &error); if (self->backend == NULL) { g_warning("failed to instantiate backend: %s", error->message); g_free(self->error_message); g_error_free(error); self->error_message = g_strdup(_("Update notifications " "are not supported.")); transition_state(self); return; } pui_backend_set_proxy(self->backend, g_getenv("http_proxy"), g_getenv("https_proxy"), g_getenv("ftp_proxy"), g_getenv("socks_proxy"), g_getenv("no_proxy"), NULL); g_settings_bind(self->settings, "refresh-interval", self->backend, "refresh-interval", G_SETTINGS_BIND_GET); g_settings_bind(self->settings, "use-mobile-connection", self->backend, "use-mobile-connection", G_SETTINGS_BIND_GET); transition_state(self); g_signal_connect(self->backend, "restart-required", G_CALLBACK(on_backend_restart_required), self); g_signal_connect(self->backend, "state-changed", G_CALLBACK(on_backend_state_changed), self); } static void pui_application_startup(GApplication *application) { PuiApplication *self = PUI_APPLICATION(application); gsize i; GtkBuilder *builder; GtkWidget *menu; G_APPLICATION_CLASS(pui_application_parent_class)->startup(application); /* create actions */ g_action_map_add_action_entries(G_ACTION_MAP(self), pui_application_actions, G_N_ELEMENTS(pui_application_actions), self); /* load icons */ for (i = 0; i < G_N_ELEMENTS(self->icons); i++) { self->icons[i] = g_themed_icon_new(icon_names[i]); } /* create settings */ self->settings = pui_settings_new(); g_settings_bind(self->settings, "update-command", self, "update-command", G_SETTINGS_BIND_GET); /* start instantiating backend */ pui_backend_new_async(self->cancellable, on_pui_backend_finished, self); /* create indicator */ self->indicator = app_indicator_new(APPLICATION_ID, "system-software-update", APP_INDICATOR_CATEGORY_APPLICATION_STATUS); app_indicator_set_title(self->indicator, _("Package Update Indicator")); /* get menu from builder and add it to the indicator */ builder = gtk_builder_new_from_resource("/org/guido-berhoerster/code/" "package-update-indicator/pui-menu.ui"); menu = GTK_WIDGET(gtk_builder_get_object(builder, "menu")); gtk_widget_insert_action_group(menu, "app", G_ACTION_GROUP(self)); gtk_widget_show_all(menu); app_indicator_set_menu(self->indicator, GTK_MENU(menu)); update_ui(self); /* keep GApplication running */ g_application_hold(application); g_object_unref(builder); } static void pui_application_shutdown(GApplication *application) { GApplicationClass *application_class = G_APPLICATION_CLASS(pui_application_parent_class); application_class->shutdown(application); } static gint pui_application_handle_local_options(GApplication *application, GVariantDict *options) { gchar *messages_debug; gchar **args = NULL; GError *error = NULL; /* filename arguments are not allowed */ if (g_variant_dict_lookup(options, G_OPTION_REMAINING, "^a&ay", &args)) { g_printerr("invalid argument: \"%s\"\n", args[0]); g_free(args); return (1); } if (g_variant_dict_contains(options, "version")) { g_print("%s %s\n", PACKAGE, VERSION); /* quit */ return (0); } if (g_variant_dict_contains(options, "debug")) { /* enable debug logging */ messages_debug = g_strjoin(":", G_LOG_DOMAIN, g_getenv("G_MESSAGES_DEBUG"), NULL); g_setenv("G_MESSAGES_DEBUG", messages_debug, TRUE); g_free(messages_debug); } /* * register with the session bus so that it is possible to discern * between remote and primary instance and that remote actions can be * invoked, this causes the startup signal to be emitted which, in case * of the primary instance, starts to instantiate the * backend with the given values */ if (!g_application_register(application, NULL, &error)) { g_critical("g_application_register: %s", error->message); g_error_free(error); return (1); } if (g_variant_dict_contains(options, "quit")) { /* only valid if a remote instance is running */ if (!g_application_get_is_remote(application)) { g_printerr("%s is not running\n", g_get_prgname()); return (1); } /* signal remote instance to quit */ g_action_group_activate_action(G_ACTION_GROUP(application), "quit", NULL); /* quit local instance */ return (0); } /* proceed with default command line processing */ return (-1); } static void pui_application_activate(GApplication *application) { GApplicationClass *application_class = G_APPLICATION_CLASS(pui_application_parent_class); /* do nothing, implementation required by GApplication */ application_class->activate(application); } static void pui_application_set_property(GObject *object, guint property_id, const GValue *value, GParamSpec *pspec) { PuiApplication *self = PUI_APPLICATION(object); switch (property_id) { case PROP_UPDATE_COMMAND: g_free(self->update_command); self->update_command = g_value_dup_string(value); g_debug("property \"update-command\" set to \"%s\"", self->update_command); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void pui_application_get_property(GObject *object, guint property_id, GValue *value, GParamSpec *pspec) { PuiApplication *self = PUI_APPLICATION(object); switch (property_id) { case PROP_UPDATE_COMMAND: g_value_set_string(value, self->update_command); break; default: G_OBJECT_WARN_INVALID_PROPERTY_ID(object, property_id, pspec); break; } } static void pui_application_dispose(GObject *object) { PuiApplication *self = PUI_APPLICATION(object); gsize i; if (self->settings != NULL) { g_signal_handlers_disconnect_by_data(self->settings, self); g_clear_object(&self->settings); } if (self->cancellable != NULL) { g_cancellable_cancel(self->cancellable); g_clear_object(&self->cancellable); } if (self->backend != NULL) { g_clear_object(&self->backend); } if (self->indicator != NULL) { g_clear_object(&self->indicator); } if (self->about_dialog != NULL) { g_clear_pointer(&self->about_dialog, (GDestroyNotify)(gtk_widget_destroy)); } for (i = 0; i < G_N_ELEMENTS(self->icons); i++) { if (self->icons[i] != NULL) { g_clear_object(&self->icons[i]); } } G_OBJECT_CLASS(pui_application_parent_class)->dispose(object); } static void pui_application_finalize(GObject *object) { PuiApplication *self = PUI_APPLICATION(object); g_free(self->update_command); g_free(self->error_message); G_OBJECT_CLASS(pui_application_parent_class)->finalize(object); } static void pui_application_class_init(PuiApplicationClass *klass) { GObjectClass *object_class = G_OBJECT_CLASS(klass); GApplicationClass *application_class = G_APPLICATION_CLASS(klass); object_class->set_property = pui_application_set_property; object_class->get_property = pui_application_get_property; object_class->dispose = pui_application_dispose; object_class->finalize = pui_application_finalize; properties[PROP_UPDATE_COMMAND] = g_param_spec_string("update-command", "Update command", "Command for installing updates", NULL, G_PARAM_READWRITE); g_object_class_install_properties(object_class, PROP_LAST, properties); application_class->startup = pui_application_startup; application_class->shutdown = pui_application_shutdown; application_class->handle_local_options = pui_application_handle_local_options; application_class->activate = pui_application_activate; } static void pui_application_init(PuiApplication *self) { g_application_add_main_option_entries(G_APPLICATION(self), cmd_options); self->cancellable = g_cancellable_new(); } PuiApplication * pui_application_new(void) { return (g_object_new(PUI_TYPE_APPLICATION, "application-id", APPLICATION_ID, NULL)); } package-update-indicator-7/org.guido-berhoerster.code.package-update-indicator.gschema.xml010064400017500001750000000015451331741424000306400ustar00gbergber "" Update command Command for installing updates. 86400 Refresh interval The interval in seconds for refreshing metadata. false Whether to use a mobile connection If enabled, use a mobile connection refreshing the package cache. package-update-indicator-7/pui-backend.h010064400017500001750000000036771331765667600171240ustar00gbergber/* * Copyright (C) 2018 Guido Berhoerster * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files (the * "Software"), to deal in the Software without restriction, including * without limitation the rights to use, copy, modify, merge, publish, * distribute, sublicense, and/or sell copies of the Software, and to * permit persons to whom the Software is furnished to do so, subject to * the following conditions: * * The above copyright notice and this permission notice shall be included * in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ #ifndef PUI_BACKEND_H #define PUI_BACKEND_H #include #include G_BEGIN_DECLS #define PUI_TYPE_BACKEND (pui_backend_get_type()) #define PUI_BACKEND_ERROR (pui_backend_error_quark()) G_DECLARE_FINAL_TYPE(PuiBackend, pui_backend, PUI, BACKEND, GObject) enum { PUI_BACKEND_ERROR_GET_UPDATES_NOT_IMPLEMENTED }; typedef enum { PUI_RESTART_NONE, PUI_RESTART_SESSION, PUI_RESTART_SYSTEM, PUI_RESTART_LAST } PuiRestart; GQuark pui_backend_error_quark(void); void pui_backend_new_async(GCancellable *, GAsyncReadyCallback, gpointer); PuiBackend * pui_backend_new_finish(GAsyncResult *, GError **); void pui_backend_set_proxy(PuiBackend *, const gchar *, const gchar *, const gchar *, const gchar *, const gchar *, const gchar *); G_END_DECLS #endif /* !PUI_BACKEND_H */ package-update-indicator-7/pui-prefs-window.ui010064400017500001750000000156701331741424000203160ustar00gbergber always always 0 one-hour every hour 3600 eight-hours every 8 hours 28800 twelve-hours twice a day 43200 one-day daily 86400 one-week weekly 604800 never never 4294967295 False False True False 18 18 18 18 vertical 18 True False 18 12 True False end _Refresh cache: True 0 0 True False end _Command for installing updates: True update-command 0 1 True True 32 1 1 True False refresh-interval-list 0 1 1 0 Use _mobile connection True True False True True 0 2 2 True True 0 True False end gtk-close True True True app.quit True True True 0 False True 1 package-update-indicator-7/pui-get-updates.h010064400017500001750000000033411331741420000177120ustar00gbergber/* * Copyright (C) 2018 Guido Berhoerster * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files (the * "Software"), to deal in the Software without restriction, including * without limitation the rights to use, copy, modify, merge, publish, * distribute, sublicense, and/or sell copies of the Software, and to * permit persons to whom the Software is furnished to do so, subject to * the following conditions: * * The above copyright notice and this permission notice shall be included * in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ #ifndef PUI_GET_UPDATES_H #define PUI_GET_UPDATES_H #include #include #include G_BEGIN_DECLS #define PUI_GET_UPDATES_ERROR (pui_get_updates_error_quark()) enum { PUI_GET_UPDATES_ERROR_REFRESH_FAILED, PUI_GET_UPDATES_ERROR_GET_UPDATES_FAILED, PUI_GET_UPDATES_ERROR_CANCELLED }; GQuark pui_get_updates_error_quark(void); void pui_get_updates_async(PkControl *, guint, GCancellable *, GAsyncReadyCallback, gpointer); GPtrArray * pui_get_updates_finish(GAsyncResult *, GError **); G_END_DECLS #endif /* !PUI_GET_UPDATES_H */ package-update-indicator-7/org.guido-berhoerster.code.package-update-indicator.desktop.in010064400017500001750000000004171331741420000305010ustar00gbergber[Desktop Entry] Name=Package Update Indicator GenericName=Package Update Indicator Comment=Notify about available software updates Icon=system-software-update Exec=package-update-indicator Terminal=false Type=Application Categories=Utility;GTK;TrayIcon; NotShowIn=GNOME; package-update-indicator-7/pui-prefs-application.h010064400017500001750000000030431331741424000211130ustar00gbergber/* * Copyright (C) 2018 Guido Berhoerster * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files (the * "Software"), to deal in the Software without restriction, including * without limitation the rights to use, copy, modify, merge, publish, * distribute, sublicense, and/or sell copies of the Software, and to * permit persons to whom the Software is furnished to do so, subject to * the following conditions: * * The above copyright notice and this permission notice shall be included * in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ #ifndef PUI_PREFS_APPLICATION_H #define PUI_PREFS_APPLICATION_H #include #include G_BEGIN_DECLS #define PUI_TYPE_PREFS_APPLICATION (pui_prefs_application_get_type()) G_DECLARE_FINAL_TYPE(PuiPrefsApplication, pui_prefs_application, PUI, PREFS_APPLICATION, GtkApplication) PuiPrefsApplication * pui_prefs_application_new(void); G_END_DECLS #endif /* !PUI_PREFS_APPLICATION_H */ package-update-indicator-7/pui-common.h010064400017500001750000000032651353220444500167740ustar00gbergber/* * Copyright (C) 2018 Guido Berhoerster * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files (the * "Software"), to deal in the Software without restriction, including * without limitation the rights to use, copy, modify, merge, publish, * distribute, sublicense, and/or sell copies of the Software, and to * permit persons to whom the Software is furnished to do so, subject to * the following conditions: * * The above copyright notice and this permission notice shall be included * in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ #ifndef PUI_COMMON_H #define PUI_COMMON_H G_BEGIN_DECLS #ifndef PUI_STARTUP_DELAY #define PUI_STARTUP_DELAY (3 * 60) #endif /* !PUI_STARTUP_DELAY */ #ifndef PUI_UPDATES_CHANGED_DELAY #define PUI_UPDATES_CHANGED_DELAY (30) #endif /* !PUI_UPDATES_CHANGED_DELAY */ #ifndef PUI_CHECK_UPDATES_INTERVAL #define PUI_CHECK_UPDATES_INTERVAL (60 * 60) #endif /* !PUI_CHECK_UPDATES_INTERVAL */ #ifndef PUI_DEFAULT_REFRESH_INTERVAL #define PUI_DEFAULT_REFRESH_INTERVAL (24 * 60 * 60) #endif /* !PUI_DEFAULT_REFRESH_INTERVAL */ G_END_DECLS #endif /* !PUI_COMMON_H */ package-update-indicator-7/pui-types.c.in010064400017500001750000000024471331765667600172730ustar00gbergber/*** BEGIN file-header ***/ #include "pui-types.h" /*** END file-header ***/ /*** BEGIN file-production ***/ /* enumerations from "@filename@" */ #include "@filename@" /*** END file-production ***/ /*** BEGIN value-header ***/ GType @enum_name@_get_type (void) { static volatile gsize g_define_type_id__volatile; GType g_@type@_type_id; if (g_once_init_enter(&g_define_type_id__volatile)) { static const G@Type@Value values[] = { /*** END value-header ***/ /*** BEGIN value-production ***/ { @VALUENAME@, "@VALUENAME@", "@valuenick@" }, /*** END value-production ***/ /*** BEGIN value-tail ***/ { 0 } }; g_@type@_type_id = g_@type@_register_static( g_intern_static_string("@EnumName@"), values); g_once_init_leave(&g_define_type_id__volatile, g_@type@_type_id); } return (g_define_type_id__volatile); } /*** END value-tail ***/ /*** BEGIN file-tail ***/ gchar * pui_types_enum_to_string(GType type, gint value) { GTypeClass *type_class; GEnumValue *enum_value; type_class = g_type_class_ref(type); g_return_val_if_fail(G_IS_ENUM_CLASS(type_class), NULL); enum_value = g_enum_get_value(G_ENUM_CLASS(type_class), value); if (enum_value == NULL) { return (g_strdup_printf("%d", value)); } return (g_strdup(enum_value->value_nick)); } /*** END file-tail ***/ package-update-indicator-7/pui-application.h010064400017500001750000000033751331765667600200330ustar00gbergber/* * Copyright (C) 2018 Guido Berhoerster * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files (the * "Software"), to deal in the Software without restriction, including * without limitation the rights to use, copy, modify, merge, publish, * distribute, sublicense, and/or sell copies of the Software, and to * permit persons to whom the Software is furnished to do so, subject to * the following conditions: * * The above copyright notice and this permission notice shall be included * in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ #ifndef PUI_APPLICATION_H #define PUI_APPLICATION_H #include #include G_BEGIN_DECLS #define PUI_TYPE_APPLICATION (pui_application_get_type()) G_DECLARE_FINAL_TYPE(PuiApplication, pui_application, PUI, APPLICATION, GApplication) typedef enum { PUI_STATE_INITIAL, PUI_STATE_UP_TO_DATE, PUI_STATE_NORMAL_UPDATES_AVAILABLE, PUI_STATE_IMPORTANT_UPDATES_AVAILABLE, PUI_STATE_SESSION_RESTART_REQUIRED, PUI_STATE_SYSTEM_RESTART_REQUIRED, PUI_STATE_ERROR, PUI_STATE_LAST } PuiState; PuiApplication * pui_application_new(void); G_END_DECLS #endif /* !PUI_APPLICATION_H */ package-update-indicator-7/package-update-indicator-prefs.c010064400017500001750000000034061331741424000226400ustar00gbergber/* * Copyright (C) 2018 Guido Berhoerster * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files (the * "Software"), to deal in the Software without restriction, including * without limitation the rights to use, copy, modify, merge, publish, * distribute, sublicense, and/or sell copies of the Software, and to * permit persons to whom the Software is furnished to do so, subject to * the following conditions: * * The above copyright notice and this permission notice shall be included * in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ #include #include #include #include #include #include "pui-prefs-application.h" int main(int argc, char *argv[]) { int status; PuiPrefsApplication *application; bindtextdomain(GETTEXT_PACKAGE, PACKAGE_LOCALE_DIR); setlocale(LC_ALL, ""); bind_textdomain_codeset(GETTEXT_PACKAGE, "UTF-8"); textdomain(GETTEXT_PACKAGE); g_set_application_name(_("Package Update Indicator Preferences")); gtk_init(&argc, &argv); application = pui_prefs_application_new(); status = g_application_run(G_APPLICATION(application), argc, argv); g_object_unref(application); exit(status); } package-update-indicator-7/NEWS010064400017500001750000000043001375473112500152340ustar00gbergberNews ==== package-update-indicator 7 (2020-11-17T12:21:47+01:00) ------------------------------------------------------ - Explicitly schedule the initial check for updates after a fixed short delay - Add debug logging when periodic checks are inhibited - Update Russin translations - Add Russian translations package-update-indicator 6 (2020-08-21T15:47:00+02:00) ------------------------------------------------------ - Add Italian translations - Correct translations - Add French translations - Fix incorrect translation - Add Danish translations - Back out fallback icon support which does not work as intended package-update-indicator 5 (2019-08-30T13:32:52+02:00) ------------------------------------------------------ - Reduce delay before checking for updates after an "updates-changed" signal - Fix continuos loop of update checks if the refresh cache interval is 0 - Add fallback icons for KDE-based themes package-update-indicator 4 (2019-07-24T16:27:25+02:00) ------------------------------------------------------ - Fix support for libayatana-appindicator package-update-indicator 3 (2019-07-24T10:33:37+02:00) ------------------------------------------------------ - Use consistent vocabulary in German translations - Add support for libayantana-indicator - Fix typo in German translations - Add missing changelog entries package-update-indicator 2 (2018-12-08T10:09:35+01:00) ------------------------------------------------------ - Add keywords to desktop files - Fix typo in notification message - Do not run glib-compile-schemas if schemas are installed into staging directory - Set application indicator title - Add note for vendors on how to override default settings package-update-indicator 1 (2018-07-06T14:21:28+02:00) ------------------------------------------------------ - Notify about required session or system restarts - Add Indonesian translations - Add German translations - Add English translations - Make PackagKit use the user's network proxies - Do not check for updates if the battery is low - Add setting to control whether to use a mobile connection - Add menu item to launch the preferences application - Use GtkBuilder for all widgets - Add preferences application - Initial revision package-update-indicator-7/docbook-update-source-data.xsl010064400017500001750000000015111331741420000223560ustar00gbergber package-update-indicator-7/po004075500017500001750000000000001373761407600151105ustar00gbergberpackage-update-indicator-7/po/LINGUAS010064400017500001750000000000251373657374400162130ustar00gbergberda de en fr id it ru package-update-indicator-7/po/id.po010064400017500001750000000145041340270276200161110ustar00gbergber# Indonesian translations for package-update-indicator package. # Copyright (C) 2018 Guido Berhoerster # This file is distributed under the same license as the package-update-indicator package. # Guido Berhoerster , 2018. # msgid "" msgstr "" "Project-Id-Version: package-update-indicator 1\n" "Report-Msgid-Bugs-To: guido+pui@berhoerster.name\n" "POT-Creation-Date: 2018-12-08 08:50+0000\n" "PO-Revision-Date: 2018-07-06 12:10+0000\n" "Last-Translator: Guido Berhoerster \n" "Language-Team: none\n" "Language: id\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=INTEGER; plural=EXPRESSION;\n" #: org.guido-berhoerster.code.package-update-indicator.desktop.in:3 #: org.guido-berhoerster.code.package-update-indicator.desktop.in:4 #: package-update-indicator.c:59 pui-application.c:489 msgid "Package Update Indicator" msgstr "" #: org.guido-berhoerster.code.package-update-indicator.desktop.in:5 #: pui-about-dialog.ui:12 msgid "Notify about available software updates" msgstr "Pemberitahuan tentang pembaharuan-pembaharuan perangkat lunak" #: org.guido-berhoerster.code.package-update-indicator.desktop.in:6 msgid "system-software-update" msgstr "" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:7 msgid "Update command" msgstr "" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:8 msgid "Command for installing updates." msgstr "Perintah untuk pasang perangkat lunak pembaharuan-pembaharuan." #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:12 msgid "Refresh interval" msgstr "" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:13 msgid "The interval in seconds for refreshing metadata." msgstr "" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:18 msgid "Whether to use a mobile connection" msgstr "" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:19 msgid "If enabled, use a mobile connection refreshing the package cache." msgstr "" #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:3 #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:4 #: package-update-indicator-prefs.c:43 msgid "Package Update Indicator Preferences" msgstr "" #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:5 msgid "Edit the Preferences for Package Update Indicator" msgstr "" #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:6 msgid "updates;preferences;" msgstr "" #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:7 msgid "preferences-other" msgstr "" #: pui-about-dialog.ui:7 msgid "About Package Update Indicator" msgstr "" #: pui-about-dialog.ui:11 msgid "Copyright © 2018 Guido Berhörster" msgstr "Copyright © 2018 Guido Berhörster" #. Place your name here. #: pui-about-dialog.ui:15 msgid "Translator" msgstr "Guido Berhörster" #: pui-application.c:73 msgid "Enable debugging messages" msgstr "" #: pui-application.c:75 msgid "Quit running instance of Package Update Indicator" msgstr "" #: pui-application.c:77 msgid "Print the version number and quit" msgstr "Tampilkan nomor versi dan keluar" #: pui-application.c:232 msgid "Up to Date" msgstr "Up-to-date" #: pui-application.c:233 msgid "The system is up to date." msgstr "Sistemnya telah up-to-date." #: pui-application.c:236 msgid "Software Update" msgid_plural "Software Updates" msgstr[0] "Pembaharuan Perangkat Lunak" msgstr[1] "Pembaharuan-Pembaharuan Perangkat Lunak" #: pui-application.c:239 msgid "There is a software update available." msgstr "Tersedia satu pembaharuan perangkat lunak." #: pui-application.c:242 #, c-format msgid "There are %u software updates available." msgstr "Tersedia %u pembaharuan-pembaharuan perangkat lunak." #: pui-application.c:247 msgid "Important Software Update" msgid_plural "Important Software Updates" msgstr[0] "Perangkat Lunak Pembaharuan yang penting" msgstr[1] "Perangkat Lunak Pembaharuan-Pembaharuan yang penting" #: pui-application.c:250 msgid "There is an important software update available." msgstr "Tersedia satu pembaharuan perangkat lunak yang penting." #: pui-application.c:253 #, c-format msgid "There are %u important software updates available." msgstr "Tersedia %u pembaharuan-pembaharuan perangkat lunak yang penting." #: pui-application.c:257 #, c-format msgid "There are %u software updates available, one of them is important." msgstr "" "Tersedia %u pembaharuan-pembaharuan perangkat lunak, diantaranya satu yang " "penting." #: pui-application.c:262 #, c-format msgid "There are %u software updates available, %u of them are important." msgstr "" "Tersedia %u pembaharuan-pembaharuan perangkat lunak, diantaranya %u yang " "penting." #: pui-application.c:270 msgid "Logout Required" msgstr "Diperlukan Log Keluar" #: pui-application.c:271 msgid "You need to log out and back in for the update to take effect." msgstr "" #: pui-application.c:275 msgid "Restart Required" msgstr "Diperlukan Reboot" #: pui-application.c:276 msgid "The computer has to be restarted for the updates to take effect." msgstr "" #: pui-application.c:324 msgid "Install Updates" msgstr "Pasang Perangkat Lunak Pembaharuan-Pembaharuan" #: pui-application.c:434 msgid "Update notifications are not supported." msgstr "Pemberitahuan pembaharuan-pembaharuan tidak didukung." #: pui-menu.ui:13 msgid "_Install updates" msgstr "_Pasang Perangkat Lunak Pembaharuan-Pembaharuan" #: pui-menu.ui:22 msgid "_Preferences…" msgstr "_Preferensi…" #: pui-menu.ui:31 msgid "_About…" msgstr "_Tentang…" #: pui-prefs-window.ui:17 msgid "always" msgstr "selalu" #: pui-prefs-window.ui:22 msgid "every hour" msgstr "setiap jam" #: pui-prefs-window.ui:27 msgid "every 8 hours" msgstr "setiap 8 jam" #: pui-prefs-window.ui:32 msgid "twice a day" msgstr "dua kali sehari" #: pui-prefs-window.ui:37 msgid "daily" msgstr "setiap hari" #: pui-prefs-window.ui:42 msgid "weekly" msgstr "setiap minggu" #: pui-prefs-window.ui:47 msgid "never" msgstr "tak pernah" #: pui-prefs-window.ui:76 msgid "_Refresh cache:" msgstr "" #: pui-prefs-window.ui:89 msgid "_Command for installing updates:" msgstr "_Perintah untuk pasang perangkat lunak pembaharuan-pembaharuan:" #: pui-prefs-window.ui:130 msgid "Use _mobile connection" msgstr "Pakai sambungan data _seluler" package-update-indicator-7/po/en.po010064400017500001750000000150341340270372500161160ustar00gbergber# English translations for package-update-indicator package. # Copyright (C) 2018 Guido Berhoerster # This file is distributed under the same license as the package-update-indicator package. # Guido Berhoerster , 2018. # msgid "" msgstr "" "Project-Id-Version: package-update-indicator 1\n" "Report-Msgid-Bugs-To: guido+pui@berhoerster.name\n" "POT-Creation-Date: 2018-12-08 08:50+0000\n" "PO-Revision-Date: 2018-07-06 12:10+0000\n" "Last-Translator: Guido Berhoerster \n" "Language-Team: none\n" "Language: en\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=(n != 1);\n" #: org.guido-berhoerster.code.package-update-indicator.desktop.in:3 #: org.guido-berhoerster.code.package-update-indicator.desktop.in:4 #: package-update-indicator.c:59 pui-application.c:489 msgid "Package Update Indicator" msgstr "Package Update Indicator" #: org.guido-berhoerster.code.package-update-indicator.desktop.in:5 #: pui-about-dialog.ui:12 msgid "Notify about available software updates" msgstr "Notify about available software updates" #: org.guido-berhoerster.code.package-update-indicator.desktop.in:6 msgid "system-software-update" msgstr "system-software-update" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:7 msgid "Update command" msgstr "Update command" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:8 msgid "Command for installing updates." msgstr "Command for installing updates." #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:12 msgid "Refresh interval" msgstr "Refresh interval" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:13 msgid "The interval in seconds for refreshing metadata." msgstr "The interval in seconds for refreshing metadata." #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:18 msgid "Whether to use a mobile connection" msgstr "Whether to use a mobile connection" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:19 msgid "If enabled, use a mobile connection refreshing the package cache." msgstr "If enabled, use a mobile connection refreshing the package cache." #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:3 #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:4 #: package-update-indicator-prefs.c:43 msgid "Package Update Indicator Preferences" msgstr "Package Update Indicator Preferences" #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:5 msgid "Edit the Preferences for Package Update Indicator" msgstr "Edit the Preferences for Package Update Indicator" #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:6 msgid "updates;preferences;" msgstr "updates;preferences;" #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:7 msgid "preferences-other" msgstr "preferences-other" #: pui-about-dialog.ui:7 msgid "About Package Update Indicator" msgstr "About Package Update Indicator" #: pui-about-dialog.ui:11 msgid "Copyright © 2018 Guido Berhörster" msgstr "Copyright © 2018 Guido Berhörster" #. Place your name here. #: pui-about-dialog.ui:15 msgid "Translator" msgstr "Translator" #: pui-application.c:73 msgid "Enable debugging messages" msgstr "Enable debugging messages" #: pui-application.c:75 msgid "Quit running instance of Package Update Indicator" msgstr "Quit running instance of Package Update Indicator" #: pui-application.c:77 msgid "Print the version number and quit" msgstr "Print the version number and quit" #: pui-application.c:232 msgid "Up to Date" msgstr "Up to Date" #: pui-application.c:233 msgid "The system is up to date." msgstr "The system is up to date." #: pui-application.c:236 msgid "Software Update" msgid_plural "Software Updates" msgstr[0] "Software Update" msgstr[1] "Software Updates" #: pui-application.c:239 msgid "There is a software update available." msgstr "There is a software update available." #: pui-application.c:242 #, c-format msgid "There are %u software updates available." msgstr "There are %u software updates available." #: pui-application.c:247 msgid "Important Software Update" msgid_plural "Important Software Updates" msgstr[0] "Important Software Update" msgstr[1] "Important Software Updates" #: pui-application.c:250 msgid "There is an important software update available." msgstr "There is an important software update available." #: pui-application.c:253 #, c-format msgid "There are %u important software updates available." msgstr "There are %u important software updates available." #: pui-application.c:257 #, c-format msgid "There are %u software updates available, one of them is important." msgstr "There are %u software updates available, one of them is important." #: pui-application.c:262 #, c-format msgid "There are %u software updates available, %u of them are important." msgstr "There are %u software updates available, %u of them are important." #: pui-application.c:270 msgid "Logout Required" msgstr "Logout Required" #: pui-application.c:271 msgid "You need to log out and back in for the update to take effect." msgstr "You need to log out and back in for the update to take effect." #: pui-application.c:275 msgid "Restart Required" msgstr "Restart Required" #: pui-application.c:276 msgid "The computer has to be restarted for the updates to take effect." msgstr "The computer has to be restarted for the updates to take effect." #: pui-application.c:324 msgid "Install Updates" msgstr "Install Updates" #: pui-application.c:434 msgid "Update notifications are not supported." msgstr "Update notifications are not supported." #: pui-menu.ui:13 msgid "_Install updates" msgstr "_Install updates" #: pui-menu.ui:22 msgid "_Preferences…" msgstr "_Preferences…" #: pui-menu.ui:31 msgid "_About…" msgstr "_About…" #: pui-prefs-window.ui:17 msgid "always" msgstr "always" #: pui-prefs-window.ui:22 msgid "every hour" msgstr "every hour" #: pui-prefs-window.ui:27 msgid "every 8 hours" msgstr "every 8 hours" #: pui-prefs-window.ui:32 msgid "twice a day" msgstr "twice a day" #: pui-prefs-window.ui:37 msgid "daily" msgstr "daily" #: pui-prefs-window.ui:42 msgid "weekly" msgstr "weekly" #: pui-prefs-window.ui:47 msgid "never" msgstr "never" #: pui-prefs-window.ui:76 msgid "_Refresh cache:" msgstr "_Refresh cache:" #: pui-prefs-window.ui:89 msgid "_Command for installing updates:" msgstr "_Command for installing updates:" #: pui-prefs-window.ui:130 msgid "Use _mobile connection" msgstr "Use _mobile connection" package-update-indicator-7/po/fr.po010060000017500001750000000154341357415604200161230ustar00gbergber# French translations for package-update-indicator package. # Copyright (C) 2018 Guido Berhoerster # This file is distributed under the same license as the package-update-indicator package. # Guido Berhoerster , 2018. # msgid "" msgstr "" "Project-Id-Version: package-update-indicator 1\n" "Report-Msgid-Bugs-To: guido+pui@berhoerster.name\n" "POT-Creation-Date: 2018-12-08 08:50+0000\n" "PO-Revision-Date: 2019-12-08 13:38+0000\n" "Last-Translator: JCE76350\n" "Language-Team: none\n" "Language: fr\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=(n != 1);\n" #: org.guido-berhoerster.code.package-update-indicator.desktop.in:3 #: org.guido-berhoerster.code.package-update-indicator.desktop.in:4 #: package-update-indicator.c:59 pui-application.c:493 msgid "Package Update Indicator" msgstr "Indicateur de mises à jour" #: org.guido-berhoerster.code.package-update-indicator.desktop.in:5 #: pui-about-dialog.ui:12 msgid "Notify about available software updates" msgstr "Informer des mises à jour disponibles" #: org.guido-berhoerster.code.package-update-indicator.desktop.in:6 msgid "system-software-update" msgstr "Mise à jour des logiciels du système" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:7 msgid "Update command" msgstr "Commande mise à jour" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:8 msgid "Command for installing updates." msgstr "Commande installation des mises à jour." #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:12 msgid "Refresh interval" msgstr "Intervalle de rafraîchissement" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:13 msgid "The interval in seconds for refreshing metadata." msgstr "L'intervalle en secondes pour rafraîchir les métadonnées." #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:18 msgid "Whether to use a mobile connection" msgstr "L'utilisation ou non d'une connexion mobile" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:19 msgid "If enabled, use a mobile connection refreshing the package cache." msgstr "" "Si cette option est activée, utilisez une connexion mobile pour rafraîchir " "le cache des paquets." #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:3 #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:4 #: package-update-indicator-prefs.c:43 msgid "Package Update Indicator Preferences" msgstr "Paramètres de l'Indicateur de Mises à Jour" #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:5 msgid "Edit the Preferences for Package Update Indicator" msgstr "Editer les paramètres de l'Indicateur de Mises à Jour" #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:6 msgid "updates;preferences;" msgstr "mises à jour;paramètres;" #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:7 msgid "preferences-other" msgstr "paramètres-autres" #: pui-about-dialog.ui:7 msgid "About Package Update Indicator" msgstr "Au sujet de Package Update Indicator" #: pui-about-dialog.ui:11 msgid "Copyright © 2018 Guido Berhörster" msgstr "Copyright © 2018 Guido Berhörster" #. Place your name here. #: pui-about-dialog.ui:15 msgid "Translator" msgstr "Traducteur" #: pui-application.c:77 msgid "Enable debugging messages" msgstr "Activer les messages de débogage" #: pui-application.c:79 msgid "Quit running instance of Package Update Indicator" msgstr "Quitter l'instance en cours d'exécution" #: pui-application.c:81 msgid "Print the version number and quit" msgstr "Affiche le numéro de version et quitte" #: pui-application.c:236 msgid "Up to Date" msgstr "À jour" #: pui-application.c:237 msgid "The system is up to date." msgstr "Le système est à jour." #: pui-application.c:240 msgid "Software Update" msgid_plural "Software Updates" msgstr[0] "Mise à jour d'un logiciel" msgstr[1] "Mises à jour de logiciels" #: pui-application.c:243 msgid "There is a software update available." msgstr "Une mise à jour est disponible." #: pui-application.c:246 #, c-format msgid "There are %u software updates available." msgstr "Il y a %u mises à jour disponibles." #: pui-application.c:251 msgid "Important Software Update" msgid_plural "Important Software Updates" msgstr[0] "Mise à jour importante d'un logiciel" msgstr[1] "Mises à jour importantes de logiciels" #: pui-application.c:254 msgid "There is an important software update available." msgstr "Une importante mise à jour du logiciel est disponible." #: pui-application.c:257 #, c-format msgid "There are %u important software updates available." msgstr "Il y a %u mises à jour disponibles." #: pui-application.c:261 #, c-format msgid "There are %u software updates available, one of them is important." msgstr "Il y a %u mises à jour disponibles, l'une d'elles est importante." #: pui-application.c:266 #, c-format msgid "There are %u software updates available, %u of them are important." msgstr "Il y a %u mises à jour disponibles, %u sont importantes." #: pui-application.c:274 msgid "Logout Required" msgstr "Déconnexion requise" #: pui-application.c:275 msgid "You need to log out and back in for the update to take effect." msgstr "Vous devez vous déconnecter pour que la mise à jour prenne effet." #: pui-application.c:279 msgid "Restart Required" msgstr "Redémarrage requis" #: pui-application.c:280 msgid "The computer has to be restarted for the updates to take effect." msgstr "L'ordinateur doit être redémarré pour que les mises à jour prennent effet." #: pui-application.c:328 msgid "Install Updates" msgstr "Installer les mises à jour" #: pui-application.c:438 msgid "Update notifications are not supported." msgstr "Les notifications de mise à jour ne sont pas prises en charge." #: pui-menu.ui:13 msgid "_Install updates" msgstr "_Installer les mises à jour" #: pui-menu.ui:22 msgid "_Preferences…" msgstr "_Préferences…" #: pui-menu.ui:31 msgid "_About…" msgstr "_À propos…" #: pui-prefs-window.ui:17 msgid "always" msgstr "toujours" #: pui-prefs-window.ui:22 msgid "every hour" msgstr "chaque heure" #: pui-prefs-window.ui:27 msgid "every 8 hours" msgstr "toutes les 8 heures" #: pui-prefs-window.ui:32 msgid "twice a day" msgstr "deux fois par jour" #: pui-prefs-window.ui:37 msgid "daily" msgstr "Chaque jour" #: pui-prefs-window.ui:42 msgid "weekly" msgstr "Chaque semaine" #: pui-prefs-window.ui:47 msgid "never" msgstr "jamais" #: pui-prefs-window.ui:76 msgid "_Refresh cache:" msgstr "_Rafraîchir le cache:" #: pui-prefs-window.ui:89 msgid "_Command for installing updates:" msgstr "_Commande d'installation des mises à jour:" #: pui-prefs-window.ui:130 msgid "Use _mobile connection" msgstr "Utiliser la connexion _mobile" package-update-indicator-7/po/ru.po010060000017500001750000000177701373761407600161560ustar00gbergber# English translations for package-update-indicator package. # Copyright (C) 2018 Guido Berhoerster # This file is distributed under the same license as the package-update-indicator package. # Guido Berhoerster , 2018. # Nikita Zlobin , 2020. # msgid "" msgstr "" "Project-Id-Version: package-update-indicator 1\n" "Report-Msgid-Bugs-To: guido+pui@berhoerster.name\n" "POT-Creation-Date: 2018-12-08 08:50+0000\n" "PO-Revision-Date: 2020-10-05 21:34+0500\n" "Last-Translator: Nikita Zlobin \n" "Language-Team: Russian <>\n" "Language: ru\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=3; plural=(n%10==1 && n%100!=11 ? 0 : n%10>=2 && n" "%10<=4 && (n%100<10 || n%100>=20) ? 1 : 2);\n" "X-Generator: Poedit 2.2.4\n" #: org.guido-berhoerster.code.package-update-indicator.desktop.in:3 #: org.guido-berhoerster.code.package-update-indicator.desktop.in:4 #: package-update-indicator.c:59 pui-application.c:489 msgid "Package Update Indicator" msgstr "Индикатор обновления пакетов" #: org.guido-berhoerster.code.package-update-indicator.desktop.in:5 #: pui-about-dialog.ui:12 msgid "Notify about available software updates" msgstr "Уведомлять о доступных обновлениях программ" #: org.guido-berhoerster.code.package-update-indicator.desktop.in:6 msgid "system-software-update" msgstr "system-software-update" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:7 msgid "Update command" msgstr "Команда обновления" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:8 msgid "Command for installing updates." msgstr "Команда установки обновлений." #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:12 msgid "Refresh interval" msgstr "Интервал обновлений" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:13 msgid "The interval in seconds for refreshing metadata." msgstr "Интервал обновления метаданных в секундах." #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:18 msgid "Whether to use a mobile connection" msgstr "Использовать мобильное соединение" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:19 msgid "If enabled, use a mobile connection refreshing the package cache." msgstr "Использовать мобильное соединение при обновлении кэша пакетов." #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:3 #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:4 #: package-update-indicator-prefs.c:43 msgid "Package Update Indicator Preferences" msgstr "Настройки индикатора обновлений" #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:5 msgid "Edit the Preferences for Package Update Indicator" msgstr "Изменить настройки индикатора обновлений" #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:6 msgid "updates;preferences;" msgstr "обновления;предпочтения;настройки;параметры;" #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:7 msgid "preferences-other" msgstr "preferences-other" #: pui-about-dialog.ui:7 msgid "About Package Update Indicator" msgstr "Об индикаторе обновления пакетов" #: pui-about-dialog.ui:11 msgid "Copyright © 2018 Guido Berhörster" msgstr "Копирайт © 2018 Guido Berhörster" #. Place your name here. #: pui-about-dialog.ui:15 msgid "Translator" msgstr "Никита Злобин" #: pui-application.c:73 msgid "Enable debugging messages" msgstr "Включить отладочные сообщения" #: pui-application.c:75 msgid "Quit running instance of Package Update Indicator" msgstr "Завершить работающий индикатор обновлений" #: pui-application.c:77 msgid "Print the version number and quit" msgstr "Показать версию и выйти" #: pui-application.c:232 msgid "Up to Date" msgstr "Нет обновлений" #: pui-application.c:233 msgid "The system is up to date." msgstr "Система обновлена." #: pui-application.c:236 msgid "Software Update" msgid_plural "Software Updates" msgstr[0] "Обновление программы" msgstr[1] "Обновления программ" msgstr[2] "Обновления программ" #: pui-application.c:239 msgid "There is a software update available." msgstr "Доступно обновление программы." #: pui-application.c:242 #, c-format msgid "There are %u software updates available." msgstr "Доступно %u обновлений программ." #: pui-application.c:247 msgid "Important Software Update" msgid_plural "Important Software Updates" msgstr[0] "Важное обновление программы" msgstr[1] "Важные обновления программ" msgstr[2] "Важные обновления программ" #: pui-application.c:250 msgid "There is an important software update available." msgstr "Доступно важное обновление программы." #: pui-application.c:253 #, c-format msgid "There are %u important software updates available." msgstr "Доступно %u важных обновлений программ." #: pui-application.c:257 #, c-format msgid "There are %u software updates available, one of them is important." msgstr "Доступно %u обновлений программ, одно из них важное." #: pui-application.c:262 #, c-format msgid "There are %u software updates available, %u of them are important." msgstr "Доступно %u обновлений программ, %u из них важные." #: pui-application.c:270 msgid "Logout Required" msgstr "Требуется завершение сеанса" #: pui-application.c:271 msgid "You need to log out and back in for the update to take effect." msgstr "" "Необходимо завершить сеанс и зайти обратно, чтобы обновление вступило в силу." #: pui-application.c:275 msgid "Restart Required" msgstr "Требуется перезагрузка" #: pui-application.c:276 msgid "The computer has to be restarted for the updates to take effect." msgstr "Необходимо перезагрузить компьютер, чтобы обновления вступили в силу." #: pui-application.c:324 msgid "Install Updates" msgstr "Установить обновления" #: pui-application.c:434 msgid "Update notifications are not supported." msgstr "Уведомления об обновлениях не поддерживаются." #: pui-menu.ui:13 msgid "_Install updates" msgstr "_Установить обновления" #: pui-menu.ui:22 msgid "_Preferences…" msgstr "_Настройки…" #: pui-menu.ui:31 msgid "_About…" msgstr "_О программе…" #: pui-prefs-window.ui:17 msgid "always" msgstr "всегда" #: pui-prefs-window.ui:22 msgid "every hour" msgstr "каждый час" #: pui-prefs-window.ui:27 msgid "every 8 hours" msgstr "каждые 8 часов" #: pui-prefs-window.ui:32 msgid "twice a day" msgstr "дважды в день" #: pui-prefs-window.ui:37 msgid "daily" msgstr "ежедневно" #: pui-prefs-window.ui:42 msgid "weekly" msgstr "еженедельно" #: pui-prefs-window.ui:47 msgid "never" msgstr "никогда" #: pui-prefs-window.ui:76 msgid "_Refresh cache:" msgstr "Обновить _кэш:" #: pui-prefs-window.ui:89 msgid "_Command for installing updates:" msgstr "_Команда для установки обновлений:" #: pui-prefs-window.ui:130 msgid "Use _mobile connection" msgstr "Использовать _мобильное соединение" package-update-indicator-7/po/it.po010060000017500001750000000154171371774512700161400ustar00gbergber# Italian translations for package-update-indicator package. # Copyright (C) 2020 Guido Berhoerster # This file is distributed under the same license as the package-update-indicator package. # Francesco Parisi , 2020. # msgid "" msgstr "" "Project-Id-Version: package-update-indicator 5\n" "Report-Msgid-Bugs-To: guido+pui@berhoerster.name\n" "POT-Creation-Date: 2020-08-21 12:43+0000\n" "PO-Revision-Date: 2020-08-20 18:42+0200\n" "Last-Translator: Francesco Parisi \n" "Language-Team: none\n" "Language: it\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=(n != 1);\n" "X-Generator: Poedit 2.4.1\n" #: org.guido-berhoerster.code.package-update-indicator.desktop.in:3 #: org.guido-berhoerster.code.package-update-indicator.desktop.in:4 #: package-update-indicator.c:59 pui-application.c:493 msgid "Package Update Indicator" msgstr "Package Update Indicator" #: org.guido-berhoerster.code.package-update-indicator.desktop.in:5 #: pui-about-dialog.ui:12 msgid "Notify about available software updates" msgstr "Notifica sulla disponibilità di aggiornamenti software" #: org.guido-berhoerster.code.package-update-indicator.desktop.in:6 msgid "system-software-update" msgstr "system-software-update" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:7 msgid "Update command" msgstr "Comando per l'aggiornamento" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:8 msgid "Command for installing updates." msgstr "Comando per installare gli aggiornamenti." #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:12 msgid "Refresh interval" msgstr "Intervallo di refresh" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:13 msgid "The interval in seconds for refreshing metadata." msgstr "L'intervallo in secondi del refresh dei metadata." #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:18 msgid "Whether to use a mobile connection" msgstr "Se utilizzare una connessione mobile" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:19 msgid "If enabled, use a mobile connection refreshing the package cache." msgstr "" "Se abilitato, usa una connessione mobile per aggiornare la cache dei " "pacchetti." #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:3 #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:4 #: package-update-indicator-prefs.c:43 msgid "Package Update Indicator Preferences" msgstr "Preferenze di Package Update Indicator" #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:5 msgid "Edit the Preferences for Package Update Indicator" msgstr "Modifica le Preferenze per Package Update Indicator" #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:6 msgid "updates;preferences;" msgstr "aggiornamenti;preferenze;" #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:7 msgid "preferences-other" msgstr "preferenze-altro" #: pui-about-dialog.ui:7 msgid "About Package Update Indicator" msgstr "Informazioni su Package Update Indicator" #: pui-about-dialog.ui:11 msgid "Copyright © 2018 Guido Berhörster" msgstr "Copyright © 2018 Guido Berhörster" #. Place your name here. #: pui-about-dialog.ui:15 msgid "Translator" msgstr "Francesco Parisi" #: pui-application.c:77 msgid "Enable debugging messages" msgstr "Abilita messaggi di debugging" #: pui-application.c:79 msgid "Quit running instance of Package Update Indicator" msgstr "Esci dall'istanza in esecuzione di Package Update Indicator" #: pui-application.c:81 msgid "Print the version number and quit" msgstr "Stampa la versione ed esce" #: pui-application.c:236 msgid "Up to Date" msgstr "Aggiornato" #: pui-application.c:237 msgid "The system is up to date." msgstr "Il sistema è aggiornato." #: pui-application.c:240 msgid "Software Update" msgid_plural "Software Updates" msgstr[0] "Aggiornamento Software" msgstr[1] "Aggiornamenti Software" #: pui-application.c:243 msgid "There is a software update available." msgstr "E' disponibile un aggiornamento software." #: pui-application.c:246 #, c-format msgid "There are %u software updates available." msgstr "Sono disponibili %u aggiornamenti software." #: pui-application.c:251 msgid "Important Software Update" msgid_plural "Important Software Updates" msgstr[0] "Aggiornamento Software Importante" msgstr[1] "Aggiornamenti Software Importanti" #: pui-application.c:254 msgid "There is an important software update available." msgstr "E' disponibile un importante aggiornamento software." #: pui-application.c:257 #, c-format msgid "There are %u important software updates available." msgstr "Sono disponibili %u aggiornamenti importanti disponibili." #: pui-application.c:261 #, c-format msgid "There are %u software updates available, one of them is important." msgstr "Sono disponibili %u aggiornamenti disponibili, di cui uno importante." #: pui-application.c:266 #, c-format msgid "There are %u software updates available, %u of them are important." msgstr "" "Sono disponibili %u aggiornamenti software disponibili, di cui %u importanti." #: pui-application.c:274 msgid "Logout Required" msgstr "Richiesta Uscita" #: pui-application.c:275 msgid "You need to log out and back in for the update to take effect." msgstr "Devi uscire e rientrare affinché l'aggiornamento abbia effetto." #: pui-application.c:279 msgid "Restart Required" msgstr "Riavvio Richiesto" #: pui-application.c:280 msgid "The computer has to be restarted for the updates to take effect." msgstr "" "Il computer deve essere riavviato affinché gli aggiornamenti abbiano effetto." #: pui-application.c:328 msgid "Install Updates" msgstr "Installa Aggiornamenti" #: pui-application.c:438 msgid "Update notifications are not supported." msgstr "Notifiche aggiornamenti non supportate." #: pui-menu.ui:13 msgid "_Install updates" msgstr "_Installa aggiornamenti" #: pui-menu.ui:22 msgid "_Preferences…" msgstr "_Preferenze…" #: pui-menu.ui:31 msgid "_About…" msgstr "_Informazioni…" #: pui-prefs-window.ui:17 msgid "always" msgstr "sempre" #: pui-prefs-window.ui:22 msgid "every hour" msgstr "ogni ora" #: pui-prefs-window.ui:27 msgid "every 8 hours" msgstr "ogni 8 ore" #: pui-prefs-window.ui:32 msgid "twice a day" msgstr "due volte al giorno" #: pui-prefs-window.ui:37 msgid "daily" msgstr "quotidianamente" #: pui-prefs-window.ui:42 msgid "weekly" msgstr "settimanalmente" #: pui-prefs-window.ui:47 msgid "never" msgstr "mai" #: pui-prefs-window.ui:76 msgid "_Refresh cache:" msgstr "_Aggiorna la cache:" #: pui-prefs-window.ui:89 msgid "_Command for installing updates:" msgstr "_Comando per installare aggiornamenti:" #: pui-prefs-window.ui:130 msgid "Use _mobile connection" msgstr "Usa connessione _mobile" package-update-indicator-7/po/da.po010060000017500001750000000151071355501247200160720ustar00gbergber# Danish translation for Package Update Indicator # Copyright (C) YEAR Guido Berhoerster # This file is distributed under the same license as the package-update-indicator package. # scootergrisen, 2019. msgid "" msgstr "" "Project-Id-Version: package-update-indicator 5\n" "Report-Msgid-Bugs-To: guido+pui@berhoerster.name\n" "POT-Creation-Date: 2019-10-07 20:44+0200\n" "PO-Revision-Date: 2019-10-24 00:00+0200\n" "Last-Translator: scootergrisen\n" "Language-Team: Danish\n" "Language: da\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=(n != 1);\n" #: org.guido-berhoerster.code.package-update-indicator.desktop.in:3 #: org.guido-berhoerster.code.package-update-indicator.desktop.in:4 #: package-update-indicator.c:59 pui-application.c:493 msgid "Package Update Indicator" msgstr "Pakkeopdateringsindikator" #: org.guido-berhoerster.code.package-update-indicator.desktop.in:5 #: pui-about-dialog.ui:12 msgid "Notify about available software updates" msgstr "Underret om tilgængelige softwareopdateringer" #: org.guido-berhoerster.code.package-update-indicator.desktop.in:6 msgid "system-software-update" msgstr "system-software-update" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:7 msgid "Update command" msgstr "Opdateringskommando" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:8 msgid "Command for installing updates." msgstr "Kommando til at installere opdateringer." #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:12 msgid "Refresh interval" msgstr "Opdateringsinterval" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:13 msgid "The interval in seconds for refreshing metadata." msgstr "Intervaller, i sekunder, til opdatering af metadata." #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:18 msgid "Whether to use a mobile connection" msgstr "Om der skal bruges en mobil forbindelse" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:19 msgid "If enabled, use a mobile connection refreshing the package cache." msgstr "" "Hvis den aktiveres, så bruges en mobil forbindelse til opdatering af " "pakkemellemlageret." #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:3 #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:4 #: package-update-indicator-prefs.c:43 msgid "Package Update Indicator Preferences" msgstr "Præferencer for pakkeopdateringsindikator" #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:5 msgid "Edit the Preferences for Package Update Indicator" msgstr "Rediger præferencerne til pakkeopdateringsindikator" #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:6 msgid "updates;preferences;" msgstr "opdateringer;præferencer;" #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:7 msgid "preferences-other" msgstr "preferences-other" #: pui-about-dialog.ui:7 msgid "About Package Update Indicator" msgstr "Om Pakkeopdateringsindikator" #: pui-about-dialog.ui:11 msgid "Copyright © 2018 Guido Berhörster" msgstr "Ophavsret © 2018 Guido Berhörster" #. Place your name here. #: pui-about-dialog.ui:15 msgid "Translator" msgstr "scootergrisen" #: pui-application.c:77 msgid "Enable debugging messages" msgstr "Aktivér fejlretningsmeddelelser" #: pui-application.c:79 msgid "Quit running instance of Package Update Indicator" msgstr "Afslut den kørende instans af pakkeopdateringsindikator" #: pui-application.c:81 msgid "Print the version number and quit" msgstr "Udskriv versionsnummeret og afslut" #: pui-application.c:236 msgid "Up to Date" msgstr "Fuldt opdateret" #: pui-application.c:237 msgid "The system is up to date." msgstr "Systemet er fuldt opdateret." #: pui-application.c:240 msgid "Software Update" msgid_plural "Software Updates" msgstr[0] "Softwareopdatering" msgstr[1] "Softwareopdateringer" #: pui-application.c:243 msgid "There is a software update available." msgstr "Der findes en softwareopdatering." #: pui-application.c:246 #, c-format msgid "There are %u software updates available." msgstr "Der findes %u softwareopdateringer." #: pui-application.c:251 msgid "Important Software Update" msgid_plural "Important Software Updates" msgstr[0] "Vigtig softwareopdatering" msgstr[1] "Vigtige softwareopdateringer" #: pui-application.c:254 msgid "There is an important software update available." msgstr "Der findes en vigtig softwareopdatering." #: pui-application.c:257 #, c-format msgid "There are %u important software updates available." msgstr "Der findes %u vigtige softwareopdateringer." #: pui-application.c:261 #, c-format msgid "There are %u software updates available, one of them is important." msgstr "Der findes %u softwareopdateringer hvoraf en er vigtig." #: pui-application.c:266 #, c-format msgid "There are %u software updates available, %u of them are important." msgstr "Der findes %u softwareopdateringer hvoraf %u er vigtige." #: pui-application.c:274 msgid "Logout Required" msgstr "Kræver udlogning" #: pui-application.c:275 msgid "You need to log out and back in for the update to take effect." msgstr "Du skal logge ud og ind igen før opdateringen træder i kraft." #: pui-application.c:279 msgid "Restart Required" msgstr "Kræver genstart" #: pui-application.c:280 msgid "The computer has to be restarted for the updates to take effect." msgstr "Computeren skal genstartes før opdateringerne træder i kraft." #: pui-application.c:328 msgid "Install Updates" msgstr "Installer opdateringer" #: pui-application.c:438 msgid "Update notifications are not supported." msgstr "Opdateringsunderretninger understøttes ikke." #: pui-menu.ui:13 msgid "_Install updates" msgstr "_Installer opdateringer" #: pui-menu.ui:22 msgid "_Preferences…" msgstr "_Præferencer …" #: pui-menu.ui:31 msgid "_About…" msgstr "_Om …" #: pui-prefs-window.ui:17 msgid "always" msgstr "altid" #: pui-prefs-window.ui:22 msgid "every hour" msgstr "hver time" #: pui-prefs-window.ui:27 msgid "every 8 hours" msgstr "hver 8. time" #: pui-prefs-window.ui:32 msgid "twice a day" msgstr "to gange om dagen" #: pui-prefs-window.ui:37 msgid "daily" msgstr "dagligt" #: pui-prefs-window.ui:42 msgid "weekly" msgstr "ugentligt" #: pui-prefs-window.ui:47 msgid "never" msgstr "aldrig" #: pui-prefs-window.ui:76 msgid "_Refresh cache:" msgstr "_Opdatering af mellemlager:" #: pui-prefs-window.ui:89 msgid "_Command for installing updates:" msgstr "_Kommando til at installere opdateringer:" #: pui-prefs-window.ui:130 msgid "Use _mobile connection" msgstr "Brug _mobil forbindelse" package-update-indicator-7/po/POTFILES.in010064400017500001750000000006421331765667600167510ustar00gbergberorg.guido-berhoerster.code.package-update-indicator.desktop.in org.guido-berhoerster.code.package-update-indicator.gschema.xml org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in package-update-indicator-prefs.c package-update-indicator.c pui-about-dialog.ui pui-application.c pui-backend.c pui-get-updates.c pui-menu.ui pui-prefs-application.c pui-prefs-window.ui pui-settings.c pui-types.c.in package-update-indicator-7/po/de.po010064400017500001750000000155541351601344000161050ustar00gbergber# German translations for package-update-indicator package. # Copyright (C) 2018 Guido Berhoerster # This file is distributed under the same license as the package-update-indicator package. # Guido Berhoerster , 2018. # msgid "" msgstr "" "Project-Id-Version: package-update-indicator 1\n" "Report-Msgid-Bugs-To: guido+pui@berhoerster.name\n" "POT-Creation-Date: 2018-12-08 08:50+0000\n" "PO-Revision-Date: 2018-07-06 12:10+0000\n" "Last-Translator: Guido Berhoerster \n" "Language-Team: none\n" "Language: de\n" "MIME-Version: 1.0\n" "Content-Type: text/plain; charset=UTF-8\n" "Content-Transfer-Encoding: 8bit\n" "Plural-Forms: nplurals=2; plural=(n != 1);\n" #: org.guido-berhoerster.code.package-update-indicator.desktop.in:3 #: org.guido-berhoerster.code.package-update-indicator.desktop.in:4 #: package-update-indicator.c:59 pui-application.c:489 msgid "Package Update Indicator" msgstr "Paketaktualisierungsanzeige" #: org.guido-berhoerster.code.package-update-indicator.desktop.in:5 #: pui-about-dialog.ui:12 msgid "Notify about available software updates" msgstr "Benachrichtigung über verfügbare Softwareaktualisierungen" #: org.guido-berhoerster.code.package-update-indicator.desktop.in:6 msgid "system-software-update" msgstr "" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:7 msgid "Update command" msgstr "Aktualisierungsbefehl" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:8 msgid "Command for installing updates." msgstr "Befehl zu Installieren von Aktualisierungen." #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:12 msgid "Refresh interval" msgstr "Aktualisierungsintervall" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:13 msgid "The interval in seconds for refreshing metadata." msgstr "Das Aktualisierungsintervall für Metadaten." #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:18 msgid "Whether to use a mobile connection" msgstr "Ob eine Mobilfunkverbindung benutzt werden kann" #: org.guido-berhoerster.code.package-update-indicator.gschema.xml:19 msgid "If enabled, use a mobile connection refreshing the package cache." msgstr "" "Wenn aktiviert, wird der Paket-Cache über eine mobile Verbindung " "aktualisiert." #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:3 #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:4 #: package-update-indicator-prefs.c:43 msgid "Package Update Indicator Preferences" msgstr "Einstellungen der Paketaktualisierungsanzeige" #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:5 msgid "Edit the Preferences for Package Update Indicator" msgstr "Bearbeite Einstellungen der Paketaktualisierungsanzeige" #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:6 msgid "updates;preferences;" msgstr "Aktualisierungen;Updates;Einstellungen;" #: org.guido-berhoerster.code.package-update-indicator.preferences.desktop.in:7 msgid "preferences-other" msgstr "" #: pui-about-dialog.ui:7 msgid "About Package Update Indicator" msgstr "Über Paketaktualisierungsanzeige" #: pui-about-dialog.ui:11 msgid "Copyright © 2018 Guido Berhörster" msgstr "Copyright © 2018 Guido Berhörster" #. Place your name here. #: pui-about-dialog.ui:15 msgid "Translator" msgstr "Guido Berhörster" #: pui-application.c:73 msgid "Enable debugging messages" msgstr "Debugging-Nachrichten aktivieren" #: pui-application.c:75 msgid "Quit running instance of Package Update Indicator" msgstr "Beende laufende Instanz der Paketaktualisierungsanzeige" #: pui-application.c:77 msgid "Print the version number and quit" msgstr "Versionsnummer zeigen und beenden" #: pui-application.c:232 msgid "Up to Date" msgstr "Auf dem neuesten Stand" #: pui-application.c:233 msgid "The system is up to date." msgstr "Das System ist auf dem neuesten Stand" #: pui-application.c:236 msgid "Software Update" msgid_plural "Software Updates" msgstr[0] "Softwareaktualisierung" msgstr[1] "Softwareaktualisierungen" #: pui-application.c:239 msgid "There is a software update available." msgstr "Es ist eine Softwareaktualisierung verfügbar." #: pui-application.c:242 #, c-format msgid "There are %u software updates available." msgstr "Es sind %u Softwareaktualisierungen verfügbar." #: pui-application.c:247 msgid "Important Software Update" msgid_plural "Important Software Updates" msgstr[0] "Wichtige Softwareaktualisierung" msgstr[1] "Wichtige Softwareaktualisierungen" #: pui-application.c:250 msgid "There is an important software update available." msgstr "Es ist eine wichtige Softwareaktualisierung verfügbar." #: pui-application.c:253 #, c-format msgid "There are %u important software updates available." msgstr "Es sind %u wichtige Softwareaktualisierungen verfügbar." #: pui-application.c:257 #, c-format msgid "There are %u software updates available, one of them is important." msgstr "Es sind %u Softwareaktualisierungen verfügbar, eine davon ist wichtig." #: pui-application.c:262 #, c-format msgid "There are %u software updates available, %u of them are important." msgstr "Es sind %u Softwareaktualisierungen verfügbar, %u davon sind wichtig." #: pui-application.c:270 msgid "Logout Required" msgstr "Abmeldung erforderlich" #: pui-application.c:271 msgid "You need to log out and back in for the update to take effect." msgstr "" "Sie müssen sich aus- und wieder einloggen, damit die Aktualisierung wirksam wird." #: pui-application.c:275 msgid "Restart Required" msgstr "Neutstart Erforderlich" #: pui-application.c:276 msgid "The computer has to be restarted for the updates to take effect." msgstr "" "Der Computer muss neu gestarte werden damit die Aktualisierungen wirksam werden." #: pui-application.c:324 msgid "Install Updates" msgstr "Installiere Aktualisierungen" #: pui-application.c:434 msgid "Update notifications are not supported." msgstr "Aktualisierungsbenachrichtigungen werden nicht unterstützt." #: pui-menu.ui:13 msgid "_Install updates" msgstr "_Installiere Aktualisierungen" #: pui-menu.ui:22 msgid "_Preferences…" msgstr "_Einstellungen…" #: pui-menu.ui:31 msgid "_About…" msgstr "Ü_ber…" #: pui-prefs-window.ui:17 msgid "always" msgstr "immer" #: pui-prefs-window.ui:22 msgid "every hour" msgstr "einmal die Stunde" #: pui-prefs-window.ui:27 msgid "every 8 hours" msgstr "alle 8 Stunden" #: pui-prefs-window.ui:32 msgid "twice a day" msgstr "zweimal täglich" #: pui-prefs-window.ui:37 msgid "daily" msgstr "täglich" #: pui-prefs-window.ui:42 msgid "weekly" msgstr "wöchentlich" #: pui-prefs-window.ui:47 msgid "never" msgstr "nie" #: pui-prefs-window.ui:76 msgid "_Refresh cache:" msgstr "Cache _aktualisieren:" #: pui-prefs-window.ui:89 msgid "_Command for installing updates:" msgstr "_Befehl zum Installieren von Aktualisierungen:" #: pui-prefs-window.ui:130 msgid "Use _mobile connection" msgstr "Benutze _Mobilfunkverbindung" package-update-indicator-7/pui-settings.h010064400017500001750000000024121331741424000173320ustar00gbergber/* * Copyright (C) 2018 Guido Berhoerster * * Permission is hereby granted, free of charge, to any person obtaining * a copy of this software and associated documentation files (the * "Software"), to deal in the Software without restriction, including * without limitation the rights to use, copy, modify, merge, publish, * distribute, sublicense, and/or sell copies of the Software, and to * permit persons to whom the Software is furnished to do so, subject to * the following conditions: * * The above copyright notice and this permission notice shall be included * in all copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. * IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY * CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ #ifndef PUI_SETTINGS_H #define PUI_SETTINGS_H #include GSettings * pui_settings_new(void); #endif /* !PUI_SETTINGS_H */ package-update-indicator-7/README010064400017500001750000000121771332111143300154100ustar00gbergberpackage-update-indicator ======================== Description ----------- The package-update-indicator utility regularly checks for software updates and notifies the user about available updates using desktop notifications and either a status notifier icon or a system tray icon. Build Instructions ------------------ package-update-indicator requires a POSIX:2004 compatible operating system, it has been tested to work on Linux distributions. The following tools and shared libraries are required to build package-update-indicator: - GNU make 3.81 or later - pkg-config - GNU gettext 0.19 or later - GNU or BSD install - GLib version 2.48 or later - GTK+ version 3.18 or later - libappindicator 12.10.0 or later - PackageKit-glib2 0.8.17 or later - upower-glib 0.99.0 or later - polkit 0.105 or later - the xsltproc tool from libxml2 Before building package-update-indicator check the commented macros in the Makefile for any macros you may need to override depending on the used toolchain and operating system. By default the "update-command" setting is empty which means users will not be offered to install updates from a notification or the indicator menu. Distribution vendors may override this or any other default setting by installing a vendor override file alongside the schema file. An example for is distributed with package-update-indicator, see the file "examples/10_vendor_update_command.gschema.override.example". For details on how to install a vendor override file see the manual page for glib-compile-schemas. By default, all files will be installed under the "/usr/local" directory, a different installation path prefix can be set via the `prefix` macro. In addition, a second path prefix can be specified via the `DESTDIR` macro which will be prepended to any path, incuding the `prefix` macro path prefix. In contrast to `prefix`, the path specified via the `DESTDIR` macro will only be prepended to paths during installation and not be used for constructing internal paths. The following instructions assume that `make` is GNU make, on some platforms it may be installed under a different name or a non-default path. In order to start the build process run `make all`. After a successful build, run `make install` to install the program, any associated data files and the documentation. Previously built binaries, object files, generated data files and documentation can be removed by running `make clean`, any additional, generated files which are not removed by the `clean` target can be removed by running `make clobber`. Contact ------- Please send any feedback, translations or bug reports via email to . Bug Reports ----------- When sending bug reports, please always mention the exact version of package-update-indicator with which the issue occurs as well as the version of the operating system you are using and make sure that you provide sufficient information to reproduce the issue and include any input, output, any error messages. In case of build issues, please also specify the implementations and versions of the tools and shared libraries used to build the program, in particular the compiler. In case of crashes, please generate a stack trace with a suitable debugger such as gdb, lldb, dbx, or debug after a crash has occurred either by examining the resulting core file or by running the program from the debugger and attach it to the bug report. In order to generate a meaningful stack trace the program as well as any dynamically linked libraries need to be built with debugging information, see the documentation of the used compiler for the required compiler flags. If any of the dynamically linked shared libraries do not contain debugging information, please either install debugging information for these libraries using mechanisms provided by your operating system or rebuild the libraries accordingly. Please refer to the documentation of the debugger for detailed instructions on generating backtraces. License ------- Except otherwise noted, all files are Copyright (C) 2018 Guido Berhoerster and distributed under the following license terms: Copyright (C) 2018 Guido Berhoerster Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. package-update-indicator-7/examples004075500017500001750000000000001332111120300162555ustar00gbergberpackage-update-indicator-7/examples/10_vendor_update_command.gschema.override010064400017500001750000000001421332105754300263520ustar00gbergber[org.guido-berhoerster.code.package-update-indicator] update-command='/usr/bin/gpk-update-viewer'