Allow only one bookmark to be added for multiple fast starring
[chromium-blink-merge.git] / components / password_manager / content / browser / credential_manager_dispatcher_unittest.cc
blobc7e8c983d6fee873dc9b6a5e062ca8035d22a371
1 // Copyright 2014 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.
5 #include "components/password_manager/content/browser/credential_manager_dispatcher.h"
7 #include "base/bind.h"
8 #include "base/command_line.h"
9 #include "base/prefs/pref_registry_simple.h"
10 #include "base/prefs/testing_pref_service.h"
11 #include "base/run_loop.h"
12 #include "base/strings/string16.h"
13 #include "base/strings/utf_string_conversions.h"
14 #include "base/thread_task_runner_handle.h"
15 #include "components/password_manager/content/common/credential_manager_messages.h"
16 #include "components/password_manager/core/browser/credential_manager_password_form_manager.h"
17 #include "components/password_manager/core/browser/stub_password_manager_client.h"
18 #include "components/password_manager/core/browser/stub_password_manager_driver.h"
19 #include "components/password_manager/core/browser/test_password_store.h"
20 #include "components/password_manager/core/common/credential_manager_types.h"
21 #include "components/password_manager/core/common/password_manager_pref_names.h"
22 #include "content/public/browser/web_contents.h"
23 #include "content/public/test/mock_render_process_host.h"
24 #include "content/public/test/test_renderer_host.h"
25 #include "testing/gmock/include/gmock/gmock.h"
26 #include "testing/gtest/include/gtest/gtest.h"
28 using content::BrowserContext;
29 using content::WebContents;
31 using testing::_;
33 namespace {
35 // Chosen by fair dice roll. Guaranteed to be random.
36 const int kRequestId = 4;
38 class MockPasswordManagerClient
39 : public password_manager::StubPasswordManagerClient {
40 public:
41 MOCK_CONST_METHOD0(IsSavingEnabledForCurrentPage, bool());
42 MOCK_CONST_METHOD0(IsOffTheRecord, bool());
43 MOCK_METHOD1(NotifyUserAutoSigninPtr,
44 bool(const std::vector<autofill::PasswordForm*>& local_forms));
45 MOCK_METHOD2(PromptUserToSavePasswordPtr,
46 void(password_manager::PasswordFormManager*,
47 password_manager::CredentialSourceType type));
48 MOCK_METHOD4(PromptUserToChooseCredentialsPtr,
49 bool(const std::vector<autofill::PasswordForm*>& local_forms,
50 const std::vector<autofill::PasswordForm*>& federated_forms,
51 const GURL& origin,
52 base::Callback<void(
53 const password_manager::CredentialInfo&)> callback));
55 MockPasswordManagerClient(password_manager::PasswordStore* store)
56 : store_(store) {
57 prefs_.registry()->RegisterBooleanPref(
58 password_manager::prefs::kPasswordManagerAutoSignin, true);
60 ~MockPasswordManagerClient() override {}
62 bool PromptUserToSavePassword(
63 scoped_ptr<password_manager::PasswordFormManager> manager,
64 password_manager::CredentialSourceType type) override {
65 manager_.swap(manager);
66 PromptUserToSavePasswordPtr(manager_.get(), type);
67 return true;
70 password_manager::PasswordStore* GetPasswordStore() const override {
71 return store_;
74 PrefService* GetPrefs() override { return &prefs_; }
76 bool PromptUserToChooseCredentials(
77 ScopedVector<autofill::PasswordForm> local_forms,
78 ScopedVector<autofill::PasswordForm> federated_forms,
79 const GURL& origin,
80 base::Callback<void(const password_manager::CredentialInfo&)> callback) {
81 EXPECT_FALSE(local_forms.empty() && federated_forms.empty());
82 password_manager::CredentialInfo info(
83 local_forms.empty() ? *federated_forms[0] : *local_forms[0],
84 local_forms.empty()
85 ? password_manager::CredentialType::CREDENTIAL_TYPE_FEDERATED
86 : password_manager::CredentialType::CREDENTIAL_TYPE_PASSWORD);
87 base::ThreadTaskRunnerHandle::Get()->PostTask(FROM_HERE,
88 base::Bind(callback, info));
89 PromptUserToChooseCredentialsPtr(local_forms.get(), federated_forms.get(),
90 origin, callback);
91 return true;
94 void NotifyUserAutoSignin(
95 ScopedVector<autofill::PasswordForm> local_forms) override {
96 EXPECT_FALSE(local_forms.empty());
97 NotifyUserAutoSigninPtr(local_forms.get());
100 password_manager::PasswordFormManager* pending_manager() const {
101 return manager_.get();
104 void set_zero_click_enabled(bool zero_click_enabled) {
105 prefs_.SetBoolean(password_manager::prefs::kPasswordManagerAutoSignin,
106 zero_click_enabled);
109 private:
110 TestingPrefServiceSimple prefs_;
111 password_manager::PasswordStore* store_;
112 scoped_ptr<password_manager::PasswordFormManager> manager_;
114 DISALLOW_COPY_AND_ASSIGN(MockPasswordManagerClient);
117 class TestCredentialManagerDispatcher
118 : public password_manager::CredentialManagerDispatcher {
119 public:
120 TestCredentialManagerDispatcher(
121 content::WebContents* web_contents,
122 password_manager::PasswordManagerClient* client,
123 password_manager::PasswordManagerDriver* driver);
125 private:
126 base::WeakPtr<password_manager::PasswordManagerDriver> GetDriver() override;
128 base::WeakPtr<password_manager::PasswordManagerDriver> driver_;
131 TestCredentialManagerDispatcher::TestCredentialManagerDispatcher(
132 content::WebContents* web_contents,
133 password_manager::PasswordManagerClient* client,
134 password_manager::PasswordManagerDriver* driver)
135 : CredentialManagerDispatcher(web_contents, client),
136 driver_(driver->AsWeakPtr()) {
139 base::WeakPtr<password_manager::PasswordManagerDriver>
140 TestCredentialManagerDispatcher::GetDriver() {
141 return driver_;
144 void RunAllPendingTasks() {
145 base::RunLoop run_loop;
146 base::MessageLoop::current()->PostTask(
147 FROM_HERE, base::MessageLoop::QuitWhenIdleClosure());
148 run_loop.Run();
151 } // namespace
153 namespace password_manager {
155 class CredentialManagerDispatcherTest
156 : public content::RenderViewHostTestHarness {
157 public:
158 CredentialManagerDispatcherTest() {}
160 void SetUp() override {
161 content::RenderViewHostTestHarness::SetUp();
162 store_ = new TestPasswordStore;
163 client_.reset(new MockPasswordManagerClient(store_.get()));
164 dispatcher_.reset(new TestCredentialManagerDispatcher(
165 web_contents(), client_.get(), &stub_driver_));
166 ON_CALL(*client_, IsSavingEnabledForCurrentPage())
167 .WillByDefault(testing::Return(true));
168 ON_CALL(*client_, IsOffTheRecord()).WillByDefault(testing::Return(false));
170 NavigateAndCommit(GURL("https://example.com/test.html"));
172 form_.username_value = base::ASCIIToUTF16("Username");
173 form_.display_name = base::ASCIIToUTF16("Display Name");
174 form_.password_value = base::ASCIIToUTF16("Password");
175 form_.origin = web_contents()->GetLastCommittedURL().GetOrigin();
176 form_.signon_realm = form_.origin.spec();
177 form_.scheme = autofill::PasswordForm::SCHEME_HTML;
178 form_.skip_zero_click = false;
180 origin_path_form_.username_value = base::ASCIIToUTF16("Username 2");
181 origin_path_form_.display_name = base::ASCIIToUTF16("Display Name 2");
182 origin_path_form_.password_value = base::ASCIIToUTF16("Password 2");
183 origin_path_form_.origin = GURL("https://example.com/path");
184 origin_path_form_.signon_realm = origin_path_form_.origin.spec();
185 origin_path_form_.scheme = autofill::PasswordForm::SCHEME_HTML;
186 origin_path_form_.skip_zero_click = false;
188 cross_origin_form_.username_value = base::ASCIIToUTF16("Username");
189 cross_origin_form_.display_name = base::ASCIIToUTF16("Display Name");
190 cross_origin_form_.password_value = base::ASCIIToUTF16("Password");
191 cross_origin_form_.origin = GURL("https://example.net/");
192 cross_origin_form_.signon_realm = cross_origin_form_.origin.spec();
193 cross_origin_form_.scheme = autofill::PasswordForm::SCHEME_HTML;
194 cross_origin_form_.skip_zero_click = false;
196 store_->Clear();
197 EXPECT_TRUE(store_->IsEmpty());
200 void TearDown() override {
201 store_->Shutdown();
202 content::RenderViewHostTestHarness::TearDown();
205 CredentialManagerDispatcher* dispatcher() { return dispatcher_.get(); }
207 protected:
208 autofill::PasswordForm form_;
209 autofill::PasswordForm origin_path_form_;
210 autofill::PasswordForm cross_origin_form_;
211 scoped_refptr<TestPasswordStore> store_;
212 scoped_ptr<MockPasswordManagerClient> client_;
213 StubPasswordManagerDriver stub_driver_;
214 scoped_ptr<CredentialManagerDispatcher> dispatcher_;
217 TEST_F(CredentialManagerDispatcherTest, CredentialManagerOnStore) {
218 CredentialInfo info(
219 form_, password_manager::CredentialType::CREDENTIAL_TYPE_PASSWORD);
220 EXPECT_CALL(
221 *client_,
222 PromptUserToSavePasswordPtr(
223 _, password_manager::CredentialSourceType::CREDENTIAL_SOURCE_API))
224 .Times(testing::Exactly(1));
226 dispatcher()->OnStore(kRequestId, info);
228 const uint32 kMsgID = CredentialManagerMsg_AcknowledgeStore::ID;
229 const IPC::Message* message =
230 process()->sink().GetFirstMessageMatching(kMsgID);
231 EXPECT_TRUE(message);
232 process()->sink().ClearMessages();
234 // Allow the PasswordFormManager to talk to the password store, determine
235 // that the form is new, and set it as pending.
236 RunAllPendingTasks();
238 EXPECT_TRUE(client_->pending_manager()->HasCompletedMatching());
240 autofill::PasswordForm new_form =
241 client_->pending_manager()->pending_credentials();
242 EXPECT_EQ(form_.username_value, new_form.username_value);
243 EXPECT_EQ(form_.display_name, new_form.display_name);
244 EXPECT_EQ(form_.password_value, new_form.password_value);
245 EXPECT_EQ(form_.origin, new_form.origin);
246 EXPECT_EQ(form_.signon_realm, new_form.signon_realm);
247 EXPECT_EQ(autofill::PasswordForm::SCHEME_HTML, new_form.scheme);
250 TEST_F(CredentialManagerDispatcherTest,
251 CredentialManagerSignInWithSavingDisabledForCurrentPage) {
252 CredentialInfo info(form_, CredentialType::CREDENTIAL_TYPE_PASSWORD);
253 EXPECT_CALL(*client_, IsSavingEnabledForCurrentPage())
254 .WillRepeatedly(testing::Return(false));
255 EXPECT_CALL(
256 *client_,
257 PromptUserToSavePasswordPtr(
258 _, password_manager::CredentialSourceType::CREDENTIAL_SOURCE_API))
259 .Times(testing::Exactly(0));
261 dispatcher()->OnStore(kRequestId, info);
263 const uint32 kMsgID = CredentialManagerMsg_AcknowledgeStore::ID;
264 const IPC::Message* message =
265 process()->sink().GetFirstMessageMatching(kMsgID);
266 EXPECT_TRUE(message);
267 process()->sink().ClearMessages();
269 RunAllPendingTasks();
271 EXPECT_FALSE(client_->pending_manager());
274 TEST_F(CredentialManagerDispatcherTest,
275 CredentialManagerOnRequireUserMediation) {
276 store_->AddLogin(form_);
277 store_->AddLogin(cross_origin_form_);
278 RunAllPendingTasks();
280 TestPasswordStore::PasswordMap passwords = store_->stored_passwords();
281 EXPECT_EQ(2U, passwords.size());
282 EXPECT_EQ(1U, passwords[form_.signon_realm].size());
283 EXPECT_EQ(1U, passwords[cross_origin_form_.signon_realm].size());
284 EXPECT_FALSE(passwords[form_.signon_realm][0].skip_zero_click);
285 EXPECT_FALSE(passwords[cross_origin_form_.signon_realm][0].skip_zero_click);
287 dispatcher()->OnRequireUserMediation(kRequestId);
288 RunAllPendingTasks();
290 const uint32 kMsgID =
291 CredentialManagerMsg_AcknowledgeRequireUserMediation::ID;
292 const IPC::Message* message =
293 process()->sink().GetFirstMessageMatching(kMsgID);
294 EXPECT_TRUE(message);
295 process()->sink().ClearMessages();
297 passwords = store_->stored_passwords();
298 EXPECT_EQ(2U, passwords.size());
299 EXPECT_EQ(1U, passwords[form_.signon_realm].size());
300 EXPECT_EQ(1U, passwords[cross_origin_form_.signon_realm].size());
301 EXPECT_TRUE(passwords[form_.signon_realm][0].skip_zero_click);
302 EXPECT_FALSE(passwords[cross_origin_form_.signon_realm][0].skip_zero_click);
305 TEST_F(CredentialManagerDispatcherTest,
306 CredentialManagerOnRequestCredentialWithEmptyPasswordStore) {
307 std::vector<GURL> federations;
308 EXPECT_CALL(
309 *client_,
310 PromptUserToSavePasswordPtr(
311 _, password_manager::CredentialSourceType::CREDENTIAL_SOURCE_API))
312 .Times(testing::Exactly(0));
313 EXPECT_CALL(*client_, PromptUserToChooseCredentialsPtr(_, _, _, _))
314 .Times(testing::Exactly(0));
315 EXPECT_CALL(*client_, NotifyUserAutoSigninPtr(_)).Times(testing::Exactly(0));
317 dispatcher()->OnRequestCredential(kRequestId, false, federations);
319 RunAllPendingTasks();
321 const uint32 kMsgID = CredentialManagerMsg_SendCredential::ID;
322 const IPC::Message* message =
323 process()->sink().GetFirstMessageMatching(kMsgID);
324 EXPECT_TRUE(message);
325 CredentialManagerMsg_SendCredential::Param param;
326 CredentialManagerMsg_SendCredential::Read(message, &param);
327 EXPECT_EQ(CredentialType::CREDENTIAL_TYPE_EMPTY, base::get<1>(param).type);
328 process()->sink().ClearMessages();
331 TEST_F(CredentialManagerDispatcherTest,
332 CredentialManagerOnRequestCredentialWithCrossOriginPasswordStore) {
333 store_->AddLogin(cross_origin_form_);
335 std::vector<GURL> federations;
336 EXPECT_CALL(
337 *client_,
338 PromptUserToSavePasswordPtr(
339 _, password_manager::CredentialSourceType::CREDENTIAL_SOURCE_API))
340 .Times(testing::Exactly(0));
341 EXPECT_CALL(*client_, PromptUserToChooseCredentialsPtr(_, _, _, _))
342 .Times(testing::Exactly(0));
343 EXPECT_CALL(*client_, NotifyUserAutoSigninPtr(_)).Times(testing::Exactly(0));
345 dispatcher()->OnRequestCredential(kRequestId, false, federations);
347 RunAllPendingTasks();
349 const uint32 kMsgID = CredentialManagerMsg_SendCredential::ID;
350 const IPC::Message* message =
351 process()->sink().GetFirstMessageMatching(kMsgID);
352 EXPECT_TRUE(message);
353 CredentialManagerMsg_SendCredential::Param param;
354 CredentialManagerMsg_SendCredential::Read(message, &param);
355 EXPECT_EQ(CredentialType::CREDENTIAL_TYPE_EMPTY, base::get<1>(param).type);
356 process()->sink().ClearMessages();
359 TEST_F(CredentialManagerDispatcherTest,
360 CredentialManagerOnRequestCredentialWithFullPasswordStore) {
361 client_->set_zero_click_enabled(false);
362 store_->AddLogin(form_);
364 std::vector<GURL> federations;
365 EXPECT_CALL(*client_, PromptUserToChooseCredentialsPtr(_, _, _, _))
366 .Times(testing::Exactly(1));
367 EXPECT_CALL(*client_, NotifyUserAutoSigninPtr(_)).Times(testing::Exactly(0));
369 dispatcher()->OnRequestCredential(kRequestId, false, federations);
371 RunAllPendingTasks();
373 const uint32 kMsgID = CredentialManagerMsg_SendCredential::ID;
374 const IPC::Message* message =
375 process()->sink().GetFirstMessageMatching(kMsgID);
376 EXPECT_TRUE(message);
379 TEST_F(
380 CredentialManagerDispatcherTest,
381 CredentialManagerOnRequestCredentialWithZeroClickOnlyEmptyPasswordStore) {
382 std::vector<GURL> federations;
383 EXPECT_CALL(*client_, PromptUserToChooseCredentialsPtr(_, _, _, _))
384 .Times(testing::Exactly(0));
385 EXPECT_CALL(*client_, NotifyUserAutoSigninPtr(_)).Times(testing::Exactly(0));
387 dispatcher()->OnRequestCredential(kRequestId, true, federations);
389 RunAllPendingTasks();
391 const uint32 kMsgID = CredentialManagerMsg_SendCredential::ID;
392 const IPC::Message* message =
393 process()->sink().GetFirstMessageMatching(kMsgID);
394 EXPECT_TRUE(message);
395 CredentialManagerMsg_SendCredential::Param send_param;
396 CredentialManagerMsg_SendCredential::Read(message, &send_param);
397 EXPECT_EQ(CredentialType::CREDENTIAL_TYPE_EMPTY,
398 base::get<1>(send_param).type);
401 TEST_F(CredentialManagerDispatcherTest,
402 CredentialManagerOnRequestCredentialWithZeroClickOnlyFullPasswordStore) {
403 store_->AddLogin(form_);
405 std::vector<GURL> federations;
406 EXPECT_CALL(*client_, PromptUserToChooseCredentialsPtr(_, _, _, _))
407 .Times(testing::Exactly(0));
408 EXPECT_CALL(*client_, NotifyUserAutoSigninPtr(_)).Times(testing::Exactly(1));
410 dispatcher()->OnRequestCredential(kRequestId, true, federations);
412 RunAllPendingTasks();
414 const uint32 kMsgID = CredentialManagerMsg_SendCredential::ID;
415 const IPC::Message* message =
416 process()->sink().GetFirstMessageMatching(kMsgID);
417 EXPECT_TRUE(message);
418 CredentialManagerMsg_SendCredential::Param send_param;
419 CredentialManagerMsg_SendCredential::Read(message, &send_param);
420 EXPECT_EQ(CredentialType::CREDENTIAL_TYPE_PASSWORD,
421 base::get<1>(send_param).type);
424 TEST_F(CredentialManagerDispatcherTest,
425 CredentialManagerOnRequestCredentialWithZeroClickOnlyTwoPasswordStore) {
426 store_->AddLogin(form_);
427 store_->AddLogin(origin_path_form_);
429 std::vector<GURL> federations;
430 EXPECT_CALL(*client_, PromptUserToChooseCredentialsPtr(_, _, _, _))
431 .Times(testing::Exactly(0));
432 EXPECT_CALL(*client_, NotifyUserAutoSigninPtr(_)).Times(testing::Exactly(0));
434 dispatcher()->OnRequestCredential(kRequestId, true, federations);
436 RunAllPendingTasks();
438 const uint32 kMsgID = CredentialManagerMsg_SendCredential::ID;
439 const IPC::Message* message =
440 process()->sink().GetFirstMessageMatching(kMsgID);
441 EXPECT_TRUE(message);
442 CredentialManagerMsg_SendCredential::Param send_param;
443 CredentialManagerMsg_SendCredential::Read(message, &send_param);
445 // With two items in the password store, we shouldn't get credentials back.
446 EXPECT_EQ(CredentialType::CREDENTIAL_TYPE_EMPTY,
447 base::get<1>(send_param).type);
450 TEST_F(CredentialManagerDispatcherTest,
451 OnRequestCredentialWithZeroClickOnlyOnePasswordStore) {
452 form_.skip_zero_click = true;
453 store_->AddLogin(form_);
454 store_->AddLogin(origin_path_form_);
456 std::vector<GURL> federations;
457 EXPECT_CALL(*client_, PromptUserToChooseCredentialsPtr(_, _, _, _))
458 .Times(testing::Exactly(0));
459 EXPECT_CALL(*client_, NotifyUserAutoSigninPtr(_)).Times(testing::Exactly(1));
461 dispatcher()->OnRequestCredential(kRequestId, true, federations);
463 RunAllPendingTasks();
465 const uint32 kMsgID = CredentialManagerMsg_SendCredential::ID;
466 const IPC::Message* message =
467 process()->sink().GetFirstMessageMatching(kMsgID);
468 EXPECT_TRUE(message);
469 CredentialManagerMsg_SendCredential::Param send_param;
470 CredentialManagerMsg_SendCredential::Read(message, &send_param);
472 // We should get |origin_path_form_| back, as |form_| is marked as skipping
473 // zero-click.
474 EXPECT_EQ(CredentialType::CREDENTIAL_TYPE_PASSWORD,
475 base::get<1>(send_param).type);
476 EXPECT_EQ(origin_path_form_.username_value, base::get<1>(send_param).id);
477 EXPECT_EQ(origin_path_form_.display_name, base::get<1>(send_param).name);
478 EXPECT_EQ(origin_path_form_.password_value,
479 base::get<1>(send_param).password);
482 TEST_F(CredentialManagerDispatcherTest,
483 OnRequestCredentialWithZeroClickOnlyCrossOriginPasswordStore) {
484 store_->AddLogin(cross_origin_form_);
486 form_.skip_zero_click = true;
487 store_->AddLogin(form_);
489 std::vector<GURL> federations;
490 EXPECT_CALL(*client_, PromptUserToChooseCredentialsPtr(_, _, _, _))
491 .Times(testing::Exactly(0));
492 EXPECT_CALL(*client_, NotifyUserAutoSigninPtr(_)).Times(testing::Exactly(0));
494 dispatcher()->OnRequestCredential(kRequestId, true, federations);
496 RunAllPendingTasks();
498 const uint32 kMsgID = CredentialManagerMsg_SendCredential::ID;
499 const IPC::Message* message =
500 process()->sink().GetFirstMessageMatching(kMsgID);
501 EXPECT_TRUE(message);
502 CredentialManagerMsg_SendCredential::Param send_param;
503 CredentialManagerMsg_SendCredential::Read(message, &send_param);
505 // We only have cross-origin zero-click credentials; they should not be
506 // returned.
507 EXPECT_EQ(CredentialType::CREDENTIAL_TYPE_EMPTY,
508 base::get<1>(send_param).type);
511 TEST_F(CredentialManagerDispatcherTest,
512 CredentialManagerOnRequestCredentialWhileRequestPending) {
513 client_->set_zero_click_enabled(false);
514 store_->AddLogin(form_);
516 std::vector<GURL> federations;
517 EXPECT_CALL(*client_, PromptUserToChooseCredentialsPtr(_, _, _, _))
518 .Times(testing::Exactly(0));
519 EXPECT_CALL(*client_, NotifyUserAutoSigninPtr(_)).Times(testing::Exactly(0));
521 dispatcher()->OnRequestCredential(kRequestId, false, federations);
522 dispatcher()->OnRequestCredential(kRequestId, false, federations);
524 // Check that the second request triggered a rejection.
525 uint32 kMsgID = CredentialManagerMsg_RejectCredentialRequest::ID;
526 const IPC::Message* message =
527 process()->sink().GetFirstMessageMatching(kMsgID);
528 EXPECT_TRUE(message);
530 CredentialManagerMsg_RejectCredentialRequest::Param reject_param;
531 CredentialManagerMsg_RejectCredentialRequest::Read(message, &reject_param);
532 EXPECT_EQ(blink::WebCredentialManagerError::ErrorTypePendingRequest,
533 base::get<1>(reject_param));
534 EXPECT_CALL(*client_, PromptUserToChooseCredentialsPtr(_, _, _, _))
535 .Times(testing::Exactly(1));
536 EXPECT_CALL(*client_, NotifyUserAutoSigninPtr(_)).Times(testing::Exactly(0));
538 process()->sink().ClearMessages();
540 // Execute the PasswordStore asynchronousness.
541 RunAllPendingTasks();
543 // Check that the first request resolves.
544 kMsgID = CredentialManagerMsg_SendCredential::ID;
545 message = process()->sink().GetFirstMessageMatching(kMsgID);
546 EXPECT_TRUE(message);
547 CredentialManagerMsg_SendCredential::Param send_param;
548 CredentialManagerMsg_SendCredential::Read(message, &send_param);
549 EXPECT_NE(CredentialType::CREDENTIAL_TYPE_EMPTY,
550 base::get<1>(send_param).type);
551 process()->sink().ClearMessages();
554 TEST_F(CredentialManagerDispatcherTest, ResetSkipZeroClickAfterPrompt) {
555 // Turn on the global zero-click flag, and add two credentials in separate
556 // origins, both set to skip zero-click.
557 client_->set_zero_click_enabled(true);
558 form_.skip_zero_click = true;
559 store_->AddLogin(form_);
560 cross_origin_form_.skip_zero_click = true;
561 store_->AddLogin(cross_origin_form_);
563 // Execute the PasswordStore asynchronousness to ensure everything is
564 // written before proceeding.
565 RunAllPendingTasks();
567 // Sanity check.
568 TestPasswordStore::PasswordMap passwords = store_->stored_passwords();
569 EXPECT_EQ(2U, passwords.size());
570 EXPECT_EQ(1U, passwords[form_.signon_realm].size());
571 EXPECT_EQ(1U, passwords[cross_origin_form_.signon_realm].size());
572 EXPECT_TRUE(passwords[form_.signon_realm][0].skip_zero_click);
573 EXPECT_TRUE(passwords[cross_origin_form_.signon_realm][0].skip_zero_click);
575 // Trigger a request which should return the credential found in |form_|, and
576 // wait for it to process.
577 std::vector<GURL> federations;
578 // Check that the form in the database has been updated. `OnRequestCredential`
579 // generates a call to prompt the user to choose a credential.
580 // MockPasswordManagerClient mocks a user choice, and when users choose a
581 // credential (and have the global zero-click flag enabled), we make sure that
582 // they'll be logged in again next time.
583 EXPECT_CALL(*client_, PromptUserToChooseCredentialsPtr(_, _, _, _))
584 .Times(testing::Exactly(1));
585 EXPECT_CALL(*client_, NotifyUserAutoSigninPtr(_)).Times(testing::Exactly(0));
587 dispatcher()->OnRequestCredential(kRequestId, false, federations);
588 RunAllPendingTasks();
590 passwords = store_->stored_passwords();
591 EXPECT_EQ(2U, passwords.size());
592 EXPECT_EQ(1U, passwords[form_.signon_realm].size());
593 EXPECT_EQ(1U, passwords[cross_origin_form_.signon_realm].size());
594 EXPECT_FALSE(passwords[form_.signon_realm][0].skip_zero_click);
595 EXPECT_TRUE(passwords[cross_origin_form_.signon_realm][0].skip_zero_click);
598 TEST_F(CredentialManagerDispatcherTest, IncognitoZeroClickRequestCredential) {
599 EXPECT_CALL(*client_, IsOffTheRecord()).WillRepeatedly(testing::Return(true));
600 store_->AddLogin(form_);
602 std::vector<GURL> federations;
603 EXPECT_CALL(*client_, PromptUserToChooseCredentialsPtr(_, _, _, _))
604 .Times(testing::Exactly(0));
605 EXPECT_CALL(*client_, NotifyUserAutoSigninPtr(_)).Times(testing::Exactly(0));
607 dispatcher()->OnRequestCredential(kRequestId, true, federations);
609 RunAllPendingTasks();
611 const uint32 kMsgID = CredentialManagerMsg_SendCredential::ID;
612 const IPC::Message* message =
613 process()->sink().GetFirstMessageMatching(kMsgID);
614 ASSERT_TRUE(message);
615 CredentialManagerMsg_SendCredential::Param param;
616 CredentialManagerMsg_SendCredential::Read(message, &param);
617 EXPECT_EQ(CredentialType::CREDENTIAL_TYPE_EMPTY, base::get<1>(param).type);
620 } // namespace password_manager