blob: d0b5ce9ba6dcca66b49b74a6cb9a47e81296757a [file] [log] [blame]
Daniel Kenji Toyamaf1e4b572017-08-03 16:31:111// 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#ifndef COMPONENTS_OMNIBOX_BROWSER_CONTEXTUAL_SUGGESTIONS_SERVICE_H_
6#define COMPONENTS_OMNIBOX_BROWSER_CONTEXTUAL_SUGGESTIONS_SERVICE_H_
7
8#include <memory>
9#include <string>
10
11#include "components/keyed_service/core/keyed_service.h"
Daniel Kenji Toyamaf1e4b572017-08-03 16:31:1112#include "net/url_request/url_fetcher_delegate.h"
13#include "url/gurl.h"
14
Jochen Eisinger4f96a312018-06-11 15:41:2615namespace base {
16class Time;
17}
18namespace identity {
19class IdentityManager;
20class PrimaryAccountAccessTokenFetcher;
21} // namespace identity
22namespace net {
23class URLRequestContextGetter;
24}
25class GoogleServiceAuthError;
Daniel Kenji Toyamaf1e4b572017-08-03 16:31:1126class TemplateURLService;
27
28// A service to fetch suggestions from a remote endpoint given a URL.
29class ContextualSuggestionsService : public KeyedService {
30 public:
Jochen Eisinger4f96a312018-06-11 15:41:2631 // |identity_manager| may be null but only unauthenticated requests will
32 // issued.
Daniel Kenji Toyamaf1e4b572017-08-03 16:31:1133 // |request_context| may be null, but some services may be disabled.
Jochen Eisinger4f96a312018-06-11 15:41:2634 ContextualSuggestionsService(identity::IdentityManager* identity_manager,
Daniel Kenji Toyamaf1e4b572017-08-03 16:31:1135 net::URLRequestContextGetter* request_context);
36
37 ~ContextualSuggestionsService() override;
38
39 using ContextualSuggestionsCallback =
40 base::OnceCallback<void(std::unique_ptr<net::URLFetcher> fetcher)>;
41
42 // Creates a fetcher for contextual suggestions for |current_url| and passes
43 // the fetcher to the provided callback.
44 //
45 // |current_url| may be empty, in which case the system will never use the
46 // experimental suggestions service. It's possible the non-experimental
47 // service may decide to offer general-purpose suggestions.
48 //
Gheorghe Comanici034cff62018-01-27 03:34:0049 // |visit_time| is the time of the visit for the URL for which suggestions
50 // should be fetched.
51 //
Daniel Kenji Toyamaf1e4b572017-08-03 16:31:1152 // |template_url_service| may be null, but some services may be disabled.
53 //
54 // |fetcher_delegate| is used to create a fetcher that is used to perform a
55 // network request. It uses a number of signals to create the fetcher,
56 // including field trial / experimental parameters, and it may pass a nullptr
57 // fetcher to the callback.
58 //
59 // |callback| is called with the fetcher produced by the |fetcher_delegate| as
60 // an argument. |callback| is called with a nullptr argument if:
61 // * The service is waiting for a previously-requested authentication token.
62 // * The authentication token had any issues.
63 //
64 // This method sends a request for an OAuth2 token and temporarily
65 // instantiates |token_fetcher_|.
66 void CreateContextualSuggestionsRequest(
67 const std::string& current_url,
Gheorghe Comanici034cff62018-01-27 03:34:0068 const base::Time& visit_time,
Daniel Kenji Toyamaf1e4b572017-08-03 16:31:1169 const TemplateURLService* template_url_service,
70 net::URLFetcherDelegate* fetcher_delegate,
71 ContextualSuggestionsCallback callback);
72
Gheorghe Comanici86bbdf62017-08-28 17:20:3373 // Advises the service to stop any process that creates a suggestion request.
74 void StopCreatingContextualSuggestionsRequest();
75
Daniel Kenji Toyamaf1e4b572017-08-03 16:31:1176 // Returns a URL representing the address of the server where the zero suggest
77 // request is being sent. Does not take into account whether sending this
78 // request is prohibited (e.g. in an incognito window).
79 // Returns an invalid URL (i.e.: GURL::is_valid() == false) in case of an
80 // error.
81 //
82 // |current_url| is the page the user is currently browsing and may be empty.
83 //
84 // Note that this method is public and is also used by ZeroSuggestProvider for
85 // suggestions that do not take |current_url| into consideration.
86 static GURL ContextualSuggestionsUrl(
87 const std::string& current_url,
88 const TemplateURLService* template_url_service);
89
90 private:
91 // Returns a URL representing the address of the server where the zero suggest
92 // requests are being redirected when serving experimental suggestions.
93 //
94 // Returns a valid URL only if all the folowing conditions are true:
95 // * The |current_url| is non-empty.
96 // * The |default_provider| is Google.
97 // * The user is in the ZeroSuggestRedirectToChrome field trial.
98 // * The field trial provides a valid server address where the suggest request
99 // is redirected.
100 // * The suggest request is over HTTPS. This avoids leaking the current page
101 // URL or personal data in unencrypted network traffic.
102 // Note: these checks are in addition to CanSendUrl() on the default
103 // contextual suggestion URL.
Gheorghe Comanicif7c65862017-09-07 18:40:29104 GURL ExperimentalContextualSuggestionsUrl(
Daniel Kenji Toyamaf1e4b572017-08-03 16:31:11105 const std::string& current_url,
106 const TemplateURLService* template_url_service) const;
107
Gheorghe Comanici923739272017-09-22 20:32:14108 // Upon succesful creation of an HTTP GET request for default contextual
Gheorghe Comanicif7c65862017-09-07 18:40:29109 // suggestions, the |callback| function is run with the HTTP GET request as a
110 // parameter.
111 //
112 // This function is called by CreateContextualSuggestionsRequest. See its
113 // function definition for details on the parameters.
114 void CreateDefaultRequest(const std::string& current_url,
115 const TemplateURLService* template_url_service,
116 net::URLFetcherDelegate* fetcher_delegate,
117 ContextualSuggestionsCallback callback);
118
Gheorghe Comanici923739272017-09-22 20:32:14119 // Upon succesful creation of an HTTP POST request for experimental contextual
Gheorghe Comanicif7c65862017-09-07 18:40:29120 // suggestions, the |callback| function is run with the HTTP POST request as a
121 // parameter.
122 //
123 // This function is called by CreateContextualSuggestionsRequest. See its
124 // function definition for details on the parameters.
125 void CreateExperimentalRequest(const std::string& current_url,
Gheorghe Comanici034cff62018-01-27 03:34:00126 const base::Time& visit_time,
Gheorghe Comanicif7c65862017-09-07 18:40:29127 const GURL& suggest_url,
128 net::URLFetcherDelegate* fetcher_delegate,
129 ContextualSuggestionsCallback callback);
Daniel Kenji Toyamaf1e4b572017-08-03 16:31:11130
131 // Called when an access token request completes (successfully or not).
132 void AccessTokenAvailable(std::unique_ptr<net::URLFetcher> fetcher,
133 ContextualSuggestionsCallback callback,
Colin Blundella29afeac2018-06-12 14:05:47134 GoogleServiceAuthError error,
135 std::string access_token);
Daniel Kenji Toyamaf1e4b572017-08-03 16:31:11136
137 net::URLRequestContextGetter* request_context_;
Jochen Eisinger4f96a312018-06-11 15:41:26138 identity::IdentityManager* identity_manager_;
Daniel Kenji Toyamaf1e4b572017-08-03 16:31:11139
140 // Helper for fetching OAuth2 access tokens. This is non-null when an access
141 // token request is currently in progress.
Colin Blundell0ee42ed62017-12-20 14:11:29142 std::unique_ptr<identity::PrimaryAccountAccessTokenFetcher> token_fetcher_;
Daniel Kenji Toyamaf1e4b572017-08-03 16:31:11143
144 DISALLOW_COPY_AND_ASSIGN(ContextualSuggestionsService);
145};
146
147#endif // COMPONENTS_OMNIBOX_BROWSER_CONTEXTUAL_SUGGESTIONS_SERVICE_H_