From b99f082db53c71fc71080cd2283df2b95116b043 Mon Sep 17 00:00:00 2001 From: Gustavo Noronha Silva Date: Fri, 3 May 2013 09:56:43 -0700 Subject: Pre-fill password field when the username field loses focus This change makes Web pass the username as a query attribute when querying the secrets service when the username field loses focus, and pre-fills the password field with the one that was stored for the username the user typed in the username field. https://bugzilla.gnome.org/show_bug.cgi?id=699606 --- embed/web-extension/ephy-embed-form-auth.c | 11 ++++++- embed/web-extension/ephy-embed-form-auth.h | 4 ++- embed/web-extension/ephy-web-extension.c | 46 +++++++++++++++++++++++++++--- lib/ephy-form-auth-data.c | 7 +++-- lib/ephy-form-auth-data.h | 1 + 5 files changed, 61 insertions(+), 8 deletions(-) diff --git a/embed/web-extension/ephy-embed-form-auth.c b/embed/web-extension/ephy-embed-form-auth.c index 9eda22064..38312203d 100644 --- a/embed/web-extension/ephy-embed-form-auth.c +++ b/embed/web-extension/ephy-embed-form-auth.c @@ -27,6 +27,7 @@ struct _EphyEmbedFormAuthPrivate SoupURI *uri; WebKitDOMNode *username_node; WebKitDOMNode *password_node; + char *username; }; G_DEFINE_TYPE (EphyEmbedFormAuth, ephy_embed_form_auth, G_TYPE_OBJECT) @@ -62,7 +63,8 @@ ephy_embed_form_auth_class_init (EphyEmbedFormAuthClass *klass) EphyEmbedFormAuth * ephy_embed_form_auth_new (WebKitWebPage *web_page, WebKitDOMNode *username_node, - WebKitDOMNode *password_node) + WebKitDOMNode *password_node, + const char* username) { EphyEmbedFormAuth *form_auth; @@ -75,6 +77,7 @@ ephy_embed_form_auth_new (WebKitWebPage *web_page, form_auth->priv->uri = soup_uri_new (webkit_web_page_get_uri (web_page)); form_auth->priv->username_node = username_node; form_auth->priv->password_node = password_node; + form_auth->priv->username = g_strdup (username); return form_auth; } @@ -102,3 +105,9 @@ ephy_embed_form_auth_get_page_id (EphyEmbedFormAuth *form_auth) { return form_auth->priv->page_id; } + +const char* +ephy_embed_form_auth_get_username (EphyEmbedFormAuth *form_auth) +{ + return form_auth->priv->username; +} diff --git a/embed/web-extension/ephy-embed-form-auth.h b/embed/web-extension/ephy-embed-form-auth.h index 6dfa92124..099ded54e 100644 --- a/embed/web-extension/ephy-embed-form-auth.h +++ b/embed/web-extension/ephy-embed-form-auth.h @@ -50,11 +50,13 @@ struct _EphyEmbedFormAuthClass GType ephy_embed_form_auth_get_type (void); EphyEmbedFormAuth *ephy_embed_form_auth_new (WebKitWebPage *web_page, WebKitDOMNode *username_node, - WebKitDOMNode *password_node); + WebKitDOMNode *password_node, + const char *username); WebKitDOMNode *ephy_embed_form_auth_get_username_node (EphyEmbedFormAuth *form_auth); WebKitDOMNode *ephy_embed_form_auth_get_password_node (EphyEmbedFormAuth *form_auth); SoupURI *ephy_embed_form_auth_get_uri (EphyEmbedFormAuth *form_auth); guint64 ephy_embed_form_auth_get_page_id (EphyEmbedFormAuth *form_auth); +const char *ephy_embed_form_auth_get_username (EphyEmbedFormAuth *form_auth); G_END_DECLS diff --git a/embed/web-extension/ephy-web-extension.c b/embed/web-extension/ephy-web-extension.c index 675efa943..a6ea34e48 100644 --- a/embed/web-extension/ephy-web-extension.c +++ b/embed/web-extension/ephy-web-extension.c @@ -256,14 +256,19 @@ form_submitted_cb (WebKitDOMHTMLFormElement *dom_form, WebKitDOMNode *username_node = NULL; WebKitDOMNode *password_node = NULL; char *username_field_name = NULL; + char *username_field_value = NULL; char *password_field_name = NULL; char *uri_str; if (!ephy_web_dom_utils_find_form_auth_elements (dom_form, &username_node, &password_node)) return TRUE; + g_object_get (username_node, + "value", &username_field_value, + NULL); + /* EphyEmbedFormAuth takes ownership of the nodes */ - form_auth = ephy_embed_form_auth_new (web_page, username_node, password_node); + form_auth = ephy_embed_form_auth_new (web_page, username_node, password_node, username_field_value); uri = ephy_embed_form_auth_get_uri (form_auth); soup_uri_set_query (uri, NULL); @@ -274,11 +279,13 @@ form_submitted_cb (WebKitDOMHTMLFormElement *dom_form, ephy_form_auth_data_query (uri_str, username_field_name, password_field_name, + username_field_value, should_store_cb, form_auth, (GDestroyNotify)g_object_unref); g_free (username_field_name); + g_free (username_field_value); g_free (password_field_name); g_free (uri_str); @@ -334,6 +341,7 @@ pre_fill_form (EphyEmbedFormAuth *form_auth) EphyFormAuthData *form_data; SoupURI *uri; char *uri_str; + char *username; uri = ephy_embed_form_auth_get_uri (form_auth); if (!uri) @@ -347,15 +355,41 @@ pre_fill_form (EphyEmbedFormAuth *form_auth) form_data = (EphyFormAuthData *)l->data; uri_str = soup_uri_to_string (uri, FALSE); + g_object_get (ephy_embed_form_auth_get_username_node (form_auth), + "value", &username, + NULL); + + /* The username node is empty, so pre-fill with the default. */ + if (g_str_equal (username, "")) + g_clear_pointer (&username, g_free); + ephy_form_auth_data_query (uri_str, form_data->form_username, form_data->form_password, + username, fill_form_cb, g_object_ref (form_auth), - (GDestroyNotify)g_object_unref); + (GDestroyNotify) g_object_unref); + + g_free (username); g_free (uri_str); } +static gboolean +username_changed_cb (WebKitDOMNode *username_node, + WebKitDOMEvent *dom_event, + EphyEmbedFormAuth *form_auth) +{ + pre_fill_form (form_auth); + return TRUE; +} + +static void +form_destroyed_cb (gpointer form_auth, GObject *form) +{ + g_object_unref (form_auth); +} + static void web_page_document_loaded (WebKitWebPage *web_page, gpointer user_data) @@ -393,12 +427,16 @@ web_page_document_loaded (WebKitWebPage *web_page, LOG ("Hooking and pre-filling a form"); /* EphyEmbedFormAuth takes ownership of the nodes */ - form_auth = ephy_embed_form_auth_new (web_page, username_node, password_node); + form_auth = ephy_embed_form_auth_new (web_page, username_node, password_node, NULL); webkit_dom_event_target_add_event_listener (WEBKIT_DOM_EVENT_TARGET (form), "submit", G_CALLBACK (form_submitted_cb), FALSE, web_page); + webkit_dom_event_target_add_event_listener (WEBKIT_DOM_EVENT_TARGET (username_node), "blur", + G_CALLBACK (username_changed_cb), FALSE, + form_auth); pre_fill_form (form_auth); - g_object_unref (form_auth); + + g_object_weak_ref (G_OBJECT (form), form_destroyed_cb, form_auth); } else LOG ("No pre-fillable/hookable form found"); } diff --git a/lib/ephy-form-auth-data.c b/lib/ephy-form-auth-data.c index ecdc50d8f..35a8a829d 100644 --- a/lib/ephy-form-auth-data.c +++ b/lib/ephy-form-auth-data.c @@ -212,6 +212,7 @@ void ephy_form_auth_data_query (const char *uri, const char *form_username, const char *form_password, + const char *username, EphyFormAuthDataQueryCallback callback, gpointer user_data, GDestroyNotify destroy_data) @@ -232,8 +233,10 @@ ephy_form_auth_data_query (const char *uri, key_str = soup_uri_to_string (key, FALSE); - attributes = ephy_form_auth_data_get_secret_attributes_table (key_str, form_username, - form_password, NULL); + attributes = ephy_form_auth_data_get_secret_attributes_table (key_str, + form_username, + form_password, + username); closure = g_slice_new0 (EphyFormAuthDataQueryClosure); closure->callback = callback; diff --git a/lib/ephy-form-auth-data.h b/lib/ephy-form-auth-data.h index 33333719c..6184beaf9 100644 --- a/lib/ephy-form-auth-data.h +++ b/lib/ephy-form-auth-data.h @@ -48,6 +48,7 @@ typedef void (*EphyFormAuthDataQueryCallback) (const char *username, void ephy_form_auth_data_query (const char *uri, const char *form_username, const char *form_password, + const char *username, EphyFormAuthDataQueryCallback callback, gpointer user_data, GDestroyNotify destroy_data); -- cgit v1.2.3