1f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)// Copyright 2013 The Chromium Authors. All rights reserved.
2f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be
3f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)// found in the LICENSE file.
4f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)
5f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)#include "chrome/browser/signin/signin_header_helper.h"
6f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)
75c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu#include "base/strings/string_number_conversions.h"
846d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)#include "base/strings/string_util.h"
9cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)#include "base/strings/stringprintf.h"
105c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu#include "chrome/browser/prefs/incognito_mode_prefs.h"
11f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)#include "chrome/browser/profiles/profile_io_data.h"
12f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)#include "chrome/browser/tab_contents/tab_util.h"
13f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)#include "chrome/browser/ui/browser_window.h"
145c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu#include "chrome/common/url_constants.h"
156d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)#include "components/google/core/browser/google_util.h"
160529e5d033099cbfc42635f6f6183833b09dff6eBen Murdoch#include "components/signin/core/common/profile_management_switches.h"
17f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)#include "content/public/browser/browser_thread.h"
1803b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles)#include "content/public/browser/resource_request_info.h"
19f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)#include "content/public/browser/web_contents.h"
20f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)#include "google_apis/gaia/gaia_auth_util.h"
21f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)#include "net/http/http_response_headers.h"
22f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)#include "net/url_request/url_request.h"
23f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)
245d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#if defined(OS_ANDROID)
255d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#include "chrome/browser/android/signin/account_management_screen_helper.h"
265c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu#else
275c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu#include "chrome/browser/ui/browser_commands.h"
285c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu#include "chrome/browser/ui/browser_finder.h"
295d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#endif  // defined(OS_ANDROID)
305d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)
31f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)namespace {
32f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)
3346d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)// Dictionary of fields in a mirror response header.
3446d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)typedef std::map<std::string, std::string> MirrorResponseHeaderDictionary;
3546d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)
36f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)const char kChromeConnectedHeader[] = "X-Chrome-Connected";
37f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)const char kChromeManageAccountsHeader[] = "X-Chrome-Manage-Accounts";
38cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)const char kGaiaIdAttrName[] = "id";
39cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)const char kProfileModeAttrName[] = "mode";
40cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)const char kEnableAccountConsistencyAttrName[] = "enable_account_consistency";
41cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)
426d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)const char kServiceTypeAttrName[] = "action";
436d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)const char kEmailAttrName[] = "email";
446d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)const char kIsSamlAttrName[] = "is_saml";
456d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)const char kContinueUrlAttrName[] = "continue_url";
466d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)const char kIsSameTabAttrName[] = "is_same_tab";
476d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)
4846d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)// Determines the service type that has been passed from GAIA in the header.
49cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)signin::GAIAServiceType GetGAIAServiceTypeFromHeader(
50cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)    const std::string& header_value) {
51cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)  if (header_value == "SIGNOUT")
52cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)    return signin::GAIA_SERVICE_TYPE_SIGNOUT;
5346d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)  else if (header_value == "INCOGNITO")
5446d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)    return signin::GAIA_SERVICE_TYPE_INCOGNITO;
55cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)  else if (header_value == "ADDSESSION")
56cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)    return signin::GAIA_SERVICE_TYPE_ADDSESSION;
57cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)  else if (header_value == "REAUTH")
58cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)    return signin::GAIA_SERVICE_TYPE_REAUTH;
5903b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles)  else if (header_value == "SIGNUP")
6003b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles)    return signin::GAIA_SERVICE_TYPE_SIGNUP;
61cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)  else if (header_value == "DEFAULT")
62cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)    return signin::GAIA_SERVICE_TYPE_DEFAULT;
63cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)  else
64cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)    return signin::GAIA_SERVICE_TYPE_NONE;
65cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)}
66f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)
6746d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)// Parses the mirror response header. Its expected format is
6846d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)// "key1=value1,key2=value2,...".
6946d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)MirrorResponseHeaderDictionary ParseMirrorResponseHeader(
7046d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)    const std::string& header_value) {
7146d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)  std::vector<std::string> fields;
7246d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)  if (!Tokenize(header_value, std::string(","), &fields))
7346d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)    return MirrorResponseHeaderDictionary();
7446d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)
7546d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)  MirrorResponseHeaderDictionary dictionary;
7646d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)  for (std::vector<std::string>::iterator i = fields.begin();
7746d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)       i != fields.end(); ++i) {
7846d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)    std::string field(*i);
7946d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)    std::vector<std::string> tokens;
801320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci    size_t delim = field.find_first_of('=');
811320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci    if (delim == std::string::npos) {
826d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)      DLOG(WARNING) << "Unexpected GAIA header field '" << field << "'.";
8346d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)      continue;
8446d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)    }
851320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci    dictionary[field.substr(0, delim)] = net::UnescapeURLComponent(
861320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci        field.substr(delim + 1), net::UnescapeRule::URL_SPECIAL_CHARS);
8746d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)  }
8846d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)  return dictionary;
8946d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)}
9046d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)
916d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)// Returns the parameters contained in the X-Chrome-Manage-Accounts response
926d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)// header.
936d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)signin::ManageAccountsParams BuildManageAccountsParams(
946d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)    const std::string& header_value) {
956d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)  signin::ManageAccountsParams params;
966d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)  MirrorResponseHeaderDictionary header_dictionary =
976d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)      ParseMirrorResponseHeader(header_value);
986d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)  MirrorResponseHeaderDictionary::const_iterator it = header_dictionary.begin();
996d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)  for (; it != header_dictionary.end(); ++it) {
1006d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)    const std::string key_name(it->first);
1016d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)    if (key_name == kServiceTypeAttrName) {
1026d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)      params.service_type =
1036d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)          GetGAIAServiceTypeFromHeader(header_dictionary[kServiceTypeAttrName]);
1046d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)    } else if (key_name == kEmailAttrName) {
1056d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)      params.email = header_dictionary[kEmailAttrName];
1066d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)    } else if (key_name == kIsSamlAttrName) {
1076d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)      params.is_saml = header_dictionary[kIsSamlAttrName] == "true";
1086d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)    } else if (key_name == kContinueUrlAttrName) {
1096d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)      params.continue_url = header_dictionary[kContinueUrlAttrName];
1106d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)    } else if (key_name == kIsSameTabAttrName) {
1116d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)      params.is_same_tab = header_dictionary[kIsSameTabAttrName] == "true";
1126d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)    } else {
1136d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)      DLOG(WARNING) << "Unexpected GAIA header attribute '" << key_name << "'.";
1146d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)    }
1156d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)  }
1166d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)  return params;
1176d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)}
1186d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)
11946d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)#if !defined(OS_IOS)
1205c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu// Processes the mirror response header on the UI thread. Currently depending
1215c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu// on the value of |header_value|, it either shows the profile avatar menu, or
1225c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu// opens an incognito window/tab.
1235c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liuvoid ProcessMirrorHeaderUIThread(
12446d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)    int child_id, int route_id,
12546d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)    signin::ManageAccountsParams manage_accounts_params) {
126f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::UI));
127f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)
12846d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)  signin::GAIAServiceType service_type = manage_accounts_params.service_type;
12946d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)  DCHECK_NE(signin::GAIA_SERVICE_TYPE_NONE, service_type);
13046d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)
131f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  content::WebContents* web_contents =
132f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)      tab_util::GetWebContentsByID(child_id, route_id);
133f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  if (!web_contents)
134f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)    return;
135f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)
1365d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#if !defined(OS_ANDROID)
137f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  Browser* browser = chrome::FindBrowserWithWebContents(web_contents);
138effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch  if (browser) {
139f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)    BrowserWindow::AvatarBubbleMode bubble_mode;
140f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)    switch (service_type) {
141f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)      case signin::GAIA_SERVICE_TYPE_INCOGNITO:
142f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)        chrome::NewIncognitoWindow(browser);
143f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)        return;
144f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)      case signin::GAIA_SERVICE_TYPE_ADDSESSION:
1451320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci        bubble_mode = BrowserWindow::AVATAR_BUBBLE_MODE_ADD_ACCOUNT;
146f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)        break;
147f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)      case signin::GAIA_SERVICE_TYPE_REAUTH:
148f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)        bubble_mode = BrowserWindow::AVATAR_BUBBLE_MODE_REAUTH;
149f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)        break;
150f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)      default:
151f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)        bubble_mode = BrowserWindow::AVATAR_BUBBLE_MODE_ACCOUNT_MANAGEMENT;
1525c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu    }
153f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)    browser->window()->ShowAvatarBubbleFromAvatarButton(
1546d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)        bubble_mode, manage_accounts_params);
155effb81e5f8246d0db0270817048dc992db66e9fbBen Murdoch  }
1565d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)#else  // defined(OS_ANDROID)
15746d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)  if (service_type == signin::GAIA_SERVICE_TYPE_INCOGNITO) {
1581320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci    GURL url(manage_accounts_params.continue_url.empty() ?
1591320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci        chrome::kChromeUINativeNewTabURL :
1601320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci        manage_accounts_params.continue_url);
1615c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu    web_contents->OpenURL(content::OpenURLParams(
1621320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci        url, content::Referrer(), OFF_THE_RECORD,
1631320f92c476a1ad9d19dba2a48c72b75566198e9Primiano Tucci        ui::PAGE_TRANSITION_AUTO_TOPLEVEL, false));
1645c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  } else {
1655c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu    AccountManagementScreenHelper::OpenAccountManagementScreen(
16646d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)        Profile::FromBrowserContext(web_contents->GetBrowserContext()),
16746d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)        service_type);
1685c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  }
169f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)#endif // OS_ANDROID
170f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)}
17146d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)#endif // !defined(OS_IOS)
172f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)
173a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)bool IsDriveOrigin(const GURL& url) {
174a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)  if (!url.SchemeIsSecure())
175a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)    return false;
176a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)
177a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)  const GURL kGoogleDriveURL("https://drive.google.com");
178a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)  const GURL kGoogleDocsURL("https://docs.google.com");
179a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)  return url == kGoogleDriveURL || url == kGoogleDocsURL;
180a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)}
181a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)
182f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)} // empty namespace
183f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)
184f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)namespace signin {
185f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)
1866d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)ManageAccountsParams::ManageAccountsParams() :
1876d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)    service_type(GAIA_SERVICE_TYPE_NONE),
1886d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)    email(""),
1896d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)    is_saml(false),
1906d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)    continue_url(""),
1916d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)    is_same_tab(false),
1926d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)    child_id(0),
1936d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)    route_id(0) {}
1946d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)
19546d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)bool AppendMirrorRequestHeaderIfPossible(
196f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)    net::URLRequest* request,
197f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)    const GURL& redirect_url,
19803b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles)    ProfileIOData* io_data) {
199f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::IO));
200f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)
201a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)  if (io_data->IsOffTheRecord() ||
202a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)      io_data->google_services_username()->GetValue().empty()) {
20346d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)    return false;
204a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)  }
2055d1f7b1de12d16ceb2c938c56701a3e8bfa558f7Torne (Richard Coles)
206a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)  // Only set the header for Drive always, and other Google properties if
207a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)  // new-profile-management is enabled.
208a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)  // Vasquette, which is integrated with most Google properties, needs the
209a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)  // header to redirect certain user actions to Chrome native UI. Drive needs
210a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)  // the header to tell if the current user is connected. The drive path is a
211a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)  // temporary workaround until the more generic chrome.principals API is
212a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)  // available.
213f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  const GURL& url = redirect_url.is_empty() ? request->url() : redirect_url;
214a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)  GURL origin(url.GetOrigin());
2155f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)  bool is_enable_account_consistency = switches::IsEnableAccountConsistency();
216a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)  bool is_google_url =
217a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)      !switches::IsEnableWebBasedSignin() &&
2185f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)      is_enable_account_consistency &&
219f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)      (google_util::IsGoogleDomainUrl(
220f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)           url,
221f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)           google_util::ALLOW_SUBDOMAIN,
222f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)           google_util::DISALLOW_NON_STANDARD_PORTS) ||
223f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)       google_util::IsYoutubeDomainUrl(
224f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)           url,
225f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)           google_util::ALLOW_SUBDOMAIN,
226f8ee788a64d60abd8f2d742a5fdedde054ecd910Torne (Richard Coles)           google_util::DISALLOW_NON_STANDARD_PORTS));
227a1401311d1ab56c4ed0a474bd38c108f75cb0cd9Torne (Richard Coles)  if (!is_google_url && !IsDriveOrigin(origin))
22846d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)    return false;
229f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)
230a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)  std::string account_id(io_data->google_services_account_id()->GetValue());
231a3f6a49ab37290eeeb8db0f41ec0f1cb74a68be7Torne (Richard Coles)
2325c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  int profile_mode_mask = PROFILE_MODE_DEFAULT;
2335c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  if (io_data->incognito_availibility()->GetValue() ==
2346d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)          IncognitoModePrefs::DISABLED ||
2356d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)      IncognitoModePrefs::ArePlatformParentalControlsEnabledCached()) {
2365c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu    profile_mode_mask |= PROFILE_MODE_INCOGNITO_DISABLED;
2375c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu  }
2385c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu
239cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)  // TODO(guohui): needs to make a new flag for enabling account consistency.
240cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)  std::string header_value(base::StringPrintf("%s=%s,%s=%s,%s=%s",
241cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)      kGaiaIdAttrName, account_id.c_str(),
242cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)      kProfileModeAttrName, base::IntToString(profile_mode_mask).c_str(),
243cedac228d2dd51db4b79ea1e72c7f249408ee061Torne (Richard Coles)      kEnableAccountConsistencyAttrName,
2445f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)      is_enable_account_consistency ? "true" : "false"));
245f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  request->SetExtraRequestHeaderByName(
2465c02ac1a9c1b504631c0a3d2b6e737b5d738bae1Bo Liu      kChromeConnectedHeader, header_value, false);
24746d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)  return true;
24846d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)}
24946d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)
250f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)void ProcessMirrorResponseHeaderIfExists(
251f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)    net::URLRequest* request,
252f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)    ProfileIOData* io_data,
253f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)    int child_id,
254f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)    int route_id) {
25546d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)#if defined(OS_IOS)
25646d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)  NOTREACHED();
25746d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)#else
258f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)  DCHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::IO));
2596d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)  if (!gaia::IsGaiaSignonRealm(request->url().GetOrigin()))
2606d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)    return;
2616d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)
26203b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles)  const content::ResourceRequestInfo* info =
26303b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles)      content::ResourceRequestInfo::ForRequest(request);
26434680572440d7894ef8dafce81d8039ed80726a2Torne (Richard Coles)  if (!(info && info->GetResourceType() == content::RESOURCE_TYPE_MAIN_FRAME))
26503b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles)    return;
26603b57e008b61dfcb1fbad3aea950ae0e001748b0Torne (Richard Coles)
2676d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)  std::string header_value;
2686d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)  if (!request->response_headers()->GetNormalizedHeader(
2696d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)          kChromeManageAccountsHeader, &header_value)) {
2706d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)    return;
2716d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)  }
2726d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)
2735f1c94371a64b3196d4be9466099bb892df9b88eTorne (Richard Coles)  DCHECK(switches::IsEnableAccountConsistency() && !io_data->IsOffTheRecord());
2746d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)  ManageAccountsParams params(BuildManageAccountsParams(header_value));
27546d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)  if (params.service_type == GAIA_SERVICE_TYPE_NONE)
27646d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)    return;
277f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)
2786d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)  params.child_id = child_id;
2796d86b77056ed63eb6871182f42a9fd5f07550f90Torne (Richard Coles)  params.route_id = route_id;
28046d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)  content::BrowserThread::PostTask(
28146d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)      content::BrowserThread::UI, FROM_HERE,
28246d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)      base::Bind(ProcessMirrorHeaderUIThread, child_id, route_id, params));
28346d4c2bc3267f3f028f39e7e311b0f89aba2e4fdTorne (Richard Coles)#endif  // defined(OS_IOS)
284f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)}
285f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)
286f2477e01787aa58f445919b809d89e252beef54fTorne (Richard Coles)} // namespace signin
287