| OLD | NEW |
| 1 // Copyright (c) 2013 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 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 "base/message_loop/message_loop.h" | 5 #include "base/message_loop/message_loop.h" |
| 6 #include "base/prefs/pref_service.h" | 6 #include "base/prefs/pref_service.h" |
| 7 #include "base/synchronization/waitable_event.h" |
| 7 #include "chrome/browser/browser_process.h" | 8 #include "chrome/browser/browser_process.h" |
| 8 #include "chrome/browser/chrome_notification_types.h" | 9 #include "chrome/browser/chrome_notification_types.h" |
| 9 #include "chrome/browser/chromeos/login/oauth2_login_manager.h" | 10 #include "chrome/browser/chromeos/login/oauth2_login_manager.h" |
| 10 #include "chrome/browser/chromeos/login/oauth2_login_manager_factory.h" | 11 #include "chrome/browser/chromeos/login/oauth2_login_manager_factory.h" |
| 11 #include "chrome/browser/chromeos/login/oobe_base_test.h" | 12 #include "chrome/browser/chromeos/login/oobe_base_test.h" |
| 12 #include "chrome/browser/chromeos/login/user_manager.h" | 13 #include "chrome/browser/chromeos/login/user_manager.h" |
| 13 #include "chrome/browser/chromeos/login/wizard_controller.h" | 14 #include "chrome/browser/chromeos/login/wizard_controller.h" |
| 14 #include "chrome/browser/profiles/profile_manager.h" | 15 #include "chrome/browser/profiles/profile_manager.h" |
| 15 #include "chrome/browser/signin/profile_oauth2_token_service.h" | 16 #include "chrome/browser/signin/profile_oauth2_token_service.h" |
| 16 #include "chrome/browser/signin/profile_oauth2_token_service_factory.h" | 17 #include "chrome/browser/signin/profile_oauth2_token_service_factory.h" |
| 18 #include "chrome/browser/ui/app_modal_dialogs/javascript_app_modal_dialog.h" |
| 19 #include "chrome/browser/ui/app_modal_dialogs/native_app_modal_dialog.h" |
| 20 #include "chrome/browser/ui/browser.h" |
| 21 #include "chrome/browser/ui/browser_tabstrip.h" |
| 22 #include "chrome/browser/ui/scoped_tabbed_browser_displayer.h" |
| 23 #include "chrome/browser/ui/tabs/tab_strip_model.h" |
| 17 #include "chrome/browser/ui/webui/chromeos/login/signin_screen_handler.h" | 24 #include "chrome/browser/ui/webui/chromeos/login/signin_screen_handler.h" |
| 25 #include "chrome/test/base/ui_test_utils.h" |
| 18 #include "content/public/browser/notification_service.h" | 26 #include "content/public/browser/notification_service.h" |
| 27 #include "content/public/test/browser_test_utils.h" |
| 19 #include "google_apis/gaia/gaia_constants.h" | 28 #include "google_apis/gaia/gaia_constants.h" |
| 20 #include "google_apis/gaia/gaia_urls.h" | 29 #include "google_apis/gaia/gaia_urls.h" |
| 21 #include "net/cookies/canonical_cookie.h" | 30 #include "net/cookies/canonical_cookie.h" |
| 22 #include "net/cookies/cookie_monster.h" | 31 #include "net/cookies/cookie_monster.h" |
| 23 #include "net/cookies/cookie_store.h" | 32 #include "net/cookies/cookie_store.h" |
| 33 #include "net/test/embedded_test_server/http_request.h" |
| 34 #include "net/test/embedded_test_server/http_response.h" |
| 24 #include "net/url_request/url_request_context.h" | 35 #include "net/url_request/url_request_context.h" |
| 25 #include "net/url_request/url_request_context_getter.h" | 36 #include "net/url_request/url_request_context_getter.h" |
| 26 | 37 |
| 38 using net::test_server::BasicHttpResponse; |
| 39 using net::test_server::HttpRequest; |
| 40 using net::test_server::HttpResponse; |
| 41 |
| 27 namespace chromeos { | 42 namespace chromeos { |
| 28 | 43 |
| 29 namespace { | 44 namespace { |
| 30 | 45 |
| 31 // Email of owner account for test. | 46 // Email of owner account for test. |
| 32 const char kTestAccountId[] = "username@gmail.com"; | 47 const char kTestAccountId[] = "username@gmail.com"; |
| 33 const char kTestRawAccountId[] = "User.Name"; | 48 const char kTestRawAccountId[] = "User.Name"; |
| 34 const char kTestAccountPassword[] = "fake-password"; | 49 const char kTestAccountPassword[] = "fake-password"; |
| 35 const char kTestAuthCode[] = "fake-auth-code"; | 50 const char kTestAuthCode[] = "fake-auth-code"; |
| 36 const char kTestGaiaUberToken[] = "fake-uber-token"; | 51 const char kTestGaiaUberToken[] = "fake-uber-token"; |
| 37 const char kTestAuthLoginAccessToken[] = "fake-access-token"; | 52 const char kTestAuthLoginAccessToken[] = "fake-access-token"; |
| 38 const char kTestRefreshToken[] = "fake-refresh-token"; | 53 const char kTestRefreshToken[] = "fake-refresh-token"; |
| 39 const char kTestAuthSIDCookie[] = "fake-auth-SID-cookie"; | 54 const char kTestAuthSIDCookie[] = "fake-auth-SID-cookie"; |
| 40 const char kTestAuthLSIDCookie[] = "fake-auth-LSID-cookie"; | 55 const char kTestAuthLSIDCookie[] = "fake-auth-LSID-cookie"; |
| 41 const char kTestSessionSIDCookie[] = "fake-session-SID-cookie"; | 56 const char kTestSessionSIDCookie[] = "fake-session-SID-cookie"; |
| 42 const char kTestSessionLSIDCookie[] = "fake-session-LSID-cookie"; | 57 const char kTestSessionLSIDCookie[] = "fake-session-LSID-cookie"; |
| 43 const char kTestSession2SIDCookie[] = "fake-session2-SID-cookie"; | 58 const char kTestSession2SIDCookie[] = "fake-session2-SID-cookie"; |
| 44 const char kTestSession2LSIDCookie[] = "fake-session2-LSID-cookie"; | 59 const char kTestSession2LSIDCookie[] = "fake-session2-LSID-cookie"; |
| 45 const char kTestUserinfoToken[] = "fake-userinfo-token"; | 60 const char kTestUserinfoToken[] = "fake-userinfo-token"; |
| 46 const char kTestLoginToken[] = "fake-login-token"; | 61 const char kTestLoginToken[] = "fake-login-token"; |
| 47 const char kTestSyncToken[] = "fake-sync-token"; | 62 const char kTestSyncToken[] = "fake-sync-token"; |
| 48 const char kTestAuthLoginToken[] = "fake-oauthlogin-token"; | 63 const char kTestAuthLoginToken[] = "fake-oauthlogin-token"; |
| 49 | 64 |
| 65 class OAuth2LoginManagerStateWaiter : public OAuth2LoginManager::Observer { |
| 66 public: |
| 67 explicit OAuth2LoginManagerStateWaiter(Profile* profile) |
| 68 : profile_(profile), |
| 69 waiting_for_state_(false), |
| 70 final_state_(OAuth2LoginManager::SESSION_RESTORE_NOT_STARTED) { |
| 71 } |
| 72 |
| 73 void WaitForStates( |
| 74 const std::set<OAuth2LoginManager::SessionRestoreState>& states) { |
| 75 DCHECK(!waiting_for_state_); |
| 76 OAuth2LoginManager* login_manager = |
| 77 OAuth2LoginManagerFactory::GetInstance()->GetForProfile(profile_); |
| 78 states_ = states; |
| 79 if (states_.find(login_manager->state()) != states_.end()) { |
| 80 final_state_ = login_manager->state(); |
| 81 return; |
| 82 } |
| 83 |
| 84 waiting_for_state_ = true; |
| 85 login_manager->AddObserver(this); |
| 86 runner_ = new content::MessageLoopRunner; |
| 87 runner_->Run(); |
| 88 login_manager->RemoveObserver(this); |
| 89 } |
| 90 |
| 91 OAuth2LoginManager::SessionRestoreState final_state() { return final_state_; } |
| 92 |
| 93 private: |
| 94 // OAuth2LoginManager::Observer overrides. |
| 95 virtual void OnSessionRestoreStateChanged( |
| 96 Profile* user_profile, |
| 97 OAuth2LoginManager::SessionRestoreState state) OVERRIDE { |
| 98 if (!waiting_for_state_) |
| 99 return; |
| 100 |
| 101 if (states_.find(state) == states_.end()) |
| 102 return; |
| 103 |
| 104 final_state_ = state; |
| 105 waiting_for_state_ = false; |
| 106 runner_->Quit(); |
| 107 } |
| 108 |
| 109 Profile* profile_; |
| 110 std::set<OAuth2LoginManager::SessionRestoreState> states_; |
| 111 bool waiting_for_state_; |
| 112 OAuth2LoginManager::SessionRestoreState final_state_; |
| 113 scoped_refptr<content::MessageLoopRunner> runner_; |
| 114 |
| 115 DISALLOW_COPY_AND_ASSIGN(OAuth2LoginManagerStateWaiter); |
| 116 }; |
| 117 |
| 50 } // namespace | 118 } // namespace |
| 51 | 119 |
| 52 class OAuth2Test : public OobeBaseTest { | 120 class OAuth2Test : public OobeBaseTest { |
| 53 protected: | 121 protected: |
| 54 OAuth2Test() {} | 122 OAuth2Test() {} |
| 55 | 123 |
| 56 virtual void SetUpOnMainThread() OVERRIDE { | |
| 57 OobeBaseTest::SetUpOnMainThread(); | |
| 58 } | |
| 59 | |
| 60 void SetupGaiaServerForNewAccount() { | 124 void SetupGaiaServerForNewAccount() { |
| 61 FakeGaia::MergeSessionParams params; | 125 FakeGaia::MergeSessionParams params; |
| 62 params.auth_sid_cookie = kTestAuthSIDCookie; | 126 params.auth_sid_cookie = kTestAuthSIDCookie; |
| 63 params.auth_lsid_cookie = kTestAuthLSIDCookie; | 127 params.auth_lsid_cookie = kTestAuthLSIDCookie; |
| 64 params.auth_code = kTestAuthCode; | 128 params.auth_code = kTestAuthCode; |
| 65 params.refresh_token = kTestRefreshToken; | 129 params.refresh_token = kTestRefreshToken; |
| 66 params.access_token = kTestAuthLoginAccessToken; | 130 params.access_token = kTestAuthLoginAccessToken; |
| 67 params.gaia_uber_token = kTestGaiaUberToken; | 131 params.gaia_uber_token = kTestGaiaUberToken; |
| 68 params.session_sid_cookie = kTestSessionSIDCookie; | 132 params.session_sid_cookie = kTestSessionSIDCookie; |
| 69 params.session_lsid_cookie = kTestSessionLSIDCookie; | 133 params.session_lsid_cookie = kTestSessionLSIDCookie; |
| 70 fake_gaia_.SetMergeSessionParams(params); | 134 fake_gaia_->SetMergeSessionParams(params); |
| 71 SetupGaiaServerWithAccessTokens(); | 135 SetupGaiaServerWithAccessTokens(); |
| 72 } | 136 } |
| 73 | 137 |
| 74 void SetupGaiaServerForExistingAccount() { | 138 void SetupGaiaServerForExistingAccount() { |
| 75 FakeGaia::MergeSessionParams params; | 139 FakeGaia::MergeSessionParams params; |
| 76 params.gaia_uber_token = kTestGaiaUberToken; | 140 params.gaia_uber_token = kTestGaiaUberToken; |
| 77 params.session_sid_cookie = kTestSession2SIDCookie; | 141 params.session_sid_cookie = kTestSession2SIDCookie; |
| 78 params.session_lsid_cookie = kTestSession2LSIDCookie; | 142 params.session_lsid_cookie = kTestSession2LSIDCookie; |
| 79 fake_gaia_.SetMergeSessionParams(params); | 143 fake_gaia_->SetMergeSessionParams(params); |
| 80 SetupGaiaServerWithAccessTokens(); | 144 SetupGaiaServerWithAccessTokens(); |
| 81 } | 145 } |
| 82 | 146 |
| 83 bool TryToLogin(const std::string& username, | 147 bool TryToLogin(const std::string& username, |
| 84 const std::string& password) { | 148 const std::string& password) { |
| 85 if (!AddUserTosession(username, password)) | 149 if (!AddUserTosession(username, password)) |
| 86 return false; | 150 return false; |
| 87 | 151 |
| 88 if (const User* active_user = UserManager::Get()->GetActiveUser()) | 152 if (const User* active_user = UserManager::Get()->GetActiveUser()) |
| 89 return active_user->email() == username; | 153 return active_user->email() == username; |
| (...skipping 10 matching lines...) Expand all Loading... |
| 100 if (prefs_oauth_status && | 164 if (prefs_oauth_status && |
| 101 prefs_oauth_status->GetIntegerWithoutPathExpansion( | 165 prefs_oauth_status->GetIntegerWithoutPathExpansion( |
| 102 user_id, &oauth_token_status)) { | 166 user_id, &oauth_token_status)) { |
| 103 User::OAuthTokenStatus result = | 167 User::OAuthTokenStatus result = |
| 104 static_cast<User::OAuthTokenStatus>(oauth_token_status); | 168 static_cast<User::OAuthTokenStatus>(oauth_token_status); |
| 105 return result; | 169 return result; |
| 106 } | 170 } |
| 107 return User::OAUTH_TOKEN_STATUS_UNKNOWN; | 171 return User::OAUTH_TOKEN_STATUS_UNKNOWN; |
| 108 } | 172 } |
| 109 | 173 |
| 110 private: | 174 protected: |
| 111 bool AddUserTosession(const std::string& username, | 175 bool AddUserTosession(const std::string& username, |
| 112 const std::string& password) { | 176 const std::string& password) { |
| 113 ExistingUserController* controller = | 177 ExistingUserController* controller = |
| 114 ExistingUserController::current_controller(); | 178 ExistingUserController::current_controller(); |
| 115 if (!controller) { | 179 if (!controller) { |
| 116 ADD_FAILURE(); | 180 ADD_FAILURE(); |
| 117 return false; | 181 return false; |
| 118 } | 182 } |
| 119 | 183 |
| 120 controller->Login(UserContext(username, password, std::string())); | 184 controller->Login(UserContext(username, password, std::string())); |
| (...skipping 14 matching lines...) Expand all Loading... |
| 135 GaiaUrls* gaia_urls = GaiaUrls::GetInstance(); | 199 GaiaUrls* gaia_urls = GaiaUrls::GetInstance(); |
| 136 | 200 |
| 137 // This token satisfies the userinfo.email request from | 201 // This token satisfies the userinfo.email request from |
| 138 // DeviceOAuth2TokenService used in token validation. | 202 // DeviceOAuth2TokenService used in token validation. |
| 139 FakeGaia::AccessTokenInfo userinfo_token_info; | 203 FakeGaia::AccessTokenInfo userinfo_token_info; |
| 140 userinfo_token_info.token = kTestUserinfoToken; | 204 userinfo_token_info.token = kTestUserinfoToken; |
| 141 userinfo_token_info.scopes.insert( | 205 userinfo_token_info.scopes.insert( |
| 142 "https://www.googleapis.com/auth/userinfo.email"); | 206 "https://www.googleapis.com/auth/userinfo.email"); |
| 143 userinfo_token_info.audience = gaia_urls->oauth2_chrome_client_id(); | 207 userinfo_token_info.audience = gaia_urls->oauth2_chrome_client_id(); |
| 144 userinfo_token_info.email = kTestAccountId; | 208 userinfo_token_info.email = kTestAccountId; |
| 145 fake_gaia_.IssueOAuthToken(kTestRefreshToken, userinfo_token_info); | 209 fake_gaia_->IssueOAuthToken(kTestRefreshToken, userinfo_token_info); |
| 146 | 210 |
| 147 FakeGaia::AccessTokenInfo userinfo_profile_token_info; | 211 FakeGaia::AccessTokenInfo userinfo_profile_token_info; |
| 148 userinfo_profile_token_info.token = kTestUserinfoToken; | 212 userinfo_profile_token_info.token = kTestUserinfoToken; |
| 149 userinfo_profile_token_info.scopes.insert( | 213 userinfo_profile_token_info.scopes.insert( |
| 150 "https://www.googleapis.com/auth/userinfo.profile"); | 214 "https://www.googleapis.com/auth/userinfo.profile"); |
| 151 userinfo_profile_token_info.audience = gaia_urls->oauth2_chrome_client_id(); | 215 userinfo_profile_token_info.audience = gaia_urls->oauth2_chrome_client_id(); |
| 152 userinfo_profile_token_info.email = kTestAccountId; | 216 userinfo_profile_token_info.email = kTestAccountId; |
| 153 fake_gaia_.IssueOAuthToken(kTestRefreshToken, userinfo_profile_token_info); | 217 fake_gaia_->IssueOAuthToken(kTestRefreshToken, userinfo_profile_token_info); |
| 154 | 218 |
| 155 // The any-api access token for accessing the token minting endpoint. | 219 // The any-api access token for accessing the token minting endpoint. |
| 156 FakeGaia::AccessTokenInfo login_token_info; | 220 FakeGaia::AccessTokenInfo login_token_info; |
| 157 login_token_info.token = kTestLoginToken; | 221 login_token_info.token = kTestLoginToken; |
| 158 login_token_info.scopes.insert(GaiaConstants::kAnyApiOAuth2Scope); | 222 login_token_info.scopes.insert(GaiaConstants::kAnyApiOAuth2Scope); |
| 159 login_token_info.audience = gaia_urls->oauth2_chrome_client_id(); | 223 login_token_info.audience = gaia_urls->oauth2_chrome_client_id(); |
| 160 fake_gaia_.IssueOAuthToken(kTestRefreshToken, login_token_info); | 224 fake_gaia_->IssueOAuthToken(kTestRefreshToken, login_token_info); |
| 161 | 225 |
| 162 // The /auth/chromesync access token for accessing sync endpoint. | 226 // The /auth/chromesync access token for accessing sync endpoint. |
| 163 FakeGaia::AccessTokenInfo sync_token_info; | 227 FakeGaia::AccessTokenInfo sync_token_info; |
| 164 sync_token_info.token = kTestSyncToken; | 228 sync_token_info.token = kTestSyncToken; |
| 165 sync_token_info.scopes.insert(GaiaConstants::kChromeSyncOAuth2Scope); | 229 sync_token_info.scopes.insert(GaiaConstants::kChromeSyncOAuth2Scope); |
| 166 sync_token_info.audience = gaia_urls->oauth2_chrome_client_id(); | 230 sync_token_info.audience = gaia_urls->oauth2_chrome_client_id(); |
| 167 fake_gaia_.IssueOAuthToken(kTestRefreshToken, sync_token_info); | 231 fake_gaia_->IssueOAuthToken(kTestRefreshToken, sync_token_info); |
| 168 | 232 |
| 169 FakeGaia::AccessTokenInfo auth_login_token_info; | 233 FakeGaia::AccessTokenInfo auth_login_token_info; |
| 170 auth_login_token_info.token = kTestAuthLoginToken; | 234 auth_login_token_info.token = kTestAuthLoginToken; |
| 171 auth_login_token_info.scopes.insert(gaia_urls->oauth1_login_scope()); | 235 auth_login_token_info.scopes.insert(gaia_urls->oauth1_login_scope()); |
| 172 auth_login_token_info.audience = gaia_urls->oauth2_chrome_client_id(); | 236 auth_login_token_info.audience = gaia_urls->oauth2_chrome_client_id(); |
| 173 fake_gaia_.IssueOAuthToken(kTestRefreshToken, auth_login_token_info); | 237 fake_gaia_->IssueOAuthToken(kTestRefreshToken, auth_login_token_info); |
| 238 } |
| 239 |
| 240 void WaitForMergeSessionCompletion( |
| 241 OAuth2LoginManager::SessionRestoreState final_state) { |
| 242 // Wait for the session merge to finish. |
| 243 std::set<OAuth2LoginManager::SessionRestoreState> states; |
| 244 states.insert(OAuth2LoginManager::SESSION_RESTORE_DONE); |
| 245 states.insert(OAuth2LoginManager::SESSION_RESTORE_FAILED); |
| 246 states.insert(OAuth2LoginManager::SESSION_RESTORE_CONNECTION_FAILED); |
| 247 OAuth2LoginManagerStateWaiter merge_session_waiter( |
| 248 ProfileManager::GetPrimaryUserProfile()); |
| 249 merge_session_waiter.WaitForStates(states); |
| 250 EXPECT_EQ(merge_session_waiter.final_state(), final_state); |
| 174 } | 251 } |
| 175 | 252 |
| 176 DISALLOW_COPY_AND_ASSIGN(OAuth2Test); | 253 DISALLOW_COPY_AND_ASSIGN(OAuth2Test); |
| 177 }; | 254 }; |
| 178 | 255 |
| 179 class CookieReader : public base::RefCountedThreadSafe<CookieReader> { | 256 class CookieReader : public base::RefCountedThreadSafe<CookieReader> { |
| 180 public: | 257 public: |
| 181 CookieReader() { | 258 CookieReader() { |
| 182 } | 259 } |
| 183 | 260 |
| (...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 228 runner_->Quit(); | 305 runner_->Quit(); |
| 229 } | 306 } |
| 230 | 307 |
| 231 scoped_refptr<net::URLRequestContextGetter> context_; | 308 scoped_refptr<net::URLRequestContextGetter> context_; |
| 232 net::CookieList cookie_list_; | 309 net::CookieList cookie_list_; |
| 233 scoped_refptr<content::MessageLoopRunner> runner_; | 310 scoped_refptr<content::MessageLoopRunner> runner_; |
| 234 | 311 |
| 235 DISALLOW_COPY_AND_ASSIGN(CookieReader); | 312 DISALLOW_COPY_AND_ASSIGN(CookieReader); |
| 236 }; | 313 }; |
| 237 | 314 |
| 238 class OAuth2LoginManagerStateWaiter : public OAuth2LoginManager::Observer { | |
| 239 public: | |
| 240 explicit OAuth2LoginManagerStateWaiter(Profile* profile) | |
| 241 : profile_(profile), | |
| 242 waiting_for_state_(false), | |
| 243 final_state_(OAuth2LoginManager::SESSION_RESTORE_NOT_STARTED) { | |
| 244 } | |
| 245 | |
| 246 void WaitForStates( | |
| 247 const std::set<OAuth2LoginManager::SessionRestoreState>& states) { | |
| 248 DCHECK(!waiting_for_state_); | |
| 249 OAuth2LoginManager* login_manager = | |
| 250 OAuth2LoginManagerFactory::GetInstance()->GetForProfile(profile_); | |
| 251 states_ = states; | |
| 252 if (states_.find(login_manager->state()) != states_.end()) { | |
| 253 final_state_ = login_manager->state(); | |
| 254 return; | |
| 255 } | |
| 256 | |
| 257 waiting_for_state_ = true; | |
| 258 login_manager->AddObserver(this); | |
| 259 runner_ = new content::MessageLoopRunner; | |
| 260 runner_->Run(); | |
| 261 login_manager->RemoveObserver(this); | |
| 262 } | |
| 263 | |
| 264 OAuth2LoginManager::SessionRestoreState final_state() { return final_state_; } | |
| 265 | |
| 266 private: | |
| 267 // OAuth2LoginManager::Observer overrides. | |
| 268 virtual void OnSessionRestoreStateChanged( | |
| 269 Profile* user_profile, | |
| 270 OAuth2LoginManager::SessionRestoreState state) OVERRIDE { | |
| 271 if (!waiting_for_state_) | |
| 272 return; | |
| 273 | |
| 274 if (states_.find(state) == states_.end()) | |
| 275 return; | |
| 276 | |
| 277 final_state_ = state; | |
| 278 waiting_for_state_ = false; | |
| 279 runner_->Quit(); | |
| 280 } | |
| 281 | |
| 282 Profile* profile_; | |
| 283 std::set<OAuth2LoginManager::SessionRestoreState> states_; | |
| 284 bool waiting_for_state_; | |
| 285 OAuth2LoginManager::SessionRestoreState final_state_; | |
| 286 scoped_refptr<content::MessageLoopRunner> runner_; | |
| 287 | |
| 288 DISALLOW_COPY_AND_ASSIGN(OAuth2LoginManagerStateWaiter); | |
| 289 }; | |
| 290 | |
| 291 // PRE_MergeSession is testing merge session for a new profile. | 315 // PRE_MergeSession is testing merge session for a new profile. |
| 292 IN_PROC_BROWSER_TEST_F(OAuth2Test, PRE_PRE_MergeSession) { | 316 IN_PROC_BROWSER_TEST_F(OAuth2Test, PRE_PRE_MergeSession) { |
| 293 SetupGaiaServerForNewAccount(); | 317 SetupGaiaServerForNewAccount(); |
| 294 SimulateNetworkOnline(); | 318 SimulateNetworkOnline(); |
| 295 chromeos::WizardController::SkipPostLoginScreensForTesting(); | 319 chromeos::WizardController::SkipPostLoginScreensForTesting(); |
| 296 chromeos::WizardController* wizard_controller = | 320 chromeos::WizardController* wizard_controller = |
| 297 chromeos::WizardController::default_controller(); | 321 chromeos::WizardController::default_controller(); |
| 298 wizard_controller->SkipToLoginForTesting(LoginScreenContext()); | 322 wizard_controller->SkipToLoginForTesting(LoginScreenContext()); |
| 299 | 323 |
| 300 content::WindowedNotificationObserver( | 324 content::WindowedNotificationObserver( |
| 301 chrome::NOTIFICATION_LOGIN_OR_LOCK_WEBUI_VISIBLE, | 325 chrome::NOTIFICATION_LOGIN_OR_LOCK_WEBUI_VISIBLE, |
| 302 content::NotificationService::AllSources()).Wait(); | 326 content::NotificationService::AllSources()).Wait(); |
| 303 | 327 |
| 304 EXPECT_EQ(GetOAuthStatusFromLocalState(kTestAccountId), | 328 EXPECT_EQ(GetOAuthStatusFromLocalState(kTestAccountId), |
| 305 User::OAUTH_TOKEN_STATUS_UNKNOWN); | 329 User::OAUTH_TOKEN_STATUS_UNKNOWN); |
| 306 | 330 |
| 307 // Use capitalized and dotted user name on purpose to make sure | 331 // Use capitalized and dotted user name on purpose to make sure |
| 308 // our email normalization kicks in. | 332 // our email normalization kicks in. |
| 309 GetLoginDisplay()->ShowSigninScreenForCreds(kTestRawAccountId, | 333 GetLoginDisplay()->ShowSigninScreenForCreds(kTestRawAccountId, |
| 310 kTestAccountPassword); | 334 kTestAccountPassword); |
| 311 | 335 |
| 312 content::WindowedNotificationObserver( | 336 content::WindowedNotificationObserver( |
| 313 chrome::NOTIFICATION_SESSION_STARTED, | 337 chrome::NOTIFICATION_SESSION_STARTED, |
| 314 content::NotificationService::AllSources()).Wait(); | 338 content::NotificationService::AllSources()).Wait(); |
| 315 Profile* profile = ProfileManager::GetPrimaryUserProfile(); | 339 Profile* profile = ProfileManager::GetPrimaryUserProfile(); |
| 316 | 340 |
| 317 // Wait for the session merge to finish. | 341 // Wait for the session merge to finish. |
| 318 std::set<OAuth2LoginManager::SessionRestoreState> states; | 342 WaitForMergeSessionCompletion(OAuth2LoginManager::SESSION_RESTORE_DONE); |
| 319 states.insert(OAuth2LoginManager::SESSION_RESTORE_DONE); | |
| 320 states.insert(OAuth2LoginManager::SESSION_RESTORE_FAILED); | |
| 321 states.insert(OAuth2LoginManager::SESSION_RESTORE_CONNECTION_FAILED); | |
| 322 OAuth2LoginManagerStateWaiter merge_session_waiter( | |
| 323 ProfileManager::GetPrimaryUserProfile()); | |
| 324 merge_session_waiter.WaitForStates(states); | |
| 325 EXPECT_EQ(merge_session_waiter.final_state(), | |
| 326 OAuth2LoginManager::SESSION_RESTORE_DONE); | |
| 327 | 343 |
| 328 // Check for existance of refresh token. | 344 // Check for existance of refresh token. |
| 329 ProfileOAuth2TokenService* token_service = | 345 ProfileOAuth2TokenService* token_service = |
| 330 ProfileOAuth2TokenServiceFactory::GetForProfile( | 346 ProfileOAuth2TokenServiceFactory::GetForProfile( |
| 331 profile); | 347 profile); |
| 332 EXPECT_TRUE(token_service->RefreshTokenIsAvailable(kTestAccountId)); | 348 EXPECT_TRUE(token_service->RefreshTokenIsAvailable(kTestAccountId)); |
| 333 | 349 |
| 334 EXPECT_EQ(GetOAuthStatusFromLocalState(kTestAccountId), | 350 EXPECT_EQ(GetOAuthStatusFromLocalState(kTestAccountId), |
| 335 User::OAUTH2_TOKEN_STATUS_VALID); | 351 User::OAUTH2_TOKEN_STATUS_VALID); |
| 336 | 352 |
| (...skipping 16 matching lines...) Expand all Loading... |
| 353 JsExpect("!!document.querySelector('#account-picker')"); | 369 JsExpect("!!document.querySelector('#account-picker')"); |
| 354 JsExpect("!!document.querySelector('#pod-row')"); | 370 JsExpect("!!document.querySelector('#pod-row')"); |
| 355 | 371 |
| 356 EXPECT_EQ(GetOAuthStatusFromLocalState(kTestAccountId), | 372 EXPECT_EQ(GetOAuthStatusFromLocalState(kTestAccountId), |
| 357 User::OAUTH2_TOKEN_STATUS_VALID); | 373 User::OAUTH2_TOKEN_STATUS_VALID); |
| 358 | 374 |
| 359 EXPECT_TRUE(TryToLogin(kTestAccountId, kTestAccountPassword)); | 375 EXPECT_TRUE(TryToLogin(kTestAccountId, kTestAccountPassword)); |
| 360 Profile* profile = ProfileManager::GetPrimaryUserProfile(); | 376 Profile* profile = ProfileManager::GetPrimaryUserProfile(); |
| 361 | 377 |
| 362 // Wait for the session merge to finish. | 378 // Wait for the session merge to finish. |
| 363 std::set<OAuth2LoginManager::SessionRestoreState> states; | 379 WaitForMergeSessionCompletion(OAuth2LoginManager::SESSION_RESTORE_DONE); |
| 364 states.insert(OAuth2LoginManager::SESSION_RESTORE_DONE); | |
| 365 states.insert(OAuth2LoginManager::SESSION_RESTORE_FAILED); | |
| 366 states.insert(OAuth2LoginManager::SESSION_RESTORE_CONNECTION_FAILED); | |
| 367 OAuth2LoginManagerStateWaiter merge_session_waiter(profile); | |
| 368 merge_session_waiter.WaitForStates(states); | |
| 369 EXPECT_EQ(merge_session_waiter.final_state(), | |
| 370 OAuth2LoginManager::SESSION_RESTORE_DONE); | |
| 371 | 380 |
| 372 // Check for existance of refresh token. | 381 // Check for existance of refresh token. |
| 373 ProfileOAuth2TokenService* token_service = | 382 ProfileOAuth2TokenService* token_service = |
| 374 ProfileOAuth2TokenServiceFactory::GetForProfile(profile); | 383 ProfileOAuth2TokenServiceFactory::GetForProfile(profile); |
| 375 EXPECT_TRUE(token_service->RefreshTokenIsAvailable(kTestAccountId)); | 384 EXPECT_TRUE(token_service->RefreshTokenIsAvailable(kTestAccountId)); |
| 376 | 385 |
| 377 EXPECT_EQ(GetOAuthStatusFromLocalState(kTestAccountId), | 386 EXPECT_EQ(GetOAuthStatusFromLocalState(kTestAccountId), |
| 378 User::OAUTH2_TOKEN_STATUS_VALID); | 387 User::OAUTH2_TOKEN_STATUS_VALID); |
| 379 | 388 |
| 380 scoped_refptr<CookieReader> cookie_reader(new CookieReader()); | 389 scoped_refptr<CookieReader> cookie_reader(new CookieReader()); |
| (...skipping 14 matching lines...) Expand all Loading... |
| 395 | 404 |
| 396 JsExpect("!!document.querySelector('#account-picker')"); | 405 JsExpect("!!document.querySelector('#account-picker')"); |
| 397 JsExpect("!!document.querySelector('#pod-row')"); | 406 JsExpect("!!document.querySelector('#pod-row')"); |
| 398 | 407 |
| 399 EXPECT_EQ(GetOAuthStatusFromLocalState(kTestAccountId), | 408 EXPECT_EQ(GetOAuthStatusFromLocalState(kTestAccountId), |
| 400 User::OAUTH2_TOKEN_STATUS_VALID); | 409 User::OAUTH2_TOKEN_STATUS_VALID); |
| 401 | 410 |
| 402 EXPECT_TRUE(TryToLogin(kTestAccountId, kTestAccountPassword)); | 411 EXPECT_TRUE(TryToLogin(kTestAccountId, kTestAccountPassword)); |
| 403 | 412 |
| 404 // Wait for the session merge to finish. | 413 // Wait for the session merge to finish. |
| 405 std::set<OAuth2LoginManager::SessionRestoreState> states; | 414 WaitForMergeSessionCompletion(OAuth2LoginManager::SESSION_RESTORE_FAILED); |
| 406 states.insert(OAuth2LoginManager::SESSION_RESTORE_DONE); | |
| 407 states.insert(OAuth2LoginManager::SESSION_RESTORE_FAILED); | |
| 408 states.insert(OAuth2LoginManager::SESSION_RESTORE_CONNECTION_FAILED); | |
| 409 OAuth2LoginManagerStateWaiter merge_session_waiter( | |
| 410 ProfileManager::GetPrimaryUserProfile()); | |
| 411 merge_session_waiter.WaitForStates(states); | |
| 412 EXPECT_EQ(merge_session_waiter.final_state(), | |
| 413 OAuth2LoginManager::SESSION_RESTORE_FAILED); | |
| 414 | 415 |
| 415 EXPECT_EQ(GetOAuthStatusFromLocalState(kTestAccountId), | 416 EXPECT_EQ(GetOAuthStatusFromLocalState(kTestAccountId), |
| 416 User::OAUTH2_TOKEN_STATUS_INVALID); | 417 User::OAUTH2_TOKEN_STATUS_INVALID); |
| 417 } | 418 } |
| 418 | 419 |
| 420 |
| 421 const char kGooglePageContent[] = |
| 422 "<html><title>Hello!</title><script>alert('hello');</script>" |
| 423 "<body>Hello Google!</body></html>"; |
| 424 const char kHelloPagePath[] = "/hello_google"; |
| 425 |
| 426 // FakeGoogle serves content of http://www.google.com/hello_google page for |
| 427 // merge session tests. |
| 428 class FakeGoogle { |
| 429 public: |
| 430 FakeGoogle() : was_page_sent_(false) { |
| 431 } |
| 432 |
| 433 ~FakeGoogle() {} |
| 434 |
| 435 scoped_ptr<HttpResponse> HandleRequest(const HttpRequest& request) { |
| 436 // The scheme and host of the URL is actually not important but required to |
| 437 // get a valid GURL in order to parse |request.relative_url|. |
| 438 GURL request_url = GURL("http://localhost").Resolve(request.relative_url); |
| 439 std::string request_path = request_url.path(); |
| 440 scoped_ptr<BasicHttpResponse> http_response(new BasicHttpResponse()); |
| 441 if (request_path == kHelloPagePath) { |
| 442 http_response->set_code(net::HTTP_OK); |
| 443 http_response->set_content_type("text/html"); |
| 444 http_response->set_content(kGooglePageContent); |
| 445 was_page_sent_ = true; |
| 446 } else { |
| 447 return scoped_ptr<HttpResponse>(); // Request not understood. |
| 448 } |
| 449 |
| 450 return http_response.PassAs<HttpResponse>(); |
| 451 } |
| 452 |
| 453 bool was_page_sent() { return was_page_sent_; } |
| 454 |
| 455 private: |
| 456 bool was_page_sent_; |
| 457 |
| 458 DISALLOW_COPY_AND_ASSIGN(FakeGoogle); |
| 459 }; |
| 460 |
| 461 // FakeGaia specialization that can delay /MergeSession handler until |
| 462 // we explicitly call DelayedFakeGaia::UnblockMergeSession(). |
| 463 class DelayedFakeGaia : public FakeGaia { |
| 464 public: |
| 465 DelayedFakeGaia() |
| 466 : blocking_event_(true, false), |
| 467 start_event_(true, false) { |
| 468 } |
| 469 |
| 470 void UnblockMergeSession() { |
| 471 blocking_event_.Signal(); |
| 472 } |
| 473 |
| 474 void WaitForMergeSessionToStart() { |
| 475 start_event_.Wait(); |
| 476 } |
| 477 |
| 478 private: |
| 479 // FakeGaia overrides. |
| 480 virtual void HandleMergeSession(const HttpRequest& request, |
| 481 BasicHttpResponse* http_response) OVERRIDE { |
| 482 start_event_.Signal(); |
| 483 blocking_event_.Wait(); |
| 484 FakeGaia::HandleMergeSession(request, http_response); |
| 485 } |
| 486 |
| 487 base::WaitableEvent blocking_event_; |
| 488 base::WaitableEvent start_event_; |
| 489 |
| 490 DISALLOW_COPY_AND_ASSIGN(DelayedFakeGaia); |
| 491 }; |
| 492 |
| 493 class MergeSessionTest : public OAuth2Test { |
| 494 protected: |
| 495 MergeSessionTest() : delayed_fake_gaia_(new DelayedFakeGaia()) { |
| 496 fake_gaia_.reset(delayed_fake_gaia_); |
| 497 } |
| 498 |
| 499 virtual void SetUpCommandLine(CommandLine* command_line) OVERRIDE { |
| 500 OAuth2Test::SetUpCommandLine(command_line); |
| 501 |
| 502 // Get fake URL for fake google.com. |
| 503 const GURL& server_url = embedded_test_server()->base_url(); |
| 504 std::string google_host("www.google.com"); |
| 505 GURL::Replacements replace_google_host; |
| 506 replace_google_host.SetHostStr(google_host); |
| 507 GURL google_url = server_url.ReplaceComponents(replace_google_host); |
| 508 fake_google_page_url_ = google_url.Resolve(kHelloPagePath); |
| 509 } |
| 510 |
| 511 virtual void SetUp() OVERRIDE { |
| 512 embedded_test_server()->RegisterRequestHandler( |
| 513 base::Bind(&FakeGoogle::HandleRequest, |
| 514 base::Unretained(&fake_google_))); |
| 515 OAuth2Test::SetUp(); |
| 516 } |
| 517 |
| 518 protected: |
| 519 void UnblockMergeSession() { |
| 520 delayed_fake_gaia_->UnblockMergeSession(); |
| 521 } |
| 522 |
| 523 void WaitForMergeSessionToStart() { |
| 524 delayed_fake_gaia_->WaitForMergeSessionToStart(); |
| 525 } |
| 526 |
| 527 void JsExpect(content::WebContents* contents, |
| 528 const std::string& expression) { |
| 529 bool result; |
| 530 ASSERT_TRUE(content::ExecuteScriptAndExtractBool( |
| 531 contents, |
| 532 "window.domAutomationController.send(!!(" + expression + "));", |
| 533 &result)); |
| 534 ASSERT_TRUE(result) << expression; |
| 535 } |
| 536 |
| 537 FakeGoogle fake_google_; |
| 538 DelayedFakeGaia* delayed_fake_gaia_; |
| 539 GURL fake_google_page_url_; |
| 540 |
| 541 private: |
| 542 DISALLOW_COPY_AND_ASSIGN(MergeSessionTest); |
| 543 }; |
| 544 |
| 545 Browser* FindOrCreateVisibleBrowser(Profile* profile) { |
| 546 chrome::ScopedTabbedBrowserDisplayer displayer( |
| 547 profile, chrome::GetActiveDesktop()); |
| 548 Browser* browser = displayer.browser(); |
| 549 if (browser->tab_strip_model()->count() == 0) |
| 550 chrome::AddTabAt(browser, GURL(), -1, true); |
| 551 return browser; |
| 552 } |
| 553 |
| 554 IN_PROC_BROWSER_TEST_F(MergeSessionTest, MergeSessionThrottle) { |
| 555 SetupGaiaServerForNewAccount(); |
| 556 SimulateNetworkOnline(); |
| 557 chromeos::WizardController::SkipPostLoginScreensForTesting(); |
| 558 chromeos::WizardController* wizard_controller = |
| 559 chromeos::WizardController::default_controller(); |
| 560 wizard_controller->SkipToLoginForTesting(LoginScreenContext()); |
| 561 |
| 562 content::WindowedNotificationObserver( |
| 563 chrome::NOTIFICATION_LOGIN_OR_LOCK_WEBUI_VISIBLE, |
| 564 content::NotificationService::AllSources()).Wait(); |
| 565 |
| 566 // Use capitalized and dotted user name on purpose to make sure |
| 567 // our email normalization kicks in. |
| 568 GetLoginDisplay()->ShowSigninScreenForCreds(kTestRawAccountId, |
| 569 kTestAccountPassword); |
| 570 |
| 571 content::WindowedNotificationObserver( |
| 572 chrome::NOTIFICATION_SESSION_STARTED, |
| 573 content::NotificationService::AllSources()).Wait(); |
| 574 |
| 575 // Try to open a page from google.com. |
| 576 Browser* browser = |
| 577 FindOrCreateVisibleBrowser(ProfileManager::GetPrimaryUserProfile()); |
| 578 ui_test_utils::NavigateToURLWithDisposition( |
| 579 browser, |
| 580 fake_google_page_url_, |
| 581 CURRENT_TAB, ui_test_utils::BROWSER_TEST_NONE); |
| 582 |
| 583 // Wait until we get send merge session request. |
| 584 WaitForMergeSessionToStart(); |
| 585 |
| 586 // Make sure the page is blocked by the throttle. |
| 587 ASSERT_FALSE(fake_google_.was_page_sent()); |
| 588 |
| 589 // Check that throttle page is displayed instead. |
| 590 string16 title; |
| 591 ui_test_utils::GetCurrentTabTitle(browser, &title); |
| 592 LOG(WARNING) << "Loaded page at the start : " << title; |
| 593 // ui_test_utils::GetCurrentTabTitle(browser, &title); |
| 594 // JsExpect(browser->tab_strip_model()->GetActiveWebContents(), |
| 595 // "document.getElementById('msg').innerText='Loading...'"); |
| 596 // LOG(WARNING) << "Loaded page at the start: " << title; |
| 597 |
| 598 // Unblock GAIA request. |
| 599 UnblockMergeSession(); |
| 600 |
| 601 // Wait for the session merge to finish. |
| 602 WaitForMergeSessionCompletion(OAuth2LoginManager::SESSION_RESTORE_DONE); |
| 603 |
| 604 // Check that real page is no longer blocked by the throttle and that the |
| 605 // real page pops up JS dialog. |
| 606 AppModalDialog* dialog = ui_test_utils::WaitForAppModalDialog(); |
| 607 ASSERT_TRUE(dialog->IsJavaScriptModalDialog()); |
| 608 JavaScriptAppModalDialog* js_dialog = |
| 609 static_cast<JavaScriptAppModalDialog*>(dialog); |
| 610 js_dialog->native_dialog()->AcceptAppModalDialog(); |
| 611 |
| 612 ASSERT_TRUE(fake_google_.was_page_sent()); |
| 613 |
| 614 ui_test_utils::GetCurrentTabTitle(browser, &title); |
| 615 LOG(WARNING) << "Loaded page at the end : " << title; |
| 616 } |
| 617 |
| 419 } // namespace chromeos | 618 } // namespace chromeos |
| OLD | NEW |