1// Copyright (c) 2011 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 "chrome/browser/sync/signin_manager.h"
6
7#include "chrome/browser/net/gaia/token_service.h"
8#include "chrome/browser/net/gaia/token_service_unittest.h"
9#include "chrome/browser/password_manager/encryptor.h"
10#include "chrome/browser/webdata/web_data_service.h"
11#include "chrome/common/net/test_url_fetcher_factory.h"
12#include "chrome/test/testing_profile.h"
13#include "chrome/test/signaling_task.h"
14#include "net/url_request/url_request.h"
15#include "net/url_request/url_request_status.h"
16
17#include "testing/gtest/include/gtest/gtest.h"
18
19class SigninManagerTest : public TokenServiceTestHarness {
20 public:
21  virtual void SetUp() {
22    TokenServiceTestHarness::SetUp();
23    manager_.reset(new SigninManager());
24    google_login_success_.ListenFor(NotificationType::GOOGLE_SIGNIN_SUCCESSFUL,
25                                    Source<Profile>(profile_.get()));
26    google_login_failure_.ListenFor(NotificationType::GOOGLE_SIGNIN_FAILED,
27                                    Source<Profile>(profile_.get()));
28
29    URLFetcher::set_factory(&factory_);
30  }
31
32  void SimulateValidResponse() {
33    // Simulate the correct ClientLogin response.
34    TestURLFetcher* fetcher = factory_.GetFetcherByID(0);
35    DCHECK(fetcher);
36    DCHECK(fetcher->delegate());
37    fetcher->delegate()->OnURLFetchComplete(
38        fetcher, GURL(GaiaAuthFetcher::kClientLoginUrl),
39        net::URLRequestStatus(), 200, ResponseCookies(),
40        "SID=sid\nLSID=lsid\nAuth=auth");
41
42    // Then simulate the correct GetUserInfo response for the canonical email.
43    // A new URL fetcher is used for each call.
44    fetcher = factory_.GetFetcherByID(0);
45    DCHECK(fetcher);
46    DCHECK(fetcher->delegate());
47    fetcher->delegate()->OnURLFetchComplete(
48        fetcher, GURL(GaiaAuthFetcher::kGetUserInfoUrl),
49        net::URLRequestStatus(), 200, ResponseCookies(),
50        "email=user@gmail.com");
51  }
52
53
54  TestURLFetcherFactory factory_;
55  scoped_ptr<SigninManager> manager_;
56  TestNotificationTracker google_login_success_;
57  TestNotificationTracker google_login_failure_;
58};
59
60TEST_F(SigninManagerTest, SignIn) {
61  manager_->Initialize(profile_.get());
62  EXPECT_TRUE(manager_->GetUsername().empty());
63
64  manager_->StartSignIn("username", "password", "", "");
65  EXPECT_FALSE(manager_->GetUsername().empty());
66
67  SimulateValidResponse();
68
69  // Should go into token service and stop.
70  EXPECT_EQ(1U, google_login_success_.size());
71  EXPECT_EQ(0U, google_login_failure_.size());
72
73  // Should persist across resets.
74  manager_.reset(new SigninManager());
75  manager_->Initialize(profile_.get());
76  EXPECT_EQ("user@gmail.com", manager_->GetUsername());
77}
78
79TEST_F(SigninManagerTest, SignOut) {
80  manager_->Initialize(profile_.get());
81  manager_->StartSignIn("username", "password", "", "");
82  SimulateValidResponse();
83  manager_->OnClientLoginSuccess(credentials_);
84
85  EXPECT_EQ("user@gmail.com", manager_->GetUsername());
86  manager_->SignOut();
87  EXPECT_TRUE(manager_->GetUsername().empty());
88  // Should not be persisted anymore
89  manager_.reset(new SigninManager());
90  manager_->Initialize(profile_.get());
91  EXPECT_TRUE(manager_->GetUsername().empty());
92}
93
94TEST_F(SigninManagerTest, SignInFailure) {
95  manager_->Initialize(profile_.get());
96  manager_->StartSignIn("username", "password", "", "");
97  GoogleServiceAuthError error(GoogleServiceAuthError::REQUEST_CANCELED);
98  manager_->OnClientLoginFailure(error);
99
100  EXPECT_EQ(0U, google_login_success_.size());
101  EXPECT_EQ(1U, google_login_failure_.size());
102
103  EXPECT_TRUE(manager_->GetUsername().empty());
104
105  // Should not be persisted
106  manager_.reset(new SigninManager());
107  manager_->Initialize(profile_.get());
108  EXPECT_TRUE(manager_->GetUsername().empty());
109}
110
111TEST_F(SigninManagerTest, ProvideSecondFactorSuccess) {
112  manager_->Initialize(profile_.get());
113  manager_->StartSignIn("username", "password", "", "");
114  GoogleServiceAuthError error(GoogleServiceAuthError::TWO_FACTOR);
115  manager_->OnClientLoginFailure(error);
116
117  EXPECT_EQ(0U, google_login_success_.size());
118  EXPECT_EQ(1U, google_login_failure_.size());
119
120  EXPECT_FALSE(manager_->GetUsername().empty());
121
122  manager_->ProvideSecondFactorAccessCode("access");
123  SimulateValidResponse();
124
125  EXPECT_EQ(1U, google_login_success_.size());
126  EXPECT_EQ(1U, google_login_failure_.size());
127}
128
129TEST_F(SigninManagerTest, ProvideSecondFactorFailure) {
130  manager_->Initialize(profile_.get());
131  manager_->StartSignIn("username", "password", "", "");
132  GoogleServiceAuthError error1(GoogleServiceAuthError::TWO_FACTOR);
133  manager_->OnClientLoginFailure(error1);
134
135  EXPECT_EQ(0U, google_login_success_.size());
136  EXPECT_EQ(1U, google_login_failure_.size());
137
138  EXPECT_FALSE(manager_->GetUsername().empty());
139
140  manager_->ProvideSecondFactorAccessCode("badaccess");
141  GoogleServiceAuthError error2(
142      GoogleServiceAuthError::INVALID_GAIA_CREDENTIALS);
143  manager_->OnClientLoginFailure(error2);
144
145  EXPECT_EQ(0U, google_login_success_.size());
146  EXPECT_EQ(2U, google_login_failure_.size());
147  EXPECT_FALSE(manager_->GetUsername().empty());
148
149  manager_->ProvideSecondFactorAccessCode("badaccess");
150  GoogleServiceAuthError error3(GoogleServiceAuthError::CONNECTION_FAILED);
151  manager_->OnClientLoginFailure(error3);
152
153  EXPECT_EQ(0U, google_login_success_.size());
154  EXPECT_EQ(3U, google_login_failure_.size());
155  EXPECT_TRUE(manager_->GetUsername().empty());
156}
157
158TEST_F(SigninManagerTest, SignOutMidConnect) {
159  manager_->Initialize(profile_.get());
160  manager_->StartSignIn("username", "password", "", "");
161  manager_->SignOut();
162  EXPECT_EQ(0U, google_login_success_.size());
163  EXPECT_EQ(0U, google_login_failure_.size());
164
165  EXPECT_TRUE(manager_->GetUsername().empty());
166}
167