OLD | NEW |
(Empty) | |
| 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 |
| 3 // found in the LICENSE file. |
| 4 |
| 5 #include "chrome/browser/signin/signin_global_error.h" |
| 6 |
| 7 #include "base/logging.h" |
| 8 #include "chrome/app/chrome_command_ids.h" |
| 9 #include "chrome/browser/signin/signin_manager.h" |
| 10 #include "chrome/browser/signin/signin_manager_factory.h" |
| 11 #include "chrome/browser/ui/browser_commands.h" |
| 12 #include "chrome/browser/ui/chrome_pages.h" |
| 13 #include "chrome/browser/ui/global_error/global_error_service.h" |
| 14 #include "chrome/browser/ui/global_error/global_error_service_factory.h" |
| 15 #include "chrome/browser/ui/webui/signin/login_ui_service.h" |
| 16 #include "chrome/browser/ui/webui/signin/login_ui_service_factory.h" |
| 17 #include "chrome/common/url_constants.h" |
| 18 #include "grit/chromium_strings.h" |
| 19 #include "grit/generated_resources.h" |
| 20 #include "ui/base/l10n/l10n_util.h" |
| 21 |
| 22 SigninGlobalError::SigninGlobalError(Profile* profile) |
| 23 : auth_error_(GoogleServiceAuthError::None()), |
| 24 profile_(profile) { |
| 25 } |
| 26 |
| 27 SigninGlobalError::~SigninGlobalError() { |
| 28 DCHECK(provider_set_.empty()) |
| 29 << "All AuthStatusProviders should be unregistered before" |
| 30 << " SigninManager::Shutdown() is called"; |
| 31 } |
| 32 |
| 33 void SigninGlobalError::AddProvider(const AuthStatusProvider* provider) { |
| 34 DCHECK(provider_set_.find(provider) == provider_set_.end()) |
| 35 << "Adding same AuthStatusProvider multiple times"; |
| 36 provider_set_.insert(provider); |
| 37 AuthStatusChanged(); |
| 38 } |
| 39 |
| 40 void SigninGlobalError::RemoveProvider(const AuthStatusProvider* provider) { |
| 41 std::set<const AuthStatusProvider*>::iterator iter = |
| 42 provider_set_.find(provider); |
| 43 DCHECK(iter != provider_set_.end()) |
| 44 << "Removing provider that was never added"; |
| 45 provider_set_.erase(iter); |
| 46 AuthStatusChanged(); |
| 47 } |
| 48 |
| 49 SigninGlobalError::AuthStatusProvider::AuthStatusProvider() { |
| 50 } |
| 51 |
| 52 SigninGlobalError::AuthStatusProvider::~AuthStatusProvider() { |
| 53 } |
| 54 |
| 55 void SigninGlobalError::AuthStatusChanged() { |
| 56 // Walk all of the status providers and collect any error. |
| 57 GoogleServiceAuthError current_error(GoogleServiceAuthError::None()); |
| 58 for (std::set<const AuthStatusProvider*>::const_iterator it = |
| 59 provider_set_.begin(); it != provider_set_.end(); ++it) { |
| 60 current_error = (*it)->GetAuthStatus(); |
| 61 // Break out if any provider reports an error (ignoring ordinary network |
| 62 // errors, which are not surfaced to the user). This logic may eventually |
| 63 // need to be extended to prioritize different auth errors, but for now |
| 64 // all auth errors are treated the same. |
| 65 if (current_error.state() != GoogleServiceAuthError::NONE && |
| 66 current_error.state() != GoogleServiceAuthError::CONNECTION_FAILED) { |
| 67 break; |
| 68 } |
| 69 } |
| 70 if (current_error.state() != auth_error_.state()) { |
| 71 auth_error_ = current_error; |
| 72 GlobalErrorServiceFactory::GetForProfile(profile_)->NotifyErrorsChanged( |
| 73 this); |
| 74 } |
| 75 } |
| 76 |
| 77 bool SigninGlobalError::HasBadge() { |
| 78 // Badge the wrench menu any time there is a menu item reflecting an auth |
| 79 // error. |
| 80 return !MenuItemLabel().empty(); |
| 81 } |
| 82 |
| 83 bool SigninGlobalError::HasMenuItem() { |
| 84 // Auth errors are only reported via a separate menu item on chromeos - on |
| 85 // other platforms, WrenchMenuModel overlays the errors on top of the |
| 86 // "Signed in as xxxxx" menu item. |
| 87 #if defined(OS_CHROMEOS) |
| 88 return HasBadge(); |
| 89 #else |
| 90 return false; |
| 91 #endif |
| 92 } |
| 93 |
| 94 int SigninGlobalError::MenuItemCommandID() { |
| 95 return IDC_SHOW_SIGNIN_ERROR; |
| 96 } |
| 97 |
| 98 string16 SigninGlobalError::MenuItemLabel() { |
| 99 if (SigninManagerFactory::GetForProfile(profile_)-> |
| 100 GetAuthenticatedUsername().empty() || |
| 101 auth_error_.state() == GoogleServiceAuthError::NONE || |
| 102 auth_error_.state() == GoogleServiceAuthError::CONNECTION_FAILED) { |
| 103 // If the user isn't signed in, or there's no auth error worth elevating to |
| 104 // the user, don't display any menu item. |
| 105 return string16(); |
| 106 } else { |
| 107 // There's an auth error the user should know about - notify the user. |
| 108 return l10n_util::GetStringUTF16(IDS_SYNC_SIGN_IN_ERROR_WRENCH_MENU_ITEM); |
| 109 } |
| 110 } |
| 111 |
| 112 void SigninGlobalError::ExecuteMenuItem(Browser* browser) { |
| 113 #if defined(OS_CHROMEOS) |
| 114 if (auth_error_.state() != GoogleServiceAuthError::NONE) { |
| 115 DLOG(INFO) << "Signing out the user to fix a sync error."; |
| 116 // TODO(beng): seems like this could just call browser::AttemptUserExit(). |
| 117 chrome::ExecuteCommand(browser, IDC_EXIT); |
| 118 return; |
| 119 } |
| 120 #endif |
| 121 |
| 122 // Global errors don't show up in the wrench menu on android. |
| 123 #if !defined(OS_ANDROID) |
| 124 LoginUIService* login_ui = LoginUIServiceFactory::GetForProfile(profile_); |
| 125 if (login_ui->current_login_ui()) { |
| 126 login_ui->current_login_ui()->FocusUI(); |
| 127 return; |
| 128 } |
| 129 // Need to navigate to the settings page and display the UI. |
| 130 chrome::ShowSettingsSubPage(browser, chrome::kSyncSetupSubPage); |
| 131 #endif |
| 132 } |
| 133 |
| 134 bool SigninGlobalError::HasBubbleView() { |
| 135 return !GetBubbleViewMessage().empty(); |
| 136 } |
| 137 |
| 138 string16 SigninGlobalError::GetBubbleViewTitle() { |
| 139 return l10n_util::GetStringUTF16(IDS_SIGNIN_ERROR_BUBBLE_VIEW_TITLE); |
| 140 } |
| 141 |
| 142 string16 SigninGlobalError::GetBubbleViewMessage() { |
| 143 // If the user isn't signed in, no need to display an error bubble. |
| 144 if (SigninManagerFactory::GetForProfile(profile_)-> |
| 145 GetAuthenticatedUsername().empty()) { |
| 146 return string16(); |
| 147 } |
| 148 |
| 149 switch (auth_error_.state()) { |
| 150 // In the case of no error, or a simple network error, don't bother |
| 151 // displaying a popup bubble. |
| 152 case GoogleServiceAuthError::CONNECTION_FAILED: |
| 153 case GoogleServiceAuthError::NONE: |
| 154 return string16(); |
| 155 |
| 156 // User credentials are invalid (bad acct, etc). |
| 157 case GoogleServiceAuthError::INVALID_GAIA_CREDENTIALS: |
| 158 case GoogleServiceAuthError::ACCOUNT_DELETED: |
| 159 case GoogleServiceAuthError::ACCOUNT_DISABLED: |
| 160 return l10n_util::GetStringFUTF16( |
| 161 IDS_SYNC_SIGN_IN_ERROR_BUBBLE_VIEW_MESSAGE, |
| 162 l10n_util::GetStringUTF16(IDS_PRODUCT_NAME)); |
| 163 |
| 164 // Sync service is not available for this account's domain. |
| 165 case GoogleServiceAuthError::SERVICE_UNAVAILABLE: |
| 166 return l10n_util::GetStringFUTF16( |
| 167 IDS_SYNC_UNAVAILABLE_ERROR_BUBBLE_VIEW_MESSAGE, |
| 168 l10n_util::GetStringUTF16(IDS_PRODUCT_NAME)); |
| 169 |
| 170 // Generic message for "other" errors. |
| 171 default: |
| 172 return l10n_util::GetStringFUTF16( |
| 173 IDS_SYNC_OTHER_SIGN_IN_ERROR_BUBBLE_VIEW_MESSAGE, |
| 174 l10n_util::GetStringUTF16(IDS_PRODUCT_NAME)); |
| 175 } |
| 176 } |
| 177 |
| 178 string16 SigninGlobalError::GetBubbleViewAcceptButtonLabel() { |
| 179 // If the service is unavailable, don't give the user the option to try |
| 180 // signing in again. |
| 181 if (auth_error_.state() == GoogleServiceAuthError::SERVICE_UNAVAILABLE) { |
| 182 return l10n_util::GetStringUTF16( |
| 183 IDS_SYNC_UNAVAILABLE_ERROR_BUBBLE_VIEW_ACCEPT); |
| 184 } else { |
| 185 return l10n_util::GetStringUTF16(IDS_SYNC_SIGN_IN_ERROR_BUBBLE_VIEW_ACCEPT); |
| 186 } |
| 187 } |
| 188 |
| 189 string16 SigninGlobalError::GetBubbleViewCancelButtonLabel() { |
| 190 return string16(); |
| 191 } |
| 192 |
| 193 void SigninGlobalError::OnBubbleViewDidClose(Browser* browser) { |
| 194 } |
| 195 |
| 196 void SigninGlobalError::BubbleViewAcceptButtonPressed(Browser* browser) { |
| 197 ExecuteMenuItem(browser); |
| 198 } |
| 199 |
| 200 void SigninGlobalError::BubbleViewCancelButtonPressed(Browser* browser) { |
| 201 NOTREACHED(); |
| 202 } |
OLD | NEW |