prerender_browsertest.cc revision 58537e28ecd584eab876aee8be7156509866d23a
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 <deque> 6#include <vector> 7 8#include "base/command_line.h" 9#include "base/path_service.h" 10#include "base/prefs/pref_service.h" 11#include "base/strings/string_util.h" 12#include "base/strings/stringprintf.h" 13#include "base/strings/utf_string_conversions.h" 14#include "base/test/test_timeouts.h" 15#include "base/values.h" 16#include "chrome/browser/browsing_data/browsing_data_helper.h" 17#include "chrome/browser/browsing_data/browsing_data_remover.h" 18#include "chrome/browser/chrome_notification_types.h" 19#include "chrome/browser/content_settings/host_content_settings_map.h" 20#include "chrome/browser/extensions/api/web_navigation/web_navigation_api.h" 21#include "chrome/browser/extensions/extension_apitest.h" 22#include "chrome/browser/favicon/favicon_tab_helper.h" 23#include "chrome/browser/prerender/prerender_contents.h" 24#include "chrome/browser/prerender/prerender_handle.h" 25#include "chrome/browser/prerender/prerender_link_manager.h" 26#include "chrome/browser/prerender/prerender_link_manager_factory.h" 27#include "chrome/browser/prerender/prerender_manager.h" 28#include "chrome/browser/prerender/prerender_manager_factory.h" 29#include "chrome/browser/profiles/profile.h" 30#include "chrome/browser/safe_browsing/database_manager.h" 31#include "chrome/browser/safe_browsing/safe_browsing_service.h" 32#include "chrome/browser/safe_browsing/safe_browsing_util.h" 33#include "chrome/browser/task_manager/task_manager.h" 34#include "chrome/browser/task_manager/task_manager_browsertest_util.h" 35#include "chrome/browser/ui/browser.h" 36#include "chrome/browser/ui/browser_commands.h" 37#include "chrome/browser/ui/browser_finder.h" 38#include "chrome/browser/ui/browser_window.h" 39#include "chrome/browser/ui/tabs/tab_strip_model.h" 40#include "chrome/common/chrome_paths.h" 41#include "chrome/common/chrome_switches.h" 42#include "chrome/common/pref_names.h" 43#include "chrome/test/base/in_process_browser_test.h" 44#include "chrome/test/base/test_switches.h" 45#include "chrome/test/base/ui_test_utils.h" 46#include "content/public/browser/browser_message_filter.h" 47#include "content/public/browser/devtools_agent_host.h" 48#include "content/public/browser/devtools_client_host.h" 49#include "content/public/browser/devtools_manager.h" 50#include "content/public/browser/notification_service.h" 51#include "content/public/browser/render_process_host.h" 52#include "content/public/browser/render_view_host.h" 53#include "content/public/browser/web_contents.h" 54#include "content/public/common/url_constants.h" 55#include "content/public/test/browser_test_utils.h" 56#include "content/public/test/test_navigation_observer.h" 57#include "content/public/test/test_utils.h" 58#include "extensions/common/switches.h" 59#include "grit/generated_resources.h" 60#include "net/dns/mock_host_resolver.h" 61#include "net/url_request/url_request_context.h" 62#include "net/url_request/url_request_context_getter.h" 63#include "net/url_request/url_request_filter.h" 64#include "net/url_request/url_request_job.h" 65#include "ui/base/l10n/l10n_util.h" 66#include "url/gurl.h" 67 68using content::BrowserThread; 69using content::DevToolsAgentHost; 70using content::DevToolsClientHost; 71using content::DevToolsManager; 72using content::NavigationController; 73using content::OpenURLParams; 74using content::Referrer; 75using content::RenderViewHost; 76using content::RenderWidgetHost; 77using content::WebContents; 78 79// Prerender tests work as follows: 80// 81// A page with a prefetch link to the test page is loaded. Once prerendered, 82// its Javascript function DidPrerenderPass() is called, which returns true if 83// the page behaves as expected when prerendered. 84// 85// The prerendered page is then displayed on a tab. The Javascript function 86// DidDisplayPass() is called, and returns true if the page behaved as it 87// should while being displayed. 88 89namespace prerender { 90 91namespace { 92 93// Constants used in the test HTML files. 94static const char* kReadyTitle = "READY"; 95static const char* kPassTitle = "PASS"; 96 97std::string CreateClientRedirect(const std::string& dest_url) { 98 const char* const kClientRedirectBase = "client-redirect?"; 99 return kClientRedirectBase + dest_url; 100} 101 102std::string CreateServerRedirect(const std::string& dest_url) { 103 const char* const kServerRedirectBase = "server-redirect?"; 104 return kServerRedirectBase + dest_url; 105} 106 107// Clears the specified data using BrowsingDataRemover. 108void ClearBrowsingData(Browser* browser, int remove_mask) { 109 BrowsingDataRemover* remover = 110 BrowsingDataRemover::CreateForUnboundedRange(browser->profile()); 111 remover->Remove(remove_mask, BrowsingDataHelper::UNPROTECTED_WEB); 112 // BrowsingDataRemover deletes itself. 113} 114 115void CancelAllPrerenders(PrerenderManager* prerender_manager) { 116 prerender_manager->CancelAllPrerenders(); 117} 118 119// Returns true if and only if the final status is one in which the prerendered 120// page should prerender correctly. The page still may not be used. 121bool ShouldRenderPrerenderedPageCorrectly(FinalStatus status) { 122 switch (status) { 123 case FINAL_STATUS_USED: 124 case FINAL_STATUS_WINDOW_OPENER: 125 case FINAL_STATUS_APP_TERMINATING: 126 case FINAL_STATUS_CACHE_OR_HISTORY_CLEARED: 127 // We'll crash the renderer after it's loaded. 128 case FINAL_STATUS_RENDERER_CRASHED: 129 case FINAL_STATUS_CANCELLED: 130 case FINAL_STATUS_DEVTOOLS_ATTACHED: 131 case FINAL_STATUS_PAGE_BEING_CAPTURED: 132 return true; 133 default: 134 return false; 135 } 136} 137 138// Waits for the destruction of a RenderProcessHost's IPC channel. 139// Used to make sure the PrerenderLinkManager's OnChannelClosed function has 140// been called, before checking its state. 141class ChannelDestructionWatcher { 142 public: 143 ChannelDestructionWatcher() : channel_destroyed_(false), 144 waiting_for_channel_destruction_(false) { 145 } 146 147 ~ChannelDestructionWatcher() { 148 } 149 150 void WatchChannel(content::RenderProcessHost* host) { 151 host->GetChannel()->AddFilter(new DestructionMessageFilter(this)); 152 } 153 154 void WaitForChannelClose() { 155 ASSERT_FALSE(waiting_for_channel_destruction_); 156 157 if (channel_destroyed_) 158 return; 159 waiting_for_channel_destruction_ = true; 160 content::RunMessageLoop(); 161 162 EXPECT_FALSE(waiting_for_channel_destruction_); 163 EXPECT_TRUE(channel_destroyed_); 164 } 165 166 private: 167 // When destroyed, calls ChannelDestructionWatcher::OnChannelDestroyed. 168 // Ignores all messages. 169 class DestructionMessageFilter : public content::BrowserMessageFilter { 170 public: 171 explicit DestructionMessageFilter(ChannelDestructionWatcher* watcher) 172 : watcher_(watcher) { 173 } 174 175 private: 176 virtual ~DestructionMessageFilter() { 177 content::BrowserThread::PostTask( 178 content::BrowserThread::UI, FROM_HERE, 179 base::Bind(&ChannelDestructionWatcher::OnChannelDestroyed, 180 base::Unretained(watcher_))); 181 } 182 183 virtual bool OnMessageReceived(const IPC::Message& message, 184 bool* message_was_ok) OVERRIDE { 185 return false; 186 } 187 188 ChannelDestructionWatcher* watcher_; 189 190 DISALLOW_COPY_AND_ASSIGN(DestructionMessageFilter); 191 }; 192 193 void OnChannelDestroyed() { 194 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI)); 195 196 EXPECT_FALSE(channel_destroyed_); 197 channel_destroyed_ = true; 198 if (waiting_for_channel_destruction_) { 199 waiting_for_channel_destruction_ = false; 200 base::MessageLoop::current()->Quit(); 201 } 202 } 203 204 bool channel_destroyed_; 205 bool waiting_for_channel_destruction_; 206 207 DISALLOW_COPY_AND_ASSIGN(ChannelDestructionWatcher); 208}; 209 210// PrerenderContents that stops the UI message loop on DidStopLoading(). 211class TestPrerenderContents : public PrerenderContents { 212 public: 213 TestPrerenderContents( 214 PrerenderManager* prerender_manager, 215 Profile* profile, 216 const GURL& url, 217 const content::Referrer& referrer, 218 Origin origin, 219 int expected_number_of_loads, 220 FinalStatus expected_final_status, 221 bool prerender_should_wait_for_ready_title) 222 : PrerenderContents(prerender_manager, profile, url, 223 referrer, origin, PrerenderManager::kNoExperiment), 224 number_of_loads_(0), 225 expected_number_of_loads_(expected_number_of_loads), 226 expected_final_status_(expected_final_status), 227 new_render_view_host_(NULL), 228 was_hidden_(false), 229 was_shown_(false), 230 should_be_shown_(expected_final_status == FINAL_STATUS_USED), 231 quit_message_loop_on_destruction_( 232 expected_final_status != FINAL_STATUS_APP_TERMINATING && 233 expected_final_status != FINAL_STATUS_MAX), 234 expected_pending_prerenders_(0), 235 prerender_should_wait_for_ready_title_( 236 prerender_should_wait_for_ready_title) { 237 if (expected_number_of_loads == 0) 238 base::MessageLoopForUI::current()->Quit(); 239 } 240 241 virtual ~TestPrerenderContents() { 242 if (expected_final_status_ == FINAL_STATUS_MAX) { 243 EXPECT_EQ(match_complete_status(), MATCH_COMPLETE_REPLACEMENT); 244 } else { 245 EXPECT_EQ(expected_final_status_, final_status()) << 246 " when testing URL " << prerender_url().path() << 247 " (Expected: " << NameFromFinalStatus(expected_final_status_) << 248 ", Actual: " << NameFromFinalStatus(final_status()) << ")"; 249 } 250 // Prerendering RenderViewHosts should be hidden before the first 251 // navigation, so this should be happen for every PrerenderContents for 252 // which a RenderViewHost is created, regardless of whether or not it's 253 // used. 254 if (new_render_view_host_) 255 EXPECT_TRUE(was_hidden_); 256 257 // A used PrerenderContents will only be destroyed when we swap out 258 // WebContents, at the end of a navigation caused by a call to 259 // NavigateToURLImpl(). 260 if (final_status() == FINAL_STATUS_USED) 261 EXPECT_TRUE(new_render_view_host_); 262 263 EXPECT_EQ(should_be_shown_, was_shown_); 264 265 // When the PrerenderContents is destroyed, quit the UI message loop. 266 // This happens on navigation to used prerendered pages, and soon 267 // after cancellation of unused prerendered pages. 268 if (quit_message_loop_on_destruction_) { 269 // The message loop may not be running if this is swapped in 270 // synchronously on a Navigation. 271 base::MessageLoop* loop = base::MessageLoopForUI::current(); 272 if (loop->is_running()) 273 loop->Quit(); 274 } 275 } 276 277 virtual void RenderProcessGone(base::TerminationStatus status) OVERRIDE { 278 // On quit, it's possible to end up here when render processes are closed 279 // before the PrerenderManager is destroyed. As a result, it's possible to 280 // get either FINAL_STATUS_APP_TERMINATING or FINAL_STATUS_RENDERER_CRASHED 281 // on quit. 282 // 283 // It's also possible for this to be called after we've been notified of 284 // app termination, but before we've been deleted, which is why the second 285 // check is needed. 286 if (expected_final_status_ == FINAL_STATUS_APP_TERMINATING && 287 final_status() != expected_final_status_) { 288 expected_final_status_ = FINAL_STATUS_RENDERER_CRASHED; 289 } 290 291 PrerenderContents::RenderProcessGone(status); 292 } 293 294 virtual bool AddAliasURL(const GURL& url) OVERRIDE { 295 // Prevent FINAL_STATUS_UNSUPPORTED_SCHEME when navigating to about:crash in 296 // the PrerenderRendererCrash test. 297 if (url.spec() != content::kChromeUICrashURL) 298 return PrerenderContents::AddAliasURL(url); 299 return true; 300 } 301 302 virtual void DidStopLoading(RenderViewHost* render_view_host) OVERRIDE { 303 PrerenderContents::DidStopLoading(render_view_host); 304 ++number_of_loads_; 305 if (ShouldRenderPrerenderedPageCorrectly(expected_final_status_) && 306 number_of_loads_ == expected_number_of_loads_) { 307 base::MessageLoopForUI::current()->Quit(); 308 } 309 } 310 311 virtual void AddPendingPrerender( 312 scoped_ptr<PendingPrerenderInfo> pending_prerender_info) OVERRIDE { 313 PrerenderContents::AddPendingPrerender(pending_prerender_info.Pass()); 314 if (expected_pending_prerenders_ > 0 && 315 pending_prerender_count() == expected_pending_prerenders_) { 316 base::MessageLoop::current()->Quit(); 317 } 318 } 319 320 virtual WebContents* CreateWebContents( 321 content::SessionStorageNamespace* session_storage_namespace) OVERRIDE { 322 WebContents* web_contents = PrerenderContents::CreateWebContents( 323 session_storage_namespace); 324 string16 ready_title = ASCIIToUTF16(kReadyTitle); 325 if (prerender_should_wait_for_ready_title_) 326 ready_title_watcher_.reset(new content::TitleWatcher( 327 web_contents, ready_title)); 328 return web_contents; 329 } 330 331 void WaitForPrerenderToHaveReadyTitleIfRequired() { 332 if (ready_title_watcher_.get()) { 333 string16 ready_title = ASCIIToUTF16(kReadyTitle); 334 ASSERT_EQ(ready_title, ready_title_watcher_->WaitAndGetTitle()); 335 } 336 } 337 338 // Waits until the prerender has |expected_pending_prerenders| pending 339 // prerenders. 340 void WaitForPendingPrerenders(size_t expected_pending_prerenders) { 341 if (pending_prerender_count() < expected_pending_prerenders) { 342 expected_pending_prerenders_ = expected_pending_prerenders; 343 content::RunMessageLoop(); 344 expected_pending_prerenders_ = 0; 345 } 346 347 EXPECT_EQ(expected_pending_prerenders, pending_prerender_count()); 348 } 349 350 // For tests that open the prerender in a new background tab, the RenderView 351 // will not have been made visible when the PrerenderContents is destroyed 352 // even though it is used. 353 void set_should_be_shown(bool value) { should_be_shown_ = value; } 354 355 int number_of_loads() const { return number_of_loads_; } 356 357 FinalStatus expected_final_status() const { return expected_final_status_; } 358 359 bool quit_message_loop_on_destruction() const { 360 return quit_message_loop_on_destruction_; 361 } 362 363 private: 364 virtual void OnRenderViewHostCreated( 365 RenderViewHost* new_render_view_host) OVERRIDE { 366 // Used to make sure the RenderViewHost is hidden and, if used, 367 // subsequently shown. 368 notification_registrar().Add( 369 this, 370 content::NOTIFICATION_RENDER_WIDGET_VISIBILITY_CHANGED, 371 content::Source<RenderWidgetHost>(new_render_view_host)); 372 373 new_render_view_host_ = new_render_view_host; 374 375 PrerenderContents::OnRenderViewHostCreated(new_render_view_host); 376 } 377 378 virtual void Observe(int type, 379 const content::NotificationSource& source, 380 const content::NotificationDetails& details) OVERRIDE { 381 if (type == 382 content::NOTIFICATION_RENDER_WIDGET_VISIBILITY_CHANGED) { 383 EXPECT_EQ(new_render_view_host_, 384 content::Source<RenderWidgetHost>(source).ptr()); 385 bool is_visible = *content::Details<bool>(details).ptr(); 386 387 if (!is_visible) { 388 was_hidden_ = true; 389 } else if (is_visible && was_hidden_) { 390 // Once hidden, a prerendered RenderViewHost should only be shown after 391 // being removed from the PrerenderContents for display. 392 EXPECT_FALSE(GetRenderViewHost()); 393 was_shown_ = true; 394 } 395 return; 396 } 397 PrerenderContents::Observe(type, source, details); 398 } 399 400 int number_of_loads_; 401 int expected_number_of_loads_; 402 FinalStatus expected_final_status_; 403 404 // The RenderViewHost created for the prerender, if any. 405 RenderViewHost* new_render_view_host_; 406 // Set to true when the prerendering RenderWidget is hidden. 407 bool was_hidden_; 408 // Set to true when the prerendering RenderWidget is shown, after having been 409 // hidden. 410 bool was_shown_; 411 // Expected final value of was_shown_. Defaults to true for 412 // FINAL_STATUS_USED, and false otherwise. 413 bool should_be_shown_; 414 415 // If true, quits message loop on destruction of |this|. 416 bool quit_message_loop_on_destruction_; 417 418 // Total number of pending prerenders we're currently waiting for. Zero 419 // indicates we currently aren't waiting for any. 420 size_t expected_pending_prerenders_; 421 422 // If true, before calling DidPrerenderPass, will wait for the title of the 423 // prerendered page to turn to "READY". 424 bool prerender_should_wait_for_ready_title_; 425 scoped_ptr<content::TitleWatcher> ready_title_watcher_; 426}; 427 428// PrerenderManager that uses TestPrerenderContents. 429class WaitForLoadPrerenderContentsFactory : public PrerenderContents::Factory { 430 public: 431 WaitForLoadPrerenderContentsFactory( 432 int expected_number_of_loads, 433 const std::deque<FinalStatus>& expected_final_status_queue, 434 bool prerender_should_wait_for_ready_title) 435 : expected_number_of_loads_(expected_number_of_loads), 436 expected_final_status_queue_(expected_final_status_queue), 437 prerender_should_wait_for_ready_title_( 438 prerender_should_wait_for_ready_title) { 439 VLOG(1) << "Factory created with queue length " << 440 expected_final_status_queue_.size(); 441 } 442 443 virtual PrerenderContents* CreatePrerenderContents( 444 PrerenderManager* prerender_manager, 445 Profile* profile, 446 const GURL& url, 447 const content::Referrer& referrer, 448 Origin origin, 449 uint8 experiment_id) OVERRIDE { 450 FinalStatus expected_final_status = FINAL_STATUS_MAX; 451 if (!expected_final_status_queue_.empty()) { 452 expected_final_status = expected_final_status_queue_.front(); 453 expected_final_status_queue_.pop_front(); 454 } 455 VLOG(1) << "Creating prerender contents for " << url.path() << 456 " with expected final status " << expected_final_status; 457 VLOG(1) << expected_final_status_queue_.size() << " left in the queue."; 458 return new TestPrerenderContents(prerender_manager, 459 profile, url, referrer, origin, 460 expected_number_of_loads_, 461 expected_final_status, 462 prerender_should_wait_for_ready_title_); 463 } 464 465 private: 466 int expected_number_of_loads_; 467 std::deque<FinalStatus> expected_final_status_queue_; 468 bool prerender_should_wait_for_ready_title_; 469}; 470 471#if defined(FULL_SAFE_BROWSING) 472// A SafeBrowsingDatabaseManager implementation that returns a fixed result for 473// a given URL. 474class FakeSafeBrowsingDatabaseManager : public SafeBrowsingDatabaseManager { 475 public: 476 explicit FakeSafeBrowsingDatabaseManager(SafeBrowsingService* service) 477 : SafeBrowsingDatabaseManager(service), 478 threat_type_(SB_THREAT_TYPE_SAFE) { } 479 480 // Called on the IO thread to check if the given url is safe or not. If we 481 // can synchronously determine that the url is safe, CheckUrl returns true. 482 // Otherwise it returns false, and "client" is called asynchronously with the 483 // result when it is ready. 484 // Returns true, indicating a SAFE result, unless the URL is the fixed URL 485 // specified by the user, and the user-specified result is not SAFE 486 // (in which that result will be communicated back via a call into the 487 // client, and false will be returned). 488 // Overrides SafeBrowsingService::CheckBrowseUrl. 489 virtual bool CheckBrowseUrl(const GURL& gurl, Client* client) OVERRIDE { 490 if (gurl != url_ || threat_type_ == SB_THREAT_TYPE_SAFE) 491 return true; 492 493 BrowserThread::PostTask( 494 BrowserThread::IO, FROM_HERE, 495 base::Bind(&FakeSafeBrowsingDatabaseManager::OnCheckBrowseURLDone, 496 this, gurl, client)); 497 return false; 498 } 499 500 void SetThreatTypeForUrl(const GURL& url, SBThreatType threat_type) { 501 url_ = url; 502 threat_type_ = threat_type; 503 } 504 505 private: 506 virtual ~FakeSafeBrowsingDatabaseManager() {} 507 508 void OnCheckBrowseURLDone(const GURL& gurl, Client* client) { 509 std::vector<SBThreatType> expected_threats; 510 expected_threats.push_back(SB_THREAT_TYPE_URL_MALWARE); 511 expected_threats.push_back(SB_THREAT_TYPE_URL_PHISHING); 512 SafeBrowsingDatabaseManager::SafeBrowsingCheck sb_check( 513 std::vector<GURL>(1, gurl), 514 std::vector<SBFullHash>(), 515 client, 516 safe_browsing_util::MALWARE, 517 expected_threats); 518 sb_check.url_results[0] = threat_type_; 519 client->OnSafeBrowsingResult(sb_check); 520 } 521 522 GURL url_; 523 SBThreatType threat_type_; 524 DISALLOW_COPY_AND_ASSIGN(FakeSafeBrowsingDatabaseManager); 525}; 526 527class FakeSafeBrowsingService : public SafeBrowsingService { 528 public: 529 FakeSafeBrowsingService() { } 530 531 // Returned pointer has the same lifespan as the database_manager_ refcounted 532 // object. 533 FakeSafeBrowsingDatabaseManager* fake_database_manager() { 534 return fake_database_manager_; 535 } 536 537 protected: 538 virtual ~FakeSafeBrowsingService() { } 539 540 virtual SafeBrowsingDatabaseManager* CreateDatabaseManager() OVERRIDE { 541 fake_database_manager_ = new FakeSafeBrowsingDatabaseManager(this); 542 return fake_database_manager_; 543 } 544 545 private: 546 FakeSafeBrowsingDatabaseManager* fake_database_manager_; 547 548 DISALLOW_COPY_AND_ASSIGN(FakeSafeBrowsingService); 549}; 550 551// Factory that creates FakeSafeBrowsingService instances. 552class TestSafeBrowsingServiceFactory : public SafeBrowsingServiceFactory { 553 public: 554 TestSafeBrowsingServiceFactory() : 555 most_recent_service_(NULL) { } 556 virtual ~TestSafeBrowsingServiceFactory() { } 557 558 virtual SafeBrowsingService* CreateSafeBrowsingService() OVERRIDE { 559 most_recent_service_ = new FakeSafeBrowsingService(); 560 return most_recent_service_; 561 } 562 563 FakeSafeBrowsingService* most_recent_service() const { 564 return most_recent_service_; 565 } 566 567 private: 568 FakeSafeBrowsingService* most_recent_service_; 569}; 570#endif 571 572class FakeDevToolsClientHost : public DevToolsClientHost { 573 public: 574 FakeDevToolsClientHost() {} 575 virtual ~FakeDevToolsClientHost() {} 576 virtual void InspectedContentsClosing() OVERRIDE {} 577 virtual void DispatchOnInspectorFrontend(const std::string& msg) OVERRIDE {} 578 virtual void ReplacedWithAnotherClient() OVERRIDE {} 579}; 580 581class RestorePrerenderMode { 582 public: 583 RestorePrerenderMode() : prev_mode_(PrerenderManager::GetMode()) { 584 } 585 586 ~RestorePrerenderMode() { PrerenderManager::SetMode(prev_mode_); } 587 private: 588 PrerenderManager::PrerenderManagerMode prev_mode_; 589}; 590 591// URLRequestJob (and associated handler) which never starts. 592class NeverStartURLRequestJob : public net::URLRequestJob { 593 public: 594 NeverStartURLRequestJob(net::URLRequest* request, 595 net::NetworkDelegate* network_delegate) 596 : net::URLRequestJob(request, network_delegate) { 597 } 598 599 virtual void Start() OVERRIDE {} 600 601 private: 602 virtual ~NeverStartURLRequestJob() {} 603}; 604 605class NeverStartProtocolHandler 606 : public net::URLRequestJobFactory::ProtocolHandler { 607 public: 608 NeverStartProtocolHandler() {} 609 virtual ~NeverStartProtocolHandler() {} 610 611 virtual net::URLRequestJob* MaybeCreateJob( 612 net::URLRequest* request, 613 net::NetworkDelegate* network_delegate) const OVERRIDE { 614 return new NeverStartURLRequestJob(request, network_delegate); 615 } 616}; 617 618void CreateNeverStartProtocolHandlerOnIO(const GURL& url) { 619 CHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); 620 scoped_ptr<net::URLRequestJobFactory::ProtocolHandler> never_respond_handler( 621 new NeverStartProtocolHandler()); 622 net::URLRequestFilter::GetInstance()->AddUrlProtocolHandler( 623 url, never_respond_handler.Pass()); 624} 625 626} // namespace 627 628// Many of these tests are flaky. See http://crbug.com/249179 629class PrerenderBrowserTest : virtual public InProcessBrowserTest { 630 public: 631 PrerenderBrowserTest() 632 : autostart_test_server_(true), 633 prerender_contents_factory_(NULL), 634#if defined(FULL_SAFE_BROWSING) 635 safe_browsing_factory_(new TestSafeBrowsingServiceFactory()), 636#endif 637 use_https_src_server_(false), 638 call_javascript_(true), 639 loader_path_("files/prerender/prerender_loader.html"), 640 explicitly_set_browser_(NULL) {} 641 642 virtual ~PrerenderBrowserTest() {} 643 644 content::SessionStorageNamespace* GetSessionStorageNamespace() const { 645 WebContents* web_contents = 646 current_browser()->tab_strip_model()->GetActiveWebContents(); 647 if (!web_contents) 648 return NULL; 649 return web_contents->GetController().GetDefaultSessionStorageNamespace(); 650 } 651 652 virtual void SetUp() OVERRIDE { 653 // TODO(danakj): The GPU Video Decoder needs real GL bindings. 654 // crbug.com/269087 655 UseRealGLBindings(); 656 657 InProcessBrowserTest::SetUp(); 658 } 659 660 virtual void SetUpInProcessBrowserTestFixture() OVERRIDE { 661#if defined(FULL_SAFE_BROWSING) 662 SafeBrowsingService::RegisterFactory(safe_browsing_factory_.get()); 663#endif 664 } 665 666 virtual void SetUpCommandLine(CommandLine* command_line) OVERRIDE { 667 command_line->AppendSwitchASCII(switches::kPrerenderMode, 668 switches::kPrerenderModeSwitchValueEnabled); 669#if defined(OS_MACOSX) 670 // The plugins directory isn't read by default on the Mac, so it needs to be 671 // explicitly registered. 672 base::FilePath app_dir; 673 PathService::Get(chrome::DIR_APP, &app_dir); 674 command_line->AppendSwitchPath( 675 switches::kExtraPluginDir, 676 app_dir.Append(FILE_PATH_LITERAL("plugins"))); 677#endif 678 command_line->AppendSwitch(switches::kAlwaysAuthorizePlugins); 679 } 680 681 virtual void SetUpOnMainThread() OVERRIDE { 682 current_browser()->profile()->GetPrefs()->SetBoolean( 683 prefs::kPromptForDownload, false); 684 IncreasePrerenderMemory(); 685 if (autostart_test_server_) 686 ASSERT_TRUE(test_server()->Start()); 687 } 688 689 // Overload for a single expected final status 690 void PrerenderTestURL(const std::string& html_file, 691 FinalStatus expected_final_status, 692 int expected_number_of_loads) { 693 PrerenderTestURL(html_file, 694 expected_final_status, 695 expected_number_of_loads, 696 false); 697 } 698 699 void PrerenderTestURL(const std::string& html_file, 700 FinalStatus expected_final_status, 701 int expected_number_of_loads, 702 bool prerender_should_wait_for_ready_title) { 703 std::deque<FinalStatus> expected_final_status_queue(1, 704 expected_final_status); 705 PrerenderTestURL(html_file, 706 expected_final_status_queue, 707 expected_number_of_loads, 708 prerender_should_wait_for_ready_title); 709 } 710 711 void PrerenderTestURL( 712 const std::string& html_file, 713 const std::deque<FinalStatus>& expected_final_status_queue, 714 int expected_number_of_loads, 715 bool prerender_should_wait_for_ready_title) { 716 GURL url = test_server()->GetURL(html_file); 717 PrerenderTestURLImpl(url, url, 718 expected_final_status_queue, 719 expected_number_of_loads, 720 prerender_should_wait_for_ready_title); 721 } 722 723 void PrerenderTestURL( 724 const std::string& html_file, 725 const std::deque<FinalStatus>& expected_final_status_queue, 726 int expected_number_of_loads) { 727 PrerenderTestURL(html_file, expected_final_status_queue, 728 expected_number_of_loads, false); 729 } 730 731 void PrerenderTestURL( 732 const GURL& url, 733 FinalStatus expected_final_status, 734 int expected_number_of_loads) { 735 std::deque<FinalStatus> expected_final_status_queue(1, 736 expected_final_status); 737 PrerenderTestURLImpl(url, url, 738 expected_final_status_queue, 739 expected_number_of_loads, 740 false); 741 } 742 743 void PrerenderTestURL( 744 const GURL& prerender_url, 745 const GURL& destination_url, 746 FinalStatus expected_final_status, 747 int expected_number_of_loads) { 748 std::deque<FinalStatus> expected_final_status_queue(1, 749 expected_final_status); 750 PrerenderTestURLImpl(prerender_url, destination_url, 751 expected_final_status_queue, 752 expected_number_of_loads, 753 false); 754 } 755 756 void NavigateToDestURL() const { 757 NavigateToDestURLWithDisposition(CURRENT_TAB, true); 758 } 759 760 // Opens the url in a new tab, with no opener. 761 void NavigateToDestURLWithDisposition( 762 WindowOpenDisposition disposition, 763 bool expect_swap_to_succeed) const { 764 NavigateToURLImpl(dest_url_, disposition, expect_swap_to_succeed); 765 } 766 767 void OpenDestURLViaClick() const { 768 OpenDestURLWithJSImpl("Click()"); 769 } 770 771 void OpenDestURLViaClickTarget() const { 772 OpenDestURLWithJSImpl("ClickTarget()"); 773 } 774 775 void OpenDestURLViaClickNewWindow() const { 776 OpenDestURLWithJSImpl("ShiftClick()"); 777 } 778 779 void OpenDestURLViaClickNewForegroundTab() const { 780#if defined(OS_MACOSX) 781 OpenDestURLWithJSImpl("MetaShiftClick()"); 782#else 783 OpenDestURLWithJSImpl("CtrlShiftClick()"); 784#endif 785 } 786 787 void OpenDestURLViaClickNewBackgroundTab() const { 788 TestPrerenderContents* prerender_contents = GetPrerenderContents(); 789 ASSERT_TRUE(prerender_contents != NULL); 790 prerender_contents->set_should_be_shown(false); 791#if defined(OS_MACOSX) 792 OpenDestURLWithJSImpl("MetaClick()"); 793#else 794 OpenDestURLWithJSImpl("CtrlClick()"); 795#endif 796 } 797 798 void OpenDestURLViaWindowOpen() const { 799 OpenDestURLWithJSImpl("WindowOpen()"); 800 } 801 802 void RemoveLinkElement(int i) const { 803 current_browser()->tab_strip_model()->GetActiveWebContents()-> 804 GetRenderViewHost()->ExecuteJavascriptInWebFrame( 805 string16(), 806 ASCIIToUTF16(base::StringPrintf("RemoveLinkElement(%d)", i))); 807 } 808 809 void ClickToNextPageAfterPrerender() { 810 content::WindowedNotificationObserver new_page_observer( 811 content::NOTIFICATION_NAV_ENTRY_COMMITTED, 812 content::NotificationService::AllSources()); 813 RenderViewHost* render_view_host = current_browser()->tab_strip_model()-> 814 GetActiveWebContents()->GetRenderViewHost(); 815 render_view_host->ExecuteJavascriptInWebFrame( 816 string16(), 817 ASCIIToUTF16("ClickOpenLink()")); 818 new_page_observer.Wait(); 819 } 820 821 void NavigateToNextPageAfterPrerender() const { 822 ui_test_utils::NavigateToURL( 823 current_browser(), 824 test_server()->GetURL("files/prerender/prerender_page.html")); 825 } 826 827 void NavigateToDestUrlAndWaitForPassTitle() { 828 string16 expected_title = ASCIIToUTF16(kPassTitle); 829 content::TitleWatcher title_watcher( 830 GetPrerenderContents()->prerender_contents(), 831 expected_title); 832 NavigateToDestURL(); 833 EXPECT_EQ(expected_title, title_watcher.WaitAndGetTitle()); 834 } 835 836 // Called after the prerendered page has been navigated to and then away from. 837 // Navigates back through the history to the prerendered page. 838 void GoBackToPrerender() { 839 content::WindowedNotificationObserver back_nav_observer( 840 content::NOTIFICATION_NAV_ENTRY_COMMITTED, 841 content::NotificationService::AllSources()); 842 chrome::GoBack(current_browser(), CURRENT_TAB); 843 back_nav_observer.Wait(); 844 bool original_prerender_page = false; 845 ASSERT_TRUE(content::ExecuteScriptAndExtractBool( 846 current_browser()->tab_strip_model()->GetActiveWebContents(), 847 "window.domAutomationController.send(IsOriginalPrerenderPage())", 848 &original_prerender_page)); 849 EXPECT_TRUE(original_prerender_page); 850 } 851 852 // Goes back to the page that was active before the prerender was swapped 853 // in. This must be called when the prerendered page is the current page 854 // in the active tab. 855 void GoBackToPageBeforePrerender() { 856 WebContents* tab = 857 current_browser()->tab_strip_model()->GetActiveWebContents(); 858 ASSERT_TRUE(tab); 859 EXPECT_FALSE(tab->IsLoading()); 860 content::WindowedNotificationObserver back_nav_observer( 861 content::NOTIFICATION_LOAD_STOP, 862 content::Source<NavigationController>(&tab->GetController())); 863 chrome::GoBack(current_browser(), CURRENT_TAB); 864 back_nav_observer.Wait(); 865 bool js_result; 866 ASSERT_TRUE(content::ExecuteScriptAndExtractBool( 867 tab, 868 "window.domAutomationController.send(DidBackToOriginalPagePass())", 869 &js_result)); 870 EXPECT_TRUE(js_result); 871 } 872 873 void NavigateToURL(const std::string& dest_html_file) const { 874 GURL dest_url = test_server()->GetURL(dest_html_file); 875 NavigateToURLImpl(dest_url, CURRENT_TAB, true); 876 } 877 878 bool UrlIsInPrerenderManager(const std::string& html_file) const { 879 return UrlIsInPrerenderManager(test_server()->GetURL(html_file)); 880 } 881 882 bool UrlIsInPrerenderManager(const GURL& url) const { 883 return GetPrerenderManager()->FindPrerenderData( 884 url, GetSessionStorageNamespace()) != NULL; 885 } 886 887 void set_use_https_src(bool use_https_src_server) { 888 use_https_src_server_ = use_https_src_server; 889 } 890 891 void DisableJavascriptCalls() { 892 call_javascript_ = false; 893 } 894 895 TaskManagerModel* GetModel() const { 896 return TaskManager::GetInstance()->model(); 897 } 898 899 PrerenderManager* GetPrerenderManager() const { 900 PrerenderManager* prerender_manager = 901 PrerenderManagerFactory::GetForProfile(current_browser()->profile()); 902 return prerender_manager; 903 } 904 905 const PrerenderLinkManager* GetPrerenderLinkManager() const { 906 PrerenderLinkManager* prerender_link_manager = 907 PrerenderLinkManagerFactory::GetForProfile( 908 current_browser()->profile()); 909 return prerender_link_manager; 910 } 911 912 bool DidReceivePrerenderStartEventForLinkNumber(int index) const { 913 bool received_prerender_started; 914 std::string expression = base::StringPrintf( 915 "window.domAutomationController.send(Boolean(" 916 "receivedPrerenderStartEvents[%d]))", index); 917 918 CHECK(content::ExecuteScriptAndExtractBool( 919 current_browser()->tab_strip_model()->GetActiveWebContents(), 920 expression, 921 &received_prerender_started)); 922 return received_prerender_started; 923 } 924 925 bool DidReceivePrerenderLoadEventForLinkNumber(int index) const { 926 bool received_prerender_loaded; 927 std::string expression = base::StringPrintf( 928 "window.domAutomationController.send(Boolean(" 929 "receivedPrerenderLoadEvents[%d]))", index); 930 931 CHECK(content::ExecuteScriptAndExtractBool( 932 current_browser()->tab_strip_model()->GetActiveWebContents(), 933 expression, 934 &received_prerender_loaded)); 935 return received_prerender_loaded; 936 } 937 938 bool DidReceivePrerenderStopEventForLinkNumber(int index) const { 939 bool received_prerender_stopped; 940 std::string expression = base::StringPrintf( 941 "window.domAutomationController.send(Boolean(" 942 "receivedPrerenderStopEvents[%d]))", index); 943 944 CHECK(content::ExecuteScriptAndExtractBool( 945 current_browser()->tab_strip_model()->GetActiveWebContents(), 946 expression, 947 &received_prerender_stopped)); 948 return received_prerender_stopped; 949 } 950 951 bool HadPrerenderEventErrors() const { 952 bool had_prerender_event_errors; 953 CHECK(content::ExecuteScriptAndExtractBool( 954 current_browser()->tab_strip_model()->GetActiveWebContents(), 955 "window.domAutomationController.send(Boolean(" 956 " hadPrerenderEventErrors))", 957 &had_prerender_event_errors)); 958 return had_prerender_event_errors; 959 } 960 961 // Asserting on this can result in flaky tests. PrerenderHandles are 962 // removed from the PrerenderLinkManager when the prerender is canceled from 963 // the browser, when the prerenders are cancelled from the renderer process, 964 // or the channel for the renderer process is closed on the IO thread. In the 965 // last case, the code must be careful to wait for the channel to close, as it 966 // is done asynchronously after swapping out the old process. See 967 // ChannelDestructionWatcher. 968 bool IsEmptyPrerenderLinkManager() const { 969 return GetPrerenderLinkManager()->IsEmpty(); 970 } 971 972 // Returns length of |prerender_manager_|'s history, or -1 on failure. 973 int GetHistoryLength() const { 974 scoped_ptr<DictionaryValue> prerender_dict( 975 static_cast<DictionaryValue*>(GetPrerenderManager()->GetAsValue())); 976 if (!prerender_dict.get()) 977 return -1; 978 ListValue* history_list; 979 if (!prerender_dict->GetList("history", &history_list)) 980 return -1; 981 return static_cast<int>(history_list->GetSize()); 982 } 983 984#if defined(FULL_SAFE_BROWSING) 985 FakeSafeBrowsingDatabaseManager* GetFakeSafeBrowsingDatabaseManager() { 986 return safe_browsing_factory_->most_recent_service()-> 987 fake_database_manager(); 988 } 989#endif 990 991 TestPrerenderContents* GetPrerenderContentsFor(const GURL& url) const { 992 PrerenderManager::PrerenderData* prerender_data = 993 GetPrerenderManager()->FindPrerenderData( 994 url, GetSessionStorageNamespace()); 995 return static_cast<TestPrerenderContents*>( 996 prerender_data ? prerender_data->contents() : NULL); 997 } 998 999 TestPrerenderContents* GetPrerenderContents() const { 1000 return GetPrerenderContentsFor(dest_url_); 1001 } 1002 1003 void set_loader_path(const std::string& path) { 1004 loader_path_ = path; 1005 } 1006 1007 void set_loader_query_and_fragment(const std::string& query_and_fragment) { 1008 loader_query_and_fragment_ = query_and_fragment; 1009 } 1010 1011 GURL GetCrossDomainTestUrl(const std::string& path) { 1012 static const std::string secondary_domain = "www.foo.com"; 1013 host_resolver()->AddRule(secondary_domain, "127.0.0.1"); 1014 std::string url_str(base::StringPrintf( 1015 "http://%s:%d/%s", 1016 secondary_domain.c_str(), 1017 test_server()->host_port_pair().port(), 1018 path.c_str())); 1019 return GURL(url_str); 1020 } 1021 1022 void set_browser(Browser* browser) { 1023 explicitly_set_browser_ = browser; 1024 } 1025 1026 Browser* current_browser() const { 1027 return explicitly_set_browser_ ? explicitly_set_browser_ : browser(); 1028 } 1029 1030 void IncreasePrerenderMemory() { 1031 // Increase the memory allowed in a prerendered page above normal settings. 1032 // Debug build bots occasionally run against the default limit, and tests 1033 // were failing because the prerender was canceled due to memory exhaustion. 1034 // http://crbug.com/93076 1035 GetPrerenderManager()->mutable_config().max_bytes = 1000 * 1024 * 1024; 1036 } 1037 1038 protected: 1039 bool autostart_test_server_; 1040 1041 private: 1042 void PrerenderTestURLImpl( 1043 const GURL& prerender_url, 1044 const GURL& destination_url, 1045 const std::deque<FinalStatus>& expected_final_status_queue, 1046 int expected_number_of_loads, 1047 bool prerender_should_wait_for_ready_title) { 1048 dest_url_ = destination_url; 1049 1050 std::vector<net::SpawnedTestServer::StringPair> replacement_text; 1051 replacement_text.push_back( 1052 make_pair("REPLACE_WITH_PRERENDER_URL", prerender_url.spec())); 1053 replacement_text.push_back( 1054 make_pair("REPLACE_WITH_DESTINATION_URL", destination_url.spec())); 1055 std::string replacement_path; 1056 ASSERT_TRUE(net::SpawnedTestServer::GetFilePathWithReplacements( 1057 loader_path_, 1058 replacement_text, 1059 &replacement_path)); 1060 1061 const net::SpawnedTestServer* src_server = test_server(); 1062 scoped_ptr<net::SpawnedTestServer> https_src_server; 1063 if (use_https_src_server_) { 1064 https_src_server.reset( 1065 new net::SpawnedTestServer( 1066 net::SpawnedTestServer::TYPE_HTTPS, 1067 net::SpawnedTestServer::kLocalhost, 1068 base::FilePath(FILE_PATH_LITERAL("chrome/test/data")))); 1069 ASSERT_TRUE(https_src_server->Start()); 1070 src_server = https_src_server.get(); 1071 } 1072 GURL loader_url = src_server->GetURL(replacement_path + 1073 loader_query_and_fragment_); 1074 1075 PrerenderManager* prerender_manager = GetPrerenderManager(); 1076 ASSERT_TRUE(prerender_manager); 1077 prerender_manager->mutable_config().rate_limit_enabled = false; 1078 prerender_manager->mutable_config().https_allowed = true; 1079 ASSERT_TRUE(prerender_contents_factory_ == NULL); 1080 prerender_contents_factory_ = 1081 new WaitForLoadPrerenderContentsFactory( 1082 expected_number_of_loads, 1083 expected_final_status_queue, 1084 prerender_should_wait_for_ready_title); 1085 prerender_manager->SetPrerenderContentsFactory( 1086 prerender_contents_factory_); 1087 FinalStatus expected_final_status = expected_final_status_queue.front(); 1088 1089 // We construct launch_nav_observer so that we can be certain our loader 1090 // page has finished loading before continuing. This prevents ambiguous 1091 // NOTIFICATION_LOAD_STOP events from making tests flaky. 1092 WebContents* web_contents = 1093 current_browser()->tab_strip_model()->GetActiveWebContents(); 1094 content::WindowedNotificationObserver loader_nav_observer( 1095 content::NOTIFICATION_LOAD_STOP, 1096 content::Source<NavigationController>( 1097 &web_contents->GetController())); 1098 1099 // ui_test_utils::NavigateToURL uses its own observer and message loop. 1100 // Since the test needs to wait until the prerendered page has stopped 1101 // loading, rather than the page directly navigated to, need to 1102 // handle browser navigation directly. 1103 current_browser()->OpenURL(OpenURLParams( 1104 loader_url, Referrer(), CURRENT_TAB, content::PAGE_TRANSITION_TYPED, 1105 false)); 1106 1107 content::RunMessageLoop(); 1108 // Now that we've run the prerender until it stopped loading, we can now 1109 // also make sure the launcher has finished loading. 1110 loader_nav_observer.Wait(); 1111 1112 TestPrerenderContents* prerender_contents = GetPrerenderContents(); 1113 1114 if (ShouldRenderPrerenderedPageCorrectly(expected_final_status)) { 1115 ASSERT_NE(static_cast<PrerenderContents*>(NULL), prerender_contents); 1116 EXPECT_EQ(FINAL_STATUS_MAX, prerender_contents->final_status()); 1117 1118 if (call_javascript_ && expected_number_of_loads > 0) { 1119 // Wait for the prerendered page to change title to signal it is ready 1120 // if required. 1121 prerender_contents->WaitForPrerenderToHaveReadyTitleIfRequired(); 1122 1123 // Check if page behaves as expected while in prerendered state. 1124 bool prerender_test_result = false; 1125 ASSERT_TRUE(content::ExecuteScriptAndExtractBool( 1126 prerender_contents->GetRenderViewHostMutable(), 1127 "window.domAutomationController.send(DidPrerenderPass())", 1128 &prerender_test_result)); 1129 EXPECT_TRUE(prerender_test_result); 1130 } 1131 } else { 1132 // In the failure case, we should have removed |dest_url_| from the 1133 // prerender_manager. We ignore dummy PrerenderContents (as indicated 1134 // by not having started), and PrerenderContents that are expected to 1135 // be left in the manager until the test finishes. 1136 EXPECT_TRUE(prerender_contents == NULL || 1137 !prerender_contents->prerendering_has_started()); 1138 } 1139 } 1140 1141 void NavigateToURLImpl(const GURL& dest_url, 1142 WindowOpenDisposition disposition, 1143 bool expect_swap_to_succeed) const { 1144 ASSERT_NE(static_cast<PrerenderManager*>(NULL), GetPrerenderManager()); 1145 // Make sure in navigating we have a URL to use in the PrerenderManager. 1146 ASSERT_NE(static_cast<PrerenderContents*>(NULL), GetPrerenderContents()); 1147 1148 // If opening the page in a background tab, it won't be shown when swapped 1149 // in. 1150 if (disposition == NEW_BACKGROUND_TAB) 1151 GetPrerenderContents()->set_should_be_shown(false); 1152 1153 scoped_ptr<content::WindowedNotificationObserver> page_load_observer; 1154 WebContents* web_contents = NULL; 1155 1156 if (GetPrerenderContents()->prerender_contents()) { 1157 // In the case of zero loads, need to wait for the page load to complete 1158 // before running any Javascript. 1159 web_contents = GetPrerenderContents()->prerender_contents(); 1160 if (GetPrerenderContents()->number_of_loads() == 0) { 1161 page_load_observer.reset( 1162 new content::WindowedNotificationObserver( 1163 content::NOTIFICATION_LOAD_STOP, 1164 content::Source<NavigationController>( 1165 &web_contents->GetController()))); 1166 } 1167 } 1168 1169 // Navigate to the prerendered URL, but don't run the message loop. Browser 1170 // issued navigations to prerendered pages will synchronously swap in the 1171 // prerendered page. 1172 ui_test_utils::NavigateToURLWithDisposition( 1173 current_browser(), dest_url, disposition, 1174 ui_test_utils::BROWSER_TEST_NONE); 1175 1176 if (call_javascript_ && web_contents && expect_swap_to_succeed) { 1177 if (page_load_observer.get()) 1178 page_load_observer->Wait(); 1179 1180 bool display_test_result = false; 1181 ASSERT_TRUE(content::ExecuteScriptAndExtractBool( 1182 web_contents, 1183 "window.domAutomationController.send(DidDisplayPass())", 1184 &display_test_result)); 1185 EXPECT_TRUE(display_test_result); 1186 } 1187 } 1188 1189 // Opens the prerendered page using javascript functions in the 1190 // loader page. |javascript_function_name| should be a 0 argument function 1191 // which is invoked. 1192 void OpenDestURLWithJSImpl(const std::string& javascript_function_name) 1193 const { 1194 TestPrerenderContents* prerender_contents = GetPrerenderContents(); 1195 ASSERT_NE(static_cast<PrerenderContents*>(NULL), prerender_contents); 1196 1197 RenderViewHost* render_view_host = current_browser()->tab_strip_model()-> 1198 GetActiveWebContents()->GetRenderViewHost(); 1199 1200 render_view_host->ExecuteJavascriptInWebFrame( 1201 string16(), ASCIIToUTF16(javascript_function_name)); 1202 1203 if (prerender_contents->quit_message_loop_on_destruction()) { 1204 // Run message loop until the prerender contents is destroyed. 1205 content::RunMessageLoop(); 1206 } else { 1207 // We don't expect to pick up a running prerender, so instead 1208 // observe one navigation. 1209 content::TestNavigationObserver observer( 1210 current_browser()->tab_strip_model()->GetActiveWebContents()); 1211 observer.StartWatchingNewWebContents(); 1212 base::RunLoop run_loop; 1213 observer.WaitForObservation( 1214 base::Bind(&content::RunThisRunLoop, 1215 base::Unretained(&run_loop)), 1216 content::GetQuitTaskForRunLoop(&run_loop)); 1217 } 1218 } 1219 1220 WaitForLoadPrerenderContentsFactory* prerender_contents_factory_; 1221#if defined(FULL_SAFE_BROWSING) 1222 scoped_ptr<TestSafeBrowsingServiceFactory> safe_browsing_factory_; 1223#endif 1224 GURL dest_url_; 1225 bool use_https_src_server_; 1226 bool call_javascript_; 1227 std::string loader_path_; 1228 std::string loader_query_and_fragment_; 1229 Browser* explicitly_set_browser_; 1230}; 1231 1232// Checks that a page is correctly prerendered in the case of a 1233// <link rel=prerender> tag and then loaded into a tab in response to a 1234// navigation. 1235IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderPage) { 1236 PrerenderTestURL("files/prerender/prerender_page.html", FINAL_STATUS_USED, 1); 1237 1238 ChannelDestructionWatcher channel_close_watcher; 1239 channel_close_watcher.WatchChannel(browser()->tab_strip_model()-> 1240 GetActiveWebContents()->GetRenderProcessHost()); 1241 NavigateToDestURL(); 1242 channel_close_watcher.WaitForChannelClose(); 1243 1244 ASSERT_TRUE(IsEmptyPrerenderLinkManager()); 1245} 1246 1247// Checks that pending prerenders launch and receive proper event treatment. 1248// Disabled due to http://crbug.com/167792 1249IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, DISABLED_PrerenderPagePending) { 1250 std::deque<FinalStatus> expected_final_status_queue; 1251 expected_final_status_queue.push_back(FINAL_STATUS_USED); 1252 expected_final_status_queue.push_back(FINAL_STATUS_USED); 1253 PrerenderTestURL("files/prerender/prerender_page_pending.html", 1254 expected_final_status_queue, 1); 1255 1256 ChannelDestructionWatcher first_channel_close_watcher; 1257 1258 first_channel_close_watcher.WatchChannel(browser()->tab_strip_model()-> 1259 GetActiveWebContents()->GetRenderProcessHost()); 1260 NavigateToDestURL(); 1261 // NavigateToDestURL doesn't run a message loop. Normally that's fine, but in 1262 // this case, we need the pending prerenders to start. 1263 content::RunMessageLoop(); 1264 first_channel_close_watcher.WaitForChannelClose(); 1265 1266 EXPECT_TRUE(DidReceivePrerenderStartEventForLinkNumber(0)); 1267 EXPECT_FALSE(DidReceivePrerenderStopEventForLinkNumber(0)); 1268 EXPECT_FALSE(HadPrerenderEventErrors()); 1269 1270 const GURL prerender_page_url = 1271 test_server()->GetURL("files/prerender/prerender_page.html"); 1272 EXPECT_FALSE(IsEmptyPrerenderLinkManager()); 1273 EXPECT_NE(static_cast<TestPrerenderContents*>(NULL), 1274 GetPrerenderContentsFor(prerender_page_url)); 1275 1276 // Now navigate to our target page. 1277 ChannelDestructionWatcher second_channel_close_watcher; 1278 second_channel_close_watcher.WatchChannel(browser()->tab_strip_model()-> 1279 GetActiveWebContents()->GetRenderProcessHost()); 1280 ui_test_utils::NavigateToURLWithDisposition( 1281 current_browser(), prerender_page_url, CURRENT_TAB, 1282 ui_test_utils::BROWSER_TEST_NONE); 1283 second_channel_close_watcher.WaitForChannelClose(); 1284 1285 EXPECT_TRUE(IsEmptyPrerenderLinkManager()); 1286} 1287 1288// Checks that pending prerenders which are canceled before they are launched 1289// never get started. 1290IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderPageRemovesPending) { 1291 PrerenderTestURL("files/prerender/prerender_page_removes_pending.html", 1292 FINAL_STATUS_USED, 1); 1293 1294 ChannelDestructionWatcher channel_close_watcher; 1295 channel_close_watcher.WatchChannel(browser()->tab_strip_model()-> 1296 GetActiveWebContents()->GetRenderProcessHost()); 1297 NavigateToDestURL(); 1298 channel_close_watcher.WaitForChannelClose(); 1299 1300 EXPECT_FALSE(DidReceivePrerenderStartEventForLinkNumber(1)); 1301 EXPECT_FALSE(DidReceivePrerenderStopEventForLinkNumber(1)); 1302 EXPECT_FALSE(HadPrerenderEventErrors()); 1303 // IsEmptyPrerenderLinkManager() is not racy because the earlier DidReceive* 1304 // calls did a thread/process hop to the renderer which insured pending 1305 // renderer events have arrived. 1306 ASSERT_TRUE(IsEmptyPrerenderLinkManager()); 1307} 1308 1309// Flaky, http://crbug.com/167340. 1310IN_PROC_BROWSER_TEST_F( 1311 PrerenderBrowserTest, DISABLED_PrerenderPageRemovingLink) { 1312 set_loader_path("files/prerender/prerender_loader_removing_links.html"); 1313 set_loader_query_and_fragment("?links_to_insert=1"); 1314 PrerenderTestURL("files/prerender/prerender_page.html", 1315 FINAL_STATUS_CANCELLED, 1); 1316 EXPECT_TRUE(DidReceivePrerenderStartEventForLinkNumber(0)); 1317 EXPECT_FALSE(DidReceivePrerenderStopEventForLinkNumber(0)); 1318 1319 // No ChannelDestructionWatcher is needed here, since prerenders in the 1320 // PrerenderLinkManager should be deleted by removing the links, rather than 1321 // shutting down the renderer process. 1322 RemoveLinkElement(0); 1323 EXPECT_TRUE(DidReceivePrerenderStartEventForLinkNumber(0)); 1324 EXPECT_FALSE(DidReceivePrerenderStopEventForLinkNumber(0)); 1325 EXPECT_FALSE(HadPrerenderEventErrors()); 1326 // IsEmptyPrerenderLinkManager() is not racy because the earlier DidReceive* 1327 // calls did a thread/process hop to the renderer which insured pending 1328 // renderer events have arrived. 1329 EXPECT_TRUE(IsEmptyPrerenderLinkManager()); 1330} 1331 1332// Flaky, http://crbug.com/167340. 1333IN_PROC_BROWSER_TEST_F( 1334 PrerenderBrowserTest, DISABLED_PrerenderPageRemovingLinkWithTwoLinks) { 1335 GetPrerenderManager()->mutable_config().max_link_concurrency = 2; 1336 GetPrerenderManager()->mutable_config().max_link_concurrency_per_launcher = 2; 1337 1338 set_loader_path("files/prerender/prerender_loader_removing_links.html"); 1339 set_loader_query_and_fragment("?links_to_insert=2"); 1340 PrerenderTestURL("files/prerender/prerender_page.html", 1341 FINAL_STATUS_CANCELLED, 1); 1342 EXPECT_TRUE(DidReceivePrerenderStartEventForLinkNumber(0)); 1343 EXPECT_FALSE(DidReceivePrerenderStopEventForLinkNumber(0)); 1344 EXPECT_TRUE(DidReceivePrerenderStartEventForLinkNumber(1)); 1345 EXPECT_FALSE(DidReceivePrerenderStopEventForLinkNumber(1)); 1346 1347 RemoveLinkElement(0); 1348 RemoveLinkElement(1); 1349 EXPECT_TRUE(DidReceivePrerenderStartEventForLinkNumber(0)); 1350 EXPECT_FALSE(DidReceivePrerenderStopEventForLinkNumber(0)); 1351 EXPECT_TRUE(DidReceivePrerenderStartEventForLinkNumber(1)); 1352 EXPECT_FALSE(DidReceivePrerenderStopEventForLinkNumber(1)); 1353 EXPECT_FALSE(HadPrerenderEventErrors()); 1354 // IsEmptyPrerenderLinkManager() is not racy because the earlier DidReceive* 1355 // calls did a thread/process hop to the renderer which insured pending 1356 // renderer events have arrived. 1357 EXPECT_TRUE(IsEmptyPrerenderLinkManager()); 1358} 1359 1360#if defined(OS_WIN) 1361// TODO(gavinp): Fails on XP Rel - http://crbug.com/128841 1362#define MAYBE_PrerenderPageRemovingLinkWithTwoLinksRemovingOne \ 1363 DISABLED_PrerenderPageRemovingLinkWithTwoLinksRemovingOne 1364#else 1365#define MAYBE_PrerenderPageRemovingLinkWithTwoLinksRemovingOne \ 1366 PrerenderPageRemovingLinkWithTwoLinksRemovingOne 1367#endif // defined(OS_WIN) 1368IN_PROC_BROWSER_TEST_F( 1369 PrerenderBrowserTest, 1370 MAYBE_PrerenderPageRemovingLinkWithTwoLinksRemovingOne) { 1371 GetPrerenderManager()->mutable_config().max_link_concurrency = 2; 1372 GetPrerenderManager()->mutable_config().max_link_concurrency_per_launcher = 2; 1373 set_loader_path("files/prerender/prerender_loader_removing_links.html"); 1374 set_loader_query_and_fragment("?links_to_insert=2"); 1375 PrerenderTestURL("files/prerender/prerender_page.html", 1376 FINAL_STATUS_USED, 1); 1377 EXPECT_TRUE(DidReceivePrerenderStartEventForLinkNumber(0)); 1378 EXPECT_FALSE(DidReceivePrerenderStopEventForLinkNumber(0)); 1379 EXPECT_TRUE(DidReceivePrerenderStartEventForLinkNumber(1)); 1380 EXPECT_FALSE(DidReceivePrerenderStopEventForLinkNumber(1)); 1381 1382 RemoveLinkElement(0); 1383 EXPECT_TRUE(DidReceivePrerenderStartEventForLinkNumber(0)); 1384 EXPECT_FALSE(DidReceivePrerenderStopEventForLinkNumber(0)); 1385 EXPECT_TRUE(DidReceivePrerenderStartEventForLinkNumber(1)); 1386 EXPECT_FALSE(DidReceivePrerenderStopEventForLinkNumber(1)); 1387 EXPECT_FALSE(HadPrerenderEventErrors()); 1388 // IsEmptyPrerenderLinkManager() is not racy because the earlier DidReceive* 1389 // calls did a thread/process hop to the renderer which insured pending 1390 // renderer events have arrived. 1391 EXPECT_FALSE(IsEmptyPrerenderLinkManager()); 1392 1393 ChannelDestructionWatcher channel_close_watcher; 1394 channel_close_watcher.WatchChannel(browser()->tab_strip_model()-> 1395 GetActiveWebContents()->GetRenderProcessHost()); 1396 NavigateToDestURL(); 1397 channel_close_watcher.WaitForChannelClose(); 1398 1399 EXPECT_TRUE(IsEmptyPrerenderLinkManager()); 1400} 1401 1402// Checks that prerendering works in incognito mode. 1403IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderIncognito) { 1404 Profile* normal_profile = current_browser()->profile(); 1405 set_browser( 1406 ui_test_utils::OpenURLOffTheRecord(normal_profile, GURL("about:blank"))); 1407 // Increase memory expectations on the incognito PrerenderManager. 1408 IncreasePrerenderMemory(); 1409 PrerenderTestURL("files/prerender/prerender_page.html", FINAL_STATUS_USED, 1); 1410 NavigateToDestURL(); 1411} 1412 1413// Checks that the visibility API works. 1414IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 1415 DISABLED_PrerenderVisibility) { 1416 PrerenderTestURL("files/prerender/prerender_visibility.html", 1417 FINAL_STATUS_USED, 1418 1); 1419 NavigateToDestURL(); 1420} 1421 1422// Checks that the prerendering of a page is canceled correctly if we try to 1423// swap it in before it commits. 1424IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderNoCommitNoSwap) { 1425 // Navigate to a page that triggers a prerender for a URL that never commits. 1426 const GURL kNoCommitUrl("http://never-respond.example.com"); 1427 BrowserThread::PostTask( 1428 BrowserThread::IO, FROM_HERE, 1429 base::Bind(&CreateNeverStartProtocolHandlerOnIO, kNoCommitUrl)); 1430 PrerenderTestURL(kNoCommitUrl, 1431 FINAL_STATUS_CANCELLED, 1432 0); 1433 1434 // Navigate to the URL, but assume the contents won't be swapped in. 1435 NavigateToDestURLWithDisposition(CURRENT_TAB, false); 1436 1437 // Confirm that the prerendered version of the URL is not swapped in, 1438 // since it never committed. 1439 EXPECT_TRUE(UrlIsInPrerenderManager(kNoCommitUrl)); 1440 1441 // Post a task to cancel all the prerenders, so that we don't wait further. 1442 base::MessageLoop::current()->PostTask( 1443 FROM_HERE, base::Bind(&CancelAllPrerenders, GetPrerenderManager())); 1444 content::RunMessageLoop(); 1445} 1446 1447// Checks that the prerendering of a page is canceled correctly when a 1448// Javascript alert is called. 1449IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderAlertBeforeOnload) { 1450 PrerenderTestURL("files/prerender/prerender_alert_before_onload.html", 1451 FINAL_STATUS_JAVASCRIPT_ALERT, 1452 1); 1453} 1454 1455// Checks that the prerendering of a page is canceled correctly when a 1456// Javascript alert is called. 1457IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderAlertAfterOnload) { 1458 PrerenderTestURL("files/prerender/prerender_alert_after_onload.html", 1459 FINAL_STATUS_JAVASCRIPT_ALERT, 1460 1); 1461} 1462 1463// Checks that plugins are not loaded while a page is being preloaded, but 1464// are loaded when the page is displayed. 1465#if defined(USE_AURA) 1466// http://crbug.com/103496 1467#define MAYBE_PrerenderDelayLoadPlugin DISABLED_PrerenderDelayLoadPlugin 1468#elif defined(OS_MACOSX) 1469// http://crbug.com/100514 1470#define MAYBE_PrerenderDelayLoadPlugin DISABLED_PrerenderDelayLoadPlugin 1471#elif defined(OS_WIN) && defined(ARCH_CPU_X86_64) 1472// TODO(jschuh): Failing plugin tests. crbug.com/244653 1473#define MAYBE_PrerenderDelayLoadPlugin DISABLED_PrerenderDelayLoadPlugin 1474#else 1475#define MAYBE_PrerenderDelayLoadPlugin PrerenderDelayLoadPlugin 1476#endif 1477IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, MAYBE_PrerenderDelayLoadPlugin) { 1478 PrerenderTestURL("files/prerender/plugin_delay_load.html", 1479 FINAL_STATUS_USED, 1480 1); 1481 NavigateToDestURL(); 1482} 1483 1484// Checks that plugins are not loaded on prerendering pages when click-to-play 1485// is enabled. 1486IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderClickToPlay) { 1487 // Enable click-to-play. 1488 HostContentSettingsMap* content_settings_map = 1489 current_browser()->profile()->GetHostContentSettingsMap(); 1490 content_settings_map->SetDefaultContentSetting( 1491 CONTENT_SETTINGS_TYPE_PLUGINS, CONTENT_SETTING_ASK); 1492 1493 PrerenderTestURL("files/prerender/prerender_plugin_click_to_play.html", 1494 FINAL_STATUS_USED, 1495 1); 1496 NavigateToDestURL(); 1497} 1498 1499// Checks that we don't load a NaCl plugin when NaCl is disabled. 1500IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderNaClPluginDisabled) { 1501 PrerenderTestURL("files/prerender/prerender_plugin_nacl_disabled.html", 1502 FINAL_STATUS_USED, 1503 1); 1504 NavigateToDestURL(); 1505 1506 1507 // Run this check again. When we try to load aa ppapi plugin, the 1508 // "loadstart" event is asynchronously posted to a message loop. 1509 // It's possible that earlier call could have been run before the 1510 // the "loadstart" event was posted. 1511 // TODO(mmenke): While this should reliably fail on regressions, the 1512 // reliability depends on the specifics of ppapi plugin 1513 // loading. It would be great if we could avoid that. 1514 WebContents* web_contents = 1515 browser()->tab_strip_model()->GetActiveWebContents(); 1516 bool display_test_result = false; 1517 ASSERT_TRUE(content::ExecuteScriptAndExtractBool( 1518 web_contents, 1519 "window.domAutomationController.send(DidDisplayPass())", 1520 &display_test_result)); 1521 EXPECT_TRUE(display_test_result); 1522} 1523 1524// Checks that plugins in an iframe are not loaded while a page is 1525// being preloaded, but are loaded when the page is displayed. 1526#if defined(USE_AURA) 1527// http://crbug.com/103496 1528#define MAYBE_PrerenderIframeDelayLoadPlugin \ 1529 DISABLED_PrerenderIframeDelayLoadPlugin 1530#elif defined(OS_MACOSX) 1531// http://crbug.com/100514 1532#define MAYBE_PrerenderIframeDelayLoadPlugin \ 1533 DISABLED_PrerenderIframeDelayLoadPlugin 1534#elif defined(OS_WIN) && defined(ARCH_CPU_X86_64) 1535// TODO(jschuh): Failing plugin tests. crbug.com/244653 1536#define MAYBE_PrerenderIframeDelayLoadPlugin \ 1537 DISABLED_PrerenderIframeDelayLoadPlugin 1538#else 1539#define MAYBE_PrerenderIframeDelayLoadPlugin PrerenderIframeDelayLoadPlugin 1540#endif 1541IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 1542 MAYBE_PrerenderIframeDelayLoadPlugin) { 1543 PrerenderTestURL("files/prerender/prerender_iframe_plugin_delay_load.html", 1544 FINAL_STATUS_USED, 1545 1); 1546 NavigateToDestURL(); 1547} 1548 1549// Renders a page that contains a prerender link to a page that contains an 1550// iframe with a source that requires http authentication. This should not 1551// prerender successfully. 1552IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderHttpAuthentication) { 1553 PrerenderTestURL("files/prerender/prerender_http_auth_container.html", 1554 FINAL_STATUS_AUTH_NEEDED, 1555 1); 1556} 1557 1558// Checks that client-issued redirects work with prerendering. 1559// This version navigates to the page which issues the redirection, rather 1560// than the final destination page. 1561IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 1562 DISABLED_PrerenderClientRedirectNavigateToFirst) { 1563 PrerenderTestURL(CreateClientRedirect("files/prerender/prerender_page.html"), 1564 FINAL_STATUS_USED, 1565 2); 1566 NavigateToDestURL(); 1567} 1568 1569// Checks that client-issued redirects work with prerendering. 1570// This version navigates to the final destination page, rather than the 1571// page which does the redirection. 1572IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 1573 PrerenderClientRedirectNavigateToSecond) { 1574 PrerenderTestURL(CreateClientRedirect("files/prerender/prerender_page.html"), 1575 FINAL_STATUS_USED, 1576 2); 1577 NavigateToURL("files/prerender/prerender_page.html"); 1578} 1579 1580// Checks that client-issued redirects work with prerendering. 1581// This version navigates to the final destination page, rather than the 1582// page which does the redirection via a mouse click. 1583IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 1584 DISABLED_PrerenderClientRedirectNavigateToSecondViaClick) { 1585 GURL prerender_url = test_server()->GetURL( 1586 CreateClientRedirect("files/prerender/prerender_page.html")); 1587 GURL destination_url = test_server()->GetURL( 1588 "files/prerender/prerender_page.html"); 1589 PrerenderTestURL(prerender_url, destination_url, FINAL_STATUS_USED, 2); 1590 OpenDestURLViaClick(); 1591} 1592 1593// Checks that a prerender for an https will prevent a prerender from happening. 1594IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderHttps) { 1595 net::SpawnedTestServer https_server( 1596 net::SpawnedTestServer::TYPE_HTTPS, net::SpawnedTestServer::kLocalhost, 1597 base::FilePath(FILE_PATH_LITERAL("chrome/test/data"))); 1598 ASSERT_TRUE(https_server.Start()); 1599 GURL https_url = https_server.GetURL("files/prerender/prerender_page.html"); 1600 PrerenderTestURL(https_url, 1601 FINAL_STATUS_USED, 1602 1); 1603 NavigateToDestURL(); 1604} 1605 1606// Checks that client-issued redirects to an https page will cancel prerenders. 1607IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 1608 DISABLED_PrerenderClientRedirectToHttps) { 1609 net::SpawnedTestServer https_server( 1610 net::SpawnedTestServer::TYPE_HTTPS, net::SpawnedTestServer::kLocalhost, 1611 base::FilePath(FILE_PATH_LITERAL("chrome/test/data"))); 1612 ASSERT_TRUE(https_server.Start()); 1613 GURL https_url = https_server.GetURL("files/prerender/prerender_page.html"); 1614 PrerenderTestURL(CreateClientRedirect(https_url.spec()), 1615 FINAL_STATUS_USED, 1616 2); 1617 NavigateToDestURL(); 1618} 1619 1620// Checks that client-issued redirects within an iframe in a prerendered 1621// page will not count as an "alias" for the prerendered page. 1622IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 1623 DISABLED_PrerenderClientRedirectInIframe) { 1624 std::string redirect_path = CreateClientRedirect( 1625 "/files/prerender/prerender_embedded_content.html"); 1626 std::vector<net::SpawnedTestServer::StringPair> replacement_text; 1627 replacement_text.push_back( 1628 std::make_pair("REPLACE_WITH_URL", "/" + redirect_path)); 1629 std::string replacement_path; 1630 ASSERT_TRUE(net::SpawnedTestServer::GetFilePathWithReplacements( 1631 "files/prerender/prerender_with_iframe.html", 1632 replacement_text, 1633 &replacement_path)); 1634 PrerenderTestURL(replacement_path, FINAL_STATUS_USED, 2); 1635 EXPECT_FALSE(UrlIsInPrerenderManager( 1636 "files/prerender/prerender_embedded_content.html")); 1637 NavigateToDestURL(); 1638} 1639 1640// Checks that client-issued redirects within an iframe in a prerendered 1641// page to an https page will not cancel the prerender, nor will it 1642// count as an "alias" for the prerendered page. 1643IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 1644 DISABLED_PrerenderClientRedirectToHttpsInIframe) { 1645 net::SpawnedTestServer https_server( 1646 net::SpawnedTestServer::TYPE_HTTPS, net::SpawnedTestServer::kLocalhost, 1647 base::FilePath(FILE_PATH_LITERAL("chrome/test/data"))); 1648 ASSERT_TRUE(https_server.Start()); 1649 GURL https_url = https_server.GetURL("files/prerender/prerender_page.html"); 1650 std::string redirect_path = CreateClientRedirect(https_url.spec()); 1651 std::vector<net::SpawnedTestServer::StringPair> replacement_text; 1652 replacement_text.push_back( 1653 std::make_pair("REPLACE_WITH_URL", "/" + redirect_path)); 1654 std::string replacement_path; 1655 ASSERT_TRUE(net::SpawnedTestServer::GetFilePathWithReplacements( 1656 "files/prerender/prerender_with_iframe.html", 1657 replacement_text, 1658 &replacement_path)); 1659 PrerenderTestURL(replacement_path, FINAL_STATUS_USED, 2); 1660 EXPECT_FALSE(UrlIsInPrerenderManager(https_url)); 1661 NavigateToDestURL(); 1662} 1663 1664// Checks that server-issued redirects work with prerendering. 1665// This version navigates to the page which issues the redirection, rather 1666// than the final destination page. 1667IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 1668 PrerenderServerRedirectNavigateToFirst) { 1669 PrerenderTestURL(CreateServerRedirect("files/prerender/prerender_page.html"), 1670 FINAL_STATUS_USED, 1671 1); 1672 NavigateToDestURL(); 1673} 1674 1675// Checks that server-issued redirects work with prerendering. 1676// This version navigates to the final destination page, rather than the 1677// page which does the redirection. 1678IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 1679 PrerenderServerRedirectNavigateToSecond) { 1680 PrerenderTestURL(CreateServerRedirect("files/prerender/prerender_page.html"), 1681 FINAL_STATUS_USED, 1682 1); 1683 NavigateToURL("files/prerender/prerender_page.html"); 1684} 1685 1686// Checks that server-issued redirects work with prerendering. 1687// This version navigates to the final destination page, rather than the 1688// page which does the redirection via a mouse click. 1689IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 1690 PrerenderServerRedirectNavigateToSecondViaClick) { 1691 GURL prerender_url = test_server()->GetURL( 1692 CreateServerRedirect("files/prerender/prerender_page.html")); 1693 GURL destination_url = test_server()->GetURL( 1694 "files/prerender/prerender_page.html"); 1695 PrerenderTestURL(prerender_url, destination_url, FINAL_STATUS_USED, 1); 1696 OpenDestURLViaClick(); 1697} 1698 1699// Checks that server-issued redirects from an http to an https 1700// location will cancel prerendering. 1701IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 1702 PrerenderServerRedirectToHttps) { 1703 net::SpawnedTestServer https_server( 1704 net::SpawnedTestServer::TYPE_HTTPS, net::SpawnedTestServer::kLocalhost, 1705 base::FilePath(FILE_PATH_LITERAL("chrome/test/data"))); 1706 ASSERT_TRUE(https_server.Start()); 1707 GURL https_url = https_server.GetURL("files/prerender/prerender_page.html"); 1708 PrerenderTestURL(CreateServerRedirect(https_url.spec()), 1709 FINAL_STATUS_USED, 1710 1); 1711 NavigateToDestURL(); 1712} 1713 1714// Checks that server-issued redirects within an iframe in a prerendered 1715// page will not count as an "alias" for the prerendered page. 1716IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderServerRedirectInIframe) { 1717 std::string redirect_path = CreateServerRedirect( 1718 "/files/prerender/prerender_embedded_content.html"); 1719 std::vector<net::SpawnedTestServer::StringPair> replacement_text; 1720 replacement_text.push_back( 1721 std::make_pair("REPLACE_WITH_URL", "/" + redirect_path)); 1722 std::string replacement_path; 1723 ASSERT_TRUE(net::SpawnedTestServer::GetFilePathWithReplacements( 1724 "files/prerender/prerender_with_iframe.html", 1725 replacement_text, 1726 &replacement_path)); 1727 PrerenderTestURL(replacement_path, FINAL_STATUS_USED, 1); 1728 EXPECT_FALSE(UrlIsInPrerenderManager( 1729 "files/prerender/prerender_embedded_content.html")); 1730 NavigateToDestURL(); 1731} 1732 1733// Checks that server-issued redirects within an iframe in a prerendered 1734// page to an https page will not cancel the prerender, nor will it 1735// count as an "alias" for the prerendered page. 1736IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 1737 DISABLED_PrerenderServerRedirectToHttpsInIframe) { 1738 net::SpawnedTestServer https_server( 1739 net::SpawnedTestServer::TYPE_HTTPS, net::SpawnedTestServer::kLocalhost, 1740 base::FilePath(FILE_PATH_LITERAL("chrome/test/data"))); 1741 ASSERT_TRUE(https_server.Start()); 1742 GURL https_url = https_server.GetURL("files/prerender/prerender_page.html"); 1743 std::string redirect_path = CreateServerRedirect(https_url.spec()); 1744 std::vector<net::SpawnedTestServer::StringPair> replacement_text; 1745 replacement_text.push_back( 1746 std::make_pair("REPLACE_WITH_URL", "/" + redirect_path)); 1747 std::string replacement_path; 1748 ASSERT_TRUE(net::SpawnedTestServer::GetFilePathWithReplacements( 1749 "files/prerender/prerender_with_iframe.html", 1750 replacement_text, 1751 &replacement_path)); 1752 PrerenderTestURL(replacement_path, FINAL_STATUS_USED, 1); 1753 EXPECT_FALSE(UrlIsInPrerenderManager(https_url)); 1754 NavigateToDestURL(); 1755} 1756 1757// Prerenders a page that contains an automatic download triggered through an 1758// iframe. This should not prerender successfully. 1759IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderDownloadIframe) { 1760 PrerenderTestURL("files/prerender/prerender_download_iframe.html", 1761 FINAL_STATUS_DOWNLOAD, 1762 1); 1763} 1764 1765// Prerenders a page that contains an automatic download triggered through 1766// Javascript changing the window.location. This should not prerender 1767// successfully 1768IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderDownloadLocation) { 1769 PrerenderTestURL(CreateClientRedirect("files/download-test1.lib"), 1770 FINAL_STATUS_DOWNLOAD, 1771 1); 1772} 1773 1774// Prerenders a page that contains an automatic download triggered through a 1775// client-issued redirect. This should not prerender successfully. 1776IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderDownloadClientRedirect) { 1777 PrerenderTestURL("files/prerender/prerender_download_refresh.html", 1778 FINAL_STATUS_DOWNLOAD, 1779 1); 1780} 1781 1782// Checks that the referrer is set when prerendering. 1783IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderReferrer) { 1784 PrerenderTestURL("files/prerender/prerender_referrer.html", 1785 FINAL_STATUS_USED, 1786 1); 1787 NavigateToDestURL(); 1788} 1789 1790// Checks that the referrer is not set when prerendering and the source page is 1791// HTTPS. 1792IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 1793 DISABLED_PrerenderNoSSLReferrer) { 1794 set_use_https_src(true); 1795 PrerenderTestURL("files/prerender/prerender_no_referrer.html", 1796 FINAL_STATUS_USED, 1797 1); 1798 NavigateToDestURL(); 1799} 1800 1801// Checks that popups on a prerendered page cause cancellation. 1802IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderPopup) { 1803 PrerenderTestURL("files/prerender/prerender_popup.html", 1804 FINAL_STATUS_CREATE_NEW_WINDOW, 1805 1); 1806} 1807 1808// Checks that registering a protocol handler causes cancellation. 1809IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderRegisterProtocolHandler) { 1810 PrerenderTestURL("files/prerender/prerender_register_protocol_handler.html", 1811 FINAL_STATUS_REGISTER_PROTOCOL_HANDLER, 1812 1); 1813} 1814 1815// Checks that renderers using excessive memory will be terminated. 1816IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderExcessiveMemory) { 1817 ASSERT_TRUE(GetPrerenderManager()); 1818 GetPrerenderManager()->mutable_config().max_bytes = 30 * 1024 * 1024; 1819 PrerenderTestURL("files/prerender/prerender_excessive_memory.html", 1820 FINAL_STATUS_MEMORY_LIMIT_EXCEEDED, 1821 1); 1822} 1823 1824// Checks shutdown code while a prerender is active. 1825IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderQuickQuit) { 1826 PrerenderTestURL("files/prerender/prerender_page.html", 1827 FINAL_STATUS_APP_TERMINATING, 1828 0); 1829} 1830 1831// TODO(gavinp,sreeram): Fix http://crbug.com/145248 and deflake this test. 1832// Checks that we don't prerender in an infinite loop. 1833IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, DISABLED_PrerenderInfiniteLoop) { 1834 const char* const kHtmlFileA = "files/prerender/prerender_infinite_a.html"; 1835 const char* const kHtmlFileB = "files/prerender/prerender_infinite_b.html"; 1836 1837 std::deque<FinalStatus> expected_final_status_queue; 1838 expected_final_status_queue.push_back(FINAL_STATUS_USED); 1839 expected_final_status_queue.push_back(FINAL_STATUS_APP_TERMINATING); 1840 1841 PrerenderTestURL(kHtmlFileA, expected_final_status_queue, 1); 1842 ASSERT_TRUE(GetPrerenderContents()); 1843 GetPrerenderContents()->WaitForPendingPrerenders(1u); 1844 1845 // Next url should be in pending list but not an active entry. 1846 EXPECT_FALSE(UrlIsInPrerenderManager(kHtmlFileB)); 1847 1848 NavigateToDestURL(); 1849 1850 // Make sure the PrerenderContents for the next url is now in the manager 1851 // and not pending. 1852 EXPECT_TRUE(UrlIsInPrerenderManager(kHtmlFileB)); 1853} 1854 1855// TODO(gavinp,sreeram): Fix http://crbug.com/145248 and deflake this test. 1856// Checks that we don't prerender in an infinite loop and multiple links are 1857// handled correctly. 1858IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 1859 DISABLED_PrerenderInfiniteLoopMultiple) { 1860 const char* const kHtmlFileA = 1861 "files/prerender/prerender_infinite_a_multiple.html"; 1862 const char* const kHtmlFileB = 1863 "files/prerender/prerender_infinite_b_multiple.html"; 1864 const char* const kHtmlFileC = 1865 "files/prerender/prerender_infinite_c_multiple.html"; 1866 1867 // This test is conceptually simplest if concurrency is at two, since we 1868 // don't have to worry about which of kHtmlFileB or kHtmlFileC gets evicted. 1869 GetPrerenderManager()->mutable_config().max_link_concurrency = 2; 1870 GetPrerenderManager()->mutable_config().max_link_concurrency_per_launcher = 2; 1871 1872 std::deque<FinalStatus> expected_final_status_queue; 1873 expected_final_status_queue.push_back(FINAL_STATUS_USED); 1874 expected_final_status_queue.push_back(FINAL_STATUS_APP_TERMINATING); 1875 expected_final_status_queue.push_back(FINAL_STATUS_APP_TERMINATING); 1876 1877 PrerenderTestURL(kHtmlFileA, expected_final_status_queue, 1); 1878 ASSERT_TRUE(GetPrerenderContents()); 1879 GetPrerenderContents()->WaitForPendingPrerenders(2u); 1880 1881 // Next url should be in pending list but not an active entry. 1882 EXPECT_FALSE(UrlIsInPrerenderManager(kHtmlFileB)); 1883 EXPECT_FALSE(UrlIsInPrerenderManager(kHtmlFileC)); 1884 1885 NavigateToDestURL(); 1886 1887 // Make sure the PrerenderContents for the next urls are now in the manager 1888 // and not pending. One and only one of the URLs (the last seen) should be the 1889 // active entry. 1890 bool url_b_is_active_prerender = UrlIsInPrerenderManager(kHtmlFileB); 1891 bool url_c_is_active_prerender = UrlIsInPrerenderManager(kHtmlFileC); 1892 EXPECT_TRUE(url_b_is_active_prerender && url_c_is_active_prerender); 1893} 1894 1895// See crbug.com/131836. 1896IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderTaskManager) { 1897 // Show the task manager. This populates the model. 1898 chrome::OpenTaskManager(current_browser()); 1899 // Wait for the model of task manager to start. 1900 TaskManagerBrowserTestUtil::WaitForWebResourceChange(1); 1901 1902 // Start with two resources. 1903 PrerenderTestURL("files/prerender/prerender_page.html", FINAL_STATUS_USED, 1); 1904 1905 // One of the resources that has a WebContents associated with it should have 1906 // the Prerender prefix. 1907 const string16 prefix = 1908 l10n_util::GetStringFUTF16(IDS_TASK_MANAGER_PRERENDER_PREFIX, string16()); 1909 string16 prerender_title; 1910 int num_prerender_tabs = 0; 1911 1912 TaskManagerModel* model = GetModel(); 1913 // The task manager caches values. Force the titles to be fresh. 1914 model->Refresh(); 1915 for (int i = 0; i < model->ResourceCount(); ++i) { 1916 if (model->GetResourceWebContents(i)) { 1917 prerender_title = model->GetResourceTitle(i); 1918 if (StartsWith(prerender_title, prefix, true)) 1919 ++num_prerender_tabs; 1920 } 1921 } 1922 EXPECT_EQ(1, num_prerender_tabs); 1923 const string16 prerender_page_title = prerender_title.substr(prefix.length()); 1924 1925 NavigateToDestURL(); 1926 1927 // There should be no tabs with the Prerender prefix. 1928 const string16 tab_prefix = 1929 l10n_util::GetStringFUTF16(IDS_TASK_MANAGER_TAB_PREFIX, string16()); 1930 num_prerender_tabs = 0; 1931 int num_tabs_with_prerender_page_title = 0; 1932 model->Refresh(); 1933 for (int i = 0; i < model->ResourceCount(); ++i) { 1934 if (model->GetResourceWebContents(i)) { 1935 string16 tab_title = model->GetResourceTitle(i); 1936 if (StartsWith(tab_title, prefix, true)) { 1937 ++num_prerender_tabs; 1938 } else { 1939 EXPECT_TRUE(StartsWith(tab_title, tab_prefix, true)); 1940 1941 // The prerender tab should now be a normal tab but the title should be 1942 // the same. Depending on timing, there may be more than one of these. 1943 const string16 tab_page_title = tab_title.substr(tab_prefix.length()); 1944 if (prerender_page_title.compare(tab_page_title) == 0) 1945 ++num_tabs_with_prerender_page_title; 1946 } 1947 } 1948 } 1949 EXPECT_EQ(0, num_prerender_tabs); 1950 1951 // We may have deleted the prerender tab, but the swapped in tab should be 1952 // active. 1953 EXPECT_GE(num_tabs_with_prerender_page_title, 1); 1954 EXPECT_LE(num_tabs_with_prerender_page_title, 2); 1955} 1956 1957// Checks that audio loads are deferred on prerendering. 1958// Times out under AddressSanitizer, see http://crbug.com/108402 1959IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, DISABLED_PrerenderHTML5Audio) { 1960 PrerenderTestURL("files/prerender/prerender_html5_audio.html", 1961 FINAL_STATUS_USED, 1962 1); 1963 NavigateToDestUrlAndWaitForPassTitle(); 1964} 1965 1966// Checks that audio loads are deferred on prerendering and played back when 1967// the prerender is swapped in if autoplay is set. 1968// Periodically fails on chrome-os. See http://crbug.com/145263 1969IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 1970 DISABLED_PrerenderHTML5AudioAutoplay) { 1971 PrerenderTestURL("files/prerender/prerender_html5_audio_autoplay.html", 1972 FINAL_STATUS_USED, 1973 1); 1974 NavigateToDestUrlAndWaitForPassTitle(); 1975} 1976 1977// Checks that audio loads are deferred on prerendering and played back when 1978// the prerender is swapped in if js starts playing. 1979IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 1980 DISABLED_PrerenderHTML5AudioJsplay) { 1981 PrerenderTestURL("files/prerender/prerender_html5_audio_jsplay.html", 1982 FINAL_STATUS_USED, 1983 1); 1984 NavigateToDestUrlAndWaitForPassTitle(); 1985} 1986 1987// Checks that video loads are deferred on prerendering. 1988IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, DISABLED_PrerenderHTML5Video) { 1989 PrerenderTestURL("files/prerender/prerender_html5_video.html", 1990 FINAL_STATUS_USED, 1991 1); 1992 NavigateToDestUrlAndWaitForPassTitle(); 1993} 1994 1995// Checks that video tags inserted by javascript are deferred and played 1996// correctly on swap in. 1997IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 1998 DISABLED_PrerenderHTML5VideoJs) { 1999 PrerenderTestURL("files/prerender/prerender_html5_video_script.html", 2000 FINAL_STATUS_USED, 2001 1); 2002 NavigateToDestUrlAndWaitForPassTitle(); 2003} 2004 2005// Checks for correct network events by using a busy sleep the javascript. 2006IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2007 DISABLED_PrerenderHTML5VideoNetwork) { 2008 PrerenderTestURL("files/prerender/prerender_html5_video_network.html", 2009 FINAL_STATUS_USED, 2010 1, 2011 true); 2012 NavigateToDestUrlAndWaitForPassTitle(); 2013} 2014 2015// Checks that scripts can retrieve the correct window size while prerendering. 2016#if defined(TOOLKIT_VIEWS) 2017// TODO(beng): Widget hierarchy split causes this to fail http://crbug.com/82363 2018IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, DISABLED_PrerenderWindowSize) { 2019#else 2020IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderWindowSize) { 2021#endif 2022 PrerenderTestURL("files/prerender/prerender_size.html", 2023 FINAL_STATUS_USED, 2024 1); 2025 NavigateToDestURL(); 2026} 2027 2028// Flakily times out: http://crbug.com/171546 2029// Checks that prerenderers will terminate when the RenderView crashes. 2030IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, DISABLED_PrerenderRendererCrash) { 2031 PrerenderTestURL("files/prerender/prerender_page.html", 2032 FINAL_STATUS_RENDERER_CRASHED, 2033 1); 2034 2035 // Navigate to about:crash and then wait for the renderer to crash. 2036 ASSERT_TRUE(GetPrerenderContents()); 2037 ASSERT_TRUE(GetPrerenderContents()->prerender_contents()); 2038 GetPrerenderContents()->prerender_contents()->GetController(). 2039 LoadURL( 2040 GURL(content::kChromeUICrashURL), 2041 content::Referrer(), 2042 content::PAGE_TRANSITION_TYPED, 2043 std::string()); 2044 content::RunMessageLoop(); 2045} 2046 2047IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2048 PrerenderPageWithFragment) { 2049 PrerenderTestURL("files/prerender/prerender_page.html#fragment", 2050 FINAL_STATUS_USED, 2051 1); 2052 2053 ChannelDestructionWatcher channel_close_watcher; 2054 channel_close_watcher.WatchChannel(browser()->tab_strip_model()-> 2055 GetActiveWebContents()->GetRenderProcessHost()); 2056 NavigateToDestURL(); 2057 channel_close_watcher.WaitForChannelClose(); 2058 2059 ASSERT_TRUE(IsEmptyPrerenderLinkManager()); 2060} 2061 2062// Checks that we correctly use a prerendered page when navigating to a 2063// fragment. 2064// DISABLED: http://crbug.com/84154 2065IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2066 DISABLED_PrerenderPageNavigateFragment) { 2067 PrerenderTestURL("files/prerender/no_prerender_page.html", 2068 FINAL_STATUS_APP_TERMINATING, 2069 1); 2070 NavigateToURL("files/prerender/no_prerender_page.html#fragment"); 2071} 2072 2073// Checks that we correctly use a prerendered page when we prerender a fragment 2074// but navigate to the main page. 2075// http://crbug.com/83901 2076IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2077 DISABLED_PrerenderFragmentNavigatePage) { 2078 PrerenderTestURL("files/prerender/no_prerender_page.html#fragment", 2079 FINAL_STATUS_APP_TERMINATING, 2080 1); 2081 NavigateToURL("files/prerender/no_prerender_page.html"); 2082} 2083 2084// Checks that we correctly use a prerendered page when we prerender a fragment 2085// but navigate to a different fragment on the same page. 2086// DISABLED: http://crbug.com/84154 2087IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2088 DISABLED_PrerenderFragmentNavigateFragment) { 2089 PrerenderTestURL("files/prerender/no_prerender_page.html#other_fragment", 2090 FINAL_STATUS_APP_TERMINATING, 2091 1); 2092 NavigateToURL("files/prerender/no_prerender_page.html#fragment"); 2093} 2094 2095// Checks that we correctly use a prerendered page when the page uses a client 2096// redirect to refresh from a fragment on the same page. 2097// http://crbug.com/83901 2098IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2099 DISABLED_PrerenderClientRedirectFromFragment) { 2100 PrerenderTestURL( 2101 CreateClientRedirect("files/prerender/no_prerender_page.html#fragment"), 2102 FINAL_STATUS_APP_TERMINATING, 2103 2); 2104 NavigateToURL("files/prerender/no_prerender_page.html"); 2105} 2106 2107// Checks that we correctly use a prerendered page when the page uses a client 2108// redirect to refresh to a fragment on the same page. 2109// DISABLED: http://crbug.com/84154 2110IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2111 DISABLED_PrerenderClientRedirectToFragment) { 2112 PrerenderTestURL( 2113 CreateClientRedirect("files/prerender/no_prerender_page.html"), 2114 FINAL_STATUS_APP_TERMINATING, 2115 2); 2116 NavigateToURL("files/prerender/no_prerender_page.html#fragment"); 2117} 2118 2119// Checks that we correctly use a prerendered page when the page uses JS to set 2120// the window.location.hash to a fragment on the same page. 2121IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2122 PrerenderPageChangeFragmentLocationHash) { 2123 PrerenderTestURL("files/prerender/prerender_fragment_location_hash.html", 2124 FINAL_STATUS_USED, 2125 1); 2126 NavigateToURL("files/prerender/prerender_fragment_location_hash.html"); 2127} 2128 2129// Checks that prerendering a PNG works correctly. 2130IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderImagePng) { 2131 DisableJavascriptCalls(); 2132 PrerenderTestURL("files/prerender/image.png", FINAL_STATUS_USED, 1); 2133 NavigateToDestURL(); 2134} 2135 2136// Checks that prerendering a JPG works correctly. 2137IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderImageJpeg) { 2138 DisableJavascriptCalls(); 2139 PrerenderTestURL("files/prerender/image.jpeg", FINAL_STATUS_USED, 1); 2140 NavigateToDestURL(); 2141} 2142 2143// Checks that a prerender of a CRX will result in a cancellation due to 2144// download. 2145IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderCrx) { 2146 PrerenderTestURL("files/prerender/extension.crx", FINAL_STATUS_DOWNLOAD, 1); 2147} 2148 2149// Checks that xhr GET requests allow prerenders. 2150IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderXhrGet) { 2151 PrerenderTestURL("files/prerender/prerender_xhr_get.html", 2152 FINAL_STATUS_USED, 2153 1); 2154 NavigateToDestURL(); 2155} 2156 2157// Checks that xhr HEAD requests allow prerenders. 2158IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderXhrHead) { 2159 PrerenderTestURL("files/prerender/prerender_xhr_head.html", 2160 FINAL_STATUS_USED, 2161 1); 2162 NavigateToDestURL(); 2163} 2164 2165// Checks that xhr OPTIONS requests allow prerenders. 2166IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderXhrOptions) { 2167 PrerenderTestURL("files/prerender/prerender_xhr_options.html", 2168 FINAL_STATUS_USED, 2169 1); 2170 NavigateToDestURL(); 2171} 2172 2173// Checks that xhr TRACE requests allow prerenders. 2174IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderXhrTrace) { 2175 PrerenderTestURL("files/prerender/prerender_xhr_trace.html", 2176 FINAL_STATUS_USED, 2177 1); 2178 NavigateToDestURL(); 2179} 2180 2181// Checks that xhr POST requests allow prerenders. 2182IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, DISABLED_PrerenderXhrPost) { 2183 PrerenderTestURL("files/prerender/prerender_xhr_post.html", 2184 FINAL_STATUS_USED, 2185 1); 2186 NavigateToDestURL(); 2187} 2188 2189// Checks that xhr PUT cancels prerenders. 2190IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderXhrPut) { 2191 PrerenderTestURL("files/prerender/prerender_xhr_put.html", 2192 FINAL_STATUS_INVALID_HTTP_METHOD, 2193 1); 2194} 2195 2196// Checks that xhr DELETE cancels prerenders. 2197IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderXhrDelete) { 2198 PrerenderTestURL("files/prerender/prerender_xhr_delete.html", 2199 FINAL_STATUS_INVALID_HTTP_METHOD, 2200 1); 2201} 2202 2203// Checks that a top-level page which would trigger an SSL error is canceled. 2204IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderSSLErrorTopLevel) { 2205 net::SpawnedTestServer::SSLOptions ssl_options; 2206 ssl_options.server_certificate = 2207 net::SpawnedTestServer::SSLOptions::CERT_MISMATCHED_NAME; 2208 net::SpawnedTestServer https_server( 2209 net::SpawnedTestServer::TYPE_HTTPS, ssl_options, 2210 base::FilePath(FILE_PATH_LITERAL("chrome/test/data"))); 2211 ASSERT_TRUE(https_server.Start()); 2212 GURL https_url = https_server.GetURL("files/prerender/prerender_page.html"); 2213 PrerenderTestURL(https_url, 2214 FINAL_STATUS_SSL_ERROR, 2215 1); 2216} 2217 2218// Checks that an SSL error that comes from a subresource does not cancel 2219// the page. Non-main-frame requests are simply cancelled if they run into 2220// an SSL problem. 2221IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderSSLErrorSubresource) { 2222 net::SpawnedTestServer::SSLOptions ssl_options; 2223 ssl_options.server_certificate = 2224 net::SpawnedTestServer::SSLOptions::CERT_MISMATCHED_NAME; 2225 net::SpawnedTestServer https_server( 2226 net::SpawnedTestServer::TYPE_HTTPS, ssl_options, 2227 base::FilePath(FILE_PATH_LITERAL("chrome/test/data"))); 2228 ASSERT_TRUE(https_server.Start()); 2229 GURL https_url = https_server.GetURL("files/prerender/image.jpeg"); 2230 std::vector<net::SpawnedTestServer::StringPair> replacement_text; 2231 replacement_text.push_back( 2232 std::make_pair("REPLACE_WITH_IMAGE_URL", https_url.spec())); 2233 std::string replacement_path; 2234 ASSERT_TRUE(net::SpawnedTestServer::GetFilePathWithReplacements( 2235 "files/prerender/prerender_with_image.html", 2236 replacement_text, 2237 &replacement_path)); 2238 PrerenderTestURL(replacement_path, FINAL_STATUS_USED, 1); 2239 NavigateToDestURL(); 2240} 2241 2242// Checks that an SSL error that comes from an iframe does not cancel 2243// the page. Non-main-frame requests are simply cancelled if they run into 2244// an SSL problem. 2245IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderSSLErrorIframe) { 2246 net::SpawnedTestServer::SSLOptions ssl_options; 2247 ssl_options.server_certificate = 2248 net::SpawnedTestServer::SSLOptions::CERT_MISMATCHED_NAME; 2249 net::SpawnedTestServer https_server( 2250 net::SpawnedTestServer::TYPE_HTTPS, ssl_options, 2251 base::FilePath(FILE_PATH_LITERAL("chrome/test/data"))); 2252 ASSERT_TRUE(https_server.Start()); 2253 GURL https_url = https_server.GetURL( 2254 "files/prerender/prerender_embedded_content.html"); 2255 std::vector<net::SpawnedTestServer::StringPair> replacement_text; 2256 replacement_text.push_back( 2257 std::make_pair("REPLACE_WITH_URL", https_url.spec())); 2258 std::string replacement_path; 2259 ASSERT_TRUE(net::SpawnedTestServer::GetFilePathWithReplacements( 2260 "files/prerender/prerender_with_iframe.html", 2261 replacement_text, 2262 &replacement_path)); 2263 PrerenderTestURL(replacement_path, FINAL_STATUS_USED, 1); 2264 NavigateToDestURL(); 2265} 2266 2267// Checks that we cancel correctly when window.print() is called. 2268IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderPrint) { 2269 PrerenderTestURL("files/prerender/prerender_print.html", 2270 FINAL_STATUS_WINDOW_PRINT, 2271 1); 2272} 2273 2274// Checks that if a page is opened in a new window by javascript and both the 2275// pages are in the same domain, the prerendered page is not used. 2276IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2277 PrerenderSameDomainWindowOpenerWindowOpen) { 2278 PrerenderTestURL("files/prerender/prerender_page.html", 2279 FINAL_STATUS_APP_TERMINATING, 2280 1); 2281 OpenDestURLViaWindowOpen(); 2282} 2283 2284// Checks that if a page is opened due to click on a href with target="_blank" 2285// and both pages are in the same domain the prerendered page is not used. 2286IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2287 PrerenderSameDomainWindowOpenerClickTarget) { 2288 PrerenderTestURL("files/prerender/prerender_page.html", 2289 FINAL_STATUS_APP_TERMINATING, 2290 1); 2291 OpenDestURLViaClickTarget(); 2292} 2293 2294// Checks that a top-level page which would normally request an SSL client 2295// certificate will never be seen since it's an https top-level resource. 2296IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderSSLClientCertTopLevel) { 2297 net::SpawnedTestServer::SSLOptions ssl_options; 2298 ssl_options.request_client_certificate = true; 2299 net::SpawnedTestServer https_server( 2300 net::SpawnedTestServer::TYPE_HTTPS, ssl_options, 2301 base::FilePath(FILE_PATH_LITERAL("chrome/test/data"))); 2302 ASSERT_TRUE(https_server.Start()); 2303 GURL https_url = https_server.GetURL("files/prerender/prerender_page.html"); 2304 PrerenderTestURL(https_url, FINAL_STATUS_SSL_CLIENT_CERTIFICATE_REQUESTED, 1); 2305} 2306 2307// Checks that an SSL Client Certificate request that originates from a 2308// subresource will cancel the prerendered page. 2309IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2310 PrerenderSSLClientCertSubresource) { 2311 net::SpawnedTestServer::SSLOptions ssl_options; 2312 ssl_options.request_client_certificate = true; 2313 net::SpawnedTestServer https_server( 2314 net::SpawnedTestServer::TYPE_HTTPS, ssl_options, 2315 base::FilePath(FILE_PATH_LITERAL("chrome/test/data"))); 2316 ASSERT_TRUE(https_server.Start()); 2317 GURL https_url = https_server.GetURL("files/prerender/image.jpeg"); 2318 std::vector<net::SpawnedTestServer::StringPair> replacement_text; 2319 replacement_text.push_back( 2320 std::make_pair("REPLACE_WITH_IMAGE_URL", https_url.spec())); 2321 std::string replacement_path; 2322 ASSERT_TRUE(net::SpawnedTestServer::GetFilePathWithReplacements( 2323 "files/prerender/prerender_with_image.html", 2324 replacement_text, 2325 &replacement_path)); 2326 PrerenderTestURL(replacement_path, 2327 FINAL_STATUS_SSL_CLIENT_CERTIFICATE_REQUESTED, 2328 1); 2329} 2330 2331// Checks that an SSL Client Certificate request that originates from an 2332// iframe will cancel the prerendered page. 2333IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderSSLClientCertIframe) { 2334 net::SpawnedTestServer::SSLOptions ssl_options; 2335 ssl_options.request_client_certificate = true; 2336 net::SpawnedTestServer https_server( 2337 net::SpawnedTestServer::TYPE_HTTPS, ssl_options, 2338 base::FilePath(FILE_PATH_LITERAL("chrome/test/data"))); 2339 ASSERT_TRUE(https_server.Start()); 2340 GURL https_url = https_server.GetURL( 2341 "files/prerender/prerender_embedded_content.html"); 2342 std::vector<net::SpawnedTestServer::StringPair> replacement_text; 2343 replacement_text.push_back( 2344 std::make_pair("REPLACE_WITH_URL", https_url.spec())); 2345 std::string replacement_path; 2346 ASSERT_TRUE(net::SpawnedTestServer::GetFilePathWithReplacements( 2347 "files/prerender/prerender_with_iframe.html", 2348 replacement_text, 2349 &replacement_path)); 2350 PrerenderTestURL(replacement_path, 2351 FINAL_STATUS_SSL_CLIENT_CERTIFICATE_REQUESTED, 2352 1); 2353} 2354 2355#if defined(FULL_SAFE_BROWSING) 2356// Ensures that we do not prerender pages with a safe browsing 2357// interstitial. 2358IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderSafeBrowsingTopLevel) { 2359 GURL url = test_server()->GetURL("files/prerender/prerender_page.html"); 2360 GetFakeSafeBrowsingDatabaseManager()->SetThreatTypeForUrl( 2361 url, SB_THREAT_TYPE_URL_MALWARE); 2362 PrerenderTestURL("files/prerender/prerender_page.html", 2363 FINAL_STATUS_SAFE_BROWSING, 1); 2364} 2365 2366// Ensures that server redirects to a malware page will cancel prerenders. 2367IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2368 PrerenderSafeBrowsingServerRedirect) { 2369 GURL url = test_server()->GetURL("files/prerender/prerender_page.html"); 2370 GetFakeSafeBrowsingDatabaseManager()->SetThreatTypeForUrl( 2371 url, SB_THREAT_TYPE_URL_MALWARE); 2372 PrerenderTestURL(CreateServerRedirect("files/prerender/prerender_page.html"), 2373 FINAL_STATUS_SAFE_BROWSING, 2374 1); 2375} 2376 2377// Ensures that client redirects to a malware page will cancel prerenders. 2378IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2379 PrerenderSafeBrowsingClientRedirect) { 2380 GURL url = test_server()->GetURL("files/prerender/prerender_page.html"); 2381 GetFakeSafeBrowsingDatabaseManager()->SetThreatTypeForUrl( 2382 url, SB_THREAT_TYPE_URL_MALWARE); 2383 PrerenderTestURL(CreateClientRedirect("files/prerender/prerender_page.html"), 2384 FINAL_STATUS_SAFE_BROWSING, 2385 1); 2386} 2387 2388// Ensures that we do not prerender pages which have a malware subresource. 2389IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderSafeBrowsingSubresource) { 2390 GURL image_url = test_server()->GetURL("files/prerender/image.jpeg"); 2391 GetFakeSafeBrowsingDatabaseManager()->SetThreatTypeForUrl( 2392 image_url, SB_THREAT_TYPE_URL_MALWARE); 2393 std::vector<net::SpawnedTestServer::StringPair> replacement_text; 2394 replacement_text.push_back( 2395 std::make_pair("REPLACE_WITH_IMAGE_URL", image_url.spec())); 2396 std::string replacement_path; 2397 ASSERT_TRUE(net::SpawnedTestServer::GetFilePathWithReplacements( 2398 "files/prerender/prerender_with_image.html", 2399 replacement_text, 2400 &replacement_path)); 2401 PrerenderTestURL(replacement_path, 2402 FINAL_STATUS_SAFE_BROWSING, 2403 1); 2404} 2405 2406// Ensures that we do not prerender pages which have a malware iframe. 2407IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderSafeBrowsingIframe) { 2408 GURL iframe_url = test_server()->GetURL( 2409 "files/prerender/prerender_embedded_content.html"); 2410 GetFakeSafeBrowsingDatabaseManager()->SetThreatTypeForUrl( 2411 iframe_url, SB_THREAT_TYPE_URL_MALWARE); 2412 std::vector<net::SpawnedTestServer::StringPair> replacement_text; 2413 replacement_text.push_back( 2414 std::make_pair("REPLACE_WITH_URL", iframe_url.spec())); 2415 std::string replacement_path; 2416 ASSERT_TRUE(net::SpawnedTestServer::GetFilePathWithReplacements( 2417 "files/prerender/prerender_with_iframe.html", 2418 replacement_text, 2419 &replacement_path)); 2420 PrerenderTestURL(replacement_path, 2421 FINAL_STATUS_SAFE_BROWSING, 2422 1); 2423} 2424 2425#endif 2426 2427// Checks that a local storage read will not cause prerender to fail. 2428IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderLocalStorageRead) { 2429 PrerenderTestURL("files/prerender/prerender_localstorage_read.html", 2430 FINAL_STATUS_USED, 2431 1); 2432 NavigateToDestURL(); 2433} 2434 2435// Checks that a local storage write will not cause prerender to fail. 2436IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderLocalStorageWrite) { 2437 PrerenderTestURL("files/prerender/prerender_localstorage_write.html", 2438 FINAL_STATUS_USED, 2439 1); 2440 NavigateToDestURL(); 2441} 2442 2443// Checks that the favicon is properly loaded on prerender. 2444IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2445 DISABLED_PrerenderFavicon) { 2446 PrerenderTestURL("files/prerender/prerender_favicon.html", 2447 FINAL_STATUS_USED, 2448 1); 2449 TestPrerenderContents* prerender_contents = GetPrerenderContents(); 2450 ASSERT_TRUE(prerender_contents != NULL); 2451 content::WindowedNotificationObserver favicon_update_watcher( 2452 chrome::NOTIFICATION_FAVICON_UPDATED, 2453 content::Source<WebContents>(prerender_contents->prerender_contents())); 2454 NavigateToDestURL(); 2455 favicon_update_watcher.Wait(); 2456} 2457 2458// Checks that when a prerendered page is swapped in to a referring page, the 2459// unload handlers on the referring page are executed. 2460// Fails about 50% on CrOS, 5-10% on linux, win, mac. http://crbug.com/128986 2461IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, DISABLED_PrerenderUnload) { 2462 set_loader_path("files/prerender/prerender_loader_with_unload.html"); 2463 PrerenderTestURL("files/prerender/prerender_page.html", FINAL_STATUS_USED, 1); 2464 string16 expected_title = ASCIIToUTF16("Unloaded"); 2465 content::TitleWatcher title_watcher( 2466 current_browser()->tab_strip_model()->GetActiveWebContents(), 2467 expected_title); 2468 NavigateToDestURL(); 2469 EXPECT_EQ(expected_title, title_watcher.WaitAndGetTitle()); 2470} 2471 2472// Checks that when the history is cleared, prerendering is cancelled and 2473// prerendering history is cleared. 2474IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderClearHistory) { 2475 PrerenderTestURL("files/prerender/prerender_page.html", 2476 FINAL_STATUS_CACHE_OR_HISTORY_CLEARED, 2477 1); 2478 2479 // Post a task to clear the history, and run the message loop until it 2480 // destroys the prerender. 2481 base::MessageLoop::current()->PostTask( 2482 FROM_HERE, 2483 base::Bind(&ClearBrowsingData, current_browser(), 2484 BrowsingDataRemover::REMOVE_HISTORY)); 2485 content::RunMessageLoop(); 2486 2487 // Make sure prerender history was cleared. 2488 EXPECT_EQ(0, GetHistoryLength()); 2489} 2490 2491// Checks that when the cache is cleared, prerenders are cancelled but 2492// prerendering history is not cleared. 2493// Flaky/times out on linux_aura, win, mac - http://crbug.com/270948 2494IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, DISABLED_PrerenderClearCache) { 2495 PrerenderTestURL("files/prerender/prerender_page.html", 2496 FINAL_STATUS_CACHE_OR_HISTORY_CLEARED, 2497 1); 2498 2499 // Post a task to clear the cache, and run the message loop until it 2500 // destroys the prerender. 2501 base::MessageLoop::current()->PostTask(FROM_HERE, 2502 base::Bind(&ClearBrowsingData, current_browser(), 2503 BrowsingDataRemover::REMOVE_CACHE)); 2504 content::RunMessageLoop(); 2505 2506 // Make sure prerender history was not cleared. Not a vital behavior, but 2507 // used to compare with PrerenderClearHistory test. 2508 EXPECT_EQ(1, GetHistoryLength()); 2509} 2510 2511IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderCancelAll) { 2512 PrerenderTestURL("files/prerender/prerender_page.html", 2513 FINAL_STATUS_CANCELLED, 2514 1); 2515 // Post a task to cancel all the prerenders. 2516 base::MessageLoop::current()->PostTask( 2517 FROM_HERE, base::Bind(&CancelAllPrerenders, GetPrerenderManager())); 2518 content::RunMessageLoop(); 2519 EXPECT_TRUE(GetPrerenderContents() == NULL); 2520} 2521 2522IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderEvents) { 2523 PrerenderTestURL("files/prerender/prerender_page.html", 2524 FINAL_STATUS_CANCELLED, 1); 2525 EXPECT_TRUE(DidReceivePrerenderStartEventForLinkNumber(0)); 2526 EXPECT_TRUE(DidReceivePrerenderLoadEventForLinkNumber(0)); 2527 EXPECT_FALSE(DidReceivePrerenderStopEventForLinkNumber(0)); 2528 2529 base::MessageLoop::current()->PostTask( 2530 FROM_HERE, base::Bind(&CancelAllPrerenders, GetPrerenderManager())); 2531 content::RunMessageLoop(); 2532 2533 EXPECT_TRUE(DidReceivePrerenderStartEventForLinkNumber(0)); 2534 EXPECT_TRUE(DidReceivePrerenderStopEventForLinkNumber(0)); 2535 EXPECT_FALSE(HadPrerenderEventErrors()); 2536} 2537 2538// Cancels the prerender of a page with its own prerender. The second prerender 2539// should never be started. 2540IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2541 PrerenderCancelPrerenderWithPrerender) { 2542 PrerenderTestURL("files/prerender/prerender_infinite_a.html", 2543 FINAL_STATUS_CANCELLED, 2544 1); 2545 // Post a task to cancel all the prerenders. 2546 base::MessageLoop::current()->PostTask( 2547 FROM_HERE, base::Bind(&CancelAllPrerenders, GetPrerenderManager())); 2548 content::RunMessageLoop(); 2549 EXPECT_TRUE(GetPrerenderContents() == NULL); 2550} 2551 2552// PrerenderBrowserTest.PrerenderEventsNoLoad may pass flakily on regression, 2553// so please be aggressive about filing bugs when this test is failing. 2554IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderEventsNoLoad) { 2555 // This should be canceled. 2556 PrerenderTestURL("files/prerender/prerender_http_auth_container.html", 2557 FINAL_STATUS_AUTH_NEEDED, 2558 1); 2559 EXPECT_TRUE(DidReceivePrerenderStartEventForLinkNumber(0)); 2560 EXPECT_FALSE(DidReceivePrerenderLoadEventForLinkNumber(0)); 2561 EXPECT_FALSE(DidReceivePrerenderStopEventForLinkNumber(0)); 2562 EXPECT_FALSE(HadPrerenderEventErrors()); 2563} 2564 2565// Prerendering and history tests. 2566// The prerendered page is navigated to in several ways [navigate via 2567// omnibox, click on link, key-modified click to open in background tab, etc], 2568// followed by a navigation to another page from the prerendered page, followed 2569// by a back navigation. 2570 2571IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2572 DISABLED_PrerenderNavigateClickGoBack) { 2573 PrerenderTestURL("files/prerender/prerender_page_with_link.html", 2574 FINAL_STATUS_USED, 2575 1); 2576 NavigateToDestURL(); 2577 ClickToNextPageAfterPrerender(); 2578 GoBackToPrerender(); 2579} 2580 2581// Disabled due to timeouts on commit queue. 2582// http://crbug.com/121130 2583IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2584 DISABLED_PrerenderNavigateNavigateGoBack) { 2585 PrerenderTestURL("files/prerender/prerender_page_with_link.html", 2586 FINAL_STATUS_USED, 2587 1); 2588 NavigateToDestURL(); 2589 NavigateToNextPageAfterPrerender(); 2590 GoBackToPrerender(); 2591} 2592 2593IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2594 DISABLED_PrerenderClickClickGoBack) { 2595 PrerenderTestURL("files/prerender/prerender_page_with_link.html", 2596 FINAL_STATUS_USED, 2597 1); 2598 OpenDestURLViaClick(); 2599 ClickToNextPageAfterPrerender(); 2600 GoBackToPrerender(); 2601} 2602 2603// Disabled due to timeouts on commit queue. 2604// http://crbug.com/121130 2605IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2606 DISABLED_PrerenderClickNavigateGoBack) { 2607 PrerenderTestURL("files/prerender/prerender_page_with_link.html", 2608 FINAL_STATUS_USED, 2609 1); 2610 OpenDestURLViaClick(); 2611 NavigateToNextPageAfterPrerender(); 2612 GoBackToPrerender(); 2613} 2614 2615IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderClickNewWindow) { 2616 PrerenderTestURL("files/prerender/prerender_page_with_link.html", 2617 FINAL_STATUS_APP_TERMINATING, 2618 1); 2619 OpenDestURLViaClickNewWindow(); 2620} 2621 2622IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderClickNewForegroundTab) { 2623 PrerenderTestURL("files/prerender/prerender_page_with_link.html", 2624 FINAL_STATUS_APP_TERMINATING, 2625 1); 2626 OpenDestURLViaClickNewForegroundTab(); 2627} 2628 2629IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2630 DISABLED_PrerenderClickNewBackgroundTab) { 2631 PrerenderTestURL("files/prerender/prerender_page_with_link.html", 2632 FINAL_STATUS_APP_TERMINATING, 2633 1); 2634 OpenDestURLViaClickNewBackgroundTab(); 2635} 2636 2637IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2638 NavigateToPrerenderedPageWhenDevToolsAttached) { 2639 DisableJavascriptCalls(); 2640 WebContents* web_contents = 2641 current_browser()->tab_strip_model()->GetActiveWebContents(); 2642 scoped_refptr<DevToolsAgentHost> agent(DevToolsAgentHost::GetOrCreateFor( 2643 web_contents->GetRenderViewHost())); 2644 DevToolsManager* manager = DevToolsManager::GetInstance(); 2645 FakeDevToolsClientHost client_host; 2646 manager->RegisterDevToolsClientHostFor(agent.get(), &client_host); 2647 const char* url = "files/prerender/prerender_page.html"; 2648 PrerenderTestURL(url, FINAL_STATUS_DEVTOOLS_ATTACHED, 1); 2649 NavigateToURL(url); 2650 manager->ClientHostClosing(&client_host); 2651} 2652 2653// Validate that the sessionStorage namespace remains the same when swapping 2654// in a prerendered page. 2655IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2656 DISABLED_PrerenderSessionStorage) { 2657 set_loader_path("files/prerender/prerender_loader_with_session_storage.html"); 2658 PrerenderTestURL(GetCrossDomainTestUrl("files/prerender/prerender_page.html"), 2659 FINAL_STATUS_USED, 2660 1); 2661 NavigateToDestURL(); 2662 GoBackToPageBeforePrerender(); 2663} 2664 2665#if defined(OS_MACOSX) 2666// http://crbug.com/142535 - Times out on Chrome Mac release builder 2667#define MAYBE_ControlGroup DISABLED_ControlGroup 2668#else 2669#define MAYBE_ControlGroup ControlGroup 2670#endif 2671// Checks that the control group works. A JS alert cannot be detected in the 2672// control group. 2673IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, MAYBE_ControlGroup) { 2674 RestorePrerenderMode restore_prerender_mode; 2675 PrerenderManager::SetMode( 2676 PrerenderManager::PRERENDER_MODE_EXPERIMENT_CONTROL_GROUP); 2677 PrerenderTestURL("files/prerender/prerender_alert_before_onload.html", 2678 FINAL_STATUS_WOULD_HAVE_BEEN_USED, 0); 2679 NavigateToDestURL(); 2680} 2681 2682// Make sure that the MatchComplete dummy works in the normal case. Once 2683// a prerender is cancelled because of a script, a dummy must be created to 2684// account for the MatchComplete case, and it must have a final status of 2685// FINAL_STATUS_WOULD_HAVE_BEEN_USED. 2686#if defined(OS_MACOSX) 2687// http://crbug.com/142912 - Times out on Chrome Mac release builder 2688#define MAYBE_MatchCompleteDummy DISABLED_MatchCompleteDummy 2689#else 2690#define MAYBE_MatchCompleteDummy MatchCompleteDummy 2691#endif 2692IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, MAYBE_MatchCompleteDummy) { 2693 std::deque<FinalStatus> expected_final_status_queue; 2694 expected_final_status_queue.push_back(FINAL_STATUS_JAVASCRIPT_ALERT); 2695 expected_final_status_queue.push_back(FINAL_STATUS_WOULD_HAVE_BEEN_USED); 2696 PrerenderTestURL("files/prerender/prerender_alert_before_onload.html", 2697 expected_final_status_queue, 1); 2698 NavigateToDestURL(); 2699} 2700 2701class PrerenderBrowserTestWithNaCl : public PrerenderBrowserTest { 2702 public: 2703 PrerenderBrowserTestWithNaCl() {} 2704 virtual ~PrerenderBrowserTestWithNaCl() {} 2705 2706 virtual void SetUpCommandLine(CommandLine* command_line) OVERRIDE { 2707 PrerenderBrowserTest::SetUpCommandLine(command_line); 2708 command_line->AppendSwitch(switches::kEnableNaCl); 2709 } 2710}; 2711 2712// Check that NaCl plugins work when enabled, with prerendering. 2713IN_PROC_BROWSER_TEST_F(PrerenderBrowserTestWithNaCl, 2714 PrerenderNaClPluginEnabled) { 2715#if defined(OS_WIN) && defined(USE_ASH) 2716 // Disable this test in Metro+Ash for now (http://crbug.com/262796). 2717 if (CommandLine::ForCurrentProcess()->HasSwitch(switches::kAshBrowserTests)) 2718 return; 2719#endif 2720 2721 PrerenderTestURL("files/prerender/prerender_plugin_nacl_enabled.html", 2722 FINAL_STATUS_USED, 2723 1); 2724 NavigateToDestURL(); 2725 2726 // To avoid any chance of a race, we have to let the script send its response 2727 // asynchronously. 2728 WebContents* web_contents = 2729 browser()->tab_strip_model()->GetActiveWebContents(); 2730 bool display_test_result = false; 2731 ASSERT_TRUE(content::ExecuteScriptAndExtractBool(web_contents, 2732 "DidDisplayReallyPass()", 2733 &display_test_result)); 2734 ASSERT_TRUE(display_test_result); 2735} 2736 2737// Checks that the referrer policy is used when prerendering. 2738IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderReferrerPolicy) { 2739 set_loader_path("files/prerender/prerender_loader_with_referrer_policy.html"); 2740 PrerenderTestURL("files/prerender/prerender_referrer_policy.html", 2741 FINAL_STATUS_USED, 2742 1); 2743 NavigateToDestURL(); 2744} 2745 2746// Checks that the referrer policy is used when prerendering on HTTPS. 2747IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2748 DISABLED_PrerenderSSLReferrerPolicy) { 2749 set_use_https_src(true); 2750 set_loader_path("files/prerender/prerender_loader_with_referrer_policy.html"); 2751 PrerenderTestURL("files/prerender/prerender_referrer_policy.html", 2752 FINAL_STATUS_USED, 2753 1); 2754 NavigateToDestURL(); 2755} 2756 2757// Test interaction of the webNavigation and tabs API with prerender. 2758class PrerenderBrowserTestWithExtensions : public PrerenderBrowserTest, 2759 public ExtensionApiTest { 2760 public: 2761 virtual void SetUp() OVERRIDE { 2762 PrerenderBrowserTest::SetUp(); 2763 } 2764 2765 virtual void SetUpCommandLine(CommandLine* command_line) OVERRIDE { 2766 PrerenderBrowserTest::SetUpCommandLine(command_line); 2767 ExtensionApiTest::SetUpCommandLine(command_line); 2768 } 2769 2770 virtual void SetUpInProcessBrowserTestFixture() OVERRIDE { 2771 PrerenderBrowserTest::SetUpInProcessBrowserTestFixture(); 2772 ExtensionApiTest::SetUpInProcessBrowserTestFixture(); 2773 } 2774 2775 virtual void TearDownInProcessBrowserTestFixture() OVERRIDE { 2776 PrerenderBrowserTest::TearDownInProcessBrowserTestFixture(); 2777 ExtensionApiTest::TearDownInProcessBrowserTestFixture(); 2778 } 2779 2780 virtual void SetUpOnMainThread() OVERRIDE { 2781 PrerenderBrowserTest::SetUpOnMainThread(); 2782 } 2783}; 2784 2785// http://crbug.com/177163 2786IN_PROC_BROWSER_TEST_F(PrerenderBrowserTestWithExtensions, 2787 DISABLED_WebNavigation) { 2788 ASSERT_TRUE(StartEmbeddedTestServer()); 2789 extensions::FrameNavigationState::set_allow_extension_scheme(true); 2790 2791 CommandLine::ForCurrentProcess()->AppendSwitch( 2792 extensions::switches::kAllowLegacyExtensionManifests); 2793 2794 // Wait for the extension to set itself up and return control to us. 2795 ASSERT_TRUE( 2796 RunExtensionSubtest("webnavigation", "test_prerender.html")) << message_; 2797 2798 ResultCatcher catcher; 2799 2800 PrerenderTestURL("files/prerender/prerender_page.html", FINAL_STATUS_USED, 1); 2801 2802 ChannelDestructionWatcher channel_close_watcher; 2803 channel_close_watcher.WatchChannel(browser()->tab_strip_model()-> 2804 GetActiveWebContents()->GetRenderProcessHost()); 2805 NavigateToDestURL(); 2806 channel_close_watcher.WaitForChannelClose(); 2807 2808 ASSERT_TRUE(IsEmptyPrerenderLinkManager()); 2809 ASSERT_TRUE(catcher.GetNextResult()) << catcher.message(); 2810} 2811 2812// Fails often on Windows dbg bots. http://crbug.com/177163 2813#if defined(OS_WIN) 2814#define MAYBE_TabsApi DISABLED_TabsApi 2815#else 2816#define MAYBE_TabsApi TabsApi 2817#endif // defined(OS_WIN) 2818IN_PROC_BROWSER_TEST_F(PrerenderBrowserTestWithExtensions, MAYBE_TabsApi) { 2819 ASSERT_TRUE(StartEmbeddedTestServer()); 2820 extensions::FrameNavigationState::set_allow_extension_scheme(true); 2821 2822 // Wait for the extension to set itself up and return control to us. 2823 ASSERT_TRUE(RunExtensionSubtest("tabs/on_replaced", "on_replaced.html")) 2824 << message_; 2825 2826 ResultCatcher catcher; 2827 2828 PrerenderTestURL("files/prerender/prerender_page.html", FINAL_STATUS_USED, 1); 2829 2830 ChannelDestructionWatcher channel_close_watcher; 2831 channel_close_watcher.WatchChannel(browser()->tab_strip_model()-> 2832 GetActiveWebContents()->GetRenderProcessHost()); 2833 NavigateToDestURL(); 2834 channel_close_watcher.WaitForChannelClose(); 2835 2836 ASSERT_TRUE(IsEmptyPrerenderLinkManager()); 2837 ASSERT_TRUE(catcher.GetNextResult()) << catcher.message(); 2838} 2839 2840// Checks that non-http/https/chrome-extension subresource cancels the 2841// prerender. 2842IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2843 DISABLED_PrerenderCancelSubresourceUnsupportedScheme) { 2844 GURL image_url = GURL("invalidscheme://www.google.com/test.jpg"); 2845 std::vector<net::SpawnedTestServer::StringPair> replacement_text; 2846 replacement_text.push_back( 2847 std::make_pair("REPLACE_WITH_IMAGE_URL", image_url.spec())); 2848 std::string replacement_path; 2849 ASSERT_TRUE(net::SpawnedTestServer::GetFilePathWithReplacements( 2850 "files/prerender/prerender_with_image.html", 2851 replacement_text, 2852 &replacement_path)); 2853 PrerenderTestURL(replacement_path, FINAL_STATUS_UNSUPPORTED_SCHEME, 1); 2854 NavigateToDestURL(); 2855} 2856 2857// Ensure that about:blank is permitted for any subresource. 2858IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2859 PrerenderAllowAboutBlankSubresource) { 2860 GURL image_url = GURL("about:blank"); 2861 std::vector<net::SpawnedTestServer::StringPair> replacement_text; 2862 replacement_text.push_back( 2863 std::make_pair("REPLACE_WITH_IMAGE_URL", image_url.spec())); 2864 std::string replacement_path; 2865 ASSERT_TRUE(net::SpawnedTestServer::GetFilePathWithReplacements( 2866 "files/prerender/prerender_with_image.html", 2867 replacement_text, 2868 &replacement_path)); 2869 PrerenderTestURL(replacement_path, FINAL_STATUS_USED, 1); 2870 NavigateToDestURL(); 2871} 2872 2873// Checks that non-http/https/chrome-extension subresource cancels the prerender 2874// on redirect. 2875IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2876 PrerenderCancelSubresourceRedirectUnsupportedScheme) { 2877 GURL image_url = test_server()->GetURL( 2878 CreateServerRedirect("invalidscheme://www.google.com/test.jpg")); 2879 std::vector<net::SpawnedTestServer::StringPair> replacement_text; 2880 replacement_text.push_back( 2881 std::make_pair("REPLACE_WITH_IMAGE_URL", image_url.spec())); 2882 std::string replacement_path; 2883 ASSERT_TRUE(net::SpawnedTestServer::GetFilePathWithReplacements( 2884 "files/prerender/prerender_with_image.html", 2885 replacement_text, 2886 &replacement_path)); 2887 PrerenderTestURL(replacement_path, FINAL_STATUS_UNSUPPORTED_SCHEME, 1); 2888 NavigateToDestURL(); 2889} 2890 2891// Checks that chrome-extension subresource does not cancel the prerender. 2892IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2893 PrerenderKeepSubresourceExtensionScheme) { 2894 GURL image_url = GURL("chrome-extension://abcdefg/test.jpg"); 2895 std::vector<net::SpawnedTestServer::StringPair> replacement_text; 2896 replacement_text.push_back( 2897 std::make_pair("REPLACE_WITH_IMAGE_URL", image_url.spec())); 2898 std::string replacement_path; 2899 ASSERT_TRUE(net::SpawnedTestServer::GetFilePathWithReplacements( 2900 "files/prerender/prerender_with_image.html", 2901 replacement_text, 2902 &replacement_path)); 2903 PrerenderTestURL(replacement_path, FINAL_STATUS_USED, 1); 2904 NavigateToDestURL(); 2905} 2906 2907// Checks that redirect to chrome-extension subresource does not cancel the 2908// prerender. 2909IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2910 PrerenderKeepSubresourceRedirectExtensionScheme) { 2911 GURL image_url = test_server()->GetURL( 2912 CreateServerRedirect("chrome-extension://abcdefg/test.jpg")); 2913 std::vector<net::SpawnedTestServer::StringPair> replacement_text; 2914 replacement_text.push_back( 2915 std::make_pair("REPLACE_WITH_IMAGE_URL", image_url.spec())); 2916 std::string replacement_path; 2917 ASSERT_TRUE(net::SpawnedTestServer::GetFilePathWithReplacements( 2918 "files/prerender/prerender_with_image.html", 2919 replacement_text, 2920 &replacement_path)); 2921 PrerenderTestURL(replacement_path, FINAL_STATUS_USED, 1); 2922 NavigateToDestURL(); 2923} 2924 2925 2926// Checks that non-http/https main page redirects cancel the prerender. 2927IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, 2928 PrerenderCancelMainFrameRedirectUnsupportedScheme) { 2929 GURL url = test_server()->GetURL( 2930 CreateServerRedirect("invalidscheme://www.google.com/test.html")); 2931 PrerenderTestURL(url, FINAL_STATUS_UNSUPPORTED_SCHEME, 1); 2932 NavigateToDestURL(); 2933} 2934 2935// Checks that media source video loads are deferred on prerendering. 2936IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderHTML5MediaSourceVideo) { 2937 PrerenderTestURL("files/prerender/prerender_html5_video_media_source.html", 2938 FINAL_STATUS_USED, 2939 1); 2940 NavigateToDestUrlAndWaitForPassTitle(); 2941} 2942 2943// Checks that a prerender that creates an audio stream (via a WebAudioDevice) 2944// is cancelled. 2945// http://crbug.com/261489 2946IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, DISABLED_PrerenderWebAudioDevice) { 2947 PrerenderTestURL("files/prerender/prerender_web_audio_device.html", 2948 FINAL_STATUS_CREATING_AUDIO_STREAM, 1); 2949} 2950 2951// Checks that prerenders do not swap in to WebContents being captured. 2952IN_PROC_BROWSER_TEST_F(PrerenderBrowserTest, PrerenderCapturedWebContents) { 2953 PrerenderTestURL("files/prerender/prerender_page.html", 2954 FINAL_STATUS_PAGE_BEING_CAPTURED, 1); 2955 WebContents* web_contents = 2956 current_browser()->tab_strip_model()->GetActiveWebContents(); 2957 web_contents->IncrementCapturerCount(); 2958 NavigateToDestURLWithDisposition(CURRENT_TAB, false); 2959 web_contents->DecrementCapturerCount(); 2960} 2961 2962} // namespace prerender 2963