Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(310)

Side by Side Diff: chrome/browser/ui/sync/one_click_signin_helper.cc

Issue 10555005: Address bug where the one-click sign-in bar would never show again once (Closed) Base URL: http://src.chromium.org/svn/trunk/src/
Patch Set: Merge Created 8 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
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/ui/sync/one_click_signin_helper.h" 5 #include "chrome/browser/ui/sync/one_click_signin_helper.h"
6 6
7 #include "base/bind.h" 7 #include "base/bind.h"
8 #include "base/compiler_specific.h" 8 #include "base/compiler_specific.h"
9 #include "base/metrics/histogram.h" 9 #include "base/metrics/histogram.h"
10 #include "base/string_split.h" 10 #include "base/string_split.h"
11 #include "base/utf_string_conversions.h" 11 #include "base/utf_string_conversions.h"
12 #include "chrome/browser/browser_process.h" 12 #include "chrome/browser/browser_process.h"
13 #include "chrome/browser/infobars/infobar_tab_helper.h" 13 #include "chrome/browser/infobars/infobar_tab_helper.h"
14 #include "chrome/browser/prefs/pref_service.h" 14 #include "chrome/browser/prefs/pref_service.h"
15 #include "chrome/browser/prefs/scoped_user_pref_update.h"
15 #include "chrome/browser/profiles/profile.h" 16 #include "chrome/browser/profiles/profile.h"
16 #include "chrome/browser/profiles/profile_info_cache.h" 17 #include "chrome/browser/profiles/profile_info_cache.h"
17 #include "chrome/browser/profiles/profile_manager.h" 18 #include "chrome/browser/profiles/profile_manager.h"
18 #include "chrome/browser/signin/signin_manager.h" 19 #include "chrome/browser/signin/signin_manager.h"
19 #include "chrome/browser/signin/signin_manager_factory.h" 20 #include "chrome/browser/signin/signin_manager_factory.h"
20 #include "chrome/browser/sync/profile_sync_service.h" 21 #include "chrome/browser/sync/profile_sync_service.h"
21 #include "chrome/browser/sync/profile_sync_service_factory.h"
22 #include "chrome/browser/tab_contents/confirm_infobar_delegate.h" 22 #include "chrome/browser/tab_contents/confirm_infobar_delegate.h"
23 #include "chrome/browser/tab_contents/tab_util.h" 23 #include "chrome/browser/tab_contents/tab_util.h"
24 #include "chrome/browser/ui/browser_finder.h" 24 #include "chrome/browser/ui/browser_finder.h"
25 #include "chrome/browser/ui/browser_window.h" 25 #include "chrome/browser/ui/browser_window.h"
26 #include "chrome/browser/ui/sync/one_click_signin_histogram.h" 26 #include "chrome/browser/ui/sync/one_click_signin_histogram.h"
27 #include "chrome/browser/ui/sync/one_click_signin_sync_starter.h" 27 #include "chrome/browser/ui/sync/one_click_signin_sync_starter.h"
28 #include "chrome/browser/ui/tab_contents/tab_contents.h" 28 #include "chrome/browser/ui/tab_contents/tab_contents.h"
29 #include "chrome/common/pref_names.h" 29 #include "chrome/common/pref_names.h"
30 #include "chrome/common/url_constants.h" 30 #include "chrome/common/url_constants.h"
31 #include "content/public/browser/browser_thread.h" 31 #include "content/public/browser/browser_thread.h"
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after
65 virtual bool Cancel() OVERRIDE; 65 virtual bool Cancel() OVERRIDE;
66 virtual string16 GetLinkText() const OVERRIDE; 66 virtual string16 GetLinkText() const OVERRIDE;
67 virtual bool LinkClicked(WindowOpenDisposition disposition) OVERRIDE; 67 virtual bool LinkClicked(WindowOpenDisposition disposition) OVERRIDE;
68 68
69 virtual InfoBarAutomationType GetInfoBarAutomationType() const OVERRIDE; 69 virtual InfoBarAutomationType GetInfoBarAutomationType() const OVERRIDE;
70 70
71 // Set the profile preference to turn off one-click sign in so that it won't 71 // Set the profile preference to turn off one-click sign in so that it won't
72 // show again in this profile. 72 // show again in this profile.
73 void DisableOneClickSignIn(); 73 void DisableOneClickSignIn();
74 74
75 // Add a specific email to the list of emails rejected for one-click
76 // sign-in, for this profile.
77 void AddEmailToOneClickRejectedList(const std::string& email);
78
75 // Record the specified action in the histogram for one-click sign in. 79 // Record the specified action in the histogram for one-click sign in.
76 void RecordHistogramAction(int action); 80 void RecordHistogramAction(int action);
77 81
78 // Information about the account that has just logged in. 82 // Information about the account that has just logged in.
79 std::string session_index_; 83 std::string session_index_;
80 std::string email_; 84 std::string email_;
81 std::string password_; 85 std::string password_;
82 86
83 // Whether any UI controls in the infobar were pressed or not. 87 // Whether any UI controls in the infobar were pressed or not.
84 bool button_pressed_; 88 bool button_pressed_;
(...skipping 54 matching lines...) Expand 10 before | Expand all | Expand 10 after
139 OneClickSigninSyncStarter::StartSyncMode start_mode) { 143 OneClickSigninSyncStarter::StartSyncMode start_mode) {
140 // The starter deletes itself once its done. 144 // The starter deletes itself once its done.
141 Browser* browser = browser::FindBrowserWithWebContents(web_contents); 145 Browser* browser = browser::FindBrowserWithWebContents(web_contents);
142 new OneClickSigninSyncStarter(browser, session_index, email, password, 146 new OneClickSigninSyncStarter(browser, session_index, email, password,
143 start_mode); 147 start_mode);
144 } 148 }
145 149
146 } // namespace 150 } // namespace
147 151
148 bool OneClickLoginInfoBarDelegate::Accept() { 152 bool OneClickLoginInfoBarDelegate::Accept() {
153 // User has accepted one-click sign-in for this account. Never ask again for
154 // this profile.
149 DisableOneClickSignIn(); 155 DisableOneClickSignIn();
150 content::WebContents* web_contents = owner()->web_contents(); 156 content::WebContents* web_contents = owner()->web_contents();
151 RecordHistogramAction(one_click_signin::HISTOGRAM_ACCEPTED); 157 RecordHistogramAction(one_click_signin::HISTOGRAM_ACCEPTED);
152 browser::FindBrowserWithWebContents(web_contents)->window()-> 158 browser::FindBrowserWithWebContents(web_contents)->window()->
153 ShowOneClickSigninBubble(base::Bind(&StartSync, web_contents, 159 ShowOneClickSigninBubble(base::Bind(&StartSync, web_contents,
154 session_index_, email_, password_)); 160 session_index_, email_, password_));
155 button_pressed_ = true; 161 button_pressed_ = true;
156 return true; 162 return true;
157 } 163 }
158 164
159 bool OneClickLoginInfoBarDelegate::Cancel() { 165 bool OneClickLoginInfoBarDelegate::Cancel() {
160 DisableOneClickSignIn(); 166 AddEmailToOneClickRejectedList(email_);
161 RecordHistogramAction(one_click_signin::HISTOGRAM_REJECTED); 167 RecordHistogramAction(one_click_signin::HISTOGRAM_REJECTED);
162 button_pressed_ = true; 168 button_pressed_ = true;
163 return true; 169 return true;
164 } 170 }
165 171
166 string16 OneClickLoginInfoBarDelegate::GetLinkText() const { 172 string16 OneClickLoginInfoBarDelegate::GetLinkText() const {
167 return l10n_util::GetStringUTF16(IDS_LEARN_MORE); 173 return l10n_util::GetStringUTF16(IDS_LEARN_MORE);
168 } 174 }
169 175
170 bool OneClickLoginInfoBarDelegate::LinkClicked( 176 bool OneClickLoginInfoBarDelegate::LinkClicked(
(...skipping 12 matching lines...) Expand all
183 return ONE_CLICK_LOGIN_INFOBAR; 189 return ONE_CLICK_LOGIN_INFOBAR;
184 } 190 }
185 191
186 void OneClickLoginInfoBarDelegate::DisableOneClickSignIn() { 192 void OneClickLoginInfoBarDelegate::DisableOneClickSignIn() {
187 PrefService* pref_service = 193 PrefService* pref_service =
188 TabContents::FromWebContents(owner()->web_contents())-> 194 TabContents::FromWebContents(owner()->web_contents())->
189 profile()->GetPrefs(); 195 profile()->GetPrefs();
190 pref_service->SetBoolean(prefs::kReverseAutologinEnabled, false); 196 pref_service->SetBoolean(prefs::kReverseAutologinEnabled, false);
191 } 197 }
192 198
199 void OneClickLoginInfoBarDelegate::AddEmailToOneClickRejectedList(
200 const std::string& email) {
201 PrefService* pref_service =
202 TabContents::FromWebContents(owner()->web_contents())->
203 profile()->GetPrefs();
204 ListPrefUpdate updater(pref_service,
205 prefs::kReverseAutologinRejectedEmailList);
206 updater->AppendIfNotPresent(base::Value::CreateStringValue(email));
207 }
208
193 void OneClickLoginInfoBarDelegate::RecordHistogramAction(int action) { 209 void OneClickLoginInfoBarDelegate::RecordHistogramAction(int action) {
194 UMA_HISTOGRAM_ENUMERATION("AutoLogin.Reverse", action, 210 UMA_HISTOGRAM_ENUMERATION("AutoLogin.Reverse", action,
195 one_click_signin::HISTOGRAM_MAX); 211 one_click_signin::HISTOGRAM_MAX);
196 } 212 }
197 213
198 // static 214 // static
199 bool OneClickSigninHelper::CanOffer(content::WebContents* web_contents, 215 bool OneClickSigninHelper::CanOffer(content::WebContents* web_contents,
216 const std::string& email,
200 bool check_connected) { 217 bool check_connected) {
201 if (!web_contents) 218 if (!web_contents)
202 return false; 219 return false;
203 220
204 if (web_contents->GetBrowserContext()->IsOffTheRecord()) 221 if (web_contents->GetBrowserContext()->IsOffTheRecord())
205 return false; 222 return false;
206 223
207 if (!ProfileSyncService::IsSyncEnabled()) 224 if (!ProfileSyncService::IsSyncEnabled())
208 return false; 225 return false;
209 226
(...skipping 10 matching lines...) Expand all
220 237
221 if (check_connected) { 238 if (check_connected) {
222 SigninManager* manager = 239 SigninManager* manager =
223 SigninManagerFactory::GetForProfile(profile); 240 SigninManagerFactory::GetForProfile(profile);
224 if (!manager) 241 if (!manager)
225 return false; 242 return false;
226 243
227 if (!manager->GetAuthenticatedUsername().empty()) 244 if (!manager->GetAuthenticatedUsername().empty())
228 return false; 245 return false;
229 246
230 // If we're about to show a one-click infobar but the user has started 247 // Make sure this username is not prohibited by policy.
231 // a concurrent signin flow (perhaps via the promo), we may not have yet 248 if (!manager->IsAllowedUsername(email))
232 // established an authenticated username but we still shouldn't move
233 // forward with two simultaneous signin processes. This is a bit
234 // contentious as the one-click flow is a much smoother flow from the user
235 // perspective, but it's much more difficult to hijack the other flow from
236 // here as it is to bail.
237 ProfileSyncService* service =
238 ProfileSyncServiceFactory::GetForProfile(profile);
239 if (!service)
240 return false; 249 return false;
241 250
242 if (service->FirstSetupInProgress()) 251 // If some profile, not just the current one, is already connected to this
243 return false; 252 // account, don't show the infobar.
253 if (g_browser_process) {
254 ProfileManager* manager = g_browser_process->profile_manager();
255 if (manager) {
256 string16 email16 = UTF8ToUTF16(email);
257 ProfileInfoCache& cache = manager->GetProfileInfoCache();
258
259 for (size_t i = 0; i < cache.GetNumberOfProfiles(); ++i) {
260 if (email16 == cache.GetUserNameOfProfileAtIndex(i))
261 return false;
262 }
263 }
264 }
265
266 // If email was already rejected by this profile for one-click sign-in.
267 if (!email.empty()) {
268 const ListValue* rejected_emails = profile->GetPrefs()->GetList(
269 prefs::kReverseAutologinRejectedEmailList);
270 if (!rejected_emails->empty()) {
271 const Value* email_value = Value::CreateStringValue(email);
272 ListValue::const_iterator iter = rejected_emails->Find(
273 *email_value);
274 if (iter != rejected_emails->end())
275 return false;
276 }
277 }
244 } 278 }
245 279
246 return true; 280 return true;
247 } 281 }
248 282
249 // static 283 // static
250 void OneClickSigninHelper::ShowInfoBarIfPossible(net::URLRequest* request, 284 void OneClickSigninHelper::ShowInfoBarIfPossible(net::URLRequest* request,
251 int child_id, 285 int child_id,
252 int route_id) { 286 int route_id) {
253 // See if the response contains the Google-Accounts-SignIn header. 287 // See if the response contains the Google-Accounts-SignIn header.
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after
291 // static 325 // static
292 void OneClickSigninHelper::ShowInfoBarUIThread( 326 void OneClickSigninHelper::ShowInfoBarUIThread(
293 const std::string& session_index, 327 const std::string& session_index,
294 const std::string& email, 328 const std::string& email,
295 int child_id, 329 int child_id,
296 int route_id) { 330 int route_id) {
297 DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::UI)); 331 DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::UI));
298 332
299 content::WebContents* web_contents = tab_util::GetWebContentsByID(child_id, 333 content::WebContents* web_contents = tab_util::GetWebContentsByID(child_id,
300 route_id); 334 route_id);
301 if (!web_contents || !CanOffer(web_contents, true))
302 return;
303 335
304 // If some profile, not just the current one, is already connected to this 336 // TODO(mathp): The appearance of this infobar should be tested using a
305 // account, don't show the infobar. 337 // browser_test.
306 if (g_browser_process) { 338 if (!web_contents || !CanOffer(web_contents, email, true))
307 ProfileManager* manager = g_browser_process->profile_manager();
308 if (manager) {
309 string16 email16 = UTF8ToUTF16(email);
310 ProfileInfoCache& cache = manager->GetProfileInfoCache();
311
312 for (size_t i = 0; i < cache.GetNumberOfProfiles(); ++i) {
313 if (email16 == cache.GetUserNameOfProfileAtIndex(i))
314 return;
315 }
316 }
317 }
318
319 // Make sure this username is not prohibited by policy.
320 Profile* profile =
321 Profile::FromBrowserContext(web_contents->GetBrowserContext());
322 SigninManager* signin = SigninManagerFactory::GetForProfile(profile);
323 if (!signin->IsAllowedUsername(email))
324 return; 339 return;
325 340
326 TabContents* tab_contents = TabContents::FromWebContents(web_contents); 341 TabContents* tab_contents = TabContents::FromWebContents(web_contents);
327 if (!tab_contents) 342 if (!tab_contents)
328 return; 343 return;
329 344
330 // Save the email in the one-click signin manager. The manager may 345 // Save the email in the one-click signin manager. The manager may
331 // not exist if the contents is incognito or if the profile is already 346 // not exist if the contents is incognito or if the profile is already
332 // connected to a Google account. 347 // connected to a Google account.
333 OneClickSigninHelper* helper = tab_contents->one_click_signin_helper(); 348 OneClickSigninHelper* helper = tab_contents->one_click_signin_helper();
(...skipping 29 matching lines...) Expand all
363 session_index_ = session_index; 378 session_index_ = session_index;
364 email_ = email; 379 email_ = email;
365 } 380 }
366 381
367 void OneClickSigninHelper::SavePassword(const std::string& password) { 382 void OneClickSigninHelper::SavePassword(const std::string& password) {
368 // TODO(rogerta): in the case of a 2-factor or captcha or some other type of 383 // TODO(rogerta): in the case of a 2-factor or captcha or some other type of
369 // challenge, its possible for the user to never complete the signin. 384 // challenge, its possible for the user to never complete the signin.
370 // Should have a way to detect this and clear the password member. 385 // Should have a way to detect this and clear the password member.
371 password_ = password; 386 password_ = password;
372 } 387 }
OLDNEW
« no previous file with comments | « chrome/browser/ui/sync/one_click_signin_helper.h ('k') | chrome/browser/ui/sync/one_click_signin_helper_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698