Implement break signal for serial api.
[chromium-blink-merge.git] / net / url_request / url_fetcher_core.h
blobb20720e3caf7782a21a772c5771bd9dc728bb105
1 // Copyright (c) 2012 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.
5 #ifndef NET_URL_REQUEST_URL_FETCHER_CORE_H_
6 #define NET_URL_REQUEST_URL_FETCHER_CORE_H_
8 #include <set>
9 #include <string>
11 #include "base/basictypes.h"
12 #include "base/compiler_specific.h"
13 #include "base/debug/stack_trace.h"
14 #include "base/files/file_path.h"
15 #include "base/lazy_instance.h"
16 #include "base/memory/ref_counted.h"
17 #include "base/memory/scoped_ptr.h"
18 #include "base/timer/timer.h"
19 #include "net/base/host_port_pair.h"
20 #include "net/http/http_request_headers.h"
21 #include "net/url_request/url_fetcher.h"
22 #include "net/url_request/url_request.h"
23 #include "net/url_request/url_request_context_getter_observer.h"
24 #include "net/url_request/url_request_status.h"
25 #include "url/gurl.h"
27 namespace base {
28 class SingleThreadTaskRunner;
29 } // namespace base
31 namespace net {
32 class DrainableIOBuffer;
33 class HttpResponseHeaders;
34 class IOBuffer;
35 class URLFetcherDelegate;
36 class URLFetcherResponseWriter;
37 class URLRequestContextGetter;
38 class URLRequestThrottlerEntryInterface;
40 class URLFetcherCore : public base::RefCountedThreadSafe<URLFetcherCore>,
41 public URLRequest::Delegate,
42 public URLRequestContextGetterObserver {
43 public:
44 URLFetcherCore(URLFetcher* fetcher,
45 const GURL& original_url,
46 URLFetcher::RequestType request_type,
47 URLFetcherDelegate* d);
49 // Starts the load. It's important that this not happen in the constructor
50 // because it causes the IO thread to begin AddRef()ing and Release()ing
51 // us. If our caller hasn't had time to fully construct us and take a
52 // reference, the IO thread could interrupt things, run a task, Release()
53 // us, and destroy us, leaving the caller with an already-destroyed object
54 // when construction finishes.
55 void Start();
57 // Stops any in-progress load and ensures no callback will happen. It is
58 // safe to call this multiple times.
59 void Stop();
61 // URLFetcher-like functions.
63 // For POST requests, set |content_type| to the MIME type of the
64 // content and set |content| to the data to upload.
65 void SetUploadData(const std::string& upload_content_type,
66 const std::string& upload_content);
67 void SetUploadFilePath(const std::string& upload_content_type,
68 const base::FilePath& file_path,
69 uint64 range_offset,
70 uint64 range_length,
71 scoped_refptr<base::TaskRunner> file_task_runner);
72 void SetUploadStreamFactory(
73 const std::string& upload_content_type,
74 const URLFetcher::CreateUploadStreamCallback& callback);
75 void SetChunkedUpload(const std::string& upload_content_type);
76 // Adds a block of data to be uploaded in a POST body. This can only be
77 // called after Start().
78 void AppendChunkToUpload(const std::string& data, bool is_last_chunk);
79 // |flags| are flags to apply to the load operation--these should be
80 // one or more of the LOAD_* flags defined in net/base/load_flags.h.
81 void SetLoadFlags(int load_flags);
82 int GetLoadFlags() const;
83 void SetReferrer(const std::string& referrer);
84 void SetReferrerPolicy(URLRequest::ReferrerPolicy referrer_policy);
85 void SetExtraRequestHeaders(const std::string& extra_request_headers);
86 void AddExtraRequestHeader(const std::string& header_line);
87 void SetRequestContext(URLRequestContextGetter* request_context_getter);
88 // Set the URL that should be consulted for the third-party cookie
89 // blocking policy.
90 void SetFirstPartyForCookies(const GURL& first_party_for_cookies);
91 // Set the key and data callback that is used when setting the user
92 // data on any URLRequest objects this object creates.
93 void SetURLRequestUserData(
94 const void* key,
95 const URLFetcher::CreateDataCallback& create_data_callback);
96 void SetStopOnRedirect(bool stop_on_redirect);
97 void SetAutomaticallyRetryOn5xx(bool retry);
98 void SetMaxRetriesOn5xx(int max_retries);
99 int GetMaxRetriesOn5xx() const;
100 base::TimeDelta GetBackoffDelay() const;
101 void SetAutomaticallyRetryOnNetworkChanges(int max_retries);
102 void SaveResponseToFileAtPath(
103 const base::FilePath& file_path,
104 scoped_refptr<base::SequencedTaskRunner> file_task_runner);
105 void SaveResponseToTemporaryFile(
106 scoped_refptr<base::SequencedTaskRunner> file_task_runner);
107 void SaveResponseWithWriter(
108 scoped_ptr<URLFetcherResponseWriter> response_writer);
109 HttpResponseHeaders* GetResponseHeaders() const;
110 HostPortPair GetSocketAddress() const;
111 bool WasFetchedViaProxy() const;
112 const GURL& GetOriginalURL() const;
113 const GURL& GetURL() const;
114 const URLRequestStatus& GetStatus() const;
115 int GetResponseCode() const;
116 const ResponseCookies& GetCookies() const;
117 // Reports that the received content was malformed (i.e. failed parsing
118 // or validation). This makes the throttling logic that does exponential
119 // back-off when servers are having problems treat the current request as
120 // a failure. Your call to this method will be ignored if your request is
121 // already considered a failure based on the HTTP response code or response
122 // headers.
123 void ReceivedContentWasMalformed();
124 bool GetResponseAsString(std::string* out_response_string) const;
125 bool GetResponseAsFilePath(bool take_ownership,
126 base::FilePath* out_response_path);
128 // Overridden from URLRequest::Delegate:
129 void OnReceivedRedirect(URLRequest* request,
130 const RedirectInfo& redirect_info,
131 bool* defer_redirect) override;
132 void OnResponseStarted(URLRequest* request) override;
133 void OnReadCompleted(URLRequest* request, int bytes_read) override;
134 void OnCertificateRequested(URLRequest* request,
135 SSLCertRequestInfo* cert_request_info) override;
137 // Overridden from URLRequestContextGetterObserver:
138 void OnContextShuttingDown() override;
140 URLFetcherDelegate* delegate() const { return delegate_; }
141 static void CancelAll();
142 static int GetNumFetcherCores();
143 static void SetEnableInterceptionForTests(bool enabled);
144 static void SetIgnoreCertificateRequests(bool ignored);
146 private:
147 friend class base::RefCountedThreadSafe<URLFetcherCore>;
149 // TODO(mmenke): Remove this class.
150 class Registry {
151 public:
152 Registry();
153 ~Registry();
155 void AddURLFetcherCore(URLFetcherCore* core);
156 void RemoveURLFetcherCore(URLFetcherCore* core);
158 void CancelAll();
160 int size() const {
161 return fetchers_.size();
164 private:
165 std::set<URLFetcherCore*> fetchers_;
167 DISALLOW_COPY_AND_ASSIGN(Registry);
170 ~URLFetcherCore() override;
172 // Wrapper functions that allow us to ensure actions happen on the right
173 // thread.
174 void StartOnIOThread();
175 void StartURLRequest();
176 void DidInitializeWriter(int result);
177 void StartURLRequestWhenAppropriate();
178 void CancelURLRequest(int error);
179 void OnCompletedURLRequest(base::TimeDelta backoff_delay);
180 void InformDelegateFetchIsComplete();
181 void NotifyMalformedContent();
182 void DidFinishWriting(int result);
183 void RetryOrCompleteUrlFetch();
185 // Cancels the URLRequest and informs the delegate that it failed with the
186 // specified error. Must be called on network thread.
187 void CancelRequestAndInformDelegate(int result);
189 // Deletes the request, removes it from the registry, and removes the
190 // destruction observer.
191 void ReleaseRequest();
193 // Returns the max value of exponential back-off release time for
194 // |original_url_| and |url_|.
195 base::TimeTicks GetBackoffReleaseTime();
197 void CompleteAddingUploadDataChunk(const std::string& data,
198 bool is_last_chunk);
200 // Writes all bytes stored in |data| with |response_writer_|.
201 // Returns OK if all bytes in |data| get written synchronously. Otherwise,
202 // returns ERR_IO_PENDING or a network error code.
203 int WriteBuffer(scoped_refptr<DrainableIOBuffer> data);
205 // Used to implement WriteBuffer().
206 void DidWriteBuffer(scoped_refptr<DrainableIOBuffer> data, int result);
208 // Read response bytes from the request.
209 void ReadResponse();
211 // Notify Delegate about the progress of upload/download.
212 void InformDelegateUploadProgress();
213 void InformDelegateUploadProgressInDelegateThread(int64 current, int64 total);
214 void InformDelegateDownloadProgress();
215 void InformDelegateDownloadProgressInDelegateThread(int64 current,
216 int64 total);
218 // Check if any upload data is set or not.
219 void AssertHasNoUploadData() const;
221 URLFetcher* fetcher_; // Corresponding fetcher object
222 GURL original_url_; // The URL we were asked to fetch
223 GURL url_; // The URL we eventually wound up at
224 URLFetcher::RequestType request_type_; // What type of request is this?
225 URLRequestStatus status_; // Status of the request
226 URLFetcherDelegate* delegate_; // Object to notify on completion
227 // Task runner for the creating thread. Used to interact with the delegate.
228 scoped_refptr<base::SingleThreadTaskRunner> delegate_task_runner_;
229 // Task runner for network operations.
230 scoped_refptr<base::SingleThreadTaskRunner> network_task_runner_;
231 // Task runner for upload file access.
232 scoped_refptr<base::TaskRunner> upload_file_task_runner_;
233 scoped_ptr<URLRequest> request_; // The actual request this wraps
234 int load_flags_; // Flags for the load operation
235 int response_code_; // HTTP status code for the request
236 scoped_refptr<IOBuffer> buffer_;
237 // Read buffer
238 scoped_refptr<URLRequestContextGetter> request_context_getter_;
239 // Cookie/cache info for the request
240 GURL first_party_for_cookies_; // The first party URL for the request
241 // The user data to add to each newly-created URLRequest.
242 const void* url_request_data_key_;
243 URLFetcher::CreateDataCallback url_request_create_data_callback_;
244 ResponseCookies cookies_; // Response cookies
245 HttpRequestHeaders extra_request_headers_;
246 scoped_refptr<HttpResponseHeaders> response_headers_;
247 bool was_fetched_via_proxy_;
248 HostPortPair socket_address_;
250 bool upload_content_set_; // SetUploadData has been called
251 std::string upload_content_; // HTTP POST payload
252 base::FilePath upload_file_path_; // Path to file containing POST payload
253 uint64 upload_range_offset_; // Offset from the beginning of the file
254 // to be uploaded.
255 uint64 upload_range_length_; // The length of the part of file to be
256 // uploaded.
257 URLFetcher::CreateUploadStreamCallback
258 upload_stream_factory_; // Callback to create HTTP POST payload.
259 std::string upload_content_type_; // MIME type of POST payload
260 std::string referrer_; // HTTP Referer header value and policy
261 URLRequest::ReferrerPolicy referrer_policy_;
262 bool is_chunked_upload_; // True if using chunked transfer encoding
264 // Used to determine how long to wait before making a request or doing a
265 // retry.
267 // Both of them can only be accessed on the IO thread.
269 // To determine the proper backoff timing, throttler entries for
270 // both |original_URL| and |url| are needed. For example, consider
271 // the case that URL A redirects to URL B, for which the server
272 // returns a 500 response. In this case, the exponential back-off
273 // release time of URL A won't increase. If only the backoff
274 // constraints for URL A are considered, too many requests for URL A
275 // may be sent in a short period of time.
277 // Both of these will be NULL if
278 // URLRequestContext::throttler_manager() is NULL.
279 scoped_refptr<URLRequestThrottlerEntryInterface>
280 original_url_throttler_entry_;
281 scoped_refptr<URLRequestThrottlerEntryInterface> url_throttler_entry_;
283 // True if the URLFetcher has been cancelled.
284 bool was_cancelled_;
286 // Writer object to write response to the destination like file and string.
287 scoped_ptr<URLFetcherResponseWriter> response_writer_;
289 // By default any server-initiated redirects are automatically followed. If
290 // this flag is set to true, however, a redirect will halt the fetch and call
291 // back to to the delegate immediately.
292 bool stop_on_redirect_;
293 // True when we're actually stopped due to a redirect halted by the above. We
294 // use this to ensure that |url_| is set to the redirect destination rather
295 // than the originally-fetched URL.
296 bool stopped_on_redirect_;
298 // If |automatically_retry_on_5xx_| is false, 5xx responses will be
299 // propagated to the observer, if it is true URLFetcher will automatically
300 // re-execute the request, after the back-off delay has expired.
301 // true by default.
302 bool automatically_retry_on_5xx_;
303 // |num_retries_on_5xx_| indicates how many times we've failed to successfully
304 // fetch this URL due to 5xx responses. Once this value exceeds the maximum
305 // number of retries specified by the owner URLFetcher instance,
306 // we'll give up.
307 int num_retries_on_5xx_;
308 // Maximum retries allowed when 5xx responses are received.
309 int max_retries_on_5xx_;
310 // Back-off time delay. 0 by default.
311 base::TimeDelta backoff_delay_;
313 // The number of retries that have been attempted due to ERR_NETWORK_CHANGED.
314 int num_retries_on_network_changes_;
315 // Maximum retries allowed when the request fails with ERR_NETWORK_CHANGED.
316 // 0 by default.
317 int max_retries_on_network_changes_;
319 // Timer to poll the progress of uploading for POST and PUT requests.
320 // When crbug.com/119629 is fixed, scoped_ptr is not necessary here.
321 scoped_ptr<base::RepeatingTimer<URLFetcherCore> >
322 upload_progress_checker_timer_;
323 // Number of bytes sent so far.
324 int64 current_upload_bytes_;
325 // Number of bytes received so far.
326 int64 current_response_bytes_;
327 // Total expected bytes to receive (-1 if it cannot be determined).
328 int64 total_response_bytes_;
330 // TODO(willchan): Get rid of this after debugging crbug.com/90971.
331 base::debug::StackTrace stack_trace_;
333 static base::LazyInstance<Registry> g_registry;
335 DISALLOW_COPY_AND_ASSIGN(URLFetcherCore);
338 } // namespace net
340 #endif // NET_URL_REQUEST_URL_FETCHER_CORE_H_