| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "base/bind.h" | 5 #include "base/bind.h" |
| 6 #include "base/prefs/pref_service.h" | 6 #include "base/prefs/pref_service.h" |
| 7 #include "base/strings/stringprintf.h" | 7 #include "base/strings/stringprintf.h" |
| 8 #include "base/strings/utf_string_conversions.h" | 8 #include "base/strings/utf_string_conversions.h" |
| 9 #include "chrome/browser/browsing_data/browsing_data_helper.h" |
| 10 #include "chrome/browser/browsing_data/browsing_data_remover.h" |
| 9 #include "chrome/browser/google/google_util.h" | 11 #include "chrome/browser/google/google_util.h" |
| 10 #include "chrome/browser/net/url_request_mock_util.h" | 12 #include "chrome/browser/net/url_request_mock_util.h" |
| 11 #include "chrome/browser/profiles/profile.h" | 13 #include "chrome/browser/profiles/profile.h" |
| 12 #include "chrome/browser/ui/browser.h" | 14 #include "chrome/browser/ui/browser.h" |
| 13 #include "chrome/browser/ui/browser_commands.h" | 15 #include "chrome/browser/ui/browser_commands.h" |
| 14 #include "chrome/browser/ui/tabs/tab_strip_model.h" | 16 #include "chrome/browser/ui/tabs/tab_strip_model.h" |
| 15 #include "chrome/common/pref_names.h" | 17 #include "chrome/common/pref_names.h" |
| 16 #include "chrome/test/base/in_process_browser_test.h" | 18 #include "chrome/test/base/in_process_browser_test.h" |
| 17 #include "chrome/test/base/ui_test_utils.h" | 19 #include "chrome/test/base/ui_test_utils.h" |
| 18 #include "content/public/browser/notification_service.h" | 20 #include "content/public/browser/notification_service.h" |
| 19 #include "content/public/browser/render_view_host.h" | 21 #include "content/public/browser/render_view_host.h" |
| 20 #include "content/public/browser/web_contents.h" | 22 #include "content/public/browser/web_contents.h" |
| 21 #include "content/public/browser/web_contents_observer.h" | 23 #include "content/public/browser/web_contents_observer.h" |
| 22 #include "content/public/test/browser_test_utils.h" | 24 #include "content/public/test/browser_test_utils.h" |
| 23 #include "content/public/test/test_navigation_observer.h" | 25 #include "content/public/test/test_navigation_observer.h" |
| 24 #include "content/test/net/url_request_failed_job.h" | 26 #include "content/test/net/url_request_failed_job.h" |
| 25 #include "content/test/net/url_request_mock_http_job.h" | 27 #include "content/test/net/url_request_mock_http_job.h" |
| 26 #include "net/base/net_errors.h" | 28 #include "net/base/net_errors.h" |
| 27 #include "net/base/net_util.h" | 29 #include "net/base/net_util.h" |
| 30 #include "net/http/failing_http_transaction_factory.h" |
| 31 #include "net/http/http_cache.h" |
| 32 #include "net/test/spawned_test_server/spawned_test_server.h" |
| 33 #include "net/url_request/url_request_context.h" |
| 34 #include "net/url_request/url_request_context_getter.h" |
| 28 #include "net/url_request/url_request_filter.h" | 35 #include "net/url_request/url_request_filter.h" |
| 29 #include "net/url_request/url_request_job_factory.h" | 36 #include "net/url_request/url_request_job_factory.h" |
| 30 | 37 |
| 31 using content::BrowserThread; | 38 using content::BrowserThread; |
| 32 using content::NavigationController; | 39 using content::NavigationController; |
| 33 using content::URLRequestFailedJob; | 40 using content::URLRequestFailedJob; |
| 34 | 41 |
| 35 namespace { | 42 namespace { |
| 36 | 43 |
| 37 class ErrorPageTest : public InProcessBrowserTest { | 44 class ErrorPageTest : public InProcessBrowserTest { |
| (...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 75 | 82 |
| 76 // Navigates forward in the history and waits for |num_navigations| to occur, | 83 // Navigates forward in the history and waits for |num_navigations| to occur, |
| 77 // and the title to change to |expected_title|. | 84 // and the title to change to |expected_title|. |
| 78 void GoForwardAndWaitForTitle(const std::string& expected_title, | 85 void GoForwardAndWaitForTitle(const std::string& expected_title, |
| 79 int num_navigations) { | 86 int num_navigations) { |
| 80 NavigateHistoryAndWaitForTitle(expected_title, | 87 NavigateHistoryAndWaitForTitle(expected_title, |
| 81 num_navigations, | 88 num_navigations, |
| 82 HISTORY_NAVIGATE_FORWARD); | 89 HISTORY_NAVIGATE_FORWARD); |
| 83 } | 90 } |
| 84 | 91 |
| 92 // Confirms that the javascript variable indicating whether or not we have |
| 93 // a stale copy in the cache has been set to |expected|. |
| 94 bool ProbeStaleCopyValue(bool expected) { |
| 95 const char* js_cache_probe = |
| 96 "(function () {\n" |
| 97 " if ('staleCopyInCache' in templateData) {\n" |
| 98 " domAutomationController.send(\n" |
| 99 " templateData.staleCopyInCache ? 'yes' : 'no');\n" |
| 100 " } else {\n" |
| 101 " domAutomationController.send('absent');\n" |
| 102 " }\n" |
| 103 "})();"; |
| 104 |
| 105 std::string result; |
| 106 bool ret = |
| 107 content::ExecuteScriptAndExtractString( |
| 108 browser()->tab_strip_model()->GetActiveWebContents(), |
| 109 js_cache_probe, |
| 110 &result); |
| 111 EXPECT_TRUE(ret); |
| 112 if (!ret) |
| 113 return false; |
| 114 EXPECT_EQ(expected ? "yes" : "no", result); |
| 115 return ((expected ? "yes" : "no") == result); |
| 116 } |
| 117 |
| 85 protected: | 118 protected: |
| 86 virtual void SetUpOnMainThread() OVERRIDE { | 119 virtual void SetUpOnMainThread() OVERRIDE { |
| 87 BrowserThread::PostTask( | 120 BrowserThread::PostTask( |
| 88 BrowserThread::IO, FROM_HERE, | 121 BrowserThread::IO, FROM_HERE, |
| 89 base::Bind(&chrome_browser_net::SetUrlRequestMocksEnabled, true)); | 122 base::Bind(&chrome_browser_net::SetUrlRequestMocksEnabled, true)); |
| 90 } | 123 } |
| 91 | 124 |
| 92 // Returns a GURL that results in a DNS error. | 125 // Returns a GURL that results in a DNS error. |
| 93 GURL GetDnsErrorURL() const { | 126 GURL GetDnsErrorURL() const { |
| 94 return URLRequestFailedJob::GetMockHttpUrl(net::ERR_NAME_NOT_RESOLVED); | 127 return URLRequestFailedJob::GetMockHttpUrl(net::ERR_NAME_NOT_RESOLVED); |
| (...skipping 19 matching lines...) Expand all Loading... |
| 114 } else { | 147 } else { |
| 115 FAIL(); | 148 FAIL(); |
| 116 } | 149 } |
| 117 test_navigation_observer.Wait(); | 150 test_navigation_observer.Wait(); |
| 118 | 151 |
| 119 EXPECT_EQ(title_watcher.WaitAndGetTitle(), | 152 EXPECT_EQ(title_watcher.WaitAndGetTitle(), |
| 120 base::ASCIIToUTF16(expected_title)); | 153 base::ASCIIToUTF16(expected_title)); |
| 121 } | 154 } |
| 122 }; | 155 }; |
| 123 | 156 |
| 124 | |
| 125 class TestFailProvisionalLoadObserver : public content::WebContentsObserver { | 157 class TestFailProvisionalLoadObserver : public content::WebContentsObserver { |
| 126 public: | 158 public: |
| 127 explicit TestFailProvisionalLoadObserver(content::WebContents* contents) | 159 explicit TestFailProvisionalLoadObserver(content::WebContents* contents) |
| 128 : content::WebContentsObserver(contents) {} | 160 : content::WebContentsObserver(contents) {} |
| 129 virtual ~TestFailProvisionalLoadObserver() {} | 161 virtual ~TestFailProvisionalLoadObserver() {} |
| 130 | 162 |
| 131 // This method is invoked when the provisional load failed. | 163 // This method is invoked when the provisional load failed. |
| 132 virtual void DidFailProvisionalLoad( | 164 virtual void DidFailProvisionalLoad( |
| 133 int64 frame_id, | 165 int64 frame_id, |
| 134 const base::string16& frame_unique_name, | 166 const base::string16& frame_unique_name, |
| 135 bool is_main_frame, | 167 bool is_main_frame, |
| 136 const GURL& validated_url, | 168 const GURL& validated_url, |
| 137 int error_code, | 169 int error_code, |
| 138 const base::string16& error_description, | 170 const base::string16& error_description, |
| 139 content::RenderViewHost* render_view_host) OVERRIDE { | 171 content::RenderViewHost* render_view_host) OVERRIDE { |
| 140 fail_url_ = validated_url; | 172 fail_url_ = validated_url; |
| 141 } | 173 } |
| 142 | 174 |
| 143 const GURL& fail_url() const { return fail_url_; } | 175 const GURL& fail_url() const { return fail_url_; } |
| 144 | 176 |
| 145 private: | 177 private: |
| 146 GURL fail_url_; | 178 GURL fail_url_; |
| 147 | 179 |
| 148 DISALLOW_COPY_AND_ASSIGN(TestFailProvisionalLoadObserver); | 180 DISALLOW_COPY_AND_ASSIGN(TestFailProvisionalLoadObserver); |
| 149 }; | 181 }; |
| 150 | 182 |
| 183 void InterceptNetworkTransactions(net::URLRequestContextGetter* getter, |
| 184 net::Error error) { |
| 185 DCHECK(content::BrowserThread::CurrentlyOn(BrowserThread::IO)); |
| 186 net::HttpCache* cache( |
| 187 getter->GetURLRequestContext()->http_transaction_factory()->GetCache()); |
| 188 DCHECK(cache); |
| 189 scoped_ptr<net::HttpTransactionFactory> factory( |
| 190 new net::FailingHttpTransactionFactory(cache->GetSession(), error)); |
| 191 // Throw away old version; since this is a a browser test, we don't |
| 192 // need to restore the old state. |
| 193 cache->SetHttpNetworkTransactionFactoryForTesting(factory.Pass()); |
| 194 } |
| 195 |
| 151 // See crbug.com/109669 | 196 // See crbug.com/109669 |
| 152 #if defined(USE_AURA) || defined(OS_WIN) | 197 #if defined(USE_AURA) || defined(OS_WIN) |
| 153 #define MAYBE_DNSError_Basic DISABLED_DNSError_Basic | 198 #define MAYBE_DNSError_Basic DISABLED_DNSError_Basic |
| 154 #else | 199 #else |
| 155 #define MAYBE_DNSError_Basic DNSError_Basic | 200 #define MAYBE_DNSError_Basic DNSError_Basic |
| 156 #endif | 201 #endif |
| 157 // Test that a DNS error occuring in the main frame redirects to an error page. | 202 // Test that a DNS error occuring in the main frame redirects to an error page. |
| 158 IN_PROC_BROWSER_TEST_F(ErrorPageTest, MAYBE_DNSError_Basic) { | 203 IN_PROC_BROWSER_TEST_F(ErrorPageTest, MAYBE_DNSError_Basic) { |
| 159 // The first navigation should fail, and the second one should be the error | 204 // The first navigation should fail, and the second one should be the error |
| 160 // page. | 205 // page. |
| (...skipping 188 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 349 | 394 |
| 350 // Checks that the Link Doctor is not loaded when we receive an actual 404 page. | 395 // Checks that the Link Doctor is not loaded when we receive an actual 404 page. |
| 351 IN_PROC_BROWSER_TEST_F(ErrorPageTest, Page404) { | 396 IN_PROC_BROWSER_TEST_F(ErrorPageTest, Page404) { |
| 352 NavigateToURLAndWaitForTitle( | 397 NavigateToURLAndWaitForTitle( |
| 353 content::URLRequestMockHTTPJob::GetMockUrl( | 398 content::URLRequestMockHTTPJob::GetMockUrl( |
| 354 base::FilePath(FILE_PATH_LITERAL("page404.html"))), | 399 base::FilePath(FILE_PATH_LITERAL("page404.html"))), |
| 355 "SUCCESS", | 400 "SUCCESS", |
| 356 1); | 401 1); |
| 357 } | 402 } |
| 358 | 403 |
| 404 // Checks that when an error occurs, the stale cache status of the page |
| 405 // is correctly transferred. |
| 406 IN_PROC_BROWSER_TEST_F(ErrorPageTest, StaleCacheStatus) { |
| 407 ASSERT_TRUE(test_server()->Start()); |
| 408 // Load cache with entry with "nocache" set, to create stale |
| 409 // cache. |
| 410 GURL test_url(test_server()->GetURL("files/nocache.html")); |
| 411 NavigateToURLAndWaitForTitle(test_url, "Nocache Test Page", 1); |
| 412 |
| 413 // Reload same URL after forcing an error from the the network layer; |
| 414 // confirm that the error page is told the cached copy exists. |
| 415 scoped_refptr<net::URLRequestContextGetter> url_request_context_getter = |
| 416 browser()->profile()->GetRequestContext(); |
| 417 BrowserThread::PostTask( |
| 418 BrowserThread::IO, FROM_HERE, |
| 419 base::Bind(&InterceptNetworkTransactions, url_request_context_getter, |
| 420 // Note that we can't use an error that'll invoke the link |
| 421 // doctor. In normal network error conditions that would |
| 422 // work (because the link doctor fetch would also fail, |
| 423 // putting us back in the main offline path), but |
| 424 // SetUrlRequestMocksEnabled() has also specfied a link |
| 425 // doctor mock, which will be accessible because it |
| 426 // won't go through the network cache. |
| 427 net::ERR_FAILED)); |
| 428 |
| 429 ui_test_utils::NavigateToURLBlockUntilNavigationsComplete( |
| 430 // With no link doctor load, there's only one navigation. |
| 431 browser(), test_url, 1); |
| 432 EXPECT_TRUE(ProbeStaleCopyValue(true)); |
| 433 |
| 434 // Clear the cache and reload the same URL; confirm the error page is told |
| 435 // that there is no cached copy. |
| 436 BrowsingDataRemover* remover = |
| 437 BrowsingDataRemover::CreateForUnboundedRange(browser()->profile()); |
| 438 remover->Remove(BrowsingDataRemover::REMOVE_CACHE, |
| 439 BrowsingDataHelper::UNPROTECTED_WEB); |
| 440 ui_test_utils::NavigateToURLBlockUntilNavigationsComplete( |
| 441 browser(), test_url, 1); |
| 442 EXPECT_TRUE(ProbeStaleCopyValue(false)); |
| 443 } |
| 444 |
| 359 // Returns Javascript code that executes plain text search for the page. | 445 // Returns Javascript code that executes plain text search for the page. |
| 360 // Pass into content::ExecuteScriptAndExtractBool as |script| parameter. | 446 // Pass into content::ExecuteScriptAndExtractBool as |script| parameter. |
| 361 std::string GetTextContentContainsStringScript( | 447 std::string GetTextContentContainsStringScript( |
| 362 const std::string& value_to_search) { | 448 const std::string& value_to_search) { |
| 363 return base::StringPrintf( | 449 return base::StringPrintf( |
| 364 "var textContent = document.body.textContent;" | 450 "var textContent = document.body.textContent;" |
| 365 "var hasError = textContent.indexOf('%s') >= 0;" | 451 "var hasError = textContent.indexOf('%s') >= 0;" |
| 366 "domAutomationController.send(hasError);", | 452 "domAutomationController.send(hasError);", |
| 367 value_to_search.c_str()); | 453 value_to_search.c_str()); |
| 368 } | 454 } |
| (...skipping 15 matching lines...) Expand all Loading... |
| 384 } | 470 } |
| 385 | 471 |
| 386 private: | 472 private: |
| 387 DISALLOW_COPY_AND_ASSIGN(AddressUnreachableProtocolHandler); | 473 DISALLOW_COPY_AND_ASSIGN(AddressUnreachableProtocolHandler); |
| 388 }; | 474 }; |
| 389 | 475 |
| 390 // A test fixture that returns ERR_ADDRESS_UNREACHABLE for all Link Doctor | 476 // A test fixture that returns ERR_ADDRESS_UNREACHABLE for all Link Doctor |
| 391 // requests. ERR_NAME_NOT_RESOLVED is more typical, but need to use a different | 477 // requests. ERR_NAME_NOT_RESOLVED is more typical, but need to use a different |
| 392 // error for the Link Doctor and the original page to validate the right page | 478 // error for the Link Doctor and the original page to validate the right page |
| 393 // is being displayed. | 479 // is being displayed. |
| 394 class ErrorPageLinkDoctorFailTest : public InProcessBrowserTest { | 480 class ErrorPageLinkDoctorFailTest : public ErrorPageTest { |
| 395 public: | 481 public: |
| 396 // InProcessBrowserTest: | 482 // InProcessBrowserTest: |
| 397 virtual void SetUpOnMainThread() OVERRIDE { | 483 virtual void SetUpOnMainThread() OVERRIDE { |
| 398 BrowserThread::PostTask( | 484 BrowserThread::PostTask( |
| 399 BrowserThread::IO, FROM_HERE, | 485 BrowserThread::IO, FROM_HERE, |
| 400 base::Bind(&ErrorPageLinkDoctorFailTest::AddFilters)); | 486 base::Bind(&ErrorPageLinkDoctorFailTest::AddFilters)); |
| 401 } | 487 } |
| 402 | 488 |
| 403 virtual void CleanUpOnMainThread() OVERRIDE { | 489 virtual void CleanUpOnMainThread() OVERRIDE { |
| 404 BrowserThread::PostTask( | 490 BrowserThread::PostTask( |
| (...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 440 // Verify that the expected error page is being displayed. Do this by making | 526 // Verify that the expected error page is being displayed. Do this by making |
| 441 // sure the original error code (ERR_NAME_NOT_RESOLVED) is displayed. | 527 // sure the original error code (ERR_NAME_NOT_RESOLVED) is displayed. |
| 442 bool result = false; | 528 bool result = false; |
| 443 EXPECT_TRUE(content::ExecuteScriptAndExtractBool( | 529 EXPECT_TRUE(content::ExecuteScriptAndExtractBool( |
| 444 browser()->tab_strip_model()->GetActiveWebContents(), | 530 browser()->tab_strip_model()->GetActiveWebContents(), |
| 445 GetTextContentContainsStringScript("ERR_NAME_NOT_RESOLVED"), | 531 GetTextContentContainsStringScript("ERR_NAME_NOT_RESOLVED"), |
| 446 &result)); | 532 &result)); |
| 447 EXPECT_TRUE(result); | 533 EXPECT_TRUE(result); |
| 448 } | 534 } |
| 449 | 535 |
| 536 // Checks that when an error occurs and a link doctor load fails, the stale |
| 537 // cache status of the page is correctly transferred. Most logic copied |
| 538 // from StaleCacheStatus above. |
| 539 IN_PROC_BROWSER_TEST_F(ErrorPageLinkDoctorFailTest, |
| 540 StaleCacheStatusFailedLinkDoctor) { |
| 541 ASSERT_TRUE(test_server()->Start()); |
| 542 // Load cache with entry with "nocache" set, to create stale |
| 543 // cache. |
| 544 GURL test_url(test_server()->GetURL("files/nocache.html")); |
| 545 NavigateToURLAndWaitForTitle(test_url, "Nocache Test Page", 1); |
| 546 |
| 547 // Reload same URL after forcing an error from the the network layer; |
| 548 // confirm that the error page is told the cached copy exists. |
| 549 scoped_refptr<net::URLRequestContextGetter> url_request_context_getter = |
| 550 browser()->profile()->GetRequestContext(); |
| 551 BrowserThread::PostTask( |
| 552 BrowserThread::IO, FROM_HERE, |
| 553 base::Bind(&InterceptNetworkTransactions, url_request_context_getter, |
| 554 net::ERR_CONNECTION_FAILED)); |
| 555 |
| 556 ui_test_utils::NavigateToURLBlockUntilNavigationsComplete( |
| 557 browser(), test_url, 2); |
| 558 ProbeStaleCopyValue(true); |
| 559 |
| 560 // Clear the cache and reload the same URL; confirm the error page is told |
| 561 // that there is no cached copy. |
| 562 BrowsingDataRemover* remover = |
| 563 BrowsingDataRemover::CreateForUnboundedRange(browser()->profile()); |
| 564 remover->Remove(BrowsingDataRemover::REMOVE_CACHE, |
| 565 BrowsingDataHelper::UNPROTECTED_WEB); |
| 566 ui_test_utils::NavigateToURLBlockUntilNavigationsComplete( |
| 567 browser(), test_url, 2); |
| 568 ProbeStaleCopyValue(false); |
| 569 } |
| 570 |
| 450 // A test fixture that simulates failing requests for an IDN domain name. | 571 // A test fixture that simulates failing requests for an IDN domain name. |
| 451 class ErrorPageForIDNTest : public InProcessBrowserTest { | 572 class ErrorPageForIDNTest : public InProcessBrowserTest { |
| 452 public: | 573 public: |
| 453 // Target hostname in different forms. | 574 // Target hostname in different forms. |
| 454 static const char kHostname[]; | 575 static const char kHostname[]; |
| 455 static const char kHostnameJSUnicode[]; | 576 static const char kHostnameJSUnicode[]; |
| 456 | 577 |
| 457 // InProcessBrowserTest: | 578 // InProcessBrowserTest: |
| 458 virtual void SetUpOnMainThread() OVERRIDE { | 579 virtual void SetUpOnMainThread() OVERRIDE { |
| 459 // Clear AcceptLanguages to force punycode decoding. | 580 // Clear AcceptLanguages to force punycode decoding. |
| (...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 499 | 620 |
| 500 bool result = false; | 621 bool result = false; |
| 501 EXPECT_TRUE(content::ExecuteScriptAndExtractBool( | 622 EXPECT_TRUE(content::ExecuteScriptAndExtractBool( |
| 502 browser()->tab_strip_model()->GetActiveWebContents(), | 623 browser()->tab_strip_model()->GetActiveWebContents(), |
| 503 GetTextContentContainsStringScript(kHostnameJSUnicode), | 624 GetTextContentContainsStringScript(kHostnameJSUnicode), |
| 504 &result)); | 625 &result)); |
| 505 EXPECT_TRUE(result); | 626 EXPECT_TRUE(result); |
| 506 } | 627 } |
| 507 | 628 |
| 508 } // namespace | 629 } // namespace |
| OLD | NEW |