OLD | NEW |
1 // Copyright 2013 The Chromium Authors. All rights reserved. | 1 // Copyright 2013 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "components/autofill/content/renderer/password_autofill_agent.h" | 5 #include "components/autofill/content/renderer/password_autofill_agent.h" |
6 | 6 |
7 #include "base/bind.h" | 7 #include "base/bind.h" |
8 #include "base/memory/scoped_ptr.h" | 8 #include "base/memory/scoped_ptr.h" |
9 #include "base/message_loop/message_loop.h" | 9 #include "base/message_loop/message_loop.h" |
10 #include "base/metrics/histogram.h" | 10 #include "base/metrics/histogram.h" |
(...skipping 216 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
227 const blink::WebFormElement& form) { | 227 const blink::WebFormElement& form) { |
228 logger->LogHTMLForm(message_id, | 228 logger->LogHTMLForm(message_id, |
229 form.name().utf8(), | 229 form.name().utf8(), |
230 GURL(form.action().utf8())); | 230 GURL(form.action().utf8())); |
231 } | 231 } |
232 | 232 |
233 bool FillDataContainsUsername(const PasswordFormFillData& fill_data) { | 233 bool FillDataContainsUsername(const PasswordFormFillData& fill_data) { |
234 return !fill_data.basic_data.fields[0].name.empty(); | 234 return !fill_data.basic_data.fields[0].name.empty(); |
235 } | 235 } |
236 | 236 |
237 // This function attempts to fill |suggestions| and |realms| form |fill_data| | 237 // Sets |suggestions_present| to true if there are any suggestions to be derived |
238 // based on |current_username|. Returns true when |suggestions| gets filled | 238 // from |fill_data|. Unless |show_all| is true, only considers suggestions with |
239 // from |fill_data.other_possible_usernames|, else returns false. | 239 // usernames having |current_username| as a prefix. Returns true if a username |
240 bool GetSuggestions(const PasswordFormFillData& fill_data, | 240 // from the |fill_data.other_possible_usernames| would be included in the |
241 const base::string16& current_username, | 241 // suggestions. |
242 std::vector<base::string16>* suggestions, | 242 bool GetSuggestionsStats(const PasswordFormFillData& fill_data, |
243 std::vector<base::string16>* realms, | 243 const base::string16& current_username, |
244 bool show_all) { | 244 bool show_all, |
245 bool other_possible_username_shown = false; | 245 bool* suggestions_present) { |
246 if (show_all || | 246 *suggestions_present = false; |
247 StartsWith( | |
248 fill_data.basic_data.fields[0].value, current_username, false)) { | |
249 suggestions->push_back(fill_data.basic_data.fields[0].value); | |
250 realms->push_back(base::UTF8ToUTF16(fill_data.preferred_realm)); | |
251 } | |
252 | 247 |
253 for (PasswordFormFillData::LoginCollection::const_iterator iter = | 248 for (const auto& usernames : fill_data.other_possible_usernames) { |
254 fill_data.additional_logins.begin(); | 249 for (size_t i = 0; i < usernames.second.size(); ++i) { |
255 iter != fill_data.additional_logins.end(); | 250 if (show_all || |
256 ++iter) { | 251 StartsWith(usernames.second[i], current_username, false)) { |
257 if (show_all || StartsWith(iter->first, current_username, false)) { | 252 *suggestions_present = true; |
258 suggestions->push_back(iter->first); | 253 return true; |
259 realms->push_back(base::UTF8ToUTF16(iter->second.realm)); | 254 } |
260 } | 255 } |
261 } | 256 } |
262 | 257 |
263 for (PasswordFormFillData::UsernamesCollection::const_iterator iter = | 258 if (show_all || StartsWith(fill_data.basic_data.fields[0].value, |
264 fill_data.other_possible_usernames.begin(); | 259 current_username, false)) { |
265 iter != fill_data.other_possible_usernames.end(); | 260 *suggestions_present = true; |
266 ++iter) { | 261 return false; |
267 for (size_t i = 0; i < iter->second.size(); ++i) { | 262 } |
268 if (show_all || StartsWith(iter->second[i], current_username, false)) { | 263 |
269 other_possible_username_shown = true; | 264 for (const auto& login : fill_data.additional_logins) { |
270 suggestions->push_back(iter->second[i]); | 265 if (show_all || StartsWith(login.first, current_username, false)) { |
271 realms->push_back(base::UTF8ToUTF16(iter->first.realm)); | 266 *suggestions_present = true; |
272 } | 267 return false; |
273 } | 268 } |
274 } | 269 } |
275 return other_possible_username_shown; | 270 |
| 271 return false; |
276 } | 272 } |
277 | 273 |
278 // This function attempts to fill |username_element| and |password_element| | 274 // This function attempts to fill |username_element| and |password_element| |
279 // with values from |fill_data|. The |password_element| will only have the | 275 // with values from |fill_data|. The |password_element| will only have the |
280 // |suggestedValue| set, and will be registered for copying that to the real | 276 // |suggestedValue| set, and will be registered for copying that to the real |
281 // value through |registration_callback|. The function returns true when | 277 // value through |registration_callback|. The function returns true when |
282 // selected username comes from |fill_data.other_possible_usernames|. | 278 // selected username comes from |fill_data.other_possible_usernames|. |
283 bool FillUserNameAndPassword( | 279 bool FillUserNameAndPassword( |
284 blink::WebInputElement* username_element, | 280 blink::WebInputElement* username_element, |
285 blink::WebInputElement* password_element, | 281 blink::WebInputElement* password_element, |
(...skipping 805 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1091 const blink::WebInputElement& user_input, | 1087 const blink::WebInputElement& user_input, |
1092 bool show_all) { | 1088 bool show_all) { |
1093 blink::WebFrame* frame = user_input.document().frame(); | 1089 blink::WebFrame* frame = user_input.document().frame(); |
1094 if (!frame) | 1090 if (!frame) |
1095 return false; | 1091 return false; |
1096 | 1092 |
1097 blink::WebView* webview = frame->view(); | 1093 blink::WebView* webview = frame->view(); |
1098 if (!webview) | 1094 if (!webview) |
1099 return false; | 1095 return false; |
1100 | 1096 |
1101 std::vector<base::string16> suggestions; | |
1102 std::vector<base::string16> realms; | |
1103 if (GetSuggestions( | |
1104 fill_data, user_input.value(), &suggestions, &realms, show_all)) { | |
1105 usernames_usage_ = OTHER_POSSIBLE_USERNAME_SHOWN; | |
1106 } | |
1107 | |
1108 DCHECK_EQ(suggestions.size(), realms.size()); | |
1109 | |
1110 FormData form; | 1097 FormData form; |
1111 FormFieldData field; | 1098 FormFieldData field; |
1112 FindFormAndFieldForFormControlElement( | 1099 FindFormAndFieldForFormControlElement( |
1113 user_input, &form, &field, REQUIRE_NONE); | 1100 user_input, &form, &field, REQUIRE_NONE); |
1114 | 1101 |
1115 blink::WebInputElement selected_element = user_input; | 1102 blink::WebInputElement selected_element = user_input; |
1116 gfx::Rect bounding_box(selected_element.boundsInViewportSpace()); | 1103 gfx::Rect bounding_box(selected_element.boundsInViewportSpace()); |
1117 | 1104 |
1118 float scale = web_view_->pageScaleFactor(); | 1105 float scale = web_view_->pageScaleFactor(); |
1119 gfx::RectF bounding_box_scaled(bounding_box.x() * scale, | 1106 gfx::RectF bounding_box_scaled(bounding_box.x() * scale, |
1120 bounding_box.y() * scale, | 1107 bounding_box.y() * scale, |
1121 bounding_box.width() * scale, | 1108 bounding_box.width() * scale, |
1122 bounding_box.height() * scale); | 1109 bounding_box.height() * scale); |
1123 Send(new AutofillHostMsg_ShowPasswordSuggestions( | 1110 Send(new AutofillHostMsg_ShowPasswordSuggestions( |
1124 routing_id(), field, bounding_box_scaled, suggestions, realms)); | 1111 routing_id(), field, user_input.value(), show_all, bounding_box_scaled)); |
1125 return !suggestions.empty(); | 1112 |
| 1113 bool suggestions_present = false; |
| 1114 if (GetSuggestionsStats(fill_data, user_input.value(), show_all, |
| 1115 &suggestions_present)) { |
| 1116 usernames_usage_ = OTHER_POSSIBLE_USERNAME_SHOWN; |
| 1117 } |
| 1118 return suggestions_present; |
1126 } | 1119 } |
1127 | 1120 |
1128 void PasswordAutofillAgent::PerformInlineAutocomplete( | 1121 void PasswordAutofillAgent::PerformInlineAutocomplete( |
1129 const blink::WebInputElement& username_input, | 1122 const blink::WebInputElement& username_input, |
1130 const blink::WebInputElement& password_input, | 1123 const blink::WebInputElement& password_input, |
1131 const PasswordFormFillData& fill_data) { | 1124 const PasswordFormFillData& fill_data) { |
1132 DCHECK(!fill_data.wait_for_username); | 1125 DCHECK(!fill_data.wait_for_username); |
1133 | 1126 |
1134 // We need non-const versions of the username and password inputs. | 1127 // We need non-const versions of the username and password inputs. |
1135 blink::WebInputElement username = username_input; | 1128 blink::WebInputElement username = username_input; |
(...skipping 97 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1233 scoped_ptr<PasswordForm> password_form(CreatePasswordForm(form)); | 1226 scoped_ptr<PasswordForm> password_form(CreatePasswordForm(form)); |
1234 if (!password_form || (restriction == RESTRICTION_NON_EMPTY_PASSWORD && | 1227 if (!password_form || (restriction == RESTRICTION_NON_EMPTY_PASSWORD && |
1235 password_form->password_value.empty() && | 1228 password_form->password_value.empty() && |
1236 password_form->new_password_value.empty())) { | 1229 password_form->new_password_value.empty())) { |
1237 return; | 1230 return; |
1238 } | 1231 } |
1239 provisionally_saved_forms_[frame].reset(password_form.release()); | 1232 provisionally_saved_forms_[frame].reset(password_form.release()); |
1240 } | 1233 } |
1241 | 1234 |
1242 } // namespace autofill | 1235 } // namespace autofill |
OLD | NEW |