1 // Copyright 2014 The Chromium Authors 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_CRONET_CRONET_URL_REQUEST_H_ 6 #define COMPONENTS_CRONET_CRONET_URL_REQUEST_H_ 7 8 #include <memory> 9 #include <string> 10 11 #include "base/functional/callback.h" 12 #include "base/memory/raw_ptr.h" 13 #include "base/memory/ref_counted.h" 14 #include "base/time/time.h" 15 #include "net/base/idempotency.h" 16 #include "net/base/network_handle.h" 17 #include "net/base/request_priority.h" 18 #include "net/url_request/url_request.h" 19 #include "url/gurl.h" 20 21 namespace net { 22 class HttpRequestHeaders; 23 enum LoadState; 24 class SSLCertRequestInfo; 25 class SSLInfo; 26 class UploadDataStream; 27 } // namespace net 28 29 namespace cronet { 30 31 class CronetContext; 32 class TestUtil; 33 34 // Wrapper around net::URLRequestContext. 35 // Created and configured from client thread. Start, ReadData, and Destroy are 36 // posted to network thread and all callbacks into the Callback() are 37 // done on the network thread. CronetUrlRequest client is expected to initiate 38 // the next step like FollowDeferredRedirect, ReadData or Destroy. Public 39 // methods can be called on any thread. 40 class CronetURLRequest { 41 public: 42 // Callback implemented by CronetURLRequest() caller and owned by 43 // CronetURLRequest::NetworkTasks. All callback methods are invoked on network 44 // thread. 45 class Callback { 46 public: 47 virtual ~Callback() = default; 48 49 // Invoked whenever a redirect is encountered. This will only be invoked 50 // between the call to CronetURLRequest::Start() and 51 // Callback::OnResponseStarted(). The body of the redirect response, if 52 // it has one, will be ignored. 53 // 54 // The redirect will not be followed until 55 // CronetURLRequest::FollowDeferredRedirect() method is called, either 56 // synchronously or asynchronously. 57 virtual void OnReceivedRedirect(const std::string& new_location, 58 int http_status_code, 59 const std::string& http_status_text, 60 const net::HttpResponseHeaders* headers, 61 bool was_cached, 62 const std::string& negotiated_protocol, 63 const std::string& proxy_server, 64 int64_t received_byte_count) = 0; 65 66 // Invoked when the final set of headers, after all redirects, is received. 67 // Will only be invoked once for each request. 68 // 69 // With the exception of Callback::OnCanceled(), 70 // no other Callback method will be invoked for the request, 71 // including Callback::OnSucceeded() and Callback::OnFailed(), until 72 // CronetUrlRequest::Read() is called to attempt to start reading the 73 // response body. 74 virtual void OnResponseStarted(int http_status_code, 75 const std::string& http_status_text, 76 const net::HttpResponseHeaders* headers, 77 bool was_cached, 78 const std::string& negotiated_protocol, 79 const std::string& proxy_server, 80 int64_t received_byte_count) = 0; 81 82 // Invoked whenever part of the response body has been read. Only part of 83 // the buffer may be populated, even if the entire response body has not yet 84 // been consumed. 85 // 86 // With the exception of Callback::OnCanceled(), 87 // no other Callback method will be invoked for the request, 88 // including Callback::OnSucceeded() and Callback::OnFailed(), until 89 // CronetUrlRequest::Read() is called to attempt to continue reading the 90 // response body. 91 virtual void OnReadCompleted(scoped_refptr<net::IOBuffer> buffer, 92 int bytes_read, 93 int64_t received_byte_count) = 0; 94 95 // Invoked when request is completed successfully. 96 virtual void OnSucceeded(int64_t received_byte_count) = 0; 97 98 // Invoked if request failed for any reason after CronetURLRequest::Start(). 99 // |net_error| provides information about the failure. |quic_error| is only 100 // valid if |net_error| is net::QUIC_PROTOCOL_ERROR. 101 virtual void OnError(int net_error, 102 int quic_error, 103 const std::string& error_string, 104 int64_t received_byte_count) = 0; 105 106 // Invoked if request was canceled via CronetURLRequest::Destroy(). 107 virtual void OnCanceled() = 0; 108 109 // Invoked when request is destroyed. Once invoked, no other Callback 110 // methods will be invoked. 111 virtual void OnDestroyed() = 0; 112 113 // Invoked right before request is destroyed to report collected metrics. 114 virtual void OnMetricsCollected( 115 const base::Time& request_start_time, 116 const base::TimeTicks& request_start, 117 const base::TimeTicks& dns_start, 118 const base::TimeTicks& dns_end, 119 const base::TimeTicks& connect_start, 120 const base::TimeTicks& connect_end, 121 const base::TimeTicks& ssl_start, 122 const base::TimeTicks& ssl_end, 123 const base::TimeTicks& send_start, 124 const base::TimeTicks& send_end, 125 const base::TimeTicks& push_start, 126 const base::TimeTicks& push_end, 127 const base::TimeTicks& receive_headers_end, 128 const base::TimeTicks& request_end, 129 bool socket_reused, 130 int64_t sent_bytes_count, 131 int64_t received_bytes_count, 132 bool quic_connection_migration_attempted, 133 bool quic_connection_migration_successful) = 0; 134 }; 135 // Invoked in response to CronetURLRequest::GetStatus() to allow multiple 136 // overlapping calls. The load states correspond to the lengthy periods of 137 // time that a request load may be blocked and unable to make progress. 138 using OnStatusCallback = base::OnceCallback<void(net::LoadState)>; 139 140 // Bypasses cache if |disable_cache| is true. If context is not set up to 141 // use cache, |disable_cache| has no effect. |disable_connection_migration| 142 // causes connection migration to be disabled for this request if true. If 143 // global connection migration flag is not enabled, 144 // |disable_connection_migration| has no effect. 145 CronetURLRequest(CronetContext* context, 146 std::unique_ptr<Callback> callback, 147 const GURL& url, 148 net::RequestPriority priority, 149 bool disable_cache, 150 bool disable_connection_migration, 151 bool traffic_stats_tag_set, 152 int32_t traffic_stats_tag, 153 bool traffic_stats_uid_set, 154 int32_t traffic_stats_uid, 155 net::Idempotency idempotency, 156 net::handles::NetworkHandle network = 157 net::handles::kInvalidNetworkHandle); 158 159 CronetURLRequest(const CronetURLRequest&) = delete; 160 CronetURLRequest& operator=(const CronetURLRequest&) = delete; 161 162 // Methods called prior to Start are never called on network thread. 163 164 // Sets the request method GET, POST etc. 165 bool SetHttpMethod(const std::string& method); 166 167 // Adds a header to the request before it starts. 168 bool AddRequestHeader(const std::string& name, const std::string& value); 169 170 // Adds a request body to the request before it starts. 171 void SetUpload(std::unique_ptr<net::UploadDataStream> upload); 172 173 // Starts the request. 174 void Start(); 175 176 // GetStatus invokes |on_status_callback| on network thread to allow multiple 177 // overlapping calls. 178 void GetStatus(OnStatusCallback on_status_callback) const; 179 180 // Follows redirect. 181 void FollowDeferredRedirect(); 182 183 // Reads more data. 184 bool ReadData(net::IOBuffer* buffer, int max_bytes); 185 186 // Releases all resources for the request and deletes the object itself. 187 // |send_on_canceled| indicates whether OnCanceled callback should be 188 // issued to indicate when no more callbacks will be issued. 189 void Destroy(bool send_on_canceled); 190 191 // On the network thread, reports metrics to the registered 192 // CronetURLRequest::Callback, and then runs |callback| on the network thread. 193 // 194 // Since metrics are only reported once, this can be used to ensure metrics 195 // are reported to the registered CronetURLRequest::Callback before resources 196 // used by the callback are deleted. 197 void MaybeReportMetricsAndRunCallback(base::OnceClosure callback); 198 199 private: 200 friend class TestUtil; 201 202 // Private destructor invoked fron NetworkTasks::Destroy() on network thread. 203 ~CronetURLRequest(); 204 205 // NetworkTasks performs tasks on the network thread and owns objects that 206 // live on the network thread. 207 class NetworkTasks : public net::URLRequest::Delegate { 208 public: 209 // Invoked off the network thread. 210 NetworkTasks(std::unique_ptr<Callback> callback, 211 const GURL& url, 212 net::RequestPriority priority, 213 int load_flags, 214 bool traffic_stats_tag_set, 215 int32_t traffic_stats_tag, 216 bool traffic_stats_uid_set, 217 int32_t traffic_stats_uid, 218 net::Idempotency idempotency, 219 net::handles::NetworkHandle network); 220 221 NetworkTasks(const NetworkTasks&) = delete; 222 NetworkTasks& operator=(const NetworkTasks&) = delete; 223 224 // Invoked on the network thread. 225 ~NetworkTasks() override; 226 227 // Starts the request. 228 void Start(CronetContext* context, 229 const std::string& method, 230 std::unique_ptr<net::HttpRequestHeaders> request_headers, 231 std::unique_ptr<net::UploadDataStream> upload); 232 233 // Gets status of the requrest and invokes |on_status_callback| to allow 234 // multiple overlapping calls. 235 void GetStatus(OnStatusCallback on_status_callback) const; 236 237 // Follows redirect. 238 void FollowDeferredRedirect(); 239 240 // Reads more data. 241 void ReadData(scoped_refptr<net::IOBuffer> read_buffer, int buffer_size); 242 243 // Releases all resources for the request and deletes the |request|, which 244 // owns |this|, so |this| is also deleted. 245 // |send_on_canceled| indicates whether OnCanceled callback should be 246 // issued to indicate when no more callbacks will be issued. 247 void Destroy(CronetURLRequest* request, bool send_on_canceled); 248 249 // Runs MaybeReportMetrics(), then runs |callback|. 250 void MaybeReportMetricsAndRunCallback(base::OnceClosure callback); 251 252 private: 253 friend class TestUtil; 254 255 // net::URLRequest::Delegate implementations: 256 void OnReceivedRedirect(net::URLRequest* request, 257 const net::RedirectInfo& redirect_info, 258 bool* defer_redirect) override; 259 void OnCertificateRequested( 260 net::URLRequest* request, 261 net::SSLCertRequestInfo* cert_request_info) override; 262 void OnSSLCertificateError(net::URLRequest* request, 263 int net_error, 264 const net::SSLInfo& ssl_info, 265 bool fatal) override; 266 void OnResponseStarted(net::URLRequest* request, int net_error) override; 267 void OnReadCompleted(net::URLRequest* request, int bytes_read) override; 268 269 // Report error and cancel request_adapter. 270 void ReportError(net::URLRequest* request, int net_error); 271 // Reports metrics collected. 272 void MaybeReportMetrics(); 273 274 // Callback implemented by the client. 275 std::unique_ptr<CronetURLRequest::Callback> callback_; 276 277 const GURL initial_url_; 278 const net::RequestPriority initial_priority_; 279 const int initial_load_flags_; 280 // Count of bytes received during redirect is added to received byte count. 281 int64_t received_byte_count_from_redirects_; 282 283 // Whether error has been already reported, for example from 284 // OnSSLCertificateError(). 285 bool error_reported_; 286 287 // Whether metrics have been reported. 288 bool metrics_reported_; 289 290 // Whether |traffic_stats_tag_| should be applied. 291 const bool traffic_stats_tag_set_; 292 // TrafficStats tag to apply to URLRequest. 293 const int32_t traffic_stats_tag_; 294 // Whether |traffic_stats_uid_| should be applied. 295 const bool traffic_stats_uid_set_; 296 // UID to be applied to URLRequest. 297 const int32_t traffic_stats_uid_; 298 // Idempotency of the request. 299 const net::Idempotency idempotency_; 300 301 net::handles::NetworkHandle network_; 302 303 scoped_refptr<net::IOBuffer> read_buffer_; 304 std::unique_ptr<net::URLRequest> url_request_; 305 306 THREAD_CHECKER(network_thread_checker_); 307 }; 308 309 raw_ptr<CronetContext> context_; 310 // |network_tasks_| is invoked on network thread. 311 NetworkTasks network_tasks_; 312 313 // Request parameters set off network thread before Start(). 314 std::string initial_method_; 315 std::unique_ptr<net::HttpRequestHeaders> initial_request_headers_; 316 std::unique_ptr<net::UploadDataStream> upload_; 317 }; 318 319 } // namespace cronet 320 321 #endif // COMPONENTS_CRONET_CRONET_URL_REQUEST_H_ 322