[seahorse] pgp: Make PgpBackend responsible for handling keyservers
- From: Niels De Graef <nielsdg src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [seahorse] pgp: Make PgpBackend responsible for handling keyservers
- Date: Fri, 19 Feb 2021 18:59:32 +0000 (UTC)
commit bc26f2bf5cb3035f0f94c412f3e675d2071b1ed4
Author: Anukul Sangwan <anukulsangwan icloud com>
Date: Fri Feb 19 18:59:31 2021 +0000
pgp: Make PgpBackend responsible for handling keyservers
That way, we don't need to fiddle around with the `GSettings` keys (and
its special values format) in several places, and we can just expose
what we need. With a bit of luck, it allows us to also get rid of the
`SeahorsePgpSettings` singleton which is strewn around in several
places.
common/config.vapi | 11 +-
common/meson.build | 3 +-
common/pgp-settings.vala | 71 ++++++++++---
common/prefs-keyservers.vala | 138 ++++++++++++++++++++++++
common/prefs.vala | 205 +-----------------------------------
common/seahorse-prefs-keyservers.ui | 137 ++++++++++++++++++++++++
common/seahorse-prefs.ui | 152 --------------------------
data/seahorse.gresource.xml | 1 +
pgp/seahorse-discovery.c | 11 +-
pgp/seahorse-pgp-backend.c | 74 +++++++------
pgp/seahorse-pgp-backend.h | 6 +-
po/POTFILES.in | 2 +
12 files changed, 394 insertions(+), 417 deletions(-)
---
diff --git a/common/config.vapi b/common/config.vapi
index f408170e..37017d1b 100644
--- a/common/config.vapi
+++ b/common/config.vapi
@@ -47,12 +47,17 @@ namespace Progress {
}
[CCode (cheader_filename = "pgp/seahorse-pgp-backend.h")]
-namespace Pgp.Backend {
- public void initialize();
+public class Pgp.Backend : GLib.Object, Gcr.Collection, Place {
+ public static void initialize();
+ public static unowned Pgp.Backend get();
+
+ public unowned GLib.ListModel get_remotes();
+ public void add_remote(string uri, bool persist);
+ public void remove_remote(string uri);
}
[CCode (cheader_filename = "pgp/seahorse-server-source.h")]
-public class ServerSource {
+public class ServerSource : GLib.Object, Gcr.Collection, Place {
}
#if WITH_LDAP
diff --git a/common/meson.build b/common/meson.build
index 849af26b..0b520dcd 100644
--- a/common/meson.build
+++ b/common/meson.build
@@ -36,10 +36,11 @@ common_deps = [
]
common_vala_args = [
+ '--gresources', resources_xml,
]
if get_option('keyservers-support')
- common_sources += 'keyserver-control.vala'
+ common_sources += ['keyserver-control.vala', 'prefs-keyservers.vala']
common_vala_args += [ '-D', 'WITH_KEYSERVER' ]
endif
diff --git a/common/pgp-settings.vala b/common/pgp-settings.vala
index ef07a6e7..0ae94e46 100644
--- a/common/pgp-settings.vala
+++ b/common/pgp-settings.vala
@@ -60,32 +60,71 @@ public class Seahorse.PgpSettings : GLib.Settings {
ServerCategory.init();
}
- private static PgpSettings? _instance = null;
- public static PgpSettings instance() {
- if (_instance == null)
- _instance = new PgpSettings();
- return _instance;
- }
+ private static PgpSettings? _instance = null;
+ public static PgpSettings instance() {
+ if (_instance == null)
+ _instance = new PgpSettings();
+ return _instance;
+ }
[CCode (array_null_terminated = true, array_length = false)]
public string[] get_uris() {
- // The values are 'uri name', remove the name part
string[] uris = {};
- foreach (string server in this.keyservers)
- uris += server.strip().split(" ", 2)[0];
-
+ foreach (unowned string server in this.keyservers)
+ uris += get_uri_for_keyserver_entry (server);
return uris;
}
[CCode (array_null_terminated = true, array_length = false)]
public string[] get_names() {
string[] names = {};
- foreach (string server in this.keyservers) {
- // The values are 'uri' or 'uri name', remove the name part if there
- string[] split = server._strip().split(" ", 2);
- names += (split.length == 1)? split[0] : split[1];
- }
-
+ foreach (unowned string server in this.keyservers)
+ names += get_name_for_keyserver_entry (server);
return names;
}
+
+ public void add_keyserver(string uri, string? name) {
+ string[] servers = {};
+
+ if (uri in this.keyservers)
+ return;
+
+ debug("Adding key server URL '%s'", uri);
+ foreach (unowned string keyserver in this.keyservers)
+ servers += keyserver;
+
+ if (name != null)
+ servers += "%s %s".printf(uri, name);
+ else
+ servers += uri;
+ servers += null;
+
+ this.keyservers = servers;
+ }
+
+ public void remove_keyserver(string uri) {
+ string[] servers = {};
+
+ if (!(uri in this.keyservers))
+ return;
+
+ debug("Removing key server URL '%s'", uri);
+ foreach (unowned string keyserver in this.keyservers)
+ if (get_uri_for_keyserver_entry(keyserver) != uri)
+ servers += keyserver;
+ servers += null;
+
+ this.keyservers = servers;
+ }
+
+ private string? get_uri_for_keyserver_entry(string keyserver) {
+ // The values are "uri" or "uri name", so remove the name part (if any)
+ return keyserver.strip().split(" ", 2)[0];
+ }
+
+ private string? get_name_for_keyserver_entry(string keyserver) {
+ // The values are "uri" or "uri name", so fallback to uri if no name
+ string[] split = keyserver.strip().split(" ", 2);
+ return (split.length == 1)? split[0] : split[1];
+ }
}
diff --git a/common/prefs-keyservers.vala b/common/prefs-keyservers.vala
new file mode 100644
index 00000000..89d101b8
--- /dev/null
+++ b/common/prefs-keyservers.vala
@@ -0,0 +1,138 @@
+/*
+ * Seahorse
+ *
+ * Copyright (C) 2004-2005 Stefan Walter
+ * Copyright (C) 2017 Niels De Graef
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
+ * See the GNU General Public License for more details.
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, see
+ * <http://www.gnu.org/licenses/>.
+ */
+
+[GtkTemplate (ui = "/org/gnome/Seahorse/seahorse-prefs-keyservers.ui")]
+public class Seahorse.PrefsKeyservers : Gtk.Box {
+
+ [GtkChild]
+ public unowned Gtk.Grid keyserver_tab;
+ [GtkChild]
+ private unowned Gtk.ListBox keyservers_list;
+ [GtkChild]
+ private unowned Gtk.Box keyserver_publish;
+ [GtkChild]
+ private unowned Gtk.Label keyserver_publish_to_label;
+ [GtkChild]
+ private unowned Gtk.CheckButton auto_retrieve;
+ [GtkChild]
+ private unowned Gtk.CheckButton auto_sync;
+
+ public PrefsKeyservers(Gtk.Window? parent) {
+ var model = Pgp.Backend.get().get_remotes();
+ this.keyservers_list.bind_model(model, (item) => {
+ return new KeyServerRow(item as ServerSource);
+ });
+
+ KeyserverControl skc = new KeyserverControl("server-publish-to",
+ _("None: Don’t publish keys"));
+ this.keyserver_publish.add(skc);
+ this.keyserver_publish.show_all();
+
+ this.keyserver_publish_to_label.set_mnemonic_widget(skc);
+
+ AppSettings.instance().bind("server-auto-retrieve", this.auto_retrieve, "active",
+ SettingsBindFlags.DEFAULT);
+ AppSettings.instance().bind("server-auto-publish", this.auto_sync, "active",
+ SettingsBindFlags.DEFAULT);
+ }
+
+ private class KeyServerRow : Gtk.ListBoxRow {
+
+ private unowned ServerSource server;
+ private Gtk.Label label;
+ private Gtk.Entry entry;
+
+ public KeyServerRow(ServerSource server) {
+ this.server = server;
+
+ var box = new Gtk.Box(Gtk.Orientation.HORIZONTAL, 2);
+ box.margin = 6;
+ add(box);
+
+ this.label = new Gtk.Label(server.uri);
+ box.pack_start(this.label, false);
+
+ this.entry = new Gtk.Entry();
+ this.entry.set_no_show_all(true);
+ this.entry.hide();
+ this.entry.activate.connect(on_entry_activated);
+ box.pack_start(this.entry);
+
+ var remove_button = new Gtk.Button.from_icon_name("list-remove-symbolic");
+ remove_button.get_style_context().add_class("flat");
+ remove_button.clicked.connect(on_remove_button_clicked);
+ box.pack_end(remove_button, false);
+
+ var edit_button = new Gtk.Button.from_icon_name("document-edit-symbolic");
+ edit_button.get_style_context().add_class("flat");
+ edit_button.clicked.connect(on_edit_button_clicked);
+ box.pack_end(edit_button, false);
+
+ show_all();
+ }
+
+ private void on_edit_button_clicked(Gtk.Button edit_button) {
+ this.label.hide();
+ this.entry.set_text(this.label.get_text());
+ this.entry.show_now();
+ this.entry.grab_focus();
+ }
+
+ private void on_remove_button_clicked(Gtk.Button remove_button) {
+ Pgp.Backend.get().remove_remote(this.server.uri);
+ }
+
+ private void on_entry_activated(Gtk.Entry entry) {
+ var uri = this.entry.get_text();
+
+ // If nothing changed, just go away
+ if (uri == server.uri) {
+ this.entry.hide();
+ return;
+ }
+
+ // Before doing anything, make sure we have a valid thing going on
+ if (!ServerCategory.is_valid_uri(uri)) {
+ this.entry.get_style_context().add_class("error");
+ return;
+ }
+
+ // We don't really have a way of ediing a remote, so simulate an edit
+ // by adding and removing one
+ Pgp.Backend.get().remove_remote(this.server.uri);
+ Pgp.Backend.get().add_remote(uri, true);
+ this.entry.hide();
+ }
+ }
+
+ [GtkCallback]
+ private void on_add_button_clicked(Gtk.Button button) {
+ AddKeyserverDialog dialog = new AddKeyserverDialog(get_toplevel() as Gtk.Window);
+
+ if (dialog.run() == Gtk.ResponseType.OK) {
+ string? result = dialog.calculate_keyserver_uri();
+
+ if (result != null)
+ Pgp.Backend.get().add_remote(result, true);
+ }
+
+ dialog.destroy();
+ }
+}
diff --git a/common/prefs.vala b/common/prefs.vala
index bab3a714..e1b681ab 100644
--- a/common/prefs.vala
+++ b/common/prefs.vala
@@ -20,17 +20,7 @@
public class Seahorse.Prefs : Gtk.Dialog {
- private bool updating_model;
-
private Gtk.Notebook notebook;
- private Gtk.Grid keyserver_tab;
- private Gtk.TreeView keyservers;
- private Gtk.Box keyserver_publish;
- private Gtk.Label keyserver_publish_to_label;
- private Gtk.Button keyserver_remove;
- private Gtk.Button keyserver_add;
- private Gtk.CheckButton auto_retrieve;
- private Gtk.CheckButton auto_sync;
/**
* Create a new preferences window.
@@ -43,9 +33,8 @@ public class Seahorse.Prefs : Gtk.Dialog {
transient_for: parent,
modal: true
);
- this.updating_model = false;
- Gtk.Builder builder = new Gtk.Builder();
+ var builder = new Gtk.Builder();
try {
string path = "/org/gnome/Seahorse/seahorse-prefs.ui";
builder.add_from_resource(path);
@@ -56,22 +45,11 @@ public class Seahorse.Prefs : Gtk.Dialog {
get_content_area().border_width = 0;
get_content_area().add(content);
this.notebook = (Gtk.Notebook) builder.get_object("notebook");
- this.keyserver_tab = (Gtk.Grid) builder.get_object("keyserver-tab");
- this.keyservers = (Gtk.TreeView) builder.get_object("keyservers");
- this.keyserver_publish = (Gtk.Box) builder.get_object("keyserver-publish");
- this.keyserver_publish_to_label = (Gtk.Label) builder.get_object("keyserver-publish-to-label");
- this.keyserver_remove = (Gtk.Button) builder.get_object("keyserver_remove");
- this.keyserver_add = (Gtk.Button) builder.get_object("keyserver_add");
- this.auto_retrieve = (Gtk.CheckButton) builder.get_object("auto_retrieve");
- this.auto_sync = (Gtk.CheckButton) builder.get_object("auto_sync");
-
- this.keyserver_remove.clicked.connect(on_prefs_keyserver_remove_clicked);
- this.keyserver_add.clicked.connect(on_prefs_keyserver_add_clicked);
#if WITH_KEYSERVER
- setup_keyservers();
-#else
- remove_tab(this.keyserver_tab);
+ var keyservers = new PrefsKeyservers(this);
+ var label = new Gtk.Label("Keyservers");
+ add_tab(label, keyservers);
#endif
if (tabid != null) {
@@ -121,179 +99,4 @@ public class Seahorse.Prefs : Gtk.Dialog {
if (pos != -1)
this.notebook.remove_page(pos);
}
-
-#if WITH_KEYSERVER
-
- private enum Columns {
- KEYSERVER,
- N_COLUMNS
- }
-
- // Perform keyserver page initialization
- private void setup_keyservers () {
- string[] keyservers = PgpSettings.instance().get_uris();
- populate_keyservers(keyservers);
-
- Gtk.TreeModel model = this.keyservers.get_model();
- model.row_changed.connect(keyserver_row_changed);
- model.row_deleted.connect(keyserver_row_deleted);
-
- Gtk.TreeSelection selection = this.keyservers.get_selection();
- selection.set_mode(Gtk.SelectionMode.SINGLE);
- selection.changed.connect(keyserver_sel_changed);
-
- PgpSettings.instance().changed["keyserver"].connect((settings, key) => {
- populate_keyservers(settings.get_strv(key));
- });
-
- KeyserverControl skc = new KeyserverControl("server-publish-to",
- _("None: Don’t publish keys"));
- this.keyserver_publish.add(skc);
- this.keyserver_publish.show_all();
-
- this.keyserver_publish_to_label.set_mnemonic_widget(skc);
-
- AppSettings.instance().bind("server-auto-retrieve", this.auto_retrieve, "active",
- SettingsBindFlags.DEFAULT);
- AppSettings.instance().bind("server-auto-publish", this.auto_sync, "active",
- SettingsBindFlags.DEFAULT);
- }
-
- // Called when a cell has completed being edited
- private void keyserver_cell_edited (Gtk.CellRendererText cell, string? path, string? text, Gtk.TreeStore
store) {
- if (!ServerCategory.is_valid_uri(text)) {
- Util.show_error (null,
- _("Not a valid Key Server address."),
- _("For help contact your system administrator or the administrator of the key
server." ));
- return;
- }
-
- Gtk.TreeIter iter;
- warn_if_fail(store.get_iter_from_string(out iter, path));
- store.set(iter, Columns.KEYSERVER, text, -1);
- }
-
- // The selection changed on the tree
- private void keyserver_sel_changed (Gtk.TreeSelection selection) {
- this.keyserver_remove.sensitive = (selection.count_selected_rows() > 0);
- }
-
- // User wants to remove selected rows
- private void on_prefs_keyserver_remove_clicked (Gtk.Widget? button) {
- this.keyservers.get_selection().selected_foreach((model, path, iter) => {
- ((Gtk.TreeStore) model).remove(ref iter);
- });
- }
-
- // Write key server list to settings
- private void save_keyservers (Gtk.TreeModel model) {
- string[] values = {};
- Gtk.TreeIter iter;
- if (model.get_iter_first(out iter)) {
- do {
- string? keyserver = null;
- model.get(iter, Columns.KEYSERVER, out keyserver, -1);
- if (keyserver == null)
- return;
- values += keyserver;
- } while (model.iter_next(ref iter));
- }
-
- PgpSettings.instance().keyservers = values;
- }
-
- private void keyserver_row_changed (Gtk.TreeModel model, Gtk.TreePath arg1, Gtk.TreeIter arg2) {
- // If currently updating (see populate_keyservers) ignore
- if (this.updating_model)
- return;
-
- save_keyservers(model);
- }
-
- private void keyserver_row_deleted (Gtk.TreeModel model, Gtk.TreePath arg1) {
- // If currently updating (see populate_keyservers) ignore
- if (this.updating_model)
- return;
-
- save_keyservers(model);
- }
-
- private void populate_keyservers(string[] keyservers) {
- Gtk.TreeStore store = (Gtk.TreeStore) this.keyservers.get_model();
-
- // This is our first time so create a store
- if (store == null) {
- store = new Gtk.TreeStore(1, typeof(string));
- this.keyservers.set_model(store);
-
- // Make the column
- Gtk.CellRendererText renderer = new Gtk.CellRendererText();
- renderer.editable = true;
- renderer.edited.connect((cell, path, text) => {
- keyserver_cell_edited(cell, path, text, store);
- });
- Gtk.TreeViewColumn column = new Gtk.TreeViewColumn.with_attributes(
- _("URL"), renderer,
- "text", Columns.KEYSERVER,
- null);
- this.keyservers.append_column(column);
- }
-
- // Mark this so we can ignore events
- this.updating_model = true;
-
- // We try and be inteligent about updating so we don't throw
- // away selections and stuff like that
- uint i = 0;
- Gtk.TreeIter iter;
- if (store.get_iter_first(out iter)) {
- bool cont = false;
- do {
- string? val;
- store.get(iter, Columns.KEYSERVER, out val, -1);
- if (keyservers[i] != null
- && val != null
- && keyservers[i].collate(val) == 0) {
- cont = store.iter_next(ref iter);
- i++;
- } else {
- cont = store.remove(ref iter);
- }
- } while (cont);
- }
-
- // Any remaining extra rows
- for ( ; keyservers[i] != null; i++) {
- store.append(out iter, null);
- store.set(iter, Columns.KEYSERVER, keyservers[i], -1);
- }
-
- // Done updating
- this.updating_model = false;
- }
-
- private void on_prefs_keyserver_add_clicked (Gtk.Button button) {
- AddKeyserverDialog dialog = new AddKeyserverDialog(this);
-
- if (dialog.run() == Gtk.ResponseType.OK) {
- string? result = dialog.calculate_keyserver_uri();
-
- if (result != null) {
- Gtk.TreeStore store = (Gtk.TreeStore) this.keyservers.get_model();
- Gtk.TreeIter iter;
- store.append(out iter, null);
- store.set(iter, Columns.KEYSERVER, result, -1);
- }
- }
-
- dialog.destroy();
- }
-
-#else
-
- private void on_prefs_keyserver_add_clicked (Gtk.Button? button) { }
- void on_prefs_keyserver_remove_clicked (Gtk.Widget? button) { }
-
-#endif
-
}
diff --git a/common/seahorse-prefs-keyservers.ui b/common/seahorse-prefs-keyservers.ui
new file mode 100644
index 00000000..40860fd9
--- /dev/null
+++ b/common/seahorse-prefs-keyservers.ui
@@ -0,0 +1,137 @@
+<?xml version="1.0"?>
+<interface>
+ <requires lib="gtk+" version="3.24"/>
+ <template class="SeahorsePrefsKeyservers" parent="GtkBox">
+ <property name="visible">True</property>
+ <child>
+ <object class="GtkBox">
+ <property name="visible">True</property>
+ <property name="orientation">vertical</property>
+ <property name="border_width">12</property>
+ <property name="spacing">6</property>
+ <child>
+ <object class="GtkBox">
+ <property name="visible">True</property>
+ <property name="orientation">horizontal</property>
+ <child>
+ <object class="GtkLabel">
+ <property name="visible">True</property>
+ <property name="xalign">0</property>
+ <property name="hexpand">true</property>
+ <property name="label" translatable="yes">Keyservers</property>
+ <property name="use_underline">True</property>
+ <attributes>
+ <attribute name="weight" value="bold"/>
+ </attributes>
+ </object>
+ </child>
+ <child>
+ <object class="GtkButton" id="keyserver_add_button">
+ <property name="visible">True</property>
+ <property name="halign">end</property>
+ <property name="tooltip-text" translatable="yes">Add a new keyserver</property>
+ <signal name="clicked" handler="on_add_button_clicked"/>
+ <child>
+ <object class="GtkImage">
+ <property name="visible">True</property>
+ <property name="icon-name">list-add-symbolic</property>
+ </object>
+ </child>
+ <style>
+ <class name="image-button"/>
+ <class name="flat"/>
+ </style>
+ </object>
+ </child>
+ </object>
+ </child>
+ <child>
+ <object class="GtkGrid" id="keyserver_tab">
+ <property name="visible">True</property>
+ <property name="column_spacing">12</property>
+ <property name="row_spacing">12</property>
+ <child>
+ <object class="GtkScrolledWindow" id="scrolledwindow1">
+ <property name="visible">True</property>
+ <property name="can_focus">True</property>
+ <property name="hscrollbar_policy">never</property>
+ <property name="vscrollbar_policy">automatic</property>
+ <property name="min-content-height">200</property>
+ <child>
+ <object class="GtkListBox" id="keyservers_list">
+ <property name="visible">True</property>
+ <property name="can_focus">True</property>
+ <property name="hexpand">True</property>
+ <style>
+ <class name="content"/>
+ </style>
+ </object>
+ </child>
+ </object>
+ <packing>
+ <property name="top_attach">0</property>
+ <property name="left_attach">0</property>
+ <property name="width">2</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkLabel" id="keyserver_publish_to_label">
+ <property name="visible">True</property>
+ <property name="xalign">0</property>
+ <property name="label" translatable="yes">_Publish keys to:</property>
+ <property name="use_underline">True</property>
+ </object>
+ <packing>
+ <property name="top_attach">1</property>
+ <property name="left_attach">0</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkBox" id="keyserver_publish">
+ <property name="visible">True</property>
+ <property name="orientation">vertical</property>
+ <child>
+ <placeholder/>
+ </child>
+ </object>
+ <packing>
+ <property name="top_attach">1</property>
+ <property name="left_attach">1</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkCheckButton" id="auto_retrieve">
+ <property name="label" translatable="yes">Automatically retrieve keys from _key
servers</property>
+ <property name="visible">True</property>
+ <property name="can_focus">True</property>
+ <property name="receives_default">False</property>
+ <property name="use_underline">True</property>
+ <property name="draw_indicator">True</property>
+ </object>
+ <packing>
+ <property name="top_attach">2</property>
+ <property name="left_attach">0</property>
+ <property name="width">2</property>
+ </packing>
+ </child>
+ <child>
+ <object class="GtkCheckButton" id="auto_sync">
+ <property name="label" translatable="yes">Automatically synchronize _modified keys with key
servers</property>
+ <property name="visible">True</property>
+ <property name="can_focus">True</property>
+ <property name="receives_default">False</property>
+ <property name="use_underline">True</property>
+ <property name="draw_indicator">True</property>
+ </object>
+ <packing>
+ <property name="top_attach">3</property>
+ <property name="left_attach">0</property>
+ <property name="width">2</property>
+ </packing>
+ </child>
+ </object>
+ </child>
+ </object>
+ </child>
+ </template>
+</interface>
diff --git a/common/seahorse-prefs.ui b/common/seahorse-prefs.ui
index 8076ef03..0ef73dfd 100644
--- a/common/seahorse-prefs.ui
+++ b/common/seahorse-prefs.ui
@@ -16,158 +16,6 @@
<property name="visible">True</property>
<property name="can_focus">True</property>
<property name="vexpand">True</property>
- <child>
- <object class="GtkGrid" id="keyserver-tab">
- <property name="visible">True</property>
- <property name="border_width">12</property>
- <property name="column_spacing">12</property>
- <property name="row_spacing">12</property>
- <child>
- <object class="GtkBox">
- <property name="visible">True</property>
- <property name="orientation">vertical</property>
- <property name="spacing">11</property>
- <child>
- <object class="GtkLabel">
- <property name="visible">True</property>
- <property name="xalign">0</property>
- <property name="label" translatable="yes">_Find keys via:</property>
- <property name="use_underline">True</property>
- <property name="mnemonic_widget">scrolledwindow1</property>
- </object>
- <packing>
- <property name="expand">False</property>
- <property name="fill">False</property>
- <property name="position">0</property>
- </packing>
- </child>
- <child>
- <object class="GtkButton" id="keyserver_add">
- <property name="label">gtk-add</property>
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="receives_default">False</property>
- <property name="use_stock">True</property>
- </object>
- <packing>
- <property name="expand">False</property>
- <property name="fill">False</property>
- <property name="position">1</property>
- </packing>
- </child>
- <child>
- <object class="GtkButton" id="keyserver_remove">
- <property name="label">gtk-remove</property>
- <property name="visible">True</property>
- <property name="sensitive">False</property>
- <property name="can_focus">True</property>
- <property name="receives_default">False</property>
- <property name="use_stock">True</property>
- <signal name="clicked" handler="on_prefs_keyserver_remove_clicked"/>
- </object>
- <packing>
- <property name="expand">False</property>
- <property name="fill">False</property>
- <property name="position">2</property>
- </packing>
- </child>
- </object>
- <packing>
- <property name="left_attach">0</property>
- <property name="top_attach">0</property>
- </packing>
- </child>
- <child>
- <object class="GtkScrolledWindow" id="scrolledwindow1">
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="hscrollbar_policy">never</property>
- <property name="vscrollbar_policy">automatic</property>
- <property name="shadow_type">in</property>
- <child>
- <object class="GtkTreeView" id="keyservers">
- <property name="height_request">130</property>
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="headers_visible">False</property>
- </object>
- </child>
- </object>
- <packing>
- <property name="top_attach">0</property>
- <property name="left_attach">1</property>
- </packing>
- </child>
- <child>
- <object class="GtkLabel" id="keyserver-publish-to-label">
- <property name="visible">True</property>
- <property name="xalign">0</property>
- <property name="label" translatable="yes">_Publish keys to:</property>
- <property name="use_underline">True</property>
- </object>
- <packing>
- <property name="top_attach">1</property>
- <property name="left_attach">0</property>
- </packing>
- </child>
- <child>
- <object class="GtkBox" id="keyserver-publish">
- <property name="visible">True</property>
- <property name="orientation">vertical</property>
- <child>
- <placeholder/>
- </child>
- </object>
- <packing>
- <property name="top_attach">1</property>
- <property name="left_attach">1</property>
- </packing>
- </child>
- <child>
- <object class="GtkCheckButton" id="auto_retrieve">
- <property name="label" translatable="yes">Automatically retrieve keys from _key
servers</property>
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="receives_default">False</property>
- <property name="use_underline">True</property>
- <property name="draw_indicator">True</property>
- </object>
- <packing>
- <property name="top_attach">2</property>
- <property name="left_attach">1</property>
- </packing>
- </child>
- <child>
- <object class="GtkCheckButton" id="auto_sync">
- <property name="label" translatable="yes">Automatically synchronize _modified keys with
key servers</property>
- <property name="visible">True</property>
- <property name="can_focus">True</property>
- <property name="receives_default">False</property>
- <property name="use_underline">True</property>
- <property name="draw_indicator">True</property>
- </object>
- <packing>
- <property name="top_attach">3</property>
- <property name="left_attach">1</property>
- </packing>
- </child>
- </object>
- </child>
- <child type="tab">
- <object class="GtkLabel">
- <property name="visible">True</property>
- <property name="label" translatable="yes">Key Servers</property>
- </object>
- <packing>
- <property name="tab_fill">False</property>
- </packing>
- </child>
- <child>
- <placeholder/>
- </child>
- <child type="tab">
- <placeholder/>
- </child>
</object>
<packing>
<property name="position">1</property>
diff --git a/data/seahorse.gresource.xml b/data/seahorse.gresource.xml
index 7c9ac10d..6156a971 100644
--- a/data/seahorse.gresource.xml
+++ b/data/seahorse.gresource.xml
@@ -8,6 +8,7 @@
<!-- Common -->
<file alias="seahorse-add-keyserver.ui"
preprocess="xml-stripblanks">../common/seahorse-add-keyserver.ui</file>
<file alias="seahorse-prefs.ui" preprocess="xml-stripblanks">../common/seahorse-prefs.ui</file>
+ <file alias="seahorse-prefs-keyservers.ui"
preprocess="xml-stripblanks">../common/seahorse-prefs-keyservers.ui</file>
<!-- Seahorse -->
<file alias="seahorse-change-passphrase.ui"
preprocess="xml-stripblanks">../src/seahorse-change-passphrase.ui</file>
diff --git a/pgp/seahorse-discovery.c b/pgp/seahorse-discovery.c
index 2020442b..9622328b 100644
--- a/pgp/seahorse-discovery.c
+++ b/pgp/seahorse-discovery.c
@@ -156,13 +156,10 @@ resolve_callback (AvahiServiceResolver *resolver, AvahiIfIndex iface, AvahiProto
g_hash_table_replace (self->services, service_name, service_uri);
g_signal_emit (self, signals[ADDED], 0, service_name);
- /* Add it to the context */
- if (!seahorse_pgp_backend_lookup_remote (NULL, service_uri)) {
- SeahorseServerSource *ssrc = seahorse_server_category_create_server (service_uri);
- g_return_if_fail (ssrc != NULL);
- seahorse_pgp_backend_add_remote (NULL, service_uri, ssrc);
- g_object_unref (ssrc);
- }
+ /* Add it to the context */
+ if (!seahorse_pgp_backend_lookup_remote (NULL, service_uri)) {
+ seahorse_pgp_backend_add_remote (NULL, service_uri, FALSE);
+ }
g_debug ("added: %s %s\n", service_name, service_uri);
break;
diff --git a/pgp/seahorse-pgp-backend.c b/pgp/seahorse-pgp-backend.c
index d19685c9..c08b26dc 100644
--- a/pgp/seahorse-pgp-backend.c
+++ b/pgp/seahorse-pgp-backend.c
@@ -51,6 +51,7 @@ struct _SeahorsePgpBackend {
GObject parent;
SeahorseGpgmeKeyring *keyring;
+ SeahorsePgpSettings *pgp_settings;
SeahorseDiscovery *discovery;
SeahorseUnknownSource *unknown;
GListModel *remotes;
@@ -73,6 +74,7 @@ seahorse_pgp_backend_init (SeahorsePgpBackend *self)
g_return_if_fail (pgp_backend == NULL);
pgp_backend = self;
+ self->pgp_settings = seahorse_pgp_settings_instance ();
self->remotes = G_LIST_MODEL (g_list_store_new (SEAHORSE_TYPE_SERVER_SOURCE));
self->actions = seahorse_pgp_backend_actions_instance ();
}
@@ -96,7 +98,7 @@ on_settings_keyservers_changed (GSettings *settings,
remote = g_list_model_get_item (self->remotes, i);
uri = seahorse_place_get_uri (SEAHORSE_PLACE (remote));
- g_ptr_array_add (check, uri);
+ g_ptr_array_add (check, g_steal_pointer (&uri));
}
/* Load and strip names from keyserver list */
@@ -107,17 +109,13 @@ on_settings_keyservers_changed (GSettings *settings,
gboolean found;
guint index;
- /* If we don't have a keysource then add it */
found = g_ptr_array_find_with_equal_func (check, uri, g_str_equal, &index);
if (found) {
/* Mark this one as present */
g_ptr_array_remove_index (check, index);
} else {
- g_autoptr(SeahorseServerSource) source = NULL;
-
- source = seahorse_server_category_create_server (uri);
- if (source != NULL)
- seahorse_pgp_backend_add_remote (self, uri, source);
+ /* If we don't have a keysource then add it */
+ seahorse_pgp_backend_add_remote (self, uri, FALSE);
}
}
@@ -168,11 +166,11 @@ seahorse_pgp_backend_constructed (GObject *obj)
self->unknown = seahorse_unknown_source_new ();
#ifdef WITH_KEYSERVER
- g_signal_connect (seahorse_pgp_settings_instance (), "changed::keyservers",
+ g_signal_connect (self->pgp_settings, "changed::keyservers",
G_CALLBACK (on_settings_keyservers_changed), self);
/* Initial loading */
- on_settings_keyservers_changed (G_SETTINGS (seahorse_pgp_settings_instance ()),
+ on_settings_keyservers_changed (G_SETTINGS (self->pgp_settings),
"keyservers",
self);
#endif
@@ -247,7 +245,7 @@ seahorse_pgp_backend_finalize (GObject *obj)
SeahorsePgpBackend *self = SEAHORSE_PGP_BACKEND (obj);
#ifdef WITH_KEYSERVER
- g_signal_handlers_disconnect_by_func (seahorse_pgp_settings_instance (),
+ g_signal_handlers_disconnect_by_func (self->pgp_settings,
on_settings_keyservers_changed, self);
#endif
@@ -362,28 +360,25 @@ seahorse_pgp_backend_get_default_keyring (SeahorsePgpBackend *self)
SeahorsePgpKey *
seahorse_pgp_backend_get_default_key (SeahorsePgpBackend *self)
{
- SeahorsePgpKey *key = NULL;
- SeahorsePgpSettings *settings;
- const gchar *keyid;
- gchar *value;
+ SeahorsePgpKey *key = NULL;
+ g_autofree char *value = NULL;
- self = self ? self : seahorse_pgp_backend_get ();
- g_return_val_if_fail (SEAHORSE_PGP_IS_BACKEND (self), NULL);
+ self = self ? self : seahorse_pgp_backend_get ();
+ g_return_val_if_fail (SEAHORSE_PGP_IS_BACKEND (self), NULL);
- settings = seahorse_pgp_settings_instance ();
- if (settings != NULL) {
- value = seahorse_pgp_settings_get_default_key (settings);
- if (value != NULL && value[0]) {
- if (g_str_has_prefix (value, "openpgp:"))
- keyid = value + strlen ("openpgp:");
- else
- keyid = value;
- key = SEAHORSE_PGP_KEY (seahorse_gpgme_keyring_lookup (self->keyring, keyid));
- }
- g_free (value);
- }
+ value = seahorse_pgp_settings_get_default_key (self->pgp_settings);
+ if (value && *value) {
+ const char *keyid;
+
+ if (g_str_has_prefix (value, "openpgp:"))
+ keyid = value + strlen ("openpgp:");
+ else
+ keyid = value;
- return key;
+ key = SEAHORSE_PGP_KEY (seahorse_gpgme_keyring_lookup (self->keyring, keyid));
+ }
+
+ return key;
}
#ifdef WITH_KEYSERVER
@@ -437,14 +432,21 @@ seahorse_pgp_backend_lookup_remote (SeahorsePgpBackend *self,
void
seahorse_pgp_backend_add_remote (SeahorsePgpBackend *self,
const char *uri,
- SeahorseServerSource *source)
+ gboolean persist)
{
- self = self ? self : seahorse_pgp_backend_get ();
g_return_if_fail (SEAHORSE_PGP_IS_BACKEND (self));
- g_return_if_fail (SEAHORSE_IS_SERVER_SOURCE (source));
g_return_if_fail (seahorse_pgp_backend_lookup_remote (self, uri) == NULL);
- g_list_store_append (G_LIST_STORE (self->remotes), source);
+ if (persist) {
+ /* Add to the PGP settings. That's all we need to do, since we're
+ * subscribed to the "changed" callback */
+ seahorse_pgp_settings_add_keyserver (self->pgp_settings, uri, NULL);
+ } else {
+ /* Don't persist, so just immediately create a ServerSource */
+ g_autoptr(SeahorseServerSource) ssrc = NULL;
+ ssrc = seahorse_server_category_create_server (uri);
+ g_list_store_append (G_LIST_STORE (self->remotes), ssrc);
+ }
}
void
@@ -455,6 +457,8 @@ seahorse_pgp_backend_remove_remote (SeahorsePgpBackend *self,
g_return_if_fail (SEAHORSE_PGP_IS_BACKEND (self));
g_return_if_fail (uri && *uri);
+ g_debug ("Removing remote %s", uri);
+
for (guint i = 0; i < g_list_model_get_n_items (self->remotes); i++) {
g_autoptr(SeahorseServerSource) ssrc = NULL;
g_autofree char *src_uri = NULL;
@@ -465,6 +469,8 @@ seahorse_pgp_backend_remove_remote (SeahorsePgpBackend *self,
if (g_ascii_strcasecmp (uri, src_uri) == 0)
g_list_store_remove (G_LIST_STORE (self->remotes), i);
}
+
+ seahorse_pgp_settings_remove_keyserver (self->pgp_settings, uri);
}
typedef struct {
@@ -520,7 +526,7 @@ seahorse_pgp_backend_search_remote_async (SeahorsePgpBackend *self,
g_return_if_fail (SEAHORSE_PGP_IS_BACKEND (self));
/* Get a list of all selected key servers */
- names = g_settings_get_strv (G_SETTINGS (seahorse_app_settings_instance ()), "last-search-servers");
+ names = g_settings_get_strv (G_SETTINGS (self->pgp_settings), "last-search-servers");
if (names != NULL && names[0] != NULL) {
servers = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, NULL);
for (guint i = 0; names[i] != NULL; i++)
diff --git a/pgp/seahorse-pgp-backend.h b/pgp/seahorse-pgp-backend.h
index 9008de46..5a877e5b 100644
--- a/pgp/seahorse-pgp-backend.h
+++ b/pgp/seahorse-pgp-backend.h
@@ -59,11 +59,11 @@ SeahorseServerSource * seahorse_pgp_backend_lookup_remote (SeahorsePgpBac
const gchar *uri);
void seahorse_pgp_backend_add_remote (SeahorsePgpBackend *self,
- const gchar *uri,
- SeahorseServerSource *source);
+ const char *uri,
+ gboolean persist);
void seahorse_pgp_backend_remove_remote (SeahorsePgpBackend *self,
- const gchar *uri);
+ const char *uri);
void seahorse_pgp_backend_search_remote_async (SeahorsePgpBackend *self,
const gchar *search,
diff --git a/po/POTFILES.in b/po/POTFILES.in
index 6f448c92..682d6e7a 100644
--- a/po/POTFILES.in
+++ b/po/POTFILES.in
@@ -9,8 +9,10 @@ common/interaction.vala
common/passphrase-prompt.vala
common/place.vala
common/prefs.vala
+common/prefs-keyservers.vala
common/seahorse-add-keyserver.ui
common/seahorse-prefs.ui
+common/seahorse-prefs-keyservers.ui
common/util.vala
common/validity.vala
data/gtk/help-overlay.ui
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]