Upstream version 9.38.198.0
[platform/framework/web/crosswalk.git] / src / net / url_request / url_fetcher_impl_unittest.cc
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.
4
5 #include "net/url_request/url_fetcher_impl.h"
6
7 #include <algorithm>
8 #include <string>
9
10 #include "base/bind.h"
11 #include "base/file_util.h"
12 #include "base/files/scoped_temp_dir.h"
13 #include "base/message_loop/message_loop_proxy.h"
14 #include "base/strings/stringprintf.h"
15 #include "base/synchronization/waitable_event.h"
16 #include "base/threading/thread.h"
17 #include "build/build_config.h"
18 #include "crypto/nss_util.h"
19 #include "net/base/network_change_notifier.h"
20 #include "net/dns/mock_host_resolver.h"
21 #include "net/http/http_response_headers.h"
22 #include "net/test/spawned_test_server/spawned_test_server.h"
23 #include "net/url_request/url_fetcher_delegate.h"
24 #include "net/url_request/url_request_context_getter.h"
25 #include "net/url_request/url_request_test_util.h"
26 #include "net/url_request/url_request_throttler_manager.h"
27 #include "testing/gtest/include/gtest/gtest.h"
28
29 #if defined(USE_NSS) || defined(OS_IOS)
30 #include "net/ocsp/nss_ocsp.h"
31 #endif
32
33 namespace net {
34
35 using base::Time;
36 using base::TimeDelta;
37
38 // TODO(eroman): Add a regression test for http://crbug.com/40505.
39
40 namespace {
41
42 // TODO(akalin): Move all the test data to somewhere under net/.
43 const base::FilePath::CharType kDocRoot[] =
44     FILE_PATH_LITERAL("net/data/url_fetcher_impl_unittest");
45 const char kTestServerFilePrefix[] = "files/";
46
47 class ThrottlingTestURLRequestContext : public TestURLRequestContext {
48  public:
49   ThrottlingTestURLRequestContext() : TestURLRequestContext(true) {
50     set_throttler_manager(&throttler_manager_);
51     Init();
52     DCHECK(throttler_manager() != NULL);
53   }
54
55  private:
56   URLRequestThrottlerManager throttler_manager_;
57 };
58
59 class ThrottlingTestURLRequestContextGetter
60     : public TestURLRequestContextGetter {
61  public:
62   ThrottlingTestURLRequestContextGetter(
63       base::MessageLoopProxy* io_message_loop_proxy,
64       TestURLRequestContext* request_context)
65       : TestURLRequestContextGetter(io_message_loop_proxy),
66         context_(request_context) {
67   }
68
69   // TestURLRequestContextGetter:
70   virtual TestURLRequestContext* GetURLRequestContext() OVERRIDE {
71     return context_;
72   }
73
74  protected:
75   virtual ~ThrottlingTestURLRequestContextGetter() {}
76
77   TestURLRequestContext* const context_;
78 };
79
80 }  // namespace
81
82 class URLFetcherTest : public testing::Test,
83                        public URLFetcherDelegate {
84  public:
85   URLFetcherTest() : fetcher_(NULL) {}
86
87   static int GetNumFetcherCores() {
88     return URLFetcherImpl::GetNumFetcherCores();
89   }
90
91   // Creates a URLFetcher, using the program's main thread to do IO.
92   virtual void CreateFetcher(const GURL& url);
93
94   // URLFetcherDelegate:
95   // Subclasses that override this should either call this function or
96   // CleanupAfterFetchComplete() at the end of their processing, depending on
97   // whether they want to check for a non-empty HTTP 200 response or not.
98   virtual void OnURLFetchComplete(const URLFetcher* source) OVERRIDE;
99
100   // Deletes |fetcher| and terminates the message loop.
101   void CleanupAfterFetchComplete();
102
103   scoped_refptr<base::MessageLoopProxy> io_message_loop_proxy() {
104     return io_message_loop_proxy_;
105   }
106
107   TestURLRequestContext* request_context() {
108     return context_.get();
109   }
110
111  protected:
112   // testing::Test:
113   virtual void SetUp() OVERRIDE {
114     testing::Test::SetUp();
115
116     context_.reset(new ThrottlingTestURLRequestContext());
117     io_message_loop_proxy_ = base::MessageLoopProxy::current();
118
119 #if defined(USE_NSS) || defined(OS_IOS)
120     crypto::EnsureNSSInit();
121     EnsureNSSHttpIOInit();
122 #endif
123   }
124
125   virtual void TearDown() OVERRIDE {
126 #if defined(USE_NSS) || defined(OS_IOS)
127     ShutdownNSSHttpIO();
128 #endif
129   }
130
131   // URLFetcher is designed to run on the main UI thread, but in our tests
132   // we assume that the current thread is the IO thread where the URLFetcher
133   // dispatches its requests to.  When we wish to simulate being used from
134   // a UI thread, we dispatch a worker thread to do so.
135   scoped_refptr<base::MessageLoopProxy> io_message_loop_proxy_;
136
137   URLFetcherImpl* fetcher_;
138   scoped_ptr<TestURLRequestContext> context_;
139 };
140
141 // A test fixture that uses a MockHostResolver, so that name resolutions can
142 // be manipulated by the tests to keep connections in the resolving state.
143 class URLFetcherMockDnsTest : public URLFetcherTest {
144  public:
145   // testing::Test:
146   virtual void SetUp() OVERRIDE;
147
148   // URLFetcherTest:
149   virtual void CreateFetcher(const GURL& url) OVERRIDE;
150
151   // URLFetcherDelegate:
152   virtual void OnURLFetchComplete(const URLFetcher* source) OVERRIDE;
153
154  protected:
155   GURL test_url_;
156   scoped_ptr<SpawnedTestServer> test_server_;
157   MockHostResolver resolver_;
158   scoped_ptr<URLFetcher> completed_fetcher_;
159 };
160
161 void URLFetcherTest::CreateFetcher(const GURL& url) {
162   fetcher_ = new URLFetcherImpl(url, URLFetcher::GET, this);
163   fetcher_->SetRequestContext(new ThrottlingTestURLRequestContextGetter(
164       io_message_loop_proxy().get(), request_context()));
165   fetcher_->Start();
166 }
167
168 void URLFetcherTest::OnURLFetchComplete(const URLFetcher* source) {
169   EXPECT_TRUE(source->GetStatus().is_success());
170   EXPECT_EQ(200, source->GetResponseCode());  // HTTP OK
171
172   std::string data;
173   EXPECT_TRUE(source->GetResponseAsString(&data));
174   EXPECT_FALSE(data.empty());
175
176   CleanupAfterFetchComplete();
177 }
178
179 void URLFetcherTest::CleanupAfterFetchComplete() {
180   delete fetcher_;  // Have to delete this here and not in the destructor,
181                     // because the destructor won't necessarily run on the
182                     // same thread that CreateFetcher() did.
183
184   io_message_loop_proxy()->PostTask(FROM_HERE,
185                                     base::MessageLoop::QuitClosure());
186   // If the current message loop is not the IO loop, it will be shut down when
187   // the main loop returns and this thread subsequently goes out of scope.
188 }
189
190 void URLFetcherMockDnsTest::SetUp() {
191   URLFetcherTest::SetUp();
192
193   resolver_.set_ondemand_mode(true);
194   resolver_.rules()->AddRule("example.com", "127.0.0.1");
195
196   context_.reset(new TestURLRequestContext(true));
197   context_->set_host_resolver(&resolver_);
198   context_->Init();
199
200   test_server_.reset(new SpawnedTestServer(SpawnedTestServer::TYPE_HTTP,
201                                            SpawnedTestServer::kLocalhost,
202                                            base::FilePath(kDocRoot)));
203   ASSERT_TRUE(test_server_->Start());
204
205   // test_server_.GetURL() returns a URL with 127.0.0.1 (kLocalhost), that is
206   // immediately resolved by the MockHostResolver. Use a hostname instead to
207   // trigger an async resolve.
208   test_url_ = GURL(
209       base::StringPrintf("http://example.com:%d/defaultresponse",
210       test_server_->host_port_pair().port()));
211   ASSERT_TRUE(test_url_.is_valid());
212 }
213
214 void URLFetcherMockDnsTest::CreateFetcher(const GURL& url) {
215   fetcher_ = new URLFetcherImpl(url, URLFetcher::GET, this);
216   fetcher_->SetRequestContext(new ThrottlingTestURLRequestContextGetter(
217       io_message_loop_proxy().get(), request_context()));
218 }
219
220 void URLFetcherMockDnsTest::OnURLFetchComplete(const URLFetcher* source) {
221   io_message_loop_proxy()->PostTask(FROM_HERE,
222                                     base::MessageLoop::QuitClosure());
223   ASSERT_EQ(fetcher_, source);
224   EXPECT_EQ(test_url_, source->GetOriginalURL());
225   completed_fetcher_.reset(fetcher_);
226 }
227
228 namespace {
229
230 // Version of URLFetcherTest that does a POST instead
231 class URLFetcherPostTest : public URLFetcherTest {
232  public:
233   // URLFetcherTest:
234   virtual void CreateFetcher(const GURL& url) OVERRIDE;
235
236   // URLFetcherDelegate:
237   virtual void OnURLFetchComplete(const URLFetcher* source) OVERRIDE;
238 };
239
240 // Version of URLFetcherTest that does a POST of a file using
241 // SetUploadDataStream
242 class URLFetcherPostFileTest : public URLFetcherTest {
243  public:
244   URLFetcherPostFileTest();
245
246   void SetUploadRange(uint64 range_offset, uint64 range_length) {
247     range_offset_ = range_offset;
248     range_length_ = range_length;
249   }
250
251   // URLFetcherTest:
252   virtual void CreateFetcher(const GURL& url) OVERRIDE;
253
254   // URLFetcherDelegate:
255   virtual void OnURLFetchComplete(const URLFetcher* source) OVERRIDE;
256
257  private:
258   base::FilePath path_;
259   uint64 range_offset_;
260   uint64 range_length_;
261 };
262
263 // Version of URLFetcherTest that does a POST instead with empty upload body
264 class URLFetcherEmptyPostTest : public URLFetcherTest {
265  public:
266   // URLFetcherTest:
267   virtual void CreateFetcher(const GURL& url) OVERRIDE;
268
269   // URLFetcherDelegate:
270   virtual void OnURLFetchComplete(const URLFetcher* source) OVERRIDE;
271 };
272
273 // Version of URLFetcherTest that tests download progress reports.
274 class URLFetcherDownloadProgressTest : public URLFetcherTest {
275  public:
276   URLFetcherDownloadProgressTest()
277       : previous_progress_(0),
278         expected_total_(0) {
279   }
280
281   // URLFetcherTest:
282   virtual void CreateFetcher(const GURL& url) OVERRIDE;
283
284   // URLFetcherDelegate:
285   virtual void OnURLFetchDownloadProgress(const URLFetcher* source,
286                                           int64 current,
287                                           int64 total) OVERRIDE;
288
289  protected:
290   // Download progress returned by the previous callback.
291   int64 previous_progress_;
292   // Size of the file being downloaded, known in advance (provided by each test
293   // case).
294   int64 expected_total_;
295 };
296
297 // Version of URLFetcherTest that tests progress reports at cancellation.
298 class URLFetcherDownloadProgressCancelTest : public URLFetcherTest {
299  public:
300   // URLFetcherTest:
301   virtual void CreateFetcher(const GURL& url) OVERRIDE;
302
303   // URLFetcherDelegate:
304   virtual void OnURLFetchComplete(const URLFetcher* source) OVERRIDE;
305   virtual void OnURLFetchDownloadProgress(const URLFetcher* source,
306                                           int64 current,
307                                           int64 total) OVERRIDE;
308  protected:
309   bool cancelled_;
310 };
311
312 // Version of URLFetcherTest that tests upload progress reports.
313 class URLFetcherUploadProgressTest : public URLFetcherTest {
314  public:
315   // URLFetcherTest:
316   virtual void CreateFetcher(const GURL& url) OVERRIDE;
317
318   // URLFetcherDelegate:
319   virtual void OnURLFetchUploadProgress(const URLFetcher* source,
320                                         int64 current,
321                                         int64 total) OVERRIDE;
322  protected:
323   int64 previous_progress_;
324   std::string chunk_;
325   int64 number_of_chunks_added_;
326 };
327
328 // Version of URLFetcherTest that tests headers.
329 class URLFetcherHeadersTest : public URLFetcherTest {
330  public:
331   // URLFetcherDelegate:
332   virtual void OnURLFetchComplete(const URLFetcher* source) OVERRIDE;
333 };
334
335 // Version of URLFetcherTest that tests SocketAddress.
336 class URLFetcherSocketAddressTest : public URLFetcherTest {
337  public:
338   // URLFetcherDelegate:
339   virtual void OnURLFetchComplete(const URLFetcher* source) OVERRIDE;
340  protected:
341   std::string expected_host_;
342   uint16 expected_port_;
343 };
344
345 // Version of URLFetcherTest that tests stopping on a redirect.
346 class URLFetcherStopOnRedirectTest : public URLFetcherTest {
347  public:
348   URLFetcherStopOnRedirectTest();
349   virtual ~URLFetcherStopOnRedirectTest();
350
351   // URLFetcherTest:
352   virtual void CreateFetcher(const GURL& url) OVERRIDE;
353
354   // URLFetcherDelegate:
355   virtual void OnURLFetchComplete(const URLFetcher* source) OVERRIDE;
356
357  protected:
358   // The URL we should be redirected to.
359   static const char* kRedirectTarget;
360
361   bool callback_called_;  // Set to true in OnURLFetchComplete().
362 };
363
364 // Version of URLFetcherTest that tests overload protection.
365 class URLFetcherProtectTest : public URLFetcherTest {
366  public:
367   // URLFetcherTest:
368   virtual void CreateFetcher(const GURL& url) OVERRIDE;
369
370   // URLFetcherDelegate:
371   virtual void OnURLFetchComplete(const URLFetcher* source) OVERRIDE;
372  private:
373   Time start_time_;
374 };
375
376 // Version of URLFetcherTest that tests overload protection, when responses
377 // passed through.
378 class URLFetcherProtectTestPassedThrough : public URLFetcherTest {
379  public:
380   // URLFetcherTest:
381   virtual void CreateFetcher(const GURL& url) OVERRIDE;
382
383   // URLFetcherDelegate:
384   virtual void OnURLFetchComplete(const URLFetcher* source) OVERRIDE;
385  private:
386   Time start_time_;
387 };
388
389 // Version of URLFetcherTest that tests bad HTTPS requests.
390 class URLFetcherBadHTTPSTest : public URLFetcherTest {
391  public:
392   URLFetcherBadHTTPSTest();
393
394   // URLFetcherDelegate:
395   virtual void OnURLFetchComplete(const URLFetcher* source) OVERRIDE;
396
397  private:
398   base::FilePath cert_dir_;
399 };
400
401 // Version of URLFetcherTest that tests request cancellation on shutdown.
402 class URLFetcherCancelTest : public URLFetcherTest {
403  public:
404   // URLFetcherTest:
405   virtual void CreateFetcher(const GURL& url) OVERRIDE;
406
407   // URLFetcherDelegate:
408   virtual void OnURLFetchComplete(const URLFetcher* source) OVERRIDE;
409
410   void CancelRequest();
411 };
412
413 // Version of TestURLRequestContext that posts a Quit task to the IO
414 // thread once it is deleted.
415 class CancelTestURLRequestContext : public ThrottlingTestURLRequestContext {
416  public:
417   explicit CancelTestURLRequestContext() {
418   }
419
420  private:
421   virtual ~CancelTestURLRequestContext() {
422     // The d'tor should execute in the IO thread. Post the quit task to the
423     // current thread.
424     base::MessageLoop::current()->PostTask(FROM_HERE,
425                                            base::MessageLoop::QuitClosure());
426   }
427 };
428
429 class CancelTestURLRequestContextGetter
430     : public TestURLRequestContextGetter {
431  public:
432   CancelTestURLRequestContextGetter(
433       base::MessageLoopProxy* io_message_loop_proxy,
434       const GURL& throttle_for_url)
435       : TestURLRequestContextGetter(io_message_loop_proxy),
436         io_message_loop_proxy_(io_message_loop_proxy),
437         context_created_(false, false),
438         throttle_for_url_(throttle_for_url) {
439   }
440
441   // TestURLRequestContextGetter:
442   virtual TestURLRequestContext* GetURLRequestContext() OVERRIDE {
443     if (!context_.get()) {
444       context_.reset(new CancelTestURLRequestContext());
445       DCHECK(context_->throttler_manager());
446
447       // Registers an entry for test url. The backoff time is calculated by:
448       //     new_backoff = 2.0 * old_backoff + 0
449       // The initial backoff is 2 seconds and maximum backoff is 4 seconds.
450       // Maximum retries allowed is set to 2.
451       scoped_refptr<URLRequestThrottlerEntry> entry(
452           new URLRequestThrottlerEntry(context_->throttler_manager(),
453                                        std::string(),
454                                        200,
455                                        3,
456                                        2000,
457                                        2.0,
458                                        0.0,
459                                        4000));
460       context_->throttler_manager()
461           ->OverrideEntryForTests(throttle_for_url_, entry.get());
462
463       context_created_.Signal();
464     }
465     return context_.get();
466   }
467
468   virtual scoped_refptr<base::MessageLoopProxy> GetIOMessageLoopProxy() const {
469     return io_message_loop_proxy_;
470   }
471
472   void WaitForContextCreation() {
473     context_created_.Wait();
474   }
475
476  protected:
477   virtual ~CancelTestURLRequestContextGetter() {}
478
479  private:
480   scoped_ptr<TestURLRequestContext> context_;
481   scoped_refptr<base::MessageLoopProxy> io_message_loop_proxy_;
482   base::WaitableEvent context_created_;
483   GURL throttle_for_url_;
484 };
485
486 // Version of URLFetcherTest that tests retying the same request twice.
487 class URLFetcherMultipleAttemptTest : public URLFetcherTest {
488  public:
489   // URLFetcherDelegate:
490   virtual void OnURLFetchComplete(const URLFetcher* source) OVERRIDE;
491  private:
492   std::string data_;
493 };
494
495 class URLFetcherFileTest : public URLFetcherTest {
496  public:
497   URLFetcherFileTest() : take_ownership_of_file_(false),
498                          expected_file_error_(OK) {}
499
500   void CreateFetcherForFile(const GURL& url, const base::FilePath& file_path);
501   void CreateFetcherForTempFile(const GURL& url);
502
503   // URLFetcherDelegate:
504   virtual void OnURLFetchComplete(const URLFetcher* source) OVERRIDE;
505
506  protected:
507   base::FilePath expected_file_;
508   base::FilePath file_path_;
509
510   // Set by the test. Used in OnURLFetchComplete() to decide if
511   // the URLFetcher should own the temp file, so that we can test
512   // disowning prevents the file from being deleted.
513   bool take_ownership_of_file_;
514
515   // Expected file error code for the test.  OK when expecting success.
516   int expected_file_error_;
517 };
518
519 void URLFetcherPostTest::CreateFetcher(const GURL& url) {
520   fetcher_ = new URLFetcherImpl(url, URLFetcher::POST, this);
521   fetcher_->SetRequestContext(new ThrottlingTestURLRequestContextGetter(
522       io_message_loop_proxy().get(), request_context()));
523   fetcher_->SetUploadData("application/x-www-form-urlencoded", "bobsyeruncle");
524   fetcher_->Start();
525 }
526
527 void URLFetcherPostTest::OnURLFetchComplete(const URLFetcher* source) {
528   std::string data;
529   EXPECT_TRUE(source->GetResponseAsString(&data));
530   EXPECT_EQ(std::string("bobsyeruncle"), data);
531   URLFetcherTest::OnURLFetchComplete(source);
532 }
533
534 URLFetcherPostFileTest::URLFetcherPostFileTest()
535     : range_offset_(0),
536       range_length_(kuint64max) {
537   PathService::Get(base::DIR_SOURCE_ROOT, &path_);
538   path_ = path_.Append(FILE_PATH_LITERAL("net"));
539   path_ = path_.Append(FILE_PATH_LITERAL("data"));
540   path_ = path_.Append(FILE_PATH_LITERAL("url_request_unittest"));
541   path_ = path_.Append(FILE_PATH_LITERAL("BullRunSpeech.txt"));
542 }
543
544 void URLFetcherPostFileTest::CreateFetcher(const GURL& url) {
545   fetcher_ = new URLFetcherImpl(url, URLFetcher::POST, this);
546   fetcher_->SetRequestContext(new ThrottlingTestURLRequestContextGetter(
547       io_message_loop_proxy().get(), request_context()));
548   fetcher_->SetUploadFilePath("application/x-www-form-urlencoded",
549                               path_,
550                               range_offset_,
551                               range_length_,
552                               base::MessageLoopProxy::current());
553   fetcher_->Start();
554 }
555
556 void URLFetcherPostFileTest::OnURLFetchComplete(const URLFetcher* source) {
557   std::string expected;
558   ASSERT_TRUE(base::ReadFileToString(path_, &expected));
559   ASSERT_LE(range_offset_, expected.size());
560   uint64 expected_size =
561       std::min(range_length_, expected.size() - range_offset_);
562
563   std::string data;
564   EXPECT_TRUE(source->GetResponseAsString(&data));
565   EXPECT_EQ(expected.substr(range_offset_, expected_size), data);
566   URLFetcherTest::OnURLFetchComplete(source);
567 }
568
569 void URLFetcherEmptyPostTest::CreateFetcher(const GURL& url) {
570   fetcher_ = new URLFetcherImpl(url, URLFetcher::POST, this);
571   fetcher_->SetRequestContext(new TestURLRequestContextGetter(
572       io_message_loop_proxy()));
573   fetcher_->SetUploadData("text/plain", std::string());
574   fetcher_->Start();
575 }
576
577 void URLFetcherEmptyPostTest::OnURLFetchComplete(const URLFetcher* source) {
578   EXPECT_TRUE(source->GetStatus().is_success());
579   EXPECT_EQ(200, source->GetResponseCode());  // HTTP OK
580
581   std::string data;
582   EXPECT_TRUE(source->GetResponseAsString(&data));
583   EXPECT_TRUE(data.empty());
584
585   CleanupAfterFetchComplete();
586   // Do not call the super class method URLFetcherTest::OnURLFetchComplete,
587   // since it expects a non-empty response.
588 }
589
590 void URLFetcherDownloadProgressTest::CreateFetcher(const GURL& url) {
591   fetcher_ = new URLFetcherImpl(url, URLFetcher::GET, this);
592   fetcher_->SetRequestContext(new ThrottlingTestURLRequestContextGetter(
593       io_message_loop_proxy().get(), request_context()));
594   fetcher_->Start();
595 }
596
597 void URLFetcherDownloadProgressTest::OnURLFetchDownloadProgress(
598     const URLFetcher* source, int64 progress, int64 total) {
599   // Increasing between 0 and total.
600   EXPECT_LE(0, progress);
601   EXPECT_GE(total, progress);
602   EXPECT_LE(previous_progress_, progress);
603   EXPECT_EQ(expected_total_, total);
604   previous_progress_ = progress;
605 }
606
607 void URLFetcherDownloadProgressCancelTest::CreateFetcher(const GURL& url) {
608   fetcher_ = new URLFetcherImpl(url, URLFetcher::GET, this);
609   fetcher_->SetRequestContext(new ThrottlingTestURLRequestContextGetter(
610       io_message_loop_proxy().get(), request_context()));
611   cancelled_ = false;
612   fetcher_->Start();
613 }
614
615 void URLFetcherDownloadProgressCancelTest::OnURLFetchDownloadProgress(
616     const URLFetcher* source, int64 current, int64 total) {
617   EXPECT_FALSE(cancelled_);
618   if (!cancelled_) {
619     cancelled_ = true;
620     CleanupAfterFetchComplete();
621   }
622 }
623
624 void URLFetcherDownloadProgressCancelTest::OnURLFetchComplete(
625     const URLFetcher* source) {
626   // Should have been cancelled.
627   ADD_FAILURE();
628   CleanupAfterFetchComplete();
629 }
630
631 void URLFetcherUploadProgressTest::CreateFetcher(const GURL& url) {
632   fetcher_ = new URLFetcherImpl(url, URLFetcher::POST, this);
633   fetcher_->SetRequestContext(new ThrottlingTestURLRequestContextGetter(
634       io_message_loop_proxy().get(), request_context()));
635   previous_progress_ = 0;
636   // Large enough data to require more than one read from UploadDataStream.
637   chunk_.assign(1<<16, 'a');
638   // Use chunked upload to wait for a timer event of progress notification.
639   fetcher_->SetChunkedUpload("application/x-www-form-urlencoded");
640   fetcher_->Start();
641   number_of_chunks_added_ = 1;
642   fetcher_->AppendChunkToUpload(chunk_, false);
643 }
644
645 void URLFetcherUploadProgressTest::OnURLFetchUploadProgress(
646     const URLFetcher* source, int64 current, int64 total) {
647   // Increasing between 0 and total.
648   EXPECT_LE(0, current);
649   EXPECT_GE(static_cast<int64>(chunk_.size()) * number_of_chunks_added_,
650             current);
651   EXPECT_LE(previous_progress_, current);
652   previous_progress_ = current;
653   EXPECT_EQ(-1, total);
654
655   if (number_of_chunks_added_ < 2) {
656     number_of_chunks_added_ += 1;
657     fetcher_->AppendChunkToUpload(chunk_, true);
658   }
659 }
660
661 void URLFetcherHeadersTest::OnURLFetchComplete(
662     const URLFetcher* source) {
663   std::string header;
664   EXPECT_TRUE(source->GetResponseHeaders()->GetNormalizedHeader("cache-control",
665                                                                 &header));
666   EXPECT_EQ("private", header);
667   URLFetcherTest::OnURLFetchComplete(source);
668 }
669
670 void URLFetcherSocketAddressTest::OnURLFetchComplete(
671     const URLFetcher* source) {
672   EXPECT_EQ("127.0.0.1", source->GetSocketAddress().host());
673   EXPECT_EQ(expected_port_, source->GetSocketAddress().port());
674   URLFetcherTest::OnURLFetchComplete(source);
675 }
676
677 // static
678 const char* URLFetcherStopOnRedirectTest::kRedirectTarget =
679     "http://redirect.target.com";
680
681 URLFetcherStopOnRedirectTest::URLFetcherStopOnRedirectTest()
682     : callback_called_(false) {
683 }
684
685 URLFetcherStopOnRedirectTest::~URLFetcherStopOnRedirectTest() {
686 }
687
688 void URLFetcherStopOnRedirectTest::CreateFetcher(const GURL& url) {
689   fetcher_ = new URLFetcherImpl(url, URLFetcher::GET, this);
690   fetcher_->SetRequestContext(new ThrottlingTestURLRequestContextGetter(
691       io_message_loop_proxy().get(), request_context()));
692   fetcher_->SetStopOnRedirect(true);
693   fetcher_->Start();
694 }
695
696 void URLFetcherStopOnRedirectTest::OnURLFetchComplete(
697     const URLFetcher* source) {
698   callback_called_ = true;
699   EXPECT_EQ(GURL(kRedirectTarget), source->GetURL());
700   EXPECT_EQ(URLRequestStatus::CANCELED, source->GetStatus().status());
701   EXPECT_EQ(ERR_ABORTED, source->GetStatus().error());
702   EXPECT_EQ(301, source->GetResponseCode());
703   CleanupAfterFetchComplete();
704 }
705
706 void URLFetcherProtectTest::CreateFetcher(const GURL& url) {
707   fetcher_ = new URLFetcherImpl(url, URLFetcher::GET, this);
708   fetcher_->SetRequestContext(new ThrottlingTestURLRequestContextGetter(
709       io_message_loop_proxy().get(), request_context()));
710   start_time_ = Time::Now();
711   fetcher_->SetMaxRetriesOn5xx(11);
712   fetcher_->Start();
713 }
714
715 void URLFetcherProtectTest::OnURLFetchComplete(const URLFetcher* source) {
716   const TimeDelta one_second = TimeDelta::FromMilliseconds(1000);
717   if (source->GetResponseCode() >= 500) {
718     // Now running ServerUnavailable test.
719     // It takes more than 1 second to finish all 11 requests.
720     EXPECT_TRUE(Time::Now() - start_time_ >= one_second);
721     EXPECT_TRUE(source->GetStatus().is_success());
722     std::string data;
723     EXPECT_TRUE(source->GetResponseAsString(&data));
724     EXPECT_FALSE(data.empty());
725     CleanupAfterFetchComplete();
726   } else {
727     // Now running Overload test.
728     static int count = 0;
729     count++;
730     if (count < 20) {
731       fetcher_->SetRequestContext(new ThrottlingTestURLRequestContextGetter(
732           io_message_loop_proxy().get(), request_context()));
733       fetcher_->Start();
734     } else {
735       // We have already sent 20 requests continuously. And we expect that
736       // it takes more than 1 second due to the overload protection settings.
737       EXPECT_TRUE(Time::Now() - start_time_ >= one_second);
738       URLFetcherTest::OnURLFetchComplete(source);
739     }
740   }
741 }
742
743 void URLFetcherProtectTestPassedThrough::CreateFetcher(const GURL& url) {
744   fetcher_ = new URLFetcherImpl(url, URLFetcher::GET, this);
745   fetcher_->SetRequestContext(new ThrottlingTestURLRequestContextGetter(
746       io_message_loop_proxy().get(), request_context()));
747   fetcher_->SetAutomaticallyRetryOn5xx(false);
748   start_time_ = Time::Now();
749   fetcher_->SetMaxRetriesOn5xx(11);
750   fetcher_->Start();
751 }
752
753 void URLFetcherProtectTestPassedThrough::OnURLFetchComplete(
754     const URLFetcher* source) {
755   const TimeDelta one_minute = TimeDelta::FromMilliseconds(60000);
756   if (source->GetResponseCode() >= 500) {
757     // Now running ServerUnavailable test.
758     // It should get here on the first attempt, so almost immediately and
759     // *not* to attempt to execute all 11 requests (2.5 minutes).
760     EXPECT_TRUE(Time::Now() - start_time_ < one_minute);
761     EXPECT_TRUE(source->GetStatus().is_success());
762     // Check that suggested back off time is bigger than 0.
763     EXPECT_GT(fetcher_->GetBackoffDelay().InMicroseconds(), 0);
764     std::string data;
765     EXPECT_TRUE(source->GetResponseAsString(&data));
766     EXPECT_FALSE(data.empty());
767   } else {
768     // We should not get here!
769     ADD_FAILURE();
770   }
771
772   CleanupAfterFetchComplete();
773 }
774
775
776 URLFetcherBadHTTPSTest::URLFetcherBadHTTPSTest() {
777   PathService::Get(base::DIR_SOURCE_ROOT, &cert_dir_);
778   cert_dir_ = cert_dir_.AppendASCII("chrome");
779   cert_dir_ = cert_dir_.AppendASCII("test");
780   cert_dir_ = cert_dir_.AppendASCII("data");
781   cert_dir_ = cert_dir_.AppendASCII("ssl");
782   cert_dir_ = cert_dir_.AppendASCII("certificates");
783 }
784
785 // The "server certificate expired" error should result in automatic
786 // cancellation of the request by
787 // URLRequest::Delegate::OnSSLCertificateError.
788 void URLFetcherBadHTTPSTest::OnURLFetchComplete(
789     const URLFetcher* source) {
790   // This part is different from URLFetcherTest::OnURLFetchComplete
791   // because this test expects the request to be cancelled.
792   EXPECT_EQ(URLRequestStatus::CANCELED, source->GetStatus().status());
793   EXPECT_EQ(ERR_ABORTED, source->GetStatus().error());
794   EXPECT_EQ(-1, source->GetResponseCode());
795   EXPECT_TRUE(source->GetCookies().empty());
796   std::string data;
797   EXPECT_TRUE(source->GetResponseAsString(&data));
798   EXPECT_TRUE(data.empty());
799   CleanupAfterFetchComplete();
800 }
801
802 void URLFetcherCancelTest::CreateFetcher(const GURL& url) {
803   fetcher_ = new URLFetcherImpl(url, URLFetcher::GET, this);
804   CancelTestURLRequestContextGetter* context_getter =
805       new CancelTestURLRequestContextGetter(io_message_loop_proxy().get(), url);
806   fetcher_->SetRequestContext(context_getter);
807   fetcher_->SetMaxRetriesOn5xx(2);
808   fetcher_->Start();
809   // We need to wait for the creation of the URLRequestContext, since we
810   // rely on it being destroyed as a signal to end the test.
811   context_getter->WaitForContextCreation();
812   CancelRequest();
813 }
814
815 void URLFetcherCancelTest::OnURLFetchComplete(
816     const URLFetcher* source) {
817   // We should have cancelled the request before completion.
818   ADD_FAILURE();
819   CleanupAfterFetchComplete();
820 }
821
822 void URLFetcherCancelTest::CancelRequest() {
823   delete fetcher_;
824   // The URLFetcher's test context will post a Quit task once it is
825   // deleted. So if this test simply hangs, it means cancellation
826   // did not work.
827 }
828
829 void URLFetcherMultipleAttemptTest::OnURLFetchComplete(
830     const URLFetcher* source) {
831   EXPECT_TRUE(source->GetStatus().is_success());
832   EXPECT_EQ(200, source->GetResponseCode());  // HTTP OK
833   std::string data;
834   EXPECT_TRUE(source->GetResponseAsString(&data));
835   EXPECT_FALSE(data.empty());
836   if (!data.empty() && data_.empty()) {
837     data_ = data;
838     fetcher_->SetRequestContext(new ThrottlingTestURLRequestContextGetter(
839         io_message_loop_proxy().get(), request_context()));
840     fetcher_->Start();
841   } else {
842     EXPECT_EQ(data, data_);
843     CleanupAfterFetchComplete();
844   }
845 }
846
847 void URLFetcherFileTest::CreateFetcherForFile(const GURL& url,
848                                               const base::FilePath& file_path) {
849   fetcher_ = new URLFetcherImpl(url, URLFetcher::GET, this);
850   fetcher_->SetRequestContext(new ThrottlingTestURLRequestContextGetter(
851       io_message_loop_proxy().get(), request_context()));
852
853   // Use the IO message loop to do the file operations in this test.
854   fetcher_->SaveResponseToFileAtPath(file_path, io_message_loop_proxy());
855   fetcher_->Start();
856 }
857
858 void URLFetcherFileTest::CreateFetcherForTempFile(const GURL& url) {
859   fetcher_ = new URLFetcherImpl(url, URLFetcher::GET, this);
860   fetcher_->SetRequestContext(new ThrottlingTestURLRequestContextGetter(
861       io_message_loop_proxy().get(), request_context()));
862
863   // Use the IO message loop to do the file operations in this test.
864   fetcher_->SaveResponseToTemporaryFile(io_message_loop_proxy());
865   fetcher_->Start();
866 }
867
868 void URLFetcherFileTest::OnURLFetchComplete(const URLFetcher* source) {
869   if (expected_file_error_ == OK) {
870     EXPECT_TRUE(source->GetStatus().is_success());
871     EXPECT_EQ(OK, source->GetStatus().error());
872     EXPECT_EQ(200, source->GetResponseCode());
873
874     EXPECT_TRUE(source->GetResponseAsFilePath(
875         take_ownership_of_file_, &file_path_));
876
877     EXPECT_TRUE(base::ContentsEqual(expected_file_, file_path_));
878   } else {
879     EXPECT_FALSE(source->GetStatus().is_success());
880     EXPECT_EQ(expected_file_error_, source->GetStatus().error());
881   }
882   CleanupAfterFetchComplete();
883 }
884
885 TEST_F(URLFetcherTest, SameThreadsTest) {
886   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
887                                 SpawnedTestServer::kLocalhost,
888                                 base::FilePath(kDocRoot));
889   ASSERT_TRUE(test_server.Start());
890
891   // Create the fetcher on the main thread.  Since IO will happen on the main
892   // thread, this will test URLFetcher's ability to do everything on one
893   // thread.
894   CreateFetcher(test_server.GetURL("defaultresponse"));
895
896   base::MessageLoop::current()->Run();
897 }
898
899 TEST_F(URLFetcherTest, DifferentThreadsTest) {
900   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
901                                 SpawnedTestServer::kLocalhost,
902                                 base::FilePath(kDocRoot));
903   ASSERT_TRUE(test_server.Start());
904
905   // Create a separate thread that will create the URLFetcher.  The current
906   // (main) thread will do the IO, and when the fetch is complete it will
907   // terminate the main thread's message loop; then the other thread's
908   // message loop will be shut down automatically as the thread goes out of
909   // scope.
910   base::Thread t("URLFetcher test thread");
911   ASSERT_TRUE(t.Start());
912   t.message_loop()->PostTask(
913       FROM_HERE,
914       base::Bind(&URLFetcherTest::CreateFetcher,
915                  base::Unretained(this),
916                  test_server.GetURL("defaultresponse")));
917
918   base::MessageLoop::current()->Run();
919 }
920
921 void CancelAllOnIO() {
922   EXPECT_EQ(1, URLFetcherTest::GetNumFetcherCores());
923   URLFetcherImpl::CancelAll();
924   EXPECT_EQ(0, URLFetcherTest::GetNumFetcherCores());
925 }
926
927 // Tests to make sure CancelAll() will successfully cancel existing URLFetchers.
928 TEST_F(URLFetcherTest, CancelAll) {
929   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
930                                 SpawnedTestServer::kLocalhost,
931                                 base::FilePath(kDocRoot));
932   ASSERT_TRUE(test_server.Start());
933   EXPECT_EQ(0, GetNumFetcherCores());
934
935   CreateFetcher(test_server.GetURL("defaultresponse"));
936   io_message_loop_proxy()->PostTaskAndReply(
937       FROM_HERE, base::Bind(&CancelAllOnIO), base::MessageLoop::QuitClosure());
938   base::MessageLoop::current()->Run();
939   EXPECT_EQ(0, GetNumFetcherCores());
940   delete fetcher_;
941 }
942
943 TEST_F(URLFetcherMockDnsTest, DontRetryOnNetworkChangedByDefault) {
944   EXPECT_EQ(0, GetNumFetcherCores());
945   EXPECT_FALSE(resolver_.has_pending_requests());
946
947   // This posts a task to start the fetcher.
948   CreateFetcher(test_url_);
949   fetcher_->Start();
950   EXPECT_EQ(0, GetNumFetcherCores());
951   base::MessageLoop::current()->RunUntilIdle();
952
953   // The fetcher is now running, but is pending the host resolve.
954   EXPECT_EQ(1, GetNumFetcherCores());
955   EXPECT_TRUE(resolver_.has_pending_requests());
956   ASSERT_FALSE(completed_fetcher_);
957
958   // A network change notification aborts the connect job.
959   NetworkChangeNotifier::NotifyObserversOfIPAddressChangeForTests();
960   base::MessageLoop::current()->RunUntilIdle();
961   EXPECT_EQ(0, GetNumFetcherCores());
962   EXPECT_FALSE(resolver_.has_pending_requests());
963   ASSERT_TRUE(completed_fetcher_);
964
965   // And the owner of the fetcher gets the ERR_NETWORK_CHANGED error.
966   EXPECT_EQ(ERR_NETWORK_CHANGED, completed_fetcher_->GetStatus().error());
967 }
968
969 TEST_F(URLFetcherMockDnsTest, RetryOnNetworkChangedAndFail) {
970   EXPECT_EQ(0, GetNumFetcherCores());
971   EXPECT_FALSE(resolver_.has_pending_requests());
972
973   // This posts a task to start the fetcher.
974   CreateFetcher(test_url_);
975   fetcher_->SetAutomaticallyRetryOnNetworkChanges(3);
976   fetcher_->Start();
977   EXPECT_EQ(0, GetNumFetcherCores());
978   base::MessageLoop::current()->RunUntilIdle();
979
980   // The fetcher is now running, but is pending the host resolve.
981   EXPECT_EQ(1, GetNumFetcherCores());
982   EXPECT_TRUE(resolver_.has_pending_requests());
983   ASSERT_FALSE(completed_fetcher_);
984
985   // Make it fail 3 times.
986   for (int i = 0; i < 3; ++i) {
987     // A network change notification aborts the connect job.
988     NetworkChangeNotifier::NotifyObserversOfIPAddressChangeForTests();
989     base::MessageLoop::current()->RunUntilIdle();
990
991     // But the fetcher retries automatically.
992     EXPECT_EQ(1, GetNumFetcherCores());
993     EXPECT_TRUE(resolver_.has_pending_requests());
994     ASSERT_FALSE(completed_fetcher_);
995   }
996
997   // A 4th failure doesn't trigger another retry, and propagates the error
998   // to the owner of the fetcher.
999   NetworkChangeNotifier::NotifyObserversOfIPAddressChangeForTests();
1000   base::MessageLoop::current()->RunUntilIdle();
1001   EXPECT_EQ(0, GetNumFetcherCores());
1002   EXPECT_FALSE(resolver_.has_pending_requests());
1003   ASSERT_TRUE(completed_fetcher_);
1004
1005   // And the owner of the fetcher gets the ERR_NETWORK_CHANGED error.
1006   EXPECT_EQ(ERR_NETWORK_CHANGED, completed_fetcher_->GetStatus().error());
1007 }
1008
1009 TEST_F(URLFetcherMockDnsTest, RetryOnNetworkChangedAndSucceed) {
1010   EXPECT_EQ(0, GetNumFetcherCores());
1011   EXPECT_FALSE(resolver_.has_pending_requests());
1012
1013   // This posts a task to start the fetcher.
1014   CreateFetcher(test_url_);
1015   fetcher_->SetAutomaticallyRetryOnNetworkChanges(3);
1016   fetcher_->Start();
1017   EXPECT_EQ(0, GetNumFetcherCores());
1018   base::MessageLoop::current()->RunUntilIdle();
1019
1020   // The fetcher is now running, but is pending the host resolve.
1021   EXPECT_EQ(1, GetNumFetcherCores());
1022   EXPECT_TRUE(resolver_.has_pending_requests());
1023   ASSERT_FALSE(completed_fetcher_);
1024
1025   // Make it fail 3 times.
1026   for (int i = 0; i < 3; ++i) {
1027     // A network change notification aborts the connect job.
1028     NetworkChangeNotifier::NotifyObserversOfIPAddressChangeForTests();
1029     base::MessageLoop::current()->RunUntilIdle();
1030
1031     // But the fetcher retries automatically.
1032     EXPECT_EQ(1, GetNumFetcherCores());
1033     EXPECT_TRUE(resolver_.has_pending_requests());
1034     ASSERT_FALSE(completed_fetcher_);
1035   }
1036
1037   // Now let it succeed by resolving the pending request.
1038   resolver_.ResolveAllPending();
1039   base::MessageLoop::current()->Run();
1040
1041   // URLFetcherMockDnsTest::OnURLFetchComplete() will quit the loop.
1042   EXPECT_EQ(0, GetNumFetcherCores());
1043   EXPECT_FALSE(resolver_.has_pending_requests());
1044   ASSERT_TRUE(completed_fetcher_);
1045
1046   // This time the request succeeded.
1047   EXPECT_EQ(OK, completed_fetcher_->GetStatus().error());
1048   EXPECT_EQ(200, completed_fetcher_->GetResponseCode());
1049 }
1050
1051 TEST_F(URLFetcherPostTest, Basic) {
1052   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
1053                                 SpawnedTestServer::kLocalhost,
1054                                 base::FilePath(kDocRoot));
1055   ASSERT_TRUE(test_server.Start());
1056
1057   CreateFetcher(test_server.GetURL("echo"));
1058   base::MessageLoop::current()->Run();
1059 }
1060
1061 TEST_F(URLFetcherPostFileTest, Basic) {
1062   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
1063                                 SpawnedTestServer::kLocalhost,
1064                                 base::FilePath(kDocRoot));
1065   ASSERT_TRUE(test_server.Start());
1066
1067   CreateFetcher(test_server.GetURL("echo"));
1068   base::MessageLoop::current()->Run();
1069 }
1070
1071 TEST_F(URLFetcherPostFileTest, Range) {
1072   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
1073                                 SpawnedTestServer::kLocalhost,
1074                                 base::FilePath(kDocRoot));
1075   ASSERT_TRUE(test_server.Start());
1076
1077   SetUploadRange(30, 100);
1078
1079   CreateFetcher(test_server.GetURL("echo"));
1080   base::MessageLoop::current()->Run();
1081 }
1082
1083 TEST_F(URLFetcherEmptyPostTest, Basic) {
1084   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
1085                                 SpawnedTestServer::kLocalhost,
1086                                 base::FilePath(kDocRoot));
1087   ASSERT_TRUE(test_server.Start());
1088
1089   CreateFetcher(test_server.GetURL("echo"));
1090   base::MessageLoop::current()->Run();
1091 }
1092
1093 TEST_F(URLFetcherUploadProgressTest, Basic) {
1094   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
1095                                 SpawnedTestServer::kLocalhost,
1096                                 base::FilePath(kDocRoot));
1097   ASSERT_TRUE(test_server.Start());
1098
1099   CreateFetcher(test_server.GetURL("echo"));
1100   base::MessageLoop::current()->Run();
1101 }
1102
1103 TEST_F(URLFetcherDownloadProgressTest, Basic) {
1104   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
1105                                 SpawnedTestServer::kLocalhost,
1106                                 base::FilePath(kDocRoot));
1107   ASSERT_TRUE(test_server.Start());
1108
1109   // Get a file large enough to require more than one read into
1110   // URLFetcher::Core's IOBuffer.
1111   static const char kFileToFetch[] = "animate1.gif";
1112   // Hardcoded file size - it cannot be easily fetched when a remote http server
1113   // is used for testing.
1114   static const int64 kFileSize = 19021;
1115
1116   expected_total_ = kFileSize;
1117
1118   CreateFetcher(test_server.GetURL(
1119       std::string(kTestServerFilePrefix) + kFileToFetch));
1120
1121   base::MessageLoop::current()->Run();
1122 }
1123
1124 TEST_F(URLFetcherDownloadProgressCancelTest, CancelWhileProgressReport) {
1125   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
1126                                 SpawnedTestServer::kLocalhost,
1127                                 base::FilePath(kDocRoot));
1128   ASSERT_TRUE(test_server.Start());
1129
1130   // Get a file large enough to require more than one read into
1131   // URLFetcher::Core's IOBuffer.
1132   static const char kFileToFetch[] = "animate1.gif";
1133   CreateFetcher(test_server.GetURL(
1134       std::string(kTestServerFilePrefix) + kFileToFetch));
1135
1136   base::MessageLoop::current()->Run();
1137 }
1138
1139 TEST_F(URLFetcherHeadersTest, Headers) {
1140   SpawnedTestServer test_server(
1141       SpawnedTestServer::TYPE_HTTP,
1142       SpawnedTestServer::kLocalhost,
1143       base::FilePath(FILE_PATH_LITERAL("net/data/url_request_unittest")));
1144   ASSERT_TRUE(test_server.Start());
1145
1146   CreateFetcher(test_server.GetURL("files/with-headers.html"));
1147   base::MessageLoop::current()->Run();
1148   // The actual tests are in the URLFetcherHeadersTest fixture.
1149 }
1150
1151 TEST_F(URLFetcherSocketAddressTest, SocketAddress) {
1152   SpawnedTestServer test_server(
1153       SpawnedTestServer::TYPE_HTTP,
1154       SpawnedTestServer::kLocalhost,
1155       base::FilePath(FILE_PATH_LITERAL("net/data/url_request_unittest")));
1156   ASSERT_TRUE(test_server.Start());
1157   expected_port_ = test_server.host_port_pair().port();
1158
1159   // Reusing "with-headers.html" but doesn't really matter.
1160   CreateFetcher(test_server.GetURL("files/with-headers.html"));
1161   base::MessageLoop::current()->Run();
1162   // The actual tests are in the URLFetcherSocketAddressTest fixture.
1163 }
1164
1165 TEST_F(URLFetcherStopOnRedirectTest, StopOnRedirect) {
1166   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
1167                                 SpawnedTestServer::kLocalhost,
1168                                 base::FilePath(kDocRoot));
1169   ASSERT_TRUE(test_server.Start());
1170
1171   CreateFetcher(
1172       test_server.GetURL(std::string("server-redirect?") + kRedirectTarget));
1173   base::MessageLoop::current()->Run();
1174   EXPECT_TRUE(callback_called_);
1175 }
1176
1177 TEST_F(URLFetcherProtectTest, Overload) {
1178   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
1179                                 SpawnedTestServer::kLocalhost,
1180                                 base::FilePath(kDocRoot));
1181   ASSERT_TRUE(test_server.Start());
1182
1183   GURL url(test_server.GetURL("defaultresponse"));
1184
1185   // Registers an entry for test url. It only allows 3 requests to be sent
1186   // in 200 milliseconds.
1187   scoped_refptr<URLRequestThrottlerEntry> entry(
1188       new URLRequestThrottlerEntry(request_context()->throttler_manager(),
1189                                    std::string(),
1190                                    200,
1191                                    3,
1192                                    1,
1193                                    2.0,
1194                                    0.0,
1195                                    256));
1196   request_context()->throttler_manager()
1197       ->OverrideEntryForTests(url, entry.get());
1198
1199   CreateFetcher(url);
1200
1201   base::MessageLoop::current()->Run();
1202 }
1203
1204 TEST_F(URLFetcherProtectTest, ServerUnavailable) {
1205   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
1206                                 SpawnedTestServer::kLocalhost,
1207                                 base::FilePath(kDocRoot));
1208   ASSERT_TRUE(test_server.Start());
1209
1210   GURL url(test_server.GetURL("files/server-unavailable.html"));
1211
1212   // Registers an entry for test url. The backoff time is calculated by:
1213   //     new_backoff = 2.0 * old_backoff + 0
1214   // and maximum backoff time is 256 milliseconds.
1215   // Maximum retries allowed is set to 11.
1216   scoped_refptr<URLRequestThrottlerEntry> entry(
1217       new URLRequestThrottlerEntry(request_context()->throttler_manager(),
1218                                    std::string(),
1219                                    200,
1220                                    3,
1221                                    1,
1222                                    2.0,
1223                                    0.0,
1224                                    256));
1225   request_context()->throttler_manager()
1226       ->OverrideEntryForTests(url, entry.get());
1227
1228   CreateFetcher(url);
1229
1230   base::MessageLoop::current()->Run();
1231 }
1232
1233 TEST_F(URLFetcherProtectTestPassedThrough, ServerUnavailablePropagateResponse) {
1234   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
1235                                 SpawnedTestServer::kLocalhost,
1236                                 base::FilePath(kDocRoot));
1237   ASSERT_TRUE(test_server.Start());
1238
1239   GURL url(test_server.GetURL("files/server-unavailable.html"));
1240
1241   // Registers an entry for test url. The backoff time is calculated by:
1242   //     new_backoff = 2.0 * old_backoff + 0
1243   // and maximum backoff time is 150000 milliseconds.
1244   // Maximum retries allowed is set to 11.
1245   scoped_refptr<URLRequestThrottlerEntry> entry(
1246       new URLRequestThrottlerEntry(request_context()->throttler_manager(),
1247                                    std::string(),
1248                                    200,
1249                                    3,
1250                                    100,
1251                                    2.0,
1252                                    0.0,
1253                                    150000));
1254   // Total time if *not* for not doing automatic backoff would be 150s.
1255   // In reality it should be "as soon as server responds".
1256   request_context()->throttler_manager()
1257       ->OverrideEntryForTests(url, entry.get());
1258
1259   CreateFetcher(url);
1260
1261   base::MessageLoop::current()->Run();
1262 }
1263
1264 TEST_F(URLFetcherBadHTTPSTest, BadHTTPSTest) {
1265   SpawnedTestServer::SSLOptions ssl_options(
1266       SpawnedTestServer::SSLOptions::CERT_EXPIRED);
1267   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTPS,
1268                                 ssl_options,
1269                                 base::FilePath(kDocRoot));
1270   ASSERT_TRUE(test_server.Start());
1271
1272   CreateFetcher(test_server.GetURL("defaultresponse"));
1273   base::MessageLoop::current()->Run();
1274 }
1275
1276 TEST_F(URLFetcherCancelTest, ReleasesContext) {
1277   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
1278                                 SpawnedTestServer::kLocalhost,
1279                                 base::FilePath(kDocRoot));
1280   ASSERT_TRUE(test_server.Start());
1281
1282   GURL url(test_server.GetURL("files/server-unavailable.html"));
1283
1284   // Create a separate thread that will create the URLFetcher.  The current
1285   // (main) thread will do the IO, and when the fetch is complete it will
1286   // terminate the main thread's message loop; then the other thread's
1287   // message loop will be shut down automatically as the thread goes out of
1288   // scope.
1289   base::Thread t("URLFetcher test thread");
1290   ASSERT_TRUE(t.Start());
1291   t.message_loop()->PostTask(
1292       FROM_HERE,
1293       base::Bind(&URLFetcherCancelTest::CreateFetcher,
1294                  base::Unretained(this), url));
1295
1296   base::MessageLoop::current()->Run();
1297 }
1298
1299 TEST_F(URLFetcherCancelTest, CancelWhileDelayedStartTaskPending) {
1300   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
1301                                 SpawnedTestServer::kLocalhost,
1302                                 base::FilePath(kDocRoot));
1303   ASSERT_TRUE(test_server.Start());
1304
1305   GURL url(test_server.GetURL("files/server-unavailable.html"));
1306
1307   // Register an entry for test url.
1308   // Using a sliding window of 4 seconds, and max of 1 request, under a fast
1309   // run we expect to have a 4 second delay when posting the Start task.
1310   scoped_refptr<URLRequestThrottlerEntry> entry(
1311       new URLRequestThrottlerEntry(request_context()->throttler_manager(),
1312                                    std::string(),
1313                                    4000,
1314                                    1,
1315                                    2000,
1316                                    2.0,
1317                                    0.0,
1318                                    4000));
1319   request_context()->throttler_manager()
1320       ->OverrideEntryForTests(url, entry.get());
1321   // Fake that a request has just started.
1322   entry->ReserveSendingTimeForNextRequest(base::TimeTicks());
1323
1324   // The next request we try to send will be delayed by ~4 seconds.
1325   // The slower the test runs, the less the delay will be (since it takes the
1326   // time difference from now).
1327
1328   base::Thread t("URLFetcher test thread");
1329   ASSERT_TRUE(t.Start());
1330   t.message_loop()->PostTask(
1331       FROM_HERE,
1332       base::Bind(&URLFetcherTest::CreateFetcher, base::Unretained(this), url));
1333
1334   base::MessageLoop::current()->Run();
1335 }
1336
1337 TEST_F(URLFetcherMultipleAttemptTest, SameData) {
1338   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
1339                                 SpawnedTestServer::kLocalhost,
1340                                 base::FilePath(kDocRoot));
1341   ASSERT_TRUE(test_server.Start());
1342
1343   // Create the fetcher on the main thread.  Since IO will happen on the main
1344   // thread, this will test URLFetcher's ability to do everything on one
1345   // thread.
1346   CreateFetcher(test_server.GetURL("defaultresponse"));
1347
1348   base::MessageLoop::current()->Run();
1349 }
1350
1351 TEST_F(URLFetcherFileTest, SmallGet) {
1352   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
1353                                 SpawnedTestServer::kLocalhost,
1354                                 base::FilePath(kDocRoot));
1355   ASSERT_TRUE(test_server.Start());
1356
1357   base::ScopedTempDir temp_dir;
1358   ASSERT_TRUE(temp_dir.CreateUniqueTempDir());
1359
1360   // Get a small file.
1361   static const char kFileToFetch[] = "simple.html";
1362   expected_file_ = test_server.GetDocumentRoot().AppendASCII(kFileToFetch);
1363   CreateFetcherForFile(
1364       test_server.GetURL(std::string(kTestServerFilePrefix) + kFileToFetch),
1365       temp_dir.path().AppendASCII(kFileToFetch));
1366
1367   base::MessageLoop::current()->Run();  // OnURLFetchComplete() will Quit().
1368
1369   ASSERT_FALSE(base::PathExists(file_path_))
1370       << file_path_.value() << " not removed.";
1371 }
1372
1373 TEST_F(URLFetcherFileTest, LargeGet) {
1374   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
1375                                 SpawnedTestServer::kLocalhost,
1376                                 base::FilePath(kDocRoot));
1377   ASSERT_TRUE(test_server.Start());
1378
1379   base::ScopedTempDir temp_dir;
1380   ASSERT_TRUE(temp_dir.CreateUniqueTempDir());
1381
1382   // Get a file large enough to require more than one read into
1383   // URLFetcher::Core's IOBuffer.
1384   static const char kFileToFetch[] = "animate1.gif";
1385   expected_file_ = test_server.GetDocumentRoot().AppendASCII(kFileToFetch);
1386   CreateFetcherForFile(
1387       test_server.GetURL(std::string(kTestServerFilePrefix) + kFileToFetch),
1388       temp_dir.path().AppendASCII(kFileToFetch));
1389
1390   base::MessageLoop::current()->Run();  // OnURLFetchComplete() will Quit().
1391 }
1392
1393 TEST_F(URLFetcherFileTest, SavedOutputFileOwnerhisp) {
1394   // If the caller takes the ownership of the output file, the file should
1395   // persist even after URLFetcher is gone. If not, the file must be deleted.
1396   const bool kTake[] = {false, true};
1397   for (size_t i = 0; i < arraysize(kTake); ++i) {
1398     take_ownership_of_file_ = kTake[i];
1399     SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
1400                                   SpawnedTestServer::kLocalhost,
1401                                   base::FilePath(kDocRoot));
1402     ASSERT_TRUE(test_server.Start());
1403
1404     base::ScopedTempDir temp_dir;
1405     ASSERT_TRUE(temp_dir.CreateUniqueTempDir());
1406
1407     // Get a small file.
1408     static const char kFileToFetch[] = "simple.html";
1409     expected_file_ = test_server.GetDocumentRoot().AppendASCII(kFileToFetch);
1410     CreateFetcherForFile(
1411         test_server.GetURL(std::string(kTestServerFilePrefix) + kFileToFetch),
1412         temp_dir.path().AppendASCII(kFileToFetch));
1413
1414     base::MessageLoop::current()->Run();  // OnURLFetchComplete() will Quit().
1415
1416     base::MessageLoop::current()->RunUntilIdle();
1417     ASSERT_EQ(kTake[i], base::PathExists(file_path_)) <<
1418         "FilePath: " << file_path_.value();
1419   }
1420 }
1421
1422 TEST_F(URLFetcherFileTest, OverwriteExistingFile) {
1423   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
1424                                 SpawnedTestServer::kLocalhost,
1425                                 base::FilePath(kDocRoot));
1426   ASSERT_TRUE(test_server.Start());
1427
1428   base::ScopedTempDir temp_dir;
1429   ASSERT_TRUE(temp_dir.CreateUniqueTempDir());
1430
1431   // Create a file before trying to fetch.
1432   static const char kFileToFetch[] = "simple.html";
1433   std::string data(10000, '?');  // Meant to be larger than simple.html.
1434   file_path_ = temp_dir.path().AppendASCII(kFileToFetch);
1435   ASSERT_EQ(static_cast<int>(data.size()),
1436             base::WriteFile(file_path_, data.data(), data.size()));
1437   ASSERT_TRUE(base::PathExists(file_path_));
1438   expected_file_ = test_server.GetDocumentRoot().AppendASCII(kFileToFetch);
1439   ASSERT_FALSE(base::ContentsEqual(file_path_, expected_file_));
1440
1441   // Get a small file.
1442   CreateFetcherForFile(
1443       test_server.GetURL(std::string(kTestServerFilePrefix) + kFileToFetch),
1444       file_path_);
1445
1446   base::MessageLoop::current()->Run();  // OnURLFetchComplete() will Quit().
1447 }
1448
1449 TEST_F(URLFetcherFileTest, TryToOverwriteDirectory) {
1450   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
1451                                 SpawnedTestServer::kLocalhost,
1452                                 base::FilePath(kDocRoot));
1453   ASSERT_TRUE(test_server.Start());
1454
1455   base::ScopedTempDir temp_dir;
1456   ASSERT_TRUE(temp_dir.CreateUniqueTempDir());
1457
1458   // Create a directory before trying to fetch.
1459   static const char kFileToFetch[] = "simple.html";
1460   file_path_ = temp_dir.path().AppendASCII(kFileToFetch);
1461   ASSERT_TRUE(base::CreateDirectory(file_path_));
1462   ASSERT_TRUE(base::PathExists(file_path_));
1463
1464   // Get a small file.
1465   expected_file_error_ = ERR_ACCESS_DENIED;
1466   expected_file_ = test_server.GetDocumentRoot().AppendASCII(kFileToFetch);
1467   CreateFetcherForFile(
1468       test_server.GetURL(std::string(kTestServerFilePrefix) + kFileToFetch),
1469       file_path_);
1470
1471   base::MessageLoop::current()->Run();  // OnURLFetchComplete() will Quit().
1472
1473   base::MessageLoop::current()->RunUntilIdle();
1474 }
1475
1476 TEST_F(URLFetcherFileTest, SmallGetToTempFile) {
1477   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
1478                                 SpawnedTestServer::kLocalhost,
1479                                 base::FilePath(kDocRoot));
1480   ASSERT_TRUE(test_server.Start());
1481
1482   // Get a small file.
1483   static const char kFileToFetch[] = "simple.html";
1484   expected_file_ = test_server.GetDocumentRoot().AppendASCII(kFileToFetch);
1485   CreateFetcherForTempFile(
1486       test_server.GetURL(std::string(kTestServerFilePrefix) + kFileToFetch));
1487
1488   base::MessageLoop::current()->Run();  // OnURLFetchComplete() will Quit().
1489
1490   ASSERT_FALSE(base::PathExists(file_path_))
1491       << file_path_.value() << " not removed.";
1492 }
1493
1494 TEST_F(URLFetcherFileTest, LargeGetToTempFile) {
1495   SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
1496                                 SpawnedTestServer::kLocalhost,
1497                                 base::FilePath(kDocRoot));
1498   ASSERT_TRUE(test_server.Start());
1499
1500   // Get a file large enough to require more than one read into
1501   // URLFetcher::Core's IOBuffer.
1502   static const char kFileToFetch[] = "animate1.gif";
1503   expected_file_ = test_server.GetDocumentRoot().AppendASCII(kFileToFetch);
1504   CreateFetcherForTempFile(test_server.GetURL(
1505       std::string(kTestServerFilePrefix) + kFileToFetch));
1506
1507   base::MessageLoop::current()->Run();  // OnURLFetchComplete() will Quit().
1508 }
1509
1510 TEST_F(URLFetcherFileTest, SavedOutputTempFileOwnerhisp) {
1511   // If the caller takes the ownership of the temp file, the file should persist
1512   // even after URLFetcher is gone. If not, the file must be deleted.
1513   const bool kTake[] = {false, true};
1514   for (size_t i = 0; i < arraysize(kTake); ++i) {
1515     take_ownership_of_file_ = kTake[i];
1516
1517     SpawnedTestServer test_server(SpawnedTestServer::TYPE_HTTP,
1518                                   SpawnedTestServer::kLocalhost,
1519                                   base::FilePath(kDocRoot));
1520     ASSERT_TRUE(test_server.Start());
1521
1522     // Get a small file.
1523     static const char kFileToFetch[] = "simple.html";
1524     expected_file_ = test_server.GetDocumentRoot().AppendASCII(kFileToFetch);
1525     CreateFetcherForTempFile(test_server.GetURL(
1526         std::string(kTestServerFilePrefix) + kFileToFetch));
1527
1528     base::MessageLoop::current()->Run();  // OnURLFetchComplete() will Quit().
1529
1530     base::MessageLoop::current()->RunUntilIdle();
1531     ASSERT_EQ(kTake[i], base::PathExists(file_path_)) <<
1532         "FilePath: " << file_path_.value();
1533   }
1534 }
1535
1536 }  // namespace
1537
1538 }  // namespace net