OLD | NEW |
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 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 "chrome/browser/extensions/api/identity/identity_api.h" | 5 #include "chrome/browser/extensions/api/identity/identity_api.h" |
6 | 6 |
7 #include <set> | 7 #include <set> |
8 #include <string> | 8 #include <string> |
9 #include <vector> | 9 #include <vector> |
10 | 10 |
11 #include "base/lazy_instance.h" | 11 #include "base/lazy_instance.h" |
12 #include "base/stringprintf.h" | 12 #include "base/stringprintf.h" |
| 13 #include "base/strings/string_number_conversions.h" |
13 #include "base/values.h" | 14 #include "base/values.h" |
14 #include "chrome/browser/app_mode/app_mode_utils.h" | 15 #include "chrome/browser/app_mode/app_mode_utils.h" |
15 #include "chrome/browser/extensions/extension_function_dispatcher.h" | 16 #include "chrome/browser/extensions/extension_function_dispatcher.h" |
16 #include "chrome/browser/extensions/extension_install_prompt.h" | 17 #include "chrome/browser/extensions/extension_install_prompt.h" |
17 #include "chrome/browser/extensions/extension_service.h" | 18 #include "chrome/browser/extensions/extension_service.h" |
18 #include "chrome/browser/extensions/permissions_updater.h" | 19 #include "chrome/browser/extensions/permissions_updater.h" |
19 #include "chrome/browser/profiles/profile.h" | 20 #include "chrome/browser/profiles/profile.h" |
20 #include "chrome/browser/signin/signin_manager.h" | 21 #include "chrome/browser/signin/signin_manager.h" |
21 #include "chrome/browser/signin/signin_manager_factory.h" | 22 #include "chrome/browser/signin/signin_manager_factory.h" |
22 #include "chrome/browser/signin/token_service.h" | 23 #include "chrome/browser/signin/token_service.h" |
(...skipping 194 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
217 StartMintTokenFlow(IdentityMintRequestQueue::MINT_TYPE_INTERACTIVE); | 218 StartMintTokenFlow(IdentityMintRequestQueue::MINT_TYPE_INTERACTIVE); |
218 break; | 219 break; |
219 } | 220 } |
220 } else { | 221 } else { |
221 DCHECK(type == IdentityMintRequestQueue::MINT_TYPE_INTERACTIVE); | 222 DCHECK(type == IdentityMintRequestQueue::MINT_TYPE_INTERACTIVE); |
222 | 223 |
223 if (cache_status == IdentityTokenCacheValue::CACHE_STATUS_TOKEN) { | 224 if (cache_status == IdentityTokenCacheValue::CACHE_STATUS_TOKEN) { |
224 CompleteMintTokenFlow(); | 225 CompleteMintTokenFlow(); |
225 CompleteFunctionWithResult(cache_entry.token()); | 226 CompleteFunctionWithResult(cache_entry.token()); |
226 } else { | 227 } else { |
227 install_ui_.reset(new ExtensionInstallPrompt(GetAssociatedWebContents())); | |
228 ShowOAuthApprovalDialog(issue_advice_); | 228 ShowOAuthApprovalDialog(issue_advice_); |
229 } | 229 } |
230 } | 230 } |
231 } | 231 } |
232 | 232 |
233 void IdentityGetAuthTokenFunction::OnMintTokenSuccess( | 233 void IdentityGetAuthTokenFunction::OnMintTokenSuccess( |
234 const std::string& access_token, int time_to_live) { | 234 const std::string& access_token, int time_to_live) { |
235 const OAuth2Info& oauth2_info = OAuth2Info::GetOAuth2Info(GetExtension()); | 235 const OAuth2Info& oauth2_info = OAuth2Info::GetOAuth2Info(GetExtension()); |
236 IdentityTokenCacheValue token(access_token, | 236 IdentityTokenCacheValue token(access_token, |
237 base::TimeDelta::FromSeconds(time_to_live)); | 237 base::TimeDelta::FromSeconds(time_to_live)); |
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
284 | 284 |
285 void IdentityGetAuthTokenFunction::SigninSuccess(const std::string& token) { | 285 void IdentityGetAuthTokenFunction::SigninSuccess(const std::string& token) { |
286 refresh_token_ = token; | 286 refresh_token_ = token; |
287 StartMintTokenFlow(IdentityMintRequestQueue::MINT_TYPE_NONINTERACTIVE); | 287 StartMintTokenFlow(IdentityMintRequestQueue::MINT_TYPE_NONINTERACTIVE); |
288 } | 288 } |
289 | 289 |
290 void IdentityGetAuthTokenFunction::SigninFailed() { | 290 void IdentityGetAuthTokenFunction::SigninFailed() { |
291 CompleteFunctionWithError(identity_constants::kUserNotSignedIn); | 291 CompleteFunctionWithError(identity_constants::kUserNotSignedIn); |
292 } | 292 } |
293 | 293 |
294 void IdentityGetAuthTokenFunction::InstallUIProceed() { | 294 void IdentityGetAuthTokenFunction::OnGaiaFlowFailure( |
295 // The user has accepted the scopes, so we may now force (recording a grant | 295 GaiaWebAuthFlow::Failure failure, |
296 // and receiving a token). | 296 GoogleServiceAuthError service_error) { |
297 StartGaiaRequest(OAuth2MintTokenFlow::MODE_MINT_TOKEN_FORCE); | 297 CompleteMintTokenFlow(); |
| 298 std::string error; |
| 299 |
| 300 switch (failure) { |
| 301 case GaiaWebAuthFlow::WINDOW_CLOSED: |
| 302 error = identity_constants::kUserRejected; |
| 303 break; |
| 304 |
| 305 case GaiaWebAuthFlow::INVALID_REDIRECT: |
| 306 error = identity_constants::kInvalidRedirect; |
| 307 break; |
| 308 |
| 309 case GaiaWebAuthFlow::SERVICE_AUTH_ERROR: |
| 310 error = std::string(identity_constants::kAuthFailure) + |
| 311 service_error.ToString(); |
| 312 break; |
| 313 |
| 314 default: |
| 315 NOTREACHED() << "Unexpected error from gaia web auth flow: " << failure; |
| 316 error = identity_constants::kInvalidRedirect; |
| 317 break; |
| 318 } |
| 319 |
| 320 CompleteFunctionWithError(error); |
298 } | 321 } |
299 | 322 |
300 void IdentityGetAuthTokenFunction::InstallUIAbort(bool user_initiated) { | 323 void IdentityGetAuthTokenFunction::OnGaiaFlowCompleted( |
| 324 const std::string& token, |
| 325 const std::string& expiration, |
| 326 const std::string& error) { |
| 327 if (!error.empty()) { |
| 328 CompleteMintTokenFlow(); |
| 329 CompleteFunctionWithError(MapOAuth2ErrorToDescription(error)); |
| 330 return; |
| 331 } |
| 332 |
| 333 int time_to_live; |
| 334 if (!expiration.empty() && base::StringToInt(expiration, &time_to_live)) { |
| 335 const OAuth2Info& oauth2_info = OAuth2Info::GetOAuth2Info(GetExtension()); |
| 336 IdentityTokenCacheValue token_value( |
| 337 token, base::TimeDelta::FromSeconds(time_to_live)); |
| 338 IdentityAPI::GetFactoryInstance()->GetForProfile(profile()) |
| 339 ->SetCachedToken(GetExtension()->id(), oauth2_info.scopes, token_value); |
| 340 } |
| 341 |
301 CompleteMintTokenFlow(); | 342 CompleteMintTokenFlow(); |
302 CompleteFunctionWithError(identity_constants::kUserRejected); | 343 CompleteFunctionWithResult(token); |
303 } | 344 } |
304 | 345 |
305 void IdentityGetAuthTokenFunction::StartGaiaRequest( | 346 void IdentityGetAuthTokenFunction::StartGaiaRequest( |
306 OAuth2MintTokenFlow::Mode mode) { | 347 OAuth2MintTokenFlow::Mode mode) { |
307 mint_token_flow_.reset(CreateMintTokenFlow(mode)); | 348 mint_token_flow_.reset(CreateMintTokenFlow(mode)); |
308 mint_token_flow_->Start(); | 349 mint_token_flow_->Start(); |
309 } | 350 } |
310 | 351 |
311 void IdentityGetAuthTokenFunction::ShowLoginPopup() { | 352 void IdentityGetAuthTokenFunction::ShowLoginPopup() { |
312 signin_flow_.reset(new IdentitySigninFlow(this, profile())); | 353 signin_flow_.reset(new IdentitySigninFlow(this, profile())); |
313 signin_flow_->Start(); | 354 signin_flow_->Start(); |
314 } | 355 } |
315 | 356 |
316 void IdentityGetAuthTokenFunction::ShowOAuthApprovalDialog( | 357 void IdentityGetAuthTokenFunction::ShowOAuthApprovalDialog( |
317 const IssueAdviceInfo& issue_advice) { | 358 const IssueAdviceInfo& issue_advice) { |
318 install_ui_->ConfirmIssueAdvice(this, GetExtension(), issue_advice); | 359 Browser* current_browser = this->GetCurrentBrowser(); |
| 360 chrome::HostDesktopType host_desktop_type = |
| 361 current_browser ? current_browser->host_desktop_type() |
| 362 : chrome::GetActiveDesktop(); |
| 363 const OAuth2Info& oauth2_info = OAuth2Info::GetOAuth2Info(GetExtension()); |
| 364 |
| 365 web_auth_flow_.reset(new GaiaWebAuthFlow( |
| 366 this, profile(), host_desktop_type, GetExtension()->id(), oauth2_info)); |
| 367 web_auth_flow_->Start(); |
319 } | 368 } |
320 | 369 |
321 OAuth2MintTokenFlow* IdentityGetAuthTokenFunction::CreateMintTokenFlow( | 370 OAuth2MintTokenFlow* IdentityGetAuthTokenFunction::CreateMintTokenFlow( |
322 OAuth2MintTokenFlow::Mode mode) { | 371 OAuth2MintTokenFlow::Mode mode) { |
323 const OAuth2Info& oauth2_info = OAuth2Info::GetOAuth2Info(GetExtension()); | 372 const OAuth2Info& oauth2_info = OAuth2Info::GetOAuth2Info(GetExtension()); |
324 OAuth2MintTokenFlow* mint_token_flow = | 373 OAuth2MintTokenFlow* mint_token_flow = |
325 new OAuth2MintTokenFlow( | 374 new OAuth2MintTokenFlow( |
326 profile()->GetRequestContext(), | 375 profile()->GetRequestContext(), |
327 this, | 376 this, |
328 OAuth2MintTokenFlow::Parameters( | 377 OAuth2MintTokenFlow::Parameters( |
(...skipping 14 matching lines...) Expand all Loading... |
343 } | 392 } |
344 #endif | 393 #endif |
345 return mint_token_flow; | 394 return mint_token_flow; |
346 } | 395 } |
347 | 396 |
348 bool IdentityGetAuthTokenFunction::HasLoginToken() const { | 397 bool IdentityGetAuthTokenFunction::HasLoginToken() const { |
349 TokenService* token_service = TokenServiceFactory::GetForProfile(profile()); | 398 TokenService* token_service = TokenServiceFactory::GetForProfile(profile()); |
350 return token_service->HasOAuthLoginToken(); | 399 return token_service->HasOAuthLoginToken(); |
351 } | 400 } |
352 | 401 |
| 402 std::string IdentityGetAuthTokenFunction::MapOAuth2ErrorToDescription( |
| 403 const std::string& error) { |
| 404 const char kOAuth2ErrorAccessDenied[] = "access_denied"; |
| 405 const char kOAuth2ErrorInvalidScope[] = "invalid_scope"; |
| 406 |
| 407 if (error == kOAuth2ErrorAccessDenied) |
| 408 return std::string(identity_constants::kUserRejected); |
| 409 else if (error == kOAuth2ErrorInvalidScope) |
| 410 return std::string(identity_constants::kInvalidScopes); |
| 411 else |
| 412 return std::string(identity_constants::kAuthFailure) + error; |
| 413 } |
| 414 |
353 IdentityRemoveCachedAuthTokenFunction::IdentityRemoveCachedAuthTokenFunction() { | 415 IdentityRemoveCachedAuthTokenFunction::IdentityRemoveCachedAuthTokenFunction() { |
354 } | 416 } |
355 | 417 |
356 IdentityRemoveCachedAuthTokenFunction:: | 418 IdentityRemoveCachedAuthTokenFunction:: |
357 ~IdentityRemoveCachedAuthTokenFunction() { | 419 ~IdentityRemoveCachedAuthTokenFunction() { |
358 } | 420 } |
359 | 421 |
360 bool IdentityRemoveCachedAuthTokenFunction::RunImpl() { | 422 bool IdentityRemoveCachedAuthTokenFunction::RunImpl() { |
361 if (profile()->IsOffTheRecord()) { | 423 if (profile()->IsOffTheRecord()) { |
362 error_ = identity_constants::kOffTheRecord; | 424 error_ = identity_constants::kOffTheRecord; |
(...skipping 249 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
612 const IdentityAPI::TokenCacheKey& rhs) const { | 674 const IdentityAPI::TokenCacheKey& rhs) const { |
613 if (extension_id < rhs.extension_id) | 675 if (extension_id < rhs.extension_id) |
614 return true; | 676 return true; |
615 else if (rhs.extension_id < extension_id) | 677 else if (rhs.extension_id < extension_id) |
616 return false; | 678 return false; |
617 | 679 |
618 return scopes < rhs.scopes; | 680 return scopes < rhs.scopes; |
619 } | 681 } |
620 | 682 |
621 } // namespace extensions | 683 } // namespace extensions |
OLD | NEW |