autocomplete_history_manager_unittest.cc revision 4e180b6a0b4720a9b8e9e959a882386f690f08ff
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 3// found in the LICENSE file. 4 5#include <vector> 6 7#include "base/memory/ref_counted.h" 8#include "base/message_loop/message_loop_proxy.h" 9#include "base/prefs/testing_pref_service.h" 10#include "base/run_loop.h" 11#include "base/strings/string16.h" 12#include "base/strings/utf_string_conversions.h" 13#include "base/synchronization/waitable_event.h" 14#include "chrome/browser/webdata/web_data_service_factory.h" 15#include "chrome/test/base/chrome_render_view_host_test_harness.h" 16#include "chrome/test/base/testing_profile.h" 17#include "components/autofill/core/browser/autocomplete_history_manager.h" 18#include "components/autofill/core/browser/autofill_external_delegate.h" 19#include "components/autofill/core/browser/autofill_manager.h" 20#include "components/autofill/core/browser/test_autofill_driver.h" 21#include "components/autofill/core/browser/test_autofill_manager_delegate.h" 22#include "components/autofill/core/browser/webdata/autofill_webdata_service.h" 23#include "components/autofill/core/common/form_data.h" 24#include "components/webdata/common/web_data_service_test_util.h" 25#include "content/public/test/test_browser_thread.h" 26#include "content/public/test/test_utils.h" 27#include "testing/gmock/include/gmock/gmock.h" 28#include "testing/gtest/include/gtest/gtest.h" 29#include "ui/gfx/rect.h" 30 31using content::WebContents; 32using testing::_; 33 34namespace autofill { 35 36namespace { 37 38class MockWebDataService : public AutofillWebDataService { 39 public: 40 MockWebDataService() 41 : AutofillWebDataService(base::MessageLoopProxy::current(), 42 base::MessageLoopProxy::current()) { 43 current_mock_web_data_service_ = this; 44 } 45 46 MOCK_METHOD1(AddFormFields, void(const std::vector<FormFieldData>&)); 47 48 static scoped_refptr<MockWebDataService> GetCurrent() { 49 if (!current_mock_web_data_service_) { 50 return new MockWebDataService(); 51 } 52 return current_mock_web_data_service_; 53 } 54 55 protected: 56 virtual ~MockWebDataService() {} 57 58 private: 59 // Keep track of the most recently created instance, so that it can be 60 // associated with the current profile when Build() is called. 61 static MockWebDataService* current_mock_web_data_service_; 62}; 63 64MockWebDataService* MockWebDataService::current_mock_web_data_service_ = NULL; 65 66class MockWebDataServiceWrapperCurrent : public MockWebDataServiceWrapperBase { 67 public: 68 static BrowserContextKeyedService* Build(content::BrowserContext* profile) { 69 return new MockWebDataServiceWrapperCurrent(); 70 } 71 72 MockWebDataServiceWrapperCurrent() {} 73 74 virtual scoped_refptr<AutofillWebDataService> GetAutofillWebData() OVERRIDE { 75 return MockWebDataService::GetCurrent(); 76 } 77 78 private: 79 DISALLOW_COPY_AND_ASSIGN(MockWebDataServiceWrapperCurrent); 80}; 81 82class MockAutofillManagerDelegate 83 : public autofill::TestAutofillManagerDelegate { 84 public: 85 MockAutofillManagerDelegate() {} 86 virtual ~MockAutofillManagerDelegate() {} 87 virtual PrefService* GetPrefs() OVERRIDE { return &prefs_; } 88 89 private: 90 TestingPrefServiceSimple prefs_; 91 92 DISALLOW_COPY_AND_ASSIGN(MockAutofillManagerDelegate); 93}; 94 95} // namespace 96 97class AutocompleteHistoryManagerTest : public ChromeRenderViewHostTestHarness { 98 protected: 99 virtual void SetUp() OVERRIDE { 100 ChromeRenderViewHostTestHarness::SetUp(); 101 web_data_service_ = new MockWebDataService(); 102 WebDataServiceFactory::GetInstance()->SetTestingFactory( 103 profile(), MockWebDataServiceWrapperCurrent::Build); 104 autofill_driver_.reset(new TestAutofillDriver(web_contents())); 105 autocomplete_manager_.reset( 106 new AutocompleteHistoryManager(autofill_driver_.get(), 107 &manager_delegate)); 108 } 109 110 virtual void TearDown() OVERRIDE { 111 autocomplete_manager_.reset(); 112 web_data_service_ = NULL; 113 ChromeRenderViewHostTestHarness::TearDown(); 114 } 115 116 scoped_refptr<MockWebDataService> web_data_service_; 117 scoped_ptr<AutocompleteHistoryManager> autocomplete_manager_; 118 scoped_ptr<AutofillDriver> autofill_driver_; 119 MockAutofillManagerDelegate manager_delegate; 120}; 121 122// Tests that credit card numbers are not sent to the WebDatabase to be saved. 123TEST_F(AutocompleteHistoryManagerTest, CreditCardNumberValue) { 124 FormData form; 125 form.name = ASCIIToUTF16("MyForm"); 126 form.method = ASCIIToUTF16("POST"); 127 form.origin = GURL("http://myform.com/form.html"); 128 form.action = GURL("http://myform.com/submit.html"); 129 form.user_submitted = true; 130 131 // Valid Visa credit card number pulled from the paypal help site. 132 FormFieldData valid_cc; 133 valid_cc.label = ASCIIToUTF16("Credit Card"); 134 valid_cc.name = ASCIIToUTF16("ccnum"); 135 valid_cc.value = ASCIIToUTF16("4012888888881881"); 136 valid_cc.form_control_type = "text"; 137 form.fields.push_back(valid_cc); 138 139 EXPECT_CALL(*web_data_service_.get(), AddFormFields(_)).Times(0); 140 autocomplete_manager_->OnFormSubmitted(form); 141} 142 143// Contrary test to AutocompleteHistoryManagerTest.CreditCardNumberValue. The 144// value being submitted is not a valid credit card number, so it will be sent 145// to the WebDatabase to be saved. 146TEST_F(AutocompleteHistoryManagerTest, NonCreditCardNumberValue) { 147 FormData form; 148 form.name = ASCIIToUTF16("MyForm"); 149 form.method = ASCIIToUTF16("POST"); 150 form.origin = GURL("http://myform.com/form.html"); 151 form.action = GURL("http://myform.com/submit.html"); 152 form.user_submitted = true; 153 154 // Invalid credit card number. 155 FormFieldData invalid_cc; 156 invalid_cc.label = ASCIIToUTF16("Credit Card"); 157 invalid_cc.name = ASCIIToUTF16("ccnum"); 158 invalid_cc.value = ASCIIToUTF16("4580123456789012"); 159 invalid_cc.form_control_type = "text"; 160 form.fields.push_back(invalid_cc); 161 162 EXPECT_CALL(*(web_data_service_.get()), AddFormFields(_)).Times(1); 163 autocomplete_manager_->OnFormSubmitted(form); 164} 165 166// Tests that SSNs are not sent to the WebDatabase to be saved. 167TEST_F(AutocompleteHistoryManagerTest, SSNValue) { 168 FormData form; 169 form.name = ASCIIToUTF16("MyForm"); 170 form.method = ASCIIToUTF16("POST"); 171 form.origin = GURL("http://myform.com/form.html"); 172 form.action = GURL("http://myform.com/submit.html"); 173 form.user_submitted = true; 174 175 FormFieldData ssn; 176 ssn.label = ASCIIToUTF16("Social Security Number"); 177 ssn.name = ASCIIToUTF16("ssn"); 178 ssn.value = ASCIIToUTF16("078-05-1120"); 179 ssn.form_control_type = "text"; 180 form.fields.push_back(ssn); 181 182 EXPECT_CALL(*web_data_service_.get(), AddFormFields(_)).Times(0); 183 autocomplete_manager_->OnFormSubmitted(form); 184} 185 186// Verify that autocomplete text is saved for search fields. 187TEST_F(AutocompleteHistoryManagerTest, SearchField) { 188 FormData form; 189 form.name = ASCIIToUTF16("MyForm"); 190 form.method = ASCIIToUTF16("POST"); 191 form.origin = GURL("http://myform.com/form.html"); 192 form.action = GURL("http://myform.com/submit.html"); 193 form.user_submitted = true; 194 195 // Search field. 196 FormFieldData search_field; 197 search_field.label = ASCIIToUTF16("Search"); 198 search_field.name = ASCIIToUTF16("search"); 199 search_field.value = ASCIIToUTF16("my favorite query"); 200 search_field.form_control_type = "search"; 201 form.fields.push_back(search_field); 202 203 EXPECT_CALL(*(web_data_service_.get()), AddFormFields(_)).Times(1); 204 autocomplete_manager_->OnFormSubmitted(form); 205} 206 207namespace { 208 209class MockAutofillExternalDelegate : public AutofillExternalDelegate { 210 public: 211 MockAutofillExternalDelegate(content::WebContents* web_contents, 212 AutofillManager* autofill_manager, 213 AutofillDriver* autofill_driver) 214 : AutofillExternalDelegate(web_contents, autofill_manager, 215 autofill_driver) {} 216 virtual ~MockAutofillExternalDelegate() {} 217 218 MOCK_METHOD5(OnSuggestionsReturned, 219 void(int query_id, 220 const std::vector<base::string16>& autofill_values, 221 const std::vector<base::string16>& autofill_labels, 222 const std::vector<base::string16>& autofill_icons, 223 const std::vector<int>& autofill_unique_ids)); 224 225 private: 226 DISALLOW_COPY_AND_ASSIGN(MockAutofillExternalDelegate); 227}; 228 229class AutocompleteHistoryManagerNoIPC : public AutocompleteHistoryManager { 230 public: 231 AutocompleteHistoryManagerNoIPC(AutofillDriver* driver, 232 AutofillManagerDelegate* delegate) 233 : AutocompleteHistoryManager(driver, delegate) { 234 // Ensure that IPC is not sent during the test. 235 set_send_ipc(false); 236 } 237 238 using AutocompleteHistoryManager::SendSuggestions; 239}; 240 241} // namespace 242 243// Make sure our external delegate is called at the right time. 244TEST_F(AutocompleteHistoryManagerTest, ExternalDelegate) { 245 AutocompleteHistoryManagerNoIPC autocomplete_history_manager( 246 autofill_driver_.get(), &manager_delegate); 247 248 scoped_ptr<AutofillManager> autofill_manager(new AutofillManager( 249 autofill_driver_.get(), 250 &manager_delegate, 251 "en-US", 252 AutofillManager::ENABLE_AUTOFILL_DOWNLOAD_MANAGER)); 253 254 MockAutofillExternalDelegate external_delegate(web_contents(), 255 autofill_manager.get(), 256 autofill_driver_.get()); 257 autocomplete_history_manager.SetExternalDelegate(&external_delegate); 258 259 // Should trigger a call to OnSuggestionsReturned, verified by the mock. 260 EXPECT_CALL(external_delegate, OnSuggestionsReturned(_, _, _, _, _)); 261 autocomplete_history_manager.SendSuggestions(NULL); 262} 263 264} // namespace autofill 265