[epiphany/wip/sync-rebase: 15/86] ephy-sync: Add ephy-sync-secret module



commit 8a15517eee22d72bbdb0fe15cf26c8eef9d948b5
Author: Gabriel Ivascu <ivascu gabriel59 gmail com>
Date:   Wed Jun 22 15:54:47 2016 +0300

    ephy-sync: Add ephy-sync-secret module
    
    Use libsecret to encrypt the sync tokens on disk.
    
    Also, keep the sync tokens in the EphySyncService instance.

 src/Makefile.am              |    2 +
 src/ephy-shell.c             |   40 ++++-----
 src/ephy-shell.h             |    3 +-
 src/ephy-sync-secret.c       |  202 ++++++++++++++++++++++++++++++++++++++++++
 src/ephy-sync-secret.h       |   49 ++++++++++
 src/ephy-sync-service.c      |  113 ++++++++++++++++++------
 src/ephy-sync-service.h      |   29 ++++---
 src/ephy-sync-window.c       |   55 +++++-------
 src/resources/sync-dialog.ui |   24 +++++-
 9 files changed, 419 insertions(+), 98 deletions(-)
---
diff --git a/src/Makefile.am b/src/Makefile.am
index 0950942..3c341a6 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -46,6 +46,8 @@ libephymain_la_SOURCES = \
        ephy-shell.h                            \
        ephy-sync-crypto.c                      \
        ephy-sync-crypto.h                      \
+       ephy-sync-secret.c                      \
+       ephy-sync-secret.h                      \
        ephy-sync-service.c                     \
        ephy-sync-service.h                     \
        ephy-sync-utils.c                       \
diff --git a/src/ephy-shell.c b/src/ephy-shell.c
index 785ef54..6cdb564 100644
--- a/src/ephy-shell.c
+++ b/src/ephy-shell.c
@@ -51,7 +51,7 @@ struct _EphyShell {
   EphyEmbedShell parent_instance;
 
   EphySession *session;
-  EphySyncService *global_sync_service;
+  EphySyncService *sync_service;
   GList *windows;
   GObject *lockdown;
   EphyBookmarksManager *bookmarks_manager;
@@ -580,6 +580,8 @@ ephy_shell_init (EphyShell *shell)
   ephy_shell = shell;
   g_object_add_weak_pointer (G_OBJECT (ephy_shell),
                              (gpointer *)ptr);
+
+  shell->sync_service = ephy_sync_service_new ();
 }
 
 static void
@@ -600,6 +602,7 @@ ephy_shell_dispose (GObject *object)
   g_clear_pointer (&shell->history_window, gtk_widget_destroy);
   g_clear_object (&shell->prefs_dialog);
   g_clear_object (&shell->network_monitor);
+  g_clear_object (&shell->sync_service);
 
   g_slist_free_full (shell->open_uris_idle_ids, remove_open_uris_idle_cb);
   shell->open_uris_idle_ids = NULL;
@@ -621,6 +624,19 @@ ephy_shell_finalize (GObject *object)
 }
 
 /**
+ * ephy_shell_get_global_sync_service:
+ *
+ * Retrieve the default #EphySyncService object
+ *
+ * Return value: (transfer none):
+ **/
+EphySyncService *
+ephy_shell_get_global_sync_service (void)
+{
+  return ephy_shell->sync_service;
+}
+
+/**
  * ephy_shell_get_default:
  *
  * Retrieve the default #EphyShell object
@@ -779,26 +795,6 @@ ephy_shell_get_net_monitor (EphyShell *shell)
 }
 
 /**
- * ephy_shell_get_global_sync_service:
- *
- * Return value: (transfer none):
- **/
-GObject *
-ephy_shell_get_global_sync_service (EphyShell *shell)
-{
-  g_return_val_if_fail (EPHY_IS_SHELL (shell), NULL);
-
-  if (shell->global_sync_service == NULL) {
-LOG ("%s:%d", __func__, __LINE__);
-    shell->global_sync_service = ephy_sync_service_new ();
-    g_return_val_if_fail (shell->global_sync_service, NULL);
-  }
-
-LOG ("%s:%d", __func__, __LINE__);
-  return G_OBJECT (shell->global_sync_service);
-}
-
-/**
  * ephy_shell_get_history_window:
  *
  * Return value: (transfer none):
@@ -831,7 +827,7 @@ ephy_shell_get_sync_window (EphyShell *shell)
 
   if (shell->sync_window == NULL) {
 LOG ("%s:%d", __func__, __LINE__);
-    sync_service = EPHY_SYNC_SERVICE (ephy_shell_get_global_sync_service (shell));
+    sync_service = ephy_shell_get_global_sync_service ();
     shell->sync_window = ephy_sync_window_new (sync_service);
     g_signal_connect (shell->sync_window,
                       "destroy",
diff --git a/src/ephy-shell.h b/src/ephy-shell.h
index a044bb3..a65b40b 100644
--- a/src/ephy-shell.h
+++ b/src/ephy-shell.h
@@ -24,6 +24,7 @@
 #include "ephy-embed-shell.h"
 #include "ephy-embed.h"
 #include "ephy-session.h"
+#include "ephy-sync-service.h"
 #include "ephy-window.h"
 
 #include <webkit2/webkit2.h>
@@ -99,7 +100,7 @@ GNetworkMonitor *ephy_shell_get_net_monitor              (EphyShell *shell);
 
 EphyBookmarksManager *ephy_shell_get_bookmarks_manager   (EphyShell *shell);
 
-GObject         *ephy_shell_get_global_sync_service      (EphyShell *shell);
+EphySyncService *ephy_shell_get_global_sync_service      (void);
 
 GtkWidget       *ephy_shell_get_history_window           (EphyShell *shell);
 
diff --git a/src/ephy-sync-secret.c b/src/ephy-sync-secret.c
new file mode 100644
index 0000000..c1fb5ea
--- /dev/null
+++ b/src/ephy-sync-secret.c
@@ -0,0 +1,202 @@
+/* -*- Mode: C; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/*
+ *  Copyright © 2016 Gabriel Ivascu <ivascu gabriel59 gmail com>
+ *
+ *  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, 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/>.
+ */
+
+#include "ephy-debug.h"
+#include "ephy-sync-secret.h"
+
+#include <glib/gi18n.h>
+
+const SecretSchema *
+ephy_sync_secret_get_token_schema (void)
+{
+  static const SecretSchema schema = {
+    "org.epiphany.SyncToken", SECRET_SCHEMA_NONE,
+    {
+      { EMAIL_KEY, SECRET_SCHEMA_ATTRIBUTE_STRING },
+      { TOKEN_KEY, SECRET_SCHEMA_ATTRIBUTE_STRING },
+      { "NULL", 0 },
+    }
+  };
+  return &schema;
+}
+
+static void
+forget_all_tokens_cb (SecretService *service,
+                      GAsyncResult  *result,
+                      GTask         *task)
+{
+  GError *error = NULL;
+
+  secret_service_clear_finish (service, result, &error);
+
+  if (error != NULL) {
+LOG ("%s:%d", __func__, __LINE__);
+    g_task_return_error (task, error);
+  }
+  else {
+LOG ("%s:%d", __func__, __LINE__);
+    g_task_return_boolean (task, TRUE);
+  }
+
+  g_object_unref (task);
+}
+
+static void
+load_tokens_cb (SecretService *service,
+                GAsyncResult  *result,
+                gpointer       user_data)
+{
+  EphySyncService *sync_service;
+  GHashTable *attributes;
+  SecretItem *secret_item;
+  SecretValue *secret_value;
+  GList *matches;
+  GList *tmp;
+  const gchar *emailUTF8;
+  const gchar *token_name;
+  const gchar *token_value_hex;
+
+  sync_service = EPHY_SYNC_SERVICE (user_data);
+  matches = secret_service_search_finish (service, result, NULL);
+
+  for (tmp = matches; tmp != NULL; tmp = tmp->next) {
+    secret_item = tmp->data;
+
+    attributes = secret_item_get_attributes (secret_item);
+    emailUTF8 = g_hash_table_lookup (attributes, EMAIL_KEY);
+    token_name = g_hash_table_lookup (attributes, TOKEN_KEY);
+    secret_value = secret_item_get_secret (secret_item);
+    token_value_hex = secret_value_get_text (secret_value);
+
+    if (g_strcmp0 (emailUTF8, sync_service->user_email) == 0) {
+      ephy_sync_service_set_token (sync_service, token_name, token_value_hex);
+LOG ("[%d] Set token %s with value %s for email: %s", __LINE__, token_name, token_value_hex, emailUTF8);
+    }
+
+    g_hash_table_unref (attributes);
+  }
+
+LOG ("%s:%d", __func__, __LINE__);
+  g_list_free_full (matches, g_object_unref);
+}
+
+static void
+store_token_cb (SecretService *service,
+                GAsyncResult  *result,
+                GTask         *task)
+{
+  GError *error = NULL;
+
+  secret_service_store_finish (service, result, &error);
+
+  if (error != NULL) {
+LOG ("%s:%d", __func__, __LINE__);
+    g_task_return_error (task, error);
+  }
+  else {
+LOG ("%s:%d", __func__, __LINE__);
+    g_task_return_boolean (task, TRUE);
+  }
+
+  g_object_unref (task);
+}
+
+void
+ephy_sync_secret_forget_all_tokens (GAsyncReadyCallback callback,
+                                    gpointer            user_data)
+{
+  GHashTable *attributes;
+  GTask *task;
+
+LOG ("%s:%d", __func__, __LINE__);
+
+  task = g_task_new (NULL, NULL, callback, user_data);
+  attributes = secret_attributes_build (EPHY_SYNC_TOKEN_SCHEMA, NULL);
+  secret_service_clear (NULL,
+                        EPHY_SYNC_TOKEN_SCHEMA,
+                        attributes,
+                        NULL,
+                        (GAsyncReadyCallback) forget_all_tokens_cb,
+                        g_object_ref (task));
+
+  g_hash_table_unref (attributes);
+  g_object_unref (task);
+}
+
+void
+ephy_sync_secret_load_tokens (EphySyncService *sync_service)
+{
+  GHashTable *attributes;
+
+  attributes = secret_attributes_build (EPHY_SYNC_TOKEN_SCHEMA, NULL);
+
+  secret_service_search (NULL,
+                         EPHY_SYNC_TOKEN_SCHEMA,
+                         attributes,
+                         SECRET_SEARCH_ALL | SECRET_SEARCH_UNLOCK | SECRET_SEARCH_LOAD_SECRETS,
+                         NULL,
+                         (GAsyncReadyCallback) load_tokens_cb,
+                         sync_service);
+
+  g_hash_table_unref (attributes);
+}
+
+void
+ephy_sync_secret_store_token (const gchar         *emailUTF8,
+                              const gchar         *token_name,
+                              const gchar         *token_value,
+                              GAsyncReadyCallback  callback,
+                              gpointer             user_data)
+{
+  SecretValue *secret_value;
+  GHashTable *attributes;
+  GTask *task;
+  gchar *label;
+
+  g_return_if_fail (token_name);
+  g_return_if_fail (token_value);
+
+LOG ("%s:%d", __func__, __LINE__);
+
+  task = g_task_new (NULL, NULL, callback, user_data);
+  secret_value = secret_value_new (token_value, -1, "text/plain");
+  attributes = secret_attributes_build (EPHY_SYNC_TOKEN_SCHEMA,
+                                        EMAIL_KEY, emailUTF8,
+                                        TOKEN_KEY, token_name,
+                                        NULL);
+LOG ("size: %u", g_hash_table_size (attributes));
+  /* Translators: The %s is the name of the token whose value is stored.
+   * Example: quickStretchedPW or authPW
+   */
+  label = g_strdup_printf (_("Token value for %s token"), token_name);
+
+  secret_service_store (NULL,
+                        EPHY_SYNC_TOKEN_SCHEMA,
+                        attributes,
+                        NULL,
+                        label,
+                        secret_value,
+                        NULL,
+                        (GAsyncReadyCallback) store_token_cb,
+                        g_object_ref (task));
+
+  g_free (label);
+  secret_value_unref (secret_value);
+  g_hash_table_unref (attributes);
+  g_object_unref (task);
+}
diff --git a/src/ephy-sync-secret.h b/src/ephy-sync-secret.h
new file mode 100644
index 0000000..1fc5ee1
--- /dev/null
+++ b/src/ephy-sync-secret.h
@@ -0,0 +1,49 @@
+/* -*- Mode: C; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/*
+ *  Copyright © 2016 Gabriel Ivascu <ivascu gabriel59 gmail com>
+ *
+ *  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, 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/>.
+ */
+
+#ifndef EPHY_SYNC_SECRET_H
+#define EPHY_SYNC_SECRET_H
+
+#include "ephy-sync-service.h"
+
+#include <glib-object.h>
+#include <libsecret/secret.h>
+
+G_BEGIN_DECLS
+
+const SecretSchema *ephy_sync_secret_get_token_schema (void) G_GNUC_CONST;
+
+#define EMAIL_KEY "email_utf8"
+#define TOKEN_KEY "token_name"
+
+#define EPHY_SYNC_TOKEN_SCHEMA (ephy_sync_secret_get_token_schema ())
+
+void ephy_sync_secret_forget_all_tokens (GAsyncReadyCallback callback,
+                                         gpointer            userdata);
+
+void ephy_sync_secret_load_tokens       (EphySyncService *sync_service);
+
+void ephy_sync_secret_store_token       (const gchar         *emailUTF8,
+                                         const gchar         *token_name,
+                                         const gchar         *token_value,
+                                         GAsyncReadyCallback  callback,
+                                         gpointer             userdata);
+
+G_END_DECLS
+
+#endif
diff --git a/src/ephy-sync-service.c b/src/ephy-sync-service.c
index 693ebda..4035f27 100644
--- a/src/ephy-sync-service.c
+++ b/src/ephy-sync-service.c
@@ -18,6 +18,7 @@
 
 #include "ephy-debug.h"
 #include "ephy-sync-crypto.h"
+#include "ephy-sync-secret.h"
 #include "ephy-sync-service.h"
 #include "ephy-sync-utils.h"
 
@@ -25,33 +26,40 @@
 #include <libsoup/soup.h>
 #include <string.h>
 
-struct _EphySyncService {
-  GObject parent_instance;
-};
-
 G_DEFINE_TYPE (EphySyncService, ephy_sync_service, G_TYPE_OBJECT);
 
 static void
+ephy_sync_service_finalize (GObject *object)
+{
+  EphySyncService *self = EPHY_SYNC_SERVICE (object);
+
+  g_free (self->user_email);
+  g_hash_table_destroy (self->tokens);
+
+  G_OBJECT_CLASS (ephy_sync_service_parent_class)->finalize (object);
+}
+
+static void
 ephy_sync_service_class_init (EphySyncServiceClass *klass)
 {
   GObjectClass *object_class = G_OBJECT_CLASS (klass);
-  object_class = object_class; // suppress warnings
 
-LOG ("%s:%d", __func__, __LINE__);
-
-  // TODO: Set finalize, dispose, set/get property methods
+  object_class->finalize = ephy_sync_service_finalize;
 }
 
 static void
 ephy_sync_service_init (EphySyncService *self)
 {
+  self->tokens = g_hash_table_new_full (NULL, g_str_equal,
+                                        NULL, g_free);
+
 LOG ("%s:%d", __func__, __LINE__);
 }
 
 static void
 server_response_cb (SoupSession *session,
                     SoupMessage *message,
-                    gpointer user_data)
+                    gpointer     user_data)
 {
   if (message->status_code == 200) {
 LOG ("response body: %s", message->response_body->data);
@@ -64,28 +72,52 @@ LOG ("Error response from server: [%u] %s", message->status_code, message->reaso
 EphySyncService *
 ephy_sync_service_new (void)
 {
-LOG ("%s:%d", __func__, __LINE__);
-
   return EPHY_SYNC_SERVICE (g_object_new (EPHY_TYPE_SYNC_SERVICE,
                                           NULL));
 }
 
+gchar *
+ephy_sync_service_get_token (EphySyncService *self,
+                             const gchar     *token_name)
+{
+  GHashTableIter iter;
+  gchar *key, *value;
+
+  g_hash_table_iter_init (&iter, self->tokens);
+
+  while (g_hash_table_iter_next (&iter, (gpointer) &key, (gpointer) &value)) {
+      if (g_strcmp0 (token_name, key) == 0) {
+LOG ("[%d] Returning token %s with value %s", __LINE__, key, value);
+        return value;
+      }
+  }
+
+  return NULL;
+}
+
 void
-ephy_sync_service_try_login (EphySyncService *self,
-                             gboolean login_with_keys,
-                             const gchar *emailUTF8,
-                             guint8 *authPW,
-                             guint8 *sessionToken,
-                             guint8 *keyFetchToken)
+ephy_sync_service_set_token (EphySyncService *self,
+                             const gchar     *token_name,
+                             const gchar     *token_value_hex)
+{
+  g_hash_table_insert (self->tokens,
+                       (gpointer) token_name,
+                       (gpointer) token_value_hex);
+
+LOG ("[%d] Set token %s with value %s", __LINE__, token_name, token_value_hex);
+}
+
+void
+ephy_sync_service_login (EphySyncService *self)
 {
   SoupSession *session;
   SoupMessage *message;
-  char *request_body;
-  char *authPW_hex;
+  gchar *request_body;
+  gchar *authPW;
 
   g_return_if_fail (EPHY_IS_SYNC_SERVICE (self));
 
-LOG ("%s:%d", __func__, __LINE__);
+LOG ("%s:%d Preparing soup message", __func__, __LINE__);
 
   session = soup_session_new_with_options (SOUP_SESSION_USER_AGENT,
                                            "test-json",
@@ -93,11 +125,13 @@ LOG ("%s:%d", __func__, __LINE__);
   message = soup_message_new (SOUP_METHOD_POST,
                               "https://api.accounts.firefox.com/v1/account/login";);
 
-  authPW_hex = ephy_sync_utils_encode_hex (authPW, EPHY_SYNC_TOKEN_LENGTH);
+  authPW = ephy_sync_service_get_token (self, "authPW");
+  g_assert (authPW != NULL);
+
   request_body = g_strconcat ("{\"authPW\": \"",
-                              authPW_hex,
+                              authPW,
                               "\", \"email\": \"",
-                              emailUTF8,
+                              self->user_email,
                               "\"}",
                               NULL);
 
@@ -108,22 +142,23 @@ LOG ("%s:%d", __func__, __LINE__);
                             strlen (request_body));
 
   soup_session_queue_message (session, message, server_response_cb, NULL);
+LOG ("%s:%d Queued the soup message", __func__, __LINE__);
 
-  // TODO: find a way to safely free authPW_hex, request_body
+  // TODO: find a way to safely free request_body
   // TODO: find a way to safely destroy session, message
 }
 
 void
 ephy_sync_service_stretch (EphySyncService *self,
-                           const gchar *emailUTF8,
-                           const gchar *passwordUTF8,
-                           guint8 *authPW,
-                           guint8 *unwrapBKey)
+                           const gchar     *emailUTF8,
+                           const gchar     *passwordUTF8)
 {
   gchar *salt_stretch;
   gchar *info_auth;
   gchar *info_unwrap;
   guint8 *quickStretchedPW;
+  guint8 *authPW;
+  guint8 *unwrapBKey;
 
   g_return_if_fail (EPHY_IS_SYNC_SERVICE (self));
 
@@ -141,6 +176,7 @@ LOG ("%s:%d", __func__, __LINE__);
 ephy_sync_utils_display_hex ("quickStretchedPW", quickStretchedPW, EPHY_SYNC_TOKEN_LENGTH);
 
   info_auth = ephy_sync_utils_kw ("authPW");
+  authPW = g_malloc (EPHY_SYNC_TOKEN_LENGTH);
   ephy_sync_crypto_hkdf (quickStretchedPW,
                          EPHY_SYNC_TOKEN_LENGTH,
                          NULL, 0,
@@ -150,6 +186,7 @@ ephy_sync_utils_display_hex ("quickStretchedPW", quickStretchedPW, EPHY_SYNC_TOK
                          EPHY_SYNC_TOKEN_LENGTH);
 
   info_unwrap = ephy_sync_utils_kw ("unwrapBkey");
+  unwrapBKey = g_malloc (EPHY_SYNC_TOKEN_LENGTH);
   ephy_sync_crypto_hkdf (quickStretchedPW,
                          EPHY_SYNC_TOKEN_LENGTH,
                          NULL, 0,
@@ -158,8 +195,28 @@ ephy_sync_utils_display_hex ("quickStretchedPW", quickStretchedPW, EPHY_SYNC_TOK
                          unwrapBKey,
                          EPHY_SYNC_TOKEN_LENGTH);
 
+  self->user_email = g_strdup (emailUTF8);
+  ephy_sync_service_set_token (self, "quickStretchedPW", ephy_sync_utils_encode_hex (quickStretchedPW, 
EPHY_SYNC_TOKEN_LENGTH));
+  ephy_sync_service_set_token (self, "authPW", ephy_sync_utils_encode_hex (authPW, EPHY_SYNC_TOKEN_LENGTH));
+  ephy_sync_service_set_token (self, "unwrapBKey", ephy_sync_utils_encode_hex (unwrapBKey, 
EPHY_SYNC_TOKEN_LENGTH));
+
+  ephy_sync_secret_store_token (self->user_email,
+                                "quickStretchedPW",
+                                ephy_sync_service_get_token (self, "quickStretchedPW"),
+                                NULL, NULL);
+  ephy_sync_secret_store_token (self->user_email,
+                                "authPW",
+                                ephy_sync_service_get_token (self, "authPW"),
+                                NULL, NULL);
+  ephy_sync_secret_store_token (self->user_email,
+                                "unwrapBKey",
+                                ephy_sync_service_get_token (self, "unwrapBKey"),
+                                NULL, NULL);
+
   g_free (salt_stretch);
   g_free (info_unwrap);
   g_free (info_auth);
   g_free (quickStretchedPW);
+  g_free (authPW);
+  g_free (unwrapBKey);
 }
diff --git a/src/ephy-sync-service.h b/src/ephy-sync-service.h
index bc22597..c35a924 100644
--- a/src/ephy-sync-service.h
+++ b/src/ephy-sync-service.h
@@ -23,24 +23,31 @@
 
 G_BEGIN_DECLS
 
+struct _EphySyncService {
+  GObject parent_instance;
+
+  gchar *user_email;
+  GHashTable *tokens;
+};
+
 #define EPHY_TYPE_SYNC_SERVICE (ephy_sync_service_get_type ())
 
 G_DECLARE_FINAL_TYPE (EphySyncService, ephy_sync_service, EPHY, SYNC_SERVICE, GObject)
 
 EphySyncService *ephy_sync_service_new       (void);
 
+gchar           *ephy_sync_service_get_token (EphySyncService *self,
+                                              const gchar     *token_name);
+
+void             ephy_sync_service_set_token (EphySyncService *self,
+                                              const gchar     *token_name,
+                                              const gchar     *token_value_hex);
+
 void             ephy_sync_service_stretch   (EphySyncService *self,
-                                              const gchar *emailUTF8,
-                                              const gchar *passwordUTF8,
-                                              guint8 *authPW,
-                                              guint8 *unwrapBKey);
-
-void             ephy_sync_service_try_login (EphySyncService *self,
-                                              gboolean login_with_keys,
-                                              const gchar *emailUTF8,
-                                              guint8 *authPW,
-                                              guint8 *sessionToken,
-                                              guint8 *keyFetchToken);
+                                              const gchar     *emailUTF8,
+                                              const gchar     *passwordUTF8);
+
+void             ephy_sync_service_login     (EphySyncService *self);
 
 G_END_DECLS
 
diff --git a/src/ephy-sync-window.c b/src/ephy-sync-window.c
index d7e4e78..6687f1a 100644
--- a/src/ephy-sync-window.c
+++ b/src/ephy-sync-window.c
@@ -18,6 +18,7 @@
 
 #include "ephy-debug.h"
 #include "ephy-gui.h"
+#include "ephy-sync-secret.h"
 #include "ephy-sync-utils.h"
 #include "ephy-sync-window.h"
 
@@ -32,7 +33,8 @@ struct _EphySyncWindow {
 
   GtkWidget *entry_email;
   GtkWidget *entry_password;
-  GtkButton *btn_submit;
+  GtkButton *btn_login;
+  GtkButton *btn_logout;
 
   GActionGroup *action_group;
 };
@@ -48,16 +50,12 @@ enum {
 static GParamSpec *obj_properties[PROP_LAST];
 
 static void
-submit_action (GSimpleAction *action,
-               GVariant      *parameter,
-               gpointer       user_data)
+login_action (GSimpleAction *action,
+              GVariant      *parameter,
+              gpointer       user_data)
 {
   const gchar *emailUTF8;
   const gchar *passwordUTF8;
-  guint8 *authPW;
-  guint8 *unwrapBKey;
-  guint8 *sessionToken;
-  guint8 *keyFetchToken;
   EphySyncWindow *self = EPHY_SYNC_WINDOW (user_data);
 
   emailUTF8 = gtk_entry_get_text (GTK_ENTRY (self->entry_email));
@@ -71,31 +69,20 @@ LOG ("password: %s", passwordUTF8);
     passwordUTF8 = g_strdup ("pässwörd");
   }
 
-  authPW = g_malloc (EPHY_SYNC_TOKEN_LENGTH);
-  unwrapBKey = g_malloc (EPHY_SYNC_TOKEN_LENGTH);
   ephy_sync_service_stretch (self->sync_service,
                              emailUTF8,
-                             passwordUTF8,
-                             authPW,
-                             unwrapBKey);
-ephy_sync_utils_display_hex ("authPW", authPW, EPHY_SYNC_TOKEN_LENGTH);
-ephy_sync_utils_display_hex ("unwrapBKey", unwrapBKey, EPHY_SYNC_TOKEN_LENGTH);
-
-  sessionToken = g_malloc (EPHY_SYNC_TOKEN_LENGTH);
-  keyFetchToken = g_malloc (EPHY_SYNC_TOKEN_LENGTH);
-  ephy_sync_service_try_login (self->sync_service,
-                               FALSE,
-                               emailUTF8,
-                               authPW,
-                               sessionToken,
-                               keyFetchToken);
-ephy_sync_utils_display_hex ("sessionToken", sessionToken, EPHY_SYNC_TOKEN_LENGTH);
-ephy_sync_utils_display_hex ("keyFetchToken", keyFetchToken, EPHY_SYNC_TOKEN_LENGTH);
-
-  g_free (authPW);
-  g_free (unwrapBKey);
-  g_free (sessionToken);
-  g_free (keyFetchToken);
+                             passwordUTF8);
+
+  ephy_sync_service_login (self->sync_service);
+}
+
+/* FIXME: Only for debugging, remove when no longer needed */
+static void
+logout_action (GSimpleAction *action,
+               GVariant      *parameter,
+               gpointer       user_data)
+{
+  ephy_sync_secret_forget_all_tokens (NULL, NULL);
 }
 
 static void
@@ -158,7 +145,8 @@ create_action_group (EphySyncWindow *self)
   GSimpleActionGroup *group;
 
   const GActionEntry entries[] = {
-    { "submit_action", submit_action }
+    { "login_action", login_action },
+    { "logout_action", logout_action }
   };
 
   group = g_simple_action_group_new ();
@@ -193,7 +181,8 @@ LOG ("%s:%d", __func__, __LINE__);
 
   gtk_widget_class_bind_template_child (widget_class, EphySyncWindow, entry_email);
   gtk_widget_class_bind_template_child (widget_class, EphySyncWindow, entry_password);
-  gtk_widget_class_bind_template_child (widget_class, EphySyncWindow, btn_submit);
+  gtk_widget_class_bind_template_child (widget_class, EphySyncWindow, btn_login);
+  gtk_widget_class_bind_template_child (widget_class, EphySyncWindow, btn_logout);
 }
 
 static void
diff --git a/src/resources/sync-dialog.ui b/src/resources/sync-dialog.ui
index df88b37..4da7b10 100644
--- a/src/resources/sync-dialog.ui
+++ b/src/resources/sync-dialog.ui
@@ -87,13 +87,13 @@
               </packing>
             </child>
             <child>
-              <object class="GtkButton" id="btn_submit">
-                <property name="label" translatable="yes">_Submit</property>
+              <object class="GtkButton" id="btn_login">
+                <property name="label" translatable="yes">_Login</property>
                 <property name="visible">True</property>
                 <property name="use-underline">True</property>
                 <property name="sensitive">True</property>
                 <property name="valign">center</property>
-                <property name="action-name">sync.submit_action</property>
+                <property name="action-name">sync.login_action</property>
                 <style>
                   <class name="suggested-action"/>
                   <class name="text-button"/>
@@ -104,6 +104,24 @@
                 <property name="top-attach">2</property>
               </packing>
             </child>
+            <child>
+              <object class="GtkButton" id="btn_logout">
+                <property name="label" translatable="yes">Logout</property>
+                <property name="visible">True</property>
+                <property name="use-underline">True</property>
+                <property name="sensitive">True</property>
+                <property name="valign">center</property>
+                <property name="action-name">sync.logout_action</property>
+                <style>
+                  <class name="suggested-action"/>
+                  <class name="text-button"/>
+                </style>
+              </object>
+              <packing>
+                <property name="left-attach">1</property>
+                <property name="top-attach">2</property>
+              </packing>
+            </child>
           </object>
         </child>
 


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]