• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 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 #ifndef CHROME_BROWSER_NET_SPDYPROXY_DATA_REDUCTION_PROXY_SETTINGS_H_
6 #define CHROME_BROWSER_NET_SPDYPROXY_DATA_REDUCTION_PROXY_SETTINGS_H_
7 
8 #include <vector>
9 
10 #include "base/basictypes.h"
11 #include "base/compiler_specific.h"
12 #include "base/gtest_prod_util.h"
13 #include "base/memory/scoped_ptr.h"
14 #include "base/prefs/pref_member.h"
15 #include "net/base/network_change_notifier.h"
16 #include "net/url_request/url_fetcher_delegate.h"
17 
18 class PrefService;
19 
20 namespace net {
21 class AuthChallengeInfo;
22 class HostPortPair;
23 class HttpAuthCache;
24 class HttpNetworkSession;
25 class HttpResponseHeaders;
26 class URLFetcher;
27 }
28 
29 namespace spdyproxy {
30 
31 // The number of days of bandwidth usage statistics that are tracked.
32 const unsigned int kNumDaysInHistory = 60;
33 
34 // The number of days of bandwidth usage statistics that are presented.
35 const unsigned int kNumDaysInHistorySummary = 30;
36 
37 COMPILE_ASSERT(kNumDaysInHistorySummary <= kNumDaysInHistory,
38                DataReductionProxySettings_summary_too_long);
39 
40 }  // namespace spdyproxy
41 
42 // Central point for configuring the data reduction proxy.
43 // This object lives on the UI thread and all of its methods are expected to
44 // be called from there.
45 // TODO(marq): Convert this to be a BrowserContextKeyedService with an
46 // associated factory class, and refactor the Java call sites accordingly.
47 class DataReductionProxySettings
48     : public net::URLFetcherDelegate,
49       public net::NetworkChangeNotifier::IPAddressObserver {
50  public:
51   typedef std::vector<long long> ContentLengthList;
52   // TODO(marq): Consider instead using a std::pair instead of a vector.
53   typedef std::vector<GURL> DataReductionProxyList;
54 
55   DataReductionProxySettings();
56   virtual ~DataReductionProxySettings();
57 
58   void InitDataReductionProxySettings();
59 
60   // If proxy authentication is compiled in, pre-cache authentication
61   // keys for all configured proxies in |session|.
62   static void InitDataReductionProxySession(net::HttpNetworkSession* session);
63 
64   // Add a host pattern to bypass. This should follow the same syntax used
65   // in net::ProxyBypassRules; that is, a hostname pattern, a hostname suffix
66   // pattern, an IP literal, a CIDR block, or the magic string '<local>'.
67   // Bypass settings persist for the life of this object and are applied
68   // each time the proxy is enabled, but are not updated while it is enabled.
69   void AddHostPatternToBypass(const std::string& pattern);
70 
71   // Add a URL pattern to bypass the proxy. The base implementation strips
72   // everything in |pattern| after the first single slash and then treats it
73   // as a hostname pattern. Subclasses may implement other semantics.
74   virtual void AddURLPatternToBypass(const std::string& pattern);
75 
76   // Returns true if the data reduction proxy is allowed to be used on this
77   // instance of Chrome. This could return false, for example, if this instance
78   // is not part of the field trial, or if the proxy name is not configured
79   // via gyp.
80   static bool IsDataReductionProxyAllowed();
81 
82   // Returns true if a screen promoting the data reduction proxy is allowed to
83   // be shown. Logic that decides when to show the promo should check its
84   // availability. This would return false if not part of a separate field
85   // trial that governs the use of the promotion.
86   static bool IsDataReductionProxyPromoAllowed();
87 
88   // Returns true if preconnect advisory hinting is enabled by command line
89   // flag or Finch trial.
90   static bool IsPreconnectHintingAllowed();
91 
92   // Returns true if the Via header indicates that this request was fetched
93   // explicitly via the Chrome Proxy.
94   static bool WasFetchedViaProxy(const net::HttpResponseHeaders* headers);
95 
96   // Returns the URL of the data reduction proxy.
97   static std::string GetDataReductionProxyOrigin();
98 
99   // Returns the URL of the fallback data reduction proxy.
100   static std::string GetDataReductionProxyFallback();
101 
102   // Returns a vector of GURLs for all configured proxies.
103   static DataReductionProxyList GetDataReductionProxies();
104 
105   // Returns true if |auth_info| represents an authentication challenge from
106   // a compatible, configured proxy.
107   bool IsAcceptableAuthChallenge(net::AuthChallengeInfo* auth_info);
108 
109   // Returns a UTF16 string suitable for use as an authentication token in
110   // response to the challenge represented by |auth_info|. If the token can't
111   // be correctly generated for |auth_info|, returns an empty UTF16 string.
112   base::string16 GetTokenForAuthChallenge(net::AuthChallengeInfo* auth_info);
113 
114   // Returns true if the proxy is enabled.
115   bool IsDataReductionProxyEnabled();
116 
117   // Returns true if the proxy is managed by an adminstrator's policy.
118   bool IsDataReductionProxyManaged();
119 
120   // Enables or disables the data reduction proxy. If a probe URL is available,
121   // and a probe request fails at some point, the proxy won't be used until a
122   // probe succeeds.
123   void SetDataReductionProxyEnabled(bool enabled);
124 
125   // Returns the time in microseconds that the last update was made to the
126   // daily original and received content lengths.
127   int64 GetDataReductionLastUpdateTime();
128 
129   // Returns a vector containing the total size of all HTTP content that was
130   // received over the last |kNumDaysInHistory| before any compression by the
131   // data reduction proxy. Each element in the vector contains one day of data.
132   ContentLengthList GetDailyOriginalContentLengths();
133 
134   // Returns an vector containing the aggregate received HTTP content in the
135   // last |kNumDaysInHistory| days.
136   ContentLengthList GetDailyReceivedContentLengths();
137 
138   // net::URLFetcherDelegate:
139   virtual void OnURLFetchComplete(const net::URLFetcher* source) OVERRIDE;
140 
141  protected:
142   void InitPrefMembers();
143 
144   virtual net::URLFetcher* GetURLFetcher();
145 
146   // Virtualized for unit test support.
147   virtual PrefService* GetOriginalProfilePrefs();
148   virtual PrefService* GetLocalStatePrefs();
149 
150   void GetContentLengths(unsigned int days,
151                          int64* original_content_length,
152                          int64* received_content_length,
153                          int64* last_update_time);
154   ContentLengthList GetDailyContentLengths(const char* pref_name);
155 
156   // Sets the proxy configs, enabling or disabling the proxy according to
157   // the value of |enabled|. If |restricted| is true, only enable the fallback
158   // proxy. |at_startup| is true when this method is called from
159   // InitDataReductionProxySettings.
160   virtual void SetProxyConfigs(bool enabled, bool restricted, bool at_startup);
161 
162   // Metrics methods. Subclasses should override if they wish to provide
163   // alternate methods.
164   virtual void RecordDataReductionInit();
165 
166   virtual void AddDefaultProxyBypassRules();
167 
168   // Writes a warning to the log that is used in backend processing of
169   // customer feedback. Virtual so tests can mock it for verification.
170   virtual void LogProxyState(bool enabled, bool restricted, bool at_startup);
171 
172   // Accessor for unit tests.
BypassRules()173   std::vector<std::string> BypassRules() { return bypass_rules_;}
174 
175  private:
176   friend class DataReductionProxySettingsTestBase;
177   friend class DataReductionProxySettingsTest;
178   FRIEND_TEST_ALL_PREFIXES(DataReductionProxySettingsTest,
179                            TestAuthenticationInit);
180   FRIEND_TEST_ALL_PREFIXES(DataReductionProxySettingsTest,
181                            TestAuthHashGeneration);
182   FRIEND_TEST_ALL_PREFIXES(DataReductionProxySettingsTest,
183                            TestAuthHashGenerationWithOriginSetViaSwitch);
184   FRIEND_TEST_ALL_PREFIXES(DataReductionProxySettingsTest,
185                            TestResetDataReductionStatistics);
186   FRIEND_TEST_ALL_PREFIXES(DataReductionProxySettingsTest,
187                            TestIsProxyEnabledOrManaged);
188   FRIEND_TEST_ALL_PREFIXES(DataReductionProxySettingsTest,
189                            TestContentLengths);
190   FRIEND_TEST_ALL_PREFIXES(DataReductionProxySettingsTest,
191                            TestGetDailyContentLengths);
192   FRIEND_TEST_ALL_PREFIXES(DataReductionProxySettingsTest,
193                            TestMaybeActivateDataReductionProxy);
194   FRIEND_TEST_ALL_PREFIXES(DataReductionProxySettingsTest,
195                            TestOnIPAddressChanged);
196   FRIEND_TEST_ALL_PREFIXES(DataReductionProxySettingsTest,
197                            TestOnProxyEnabledPrefChange);
198   FRIEND_TEST_ALL_PREFIXES(DataReductionProxySettingsTest,
199                            TestInitDataReductionProxyOn);
200   FRIEND_TEST_ALL_PREFIXES(DataReductionProxySettingsTest,
201                            TestInitDataReductionProxyOff);
202   FRIEND_TEST_ALL_PREFIXES(DataReductionProxySettingsTest,
203                            TestBypassList);
204 
205   // NetworkChangeNotifier::IPAddressObserver:
206   virtual void OnIPAddressChanged() OVERRIDE;
207 
208   // Underlying implementation of InitDataReductionProxySession(), factored
209   // out to be testable without creating a full HttpNetworkSession.
210   static void InitDataReductionAuthentication(net::HttpAuthCache* auth_cache);
211 
212   void OnProxyEnabledPrefChange();
213 
214   void ResetDataReductionStatistics();
215 
216   void MaybeActivateDataReductionProxy(bool at_startup);
217 
218   // Requests the proxy probe URL, if one is set.  If unable to do so, disables
219   // the proxy, if enabled. Otherwise enables the proxy if disabled by a probe
220   // failure.
221   void ProbeWhetherDataReductionProxyIsAvailable();
222   std::string GetProxyCheckURL();
223 
224   // Returns a UTF16 string that's the hash of the configured authentication
225   // key and |salt|. Returns an empty UTF16 string if no key is configured or
226   // the data reduction proxy feature isn't available.
227   static base::string16 AuthHashForSalt(int64 salt);
228 
229   std::vector<std::string> bypass_rules_;
230 
231   bool restricted_by_carrier_;
232   bool enabled_by_user_;
233 
234   scoped_ptr<net::URLFetcher> fetcher_;
235   BooleanPrefMember spdy_proxy_auth_enabled_;
236 
237   DISALLOW_COPY_AND_ASSIGN(DataReductionProxySettings);
238 };
239 
240 #endif  // CHROME_BROWSER_NET_SPDYPROXY_DATA_REDUCTION_PROXY_SETTINGS_H_
241