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

Side by Side Diff: components/contextual_suggestions/contextual_suggestions_service.cc

Issue 2965173002: Add ContextualSuggestionsService to Omnibox (Closed)
Patch Set: Created 3 years, 5 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
OLDNEW
(Empty)
1 // Copyright 2017 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 "components/contextual_suggestions/contextual_suggestions_service.h"
6
7 #include "base/feature_list.h"
8 #include "base/memory/ptr_util.h"
9 #include "base/metrics/field_trial_params.h"
10 #include "base/strings/stringprintf.h"
11 #include "components/contextual_suggestions/features.h"
12 #include "components/data_use_measurement/core/data_use_user_data.h"
13 #include "components/variations/net/variations_http_headers.h"
14 #include "google_apis/gaia/gaia_constants.h"
15 #include "net/base/escape.h"
16 #include "net/base/load_flags.h"
17 #include "net/http/http_response_headers.h"
18 #include "net/traffic_annotation/network_traffic_annotation.h"
19 #include "net/url_request/url_fetcher.h"
20
21 namespace contextual_suggestions {
22
23 namespace {
24
25 // Parameter names used by the experiment redirecting Zero Suggestion requests
26 // to a service provided by the Chrome team
27 const char kZeroSuggestRedirectToChromeServerAddressParam[] =
28 "ZeroSuggestRedirectToChromeServerAddress";
29 const char kZeroSuggestRedirectToChromeAdditionalFieldsParam[] =
30 "ZeroSuggestRedirectToChromeAdditionalFields";
31
32 // Format string for OAuth2 authentication headers.
33 const char kAuthorizationHeaderFormat[] = "Authorization: Bearer %s";
34
35 } // namespace
36
37 ContextualSuggestionsService::ContextualSuggestionsService(
38 SigninManagerBase* signin_manager,
39 OAuth2TokenService* token_service,
40 TemplateURLService* template_url_service,
41 net::URLRequestContextGetter* request_context)
42 : request_context_(request_context),
43 signin_manager_(signin_manager),
44 template_url_service_(template_url_service),
45 token_service_(token_service) {}
46
47 ContextualSuggestionsService::~ContextualSuggestionsService() {}
48
49 bool ContextualSuggestionsService::UseExperimentalZeroSuggestSuggestions()
50 const {
51 if (!base::FeatureList::IsEnabled(features::kZeroSuggestRedirectToChrome) ||
52 template_url_service_ == nullptr) {
53 return false;
54 }
55
56 // Check that the default search engine is Google.
57 const TemplateURL& default_provider_url =
58 *template_url_service_->GetDefaultSearchProvider();
59 const SearchTermsData& search_terms_data =
60 template_url_service_->search_terms_data();
61 if (default_provider_url.GetEngineType(search_terms_data) !=
62 SEARCH_ENGINE_GOOGLE) {
63 return false;
64 }
65
66 // Check that the suggest URL for redirect to chrome field trial is valid.
67 const GURL suggest_url =
68 ExperimentalZeroSuggestURL(/*visited_url=*/std::string());
69 if (!suggest_url.is_valid()) {
70 return false;
71 }
72
73 // Check that the suggest URL for redirect to chrome is HTTPS.
74 return suggest_url.SchemeIsCryptographic();
75 }
76
77 void ContextualSuggestionsService::CreateContextualSuggestionsRequest(
78 const std::string& visited_url,
79 net::URLFetcherDelegate* fetcher_delegate,
80 ContextualSuggestionsCallback callback) {
81 DCHECK(signin_manager_);
82 DCHECK(token_service_);
83
84 // Skip this request if still waiting for oauth2 token.
85 if (token_fetcher_) {
86 std::move(callback).Run(nullptr);
87 return;
88 }
89
90 std::unique_ptr<net::URLFetcher> fetcher =
91 CreateRequest(visited_url, fetcher_delegate);
92 if (fetcher == nullptr) {
93 std::move(callback).Run(nullptr);
94 return;
95 }
96
97 // Create the oauth2 token fetcher.
98 OAuth2TokenService::ScopeSet scopes{GaiaConstants::kAnyApiOAuth2Scope};
99 token_fetcher_ = base::MakeUnique<AccessTokenFetcher>(
100 "contextual_suggestions_service", signin_manager_, token_service_, scopes,
101 base::BindOnce(&ContextualSuggestionsService::AccessTokenAvailable,
102 base::Unretained(this), std::move(fetcher),
103 std::move(callback)));
104 }
105
106 // static
107 GURL ContextualSuggestionsService::ExperimentalZeroSuggestURL(
108 const std::string& visited_url) {
109 const std::string server_address = base::GetFieldTrialParamValueByFeature(
110 features::kZeroSuggestRedirectToChrome,
111 kZeroSuggestRedirectToChromeServerAddressParam);
112 const std::string additional_parameters =
113 base::GetFieldTrialParamValueByFeature(
114 features::kZeroSuggestRedirectToChrome,
115 kZeroSuggestRedirectToChromeAdditionalFieldsParam);
116 return GURL(server_address + "/url=" + net::EscapePath(visited_url) +
117 additional_parameters);
118 }
119
Mark P 2017/07/07 20:13:54 I'm a bit bothered that the whole rest of this fil
gcomanici 2017/07/07 21:24:45 I share the feeling with you and I am willing to m
120 std::unique_ptr<net::URLFetcher> ContextualSuggestionsService::CreateRequest(
121 const std::string& visited_url,
122 net::URLFetcherDelegate* fetcher_delegate) const {
123 net::NetworkTrafficAnnotationTag traffic_annotation =
124 net::DefineNetworkTrafficAnnotation("omnibox_contextual_zerosuggest", R"(
Mark P 2017/07/07 20:13:54 Not sure if you should be using a new annotation h
gcomanici 2017/07/07 21:24:45 The annotation is different though. First, it send
125 semantics {
126 sender: "Omnibox"
127 description:
128 "When the user focuses the omnibox, Chrome can provide search or "
129 "navigation suggestions from the default search provider in the "
130 "omnibox dropdown, based on the current page URL.\n"
131 "This is limited to users whose default search engine is Google, "
132 "as no other search engines currently support this kind of "
133 "suggestion."
134 trigger: "The omnibox receives focus."
135 data: "The URL of the current page."
136 destination: GOOGLE_OWNED_SERVICE
137 }
138 policy {
139 cookies_allowed: false
140 setting:
141 "Users can control this feature via the 'Use a prediction service "
142 "to help complete searches and URLs typed in the address bar' "
143 "settings under 'Privacy'. The feature is enabled by default."
144 chrome_policy {
145 SearchSuggestEnabled {
146 policy_options {mode: MANDATORY}
147 SearchSuggestEnabled: false
148 }
149 }
150 })");
151 const int kFetcherID = 1;
152 const GURL suggest_url = ExperimentalZeroSuggestURL(visited_url);
153 DCHECK(suggest_url.is_valid());
154
155 std::unique_ptr<net::URLFetcher> fetcher =
156 net::URLFetcher::Create(kFetcherID, suggest_url, net::URLFetcher::GET,
157 fetcher_delegate, traffic_annotation);
158 data_use_measurement::DataUseUserData::AttachToFetcher(
159 fetcher.get(), data_use_measurement::DataUseUserData::OMNIBOX);
160 fetcher->SetRequestContext(request_context_);
161 fetcher->SetLoadFlags(net::LOAD_DO_NOT_SEND_COOKIES |
Mark P 2017/07/07 20:13:54 Are you sure you want to set this flag?
gcomanici 2017/07/07 21:24:46 The request sends the oauth token. As such, there
162 net::LOAD_DO_NOT_SAVE_COOKIES);
163 // Add Chrome experiment state to the request headers.
164 net::HttpRequestHeaders headers;
165 // Note: It's OK to pass |is_signed_in| false if it's unknown, as it does
166 // not affect transmission of experiments coming from the variations server.
167 variations::AppendVariationHeaders(fetcher->GetOriginalURL(),
168 /*incognito=*/false,
169 /*uma_enabled=*/false,
170 /*is_signed_in=*/false, &headers);
171 fetcher->SetExtraRequestHeaders(headers.ToString());
172 return fetcher;
173 }
174
175 void ContextualSuggestionsService::AccessTokenAvailable(
176 std::unique_ptr<net::URLFetcher> fetcher,
177 ContextualSuggestionsCallback callback,
178 const GoogleServiceAuthError& error,
179 const std::string& access_token) {
180 DCHECK(token_fetcher_);
181 std::unique_ptr<AccessTokenFetcher> token_fetcher_deleter(
182 std::move(token_fetcher_));
183
184 if (error.state() != GoogleServiceAuthError::NONE) {
185 std::move(callback).Run(nullptr);
186 return;
187 }
188 DCHECK(!access_token.empty());
189 fetcher->AddExtraRequestHeader(
190 base::StringPrintf(kAuthorizationHeaderFormat, access_token.c_str()));
191 std::move(callback).Run(std::move(fetcher));
192 }
193
194 } // namespace contextual_suggestions
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698