summaryrefslogtreecommitdiffstats
path: root/chrome/browser
diff options
context:
space:
mode:
Diffstat (limited to 'chrome/browser')
-rw-r--r--chrome/browser/chrome_main_browsertest.cc59
-rw-r--r--chrome/browser/sessions/session_restore_browsertest.cc392
-rw-r--r--chrome/browser/sessions/session_restore_uitest.cc491
-rw-r--r--chrome/browser/sessions/session_service.cc12
-rw-r--r--chrome/browser/sessions/session_service.h8
5 files changed, 395 insertions, 567 deletions
diff --git a/chrome/browser/chrome_main_browsertest.cc b/chrome/browser/chrome_main_browsertest.cc
index 888079c..5f38cb2 100644
--- a/chrome/browser/chrome_main_browsertest.cc
+++ b/chrome/browser/chrome_main_browsertest.cc
@@ -8,7 +8,6 @@
#include "base/file_util.h"
#include "base/path_service.h"
#include "base/process_util.h"
-#include "base/test/test_suite.h"
#include "chrome/browser/ui/browser.h"
#include "chrome/browser/ui/browser_list.h"
#include "chrome/common/chrome_notification_types.h"
@@ -20,52 +19,25 @@
#include "content/public/browser/navigation_entry.h"
#include "content/public/browser/notification_service.h"
#include "content/public/browser/web_contents.h"
-#include "content/test/test_launcher.h"
#include "net/base/net_util.h"
-// These tests don't apply to the Mac version; see
-// LaunchAnotherBrowserBlockUntilClosed for details.
+// These tests don't apply to the Mac version; see GetCommandLineForRelaunch
+// for details.
#if !defined(OS_MACOSX)
class ChromeMainTest : public InProcessBrowserTest {
public:
- ChromeMainTest()
- : InProcessBrowserTest(),
- new_command_line_(CommandLine::ForCurrentProcess()->GetProgram()) {
- }
-
- virtual void SetUpOnMainThread() OVERRIDE {
- CommandLine::SwitchMap switches =
- CommandLine::ForCurrentProcess()->GetSwitches();
- switches.erase(switches::kUserDataDir);
- switches.erase(test_launcher::kGTestFilterFlag);
-
- for (CommandLine::SwitchMap::const_iterator iter = switches.begin();
- iter != switches.end(); ++iter) {
- new_command_line_.AppendSwitchNative((*iter).first, (*iter).second);
- }
-
- FilePath user_data_dir;
- PathService::Get(chrome::DIR_USER_DATA, &user_data_dir);
- new_command_line_.AppendSwitchPath(switches::kUserDataDir, user_data_dir);
+ ChromeMainTest() {}
- new_command_line_.AppendSwitchASCII(
- test_launcher::kGTestFilterFlag, test_launcher::kEmptyTestName);
- new_command_line_.AppendSwitch(TestSuite::kSilent);
+ void Relaunch(const CommandLine& new_command_line) {
+ base::LaunchProcess(new_command_line, base::LaunchOptions(), NULL);
}
-
- void Relaunch() {
- base::LaunchProcess(new_command_line_, base::LaunchOptions(), NULL);
- }
-
- protected:
- CommandLine new_command_line_;
};
// Make sure that the second invocation creates a new window.
IN_PROC_BROWSER_TEST_F(ChromeMainTest, SecondLaunch) {
ui_test_utils::BrowserAddedObserver observer;
- Relaunch();
+ Relaunch(GetCommandLineForRelaunch());
observer.WaitForSingleNewBrowser();
ASSERT_EQ(BrowserList::GetBrowserCount(browser()->profile()), 2u);
}
@@ -73,11 +45,12 @@ IN_PROC_BROWSER_TEST_F(ChromeMainTest, SecondLaunch) {
IN_PROC_BROWSER_TEST_F(ChromeMainTest, ReuseBrowserInstanceWhenOpeningFile) {
FilePath test_file_path = ui_test_utils::GetTestFilePath(
FilePath(), FilePath().AppendASCII("empty.html"));
- new_command_line_.AppendArgPath(test_file_path);
+ CommandLine new_command_line(GetCommandLineForRelaunch());
+ new_command_line.AppendArgPath(test_file_path);
ui_test_utils::WindowedNotificationObserver observer(
chrome::NOTIFICATION_TAB_ADDED,
content::NotificationService::AllSources());
- Relaunch();
+ Relaunch(new_command_line);
observer.Wait();
GURL url = net::FilePathToFileURL(test_file_path);
@@ -94,14 +67,15 @@ IN_PROC_BROWSER_TEST_F(ChromeMainTest, SecondLaunchWithIncognitoUrl) {
// Run with --incognito switch and an URL specified.
FilePath test_file_path = ui_test_utils::GetTestFilePath(
FilePath(), FilePath().AppendASCII("empty.html"));
- new_command_line_.AppendSwitch(switches::kIncognito);
- new_command_line_.AppendArgPath(test_file_path);
+ CommandLine new_command_line(GetCommandLineForRelaunch());
+ new_command_line.AppendSwitch(switches::kIncognito);
+ new_command_line.AppendArgPath(test_file_path);
- Relaunch();
+ Relaunch(new_command_line);
// There should be one normal and one incognito window now.
ui_test_utils::BrowserAddedObserver observer;
- Relaunch();
+ Relaunch(new_command_line);
observer.WaitForSingleNewBrowser();
ASSERT_EQ(2u, BrowserList::size());
@@ -136,11 +110,12 @@ IN_PROC_BROWSER_TEST_F(ChromeMainTest, SecondLaunchFromIncognitoWithNormalUrl) {
// Run with just an URL specified, no --incognito switch.
FilePath test_file_path = ui_test_utils::GetTestFilePath(
FilePath(), FilePath().AppendASCII("empty.html"));
- new_command_line_.AppendArgPath(test_file_path);
+ CommandLine new_command_line(GetCommandLineForRelaunch());
+ new_command_line.AppendArgPath(test_file_path);
ui_test_utils::WindowedNotificationObserver tab_observer(
chrome::NOTIFICATION_TAB_ADDED,
content::NotificationService::AllSources());
- Relaunch();
+ Relaunch(new_command_line);
tab_observer.Wait();
// There should be one normal and one incognito window now.
diff --git a/chrome/browser/sessions/session_restore_browsertest.cc b/chrome/browser/sessions/session_restore_browsertest.cc
index 76f9797..cf29893 100644
--- a/chrome/browser/sessions/session_restore_browsertest.cc
+++ b/chrome/browser/sessions/session_restore_browsertest.cc
@@ -5,6 +5,7 @@
#include "base/command_line.h"
#include "base/file_path.h"
#include "base/utf_string_conversions.h"
+#include "chrome/browser/browser_process.h"
#include "chrome/browser/defaults.h"
#include "chrome/browser/first_run/first_run.h"
#include "chrome/browser/profiles/profile.h"
@@ -21,47 +22,140 @@
#include "chrome/browser/ui/browser_window.h"
#include "chrome/common/url_constants.h"
#include "chrome/common/chrome_notification_types.h"
+#include "chrome/common/chrome_switches.h"
#include "chrome/test/base/in_process_browser_test.h"
#include "chrome/test/base/ui_test_utils.h"
#include "content/public/browser/navigation_controller.h"
#include "content/public/browser/navigation_entry.h"
#include "content/public/browser/notification_service.h"
#include "content/public/browser/notification_types.h"
+#include "content/public/browser/render_process_host.h"
#include "content/public/browser/web_contents.h"
#include "content/public/common/page_transition_types.h"
+#include "content/test/test_navigation_observer.h"
-namespace {
-
-// Verifies that the given NavigationController has exactly two entries that
-// correspond to the given URLs.
-void VerifyNavigationEntries(
- content::NavigationController& controller, GURL url1, GURL url2) {
- ASSERT_EQ(2, controller.GetEntryCount());
- EXPECT_EQ(1, controller.GetCurrentEntryIndex());
- EXPECT_EQ(url1, controller.GetEntryAtIndex(0)->GetURL());
- EXPECT_EQ(url2, controller.GetEntryAtIndex(1)->GetURL());
-}
-
-void CloseBrowserSynchronously(Browser* browser) {
- ui_test_utils::WindowedNotificationObserver observer(
- chrome::NOTIFICATION_BROWSER_CLOSED,
- content::NotificationService::AllSources());
- browser->window()->Close();
- observer.Wait();
-}
-
-} // namespace
+#if defined(OS_MACOSX)
+#include "base/mac/scoped_nsautorelease_pool.h"
+#endif
class SessionRestoreTest : public InProcessBrowserTest {
protected:
+
+ virtual void SetUpOnMainThread() OVERRIDE {
+ SessionStartupPref pref(SessionStartupPref::LAST);
+ SessionStartupPref::SetStartupPref(browser()->profile(), pref);
+#if defined(OS_CHROMEOS) || defined(OS_MACOSX)
+ const testing::TestInfo* const test_info =
+ testing::UnitTest::GetInstance()->current_test_info();
+ if (strcmp(test_info->name(), "NoSessionRestoreNewWindowChromeOS")) {
+ // Undo the effect of kBrowserAliveWithNoWindows in defaults.cc so that we
+ // can get these test to work without quitting.
+ SessionServiceFactory::GetForProfile(browser()->profile())->
+ force_browser_not_alive_with_no_windows_ = true;
+ }
+#endif
+ }
+
virtual bool SetUpUserDataDirectory() OVERRIDE {
// Make sure the first run sentinel file exists before running these tests,
// since some of them customize the session startup pref whose value can
// be different than the default during the first run.
// TODO(bauerb): set the first run flag instead of creating a sentinel file.
first_run::CreateSentinel();
+
+ url1_ = ui_test_utils::GetTestUrl(
+ FilePath().AppendASCII("session_history"),
+ FilePath().AppendASCII("bot1.html"));
+ url2_ = ui_test_utils::GetTestUrl(
+ FilePath().AppendASCII("session_history"),
+ FilePath().AppendASCII("bot2.html"));
+ url3_ = ui_test_utils::GetTestUrl(
+ FilePath().AppendASCII("session_history"),
+ FilePath().AppendASCII("bot3.html"));
+
return InProcessBrowserTest::SetUpUserDataDirectory();
}
+
+ // Verifies that the given NavigationController has exactly two entries that
+ // correspond to the given URLs.
+ void VerifyNavigationEntries(
+ content::NavigationController& controller, GURL url1, GURL url2) {
+ ASSERT_EQ(2, controller.GetEntryCount());
+ EXPECT_EQ(1, controller.GetCurrentEntryIndex());
+ EXPECT_EQ(url1, controller.GetEntryAtIndex(0)->GetURL());
+ EXPECT_EQ(url2, controller.GetEntryAtIndex(1)->GetURL());
+ }
+
+ void CloseBrowserSynchronously(Browser* browser) {
+ ui_test_utils::WindowedNotificationObserver observer(
+ chrome::NOTIFICATION_BROWSER_CLOSED,
+ content::NotificationService::AllSources());
+ browser->window()->Close();
+#if defined(OS_MACOSX)
+ // BrowserWindowController depends on the auto release pool being recycled
+ // in the message loop to delete itself, which frees the Browser object
+ // which fires this event.
+ AutoreleasePool()->Recycle();
+#endif
+ observer.Wait();
+ }
+
+ Browser* QuitBrowserAndRestore(Browser* browser, int expected_tab_count) {
+ // Create a new popup.
+ Profile* profile = browser->profile();
+
+ // Close the browser.
+ g_browser_process->AddRefModule();
+ CloseBrowserSynchronously(browser);
+
+ // Create a new window, which should trigger session restore.
+ ui_test_utils::BrowserAddedObserver window_observer;
+ TestNavigationObserver navigation_observer(
+ content::NotificationService::AllSources(), NULL, expected_tab_count);
+ Browser::NewEmptyWindow(profile);
+ Browser* new_browser = window_observer.WaitForSingleNewBrowser();
+ navigation_observer.Wait();
+ g_browser_process->ReleaseModule();
+
+ return new_browser;
+ }
+
+ void GoBack(Browser* browser) {
+ ui_test_utils::WindowedNotificationObserver observer(
+ content::NOTIFICATION_LOAD_STOP,
+ content::NotificationService::AllSources());
+ browser->GoBack(CURRENT_TAB);
+ observer.Wait();
+ }
+
+ void GoForward(Browser* browser) {
+ ui_test_utils::WindowedNotificationObserver observer(
+ content::NOTIFICATION_LOAD_STOP,
+ content::NotificationService::AllSources());
+ browser->GoForward(CURRENT_TAB);
+ observer.Wait();
+ }
+
+ void AssertOneWindowWithOneTab(Browser* browser) {
+ ASSERT_EQ(1u, BrowserList::size());
+ ASSERT_EQ(1, browser->tab_count());
+ }
+
+ int RenderProcessHostCount() {
+ content::RenderProcessHost::iterator hosts =
+ content::RenderProcessHost::AllHostsIterator();
+ int count = 0;
+ while (!hosts.IsAtEnd()) {
+ if (hosts.GetCurrentValue()->HasConnection())
+ count++;
+ hosts.Advance();
+ }
+ return count;
+ }
+
+ GURL url1_;
+ GURL url2_;
+ GURL url3_;
};
#if defined(OS_CHROMEOS)
@@ -74,10 +168,6 @@ class SessionRestoreTest : public InProcessBrowserTest {
// not do session restore if an incognito window is already open.
// (http://crbug.com/120927)
IN_PROC_BROWSER_TEST_F(SessionRestoreTest, NoSessionRestoreNewWindowChromeOS) {
- // Turn on session restore.
- SessionStartupPref pref(SessionStartupPref::LAST);
- SessionStartupPref::SetStartupPref(browser()->profile(), pref);
-
GURL url(ui_test_utils::GetTestUrl(
FilePath(FilePath::kCurrentDirectory),
FilePath(FILE_PATH_LITERAL("title1.html"))));
@@ -255,10 +345,6 @@ IN_PROC_BROWSER_TEST_F(SessionRestoreTest, WindowWithOneTab) {
// Verifies we remember the last browser window when closing the last
// non-incognito window while an incognito window is open.
IN_PROC_BROWSER_TEST_F(SessionRestoreTest, IncognitotoNonIncognito) {
- // Turn on session restore.
- SessionStartupPref pref(SessionStartupPref::LAST);
- SessionStartupPref::SetStartupPref(browser()->profile(), pref);
-
GURL url(ui_test_utils::GetTestUrl(
FilePath(FilePath::kCurrentDirectory),
FilePath(FILE_PATH_LITERAL("title1.html"))));
@@ -339,3 +425,251 @@ IN_PROC_BROWSER_TEST_F(SessionRestoreTest, RestoreForeignTab) {
VerifyNavigationEntries(
new_browser->GetWebContentsAt(0)->GetController(), url1, url2);
}
+
+IN_PROC_BROWSER_TEST_F(SessionRestoreTest, Basic) {
+ ui_test_utils::NavigateToURL(browser(), url1_);
+ ui_test_utils::NavigateToURL(browser(), url2_);
+
+ Browser* new_browser = QuitBrowserAndRestore(browser(), 1);
+ ASSERT_EQ(1u, BrowserList::size());
+ ASSERT_EQ(url2_, new_browser->GetSelectedWebContents()->GetURL());
+ GoBack(new_browser);
+ ASSERT_EQ(url1_, new_browser->GetSelectedWebContents()->GetURL());
+}
+
+IN_PROC_BROWSER_TEST_F(SessionRestoreTest, RestoresForwardAndBackwardNavs) {
+ ui_test_utils::NavigateToURL(browser(), url1_);
+ ui_test_utils::NavigateToURL(browser(), url2_);
+ ui_test_utils::NavigateToURL(browser(), url3_);
+
+ GoBack(browser());
+ Browser* new_browser = QuitBrowserAndRestore(browser(), 1);
+ ASSERT_EQ(1u, BrowserList::size());
+ ASSERT_EQ(url2_, new_browser->GetSelectedWebContents()->GetURL());
+ GoForward(new_browser);
+ ASSERT_EQ(url3_, new_browser->GetSelectedWebContents()->GetURL());
+ GoBack(new_browser);
+ ASSERT_EQ(url2_, new_browser->GetSelectedWebContents()->GetURL());
+
+ // Test renderer-initiated back/forward as well.
+ GURL go_back_url("javascript:history.back();");
+ ui_test_utils::NavigateToURL(new_browser, go_back_url);
+ ASSERT_EQ(url1_, new_browser->GetSelectedWebContents()->GetURL());
+}
+
+// Tests that the SiteInstances used for entries in a restored tab's history
+// are given appropriate max page IDs, so that going back to a restored
+// cross-site page and then forward again works. (Bug 1204135)
+IN_PROC_BROWSER_TEST_F(SessionRestoreTest,
+ RestoresCrossSiteForwardAndBackwardNavs) {
+ ASSERT_TRUE(test_server()->Start());
+
+ GURL cross_site_url(test_server()->GetURL("files/title2.html"));
+
+ // Visit URLs on different sites.
+ ui_test_utils::NavigateToURL(browser(), url1_);
+ ui_test_utils::NavigateToURL(browser(), cross_site_url);
+ ui_test_utils::NavigateToURL(browser(), url2_);
+
+ GoBack(browser());
+ Browser* new_browser = QuitBrowserAndRestore(browser(), 1);
+ ASSERT_EQ(1u, BrowserList::size());
+ ASSERT_EQ(1, new_browser->tab_count());
+
+ // Check that back and forward work as expected.
+ ASSERT_EQ(cross_site_url, new_browser->GetSelectedWebContents()->GetURL());
+
+ GoBack(new_browser);
+ ASSERT_EQ(url1_, new_browser->GetSelectedWebContents()->GetURL());
+
+ GoForward(new_browser);
+ ASSERT_EQ(cross_site_url, new_browser->GetSelectedWebContents()->GetURL());
+
+ // Test renderer-initiated back/forward as well.
+ GURL go_forward_url("javascript:history.forward();");
+ ui_test_utils::NavigateToURL(new_browser, go_forward_url);
+ ASSERT_EQ(url2_, new_browser->GetSelectedWebContents()->GetURL());
+}
+
+IN_PROC_BROWSER_TEST_F(SessionRestoreTest, TwoTabsSecondSelected) {
+ ui_test_utils::NavigateToURL(browser(), url1_);
+
+ ui_test_utils::NavigateToURLWithDisposition(
+ browser(), url2_, NEW_FOREGROUND_TAB,
+ ui_test_utils::BROWSER_TEST_WAIT_FOR_NAVIGATION);
+
+ Browser* new_browser = QuitBrowserAndRestore(browser(), 2);
+
+ ASSERT_EQ(1u, BrowserList::size());
+ ASSERT_EQ(2, new_browser->tab_count());
+ ASSERT_EQ(1, new_browser->active_index());
+ ASSERT_EQ(url2_, new_browser->GetSelectedWebContents()->GetURL());
+
+ ASSERT_EQ(url1_, new_browser->GetWebContentsAt(0)->GetURL());
+}
+
+// Creates two tabs, closes one, quits and makes sure only one tab is restored.
+IN_PROC_BROWSER_TEST_F(SessionRestoreTest, ClosedTabStaysClosed) {
+ ui_test_utils::NavigateToURL(browser(), url1_);
+
+ ui_test_utils::NavigateToURLWithDisposition(
+ browser(), url2_, NEW_FOREGROUND_TAB,
+ ui_test_utils::BROWSER_TEST_WAIT_FOR_NAVIGATION);
+ browser()->CloseTab();
+
+ Browser* new_browser = QuitBrowserAndRestore(browser(), 1);
+
+ AssertOneWindowWithOneTab(new_browser);
+ ASSERT_EQ(url1_, new_browser->GetSelectedWebContents()->GetURL());
+}
+
+// Test to verify that the print preview tab is not restored.
+IN_PROC_BROWSER_TEST_F(SessionRestoreTest, DontRestorePrintPreviewTabTest) {
+ ui_test_utils::NavigateToURL(browser(), url1_);
+
+ // Append the print preview tab.
+ ui_test_utils::NavigateToURLWithDisposition(
+ browser(), GURL(chrome::kChromeUIPrintURL), NEW_FOREGROUND_TAB,
+ ui_test_utils::BROWSER_TEST_WAIT_FOR_NAVIGATION);
+
+ // Restart and make sure we have only one window with one tab and the url
+ // is url1_.
+ Browser* new_browser = QuitBrowserAndRestore(browser(), 1);
+
+ AssertOneWindowWithOneTab(new_browser);
+ ASSERT_EQ(url1_, new_browser->GetSelectedWebContents()->GetURL());
+}
+
+// Creates a tabbed browser and popup and makes sure we restore both.
+IN_PROC_BROWSER_TEST_F(SessionRestoreTest, NormalAndPopup) {
+ if (!browser_defaults::kRestorePopups)
+ return; // Test only applicable if restoring popups.
+
+ ui_test_utils::NavigateToURL(browser(), url1_);
+
+ // Make sure we have one window.
+ AssertOneWindowWithOneTab(browser());
+
+ // Open a popup.
+ Browser* popup = Browser::CreateWithParams(
+ Browser::CreateParams(Browser::TYPE_POPUP, browser()->profile()));
+ popup->window()->Show();
+ ASSERT_EQ(2u, BrowserList::size());
+
+ ui_test_utils::NavigateToURL(popup, url1_);
+
+ // Simulate an exit by shuting down the session service. If we don't do this
+ // the first window close is treated as though the user closed the window
+ // and won't be restored.
+ SessionServiceFactory::ShutdownForProfile(browser()->profile());
+
+ // Restart and make sure we have two windows.
+ QuitBrowserAndRestore(browser(), 1);
+
+ ASSERT_EQ(2u, BrowserList::size());
+
+ Browser* browser1 = *BrowserList::begin();
+ Browser* browser2 = *(++BrowserList::begin());
+
+ Browser::Type type1 = browser1->type();
+ Browser::Type type2 = browser2->type();
+
+ // The order of whether the normal window or popup is first depends upon
+ // activation order, which is not necessarily consistant across runs.
+ if (type1 == Browser::TYPE_TABBED) {
+ EXPECT_EQ(type2, Browser::TYPE_POPUP);
+ } else {
+ EXPECT_EQ(type1, Browser::TYPE_POPUP);
+ EXPECT_EQ(type2, Browser::TYPE_TABBED);
+ }
+}
+
+#if !defined(OS_CHROMEOS) && !defined(OS_MACOSX)
+// This test doesn't apply to the Mac version; see GetCommandLineForRelaunch
+// for details. It was disabled for a long time so might never have worked on
+// ChromeOS.
+
+// Launches an app window, closes tabbed browser, launches and makes sure
+// we restore the tabbed browser url.
+// If this test flakes, use http://crbug.com/29110
+IN_PROC_BROWSER_TEST_F(SessionRestoreTest,
+ RestoreAfterClosingTabbedBrowserWithAppAndLaunching) {
+ ui_test_utils::NavigateToURL(browser(), url1_);
+
+ // Launch an app.
+ CommandLine app_launch_arguments = GetCommandLineForRelaunch();
+ app_launch_arguments.AppendSwitchASCII(switches::kApp, url2_.spec());
+
+ ui_test_utils::BrowserAddedObserver window_observer;
+
+ base::LaunchProcess(app_launch_arguments, base::LaunchOptions(), NULL);
+
+ Browser* app_window = window_observer.WaitForSingleNewBrowser();
+ ASSERT_EQ(2u, BrowserList::size());
+
+ // Close the first window. The only window left is the App window.
+ CloseBrowserSynchronously(browser());
+
+ // Restore the session, which should bring back the first window with url1_.
+ Browser* new_browser = QuitBrowserAndRestore(app_window, 1);
+
+ AssertOneWindowWithOneTab(new_browser);
+
+ ASSERT_EQ(url1_, new_browser->GetSelectedWebContents()->GetURL());
+}
+
+#endif // !defined(OS_CHROMEOS) && !defined(OS_MACOSX)
+
+// Creates two windows, closes one, restores, make sure only one window open.
+IN_PROC_BROWSER_TEST_F(SessionRestoreTest, TwoWindowsCloseOneRestoreOnlyOne) {
+ ui_test_utils::NavigateToURL(browser(), url1_);
+
+ // Open a second window.
+ ui_test_utils::NavigateToURLWithDisposition(
+ browser(), GURL(chrome::kAboutBlankURL), NEW_WINDOW,
+ ui_test_utils::BROWSER_TEST_WAIT_FOR_BROWSER);
+
+ ASSERT_EQ(2u, BrowserList::size());
+
+ // Close it.
+ Browser* new_window = *(++BrowserList::begin());
+ CloseBrowserSynchronously(new_window);
+
+ // Restart and make sure we have only one window with one tab and the url
+ // is url1_.
+ Browser* new_browser = QuitBrowserAndRestore(browser(), 1);
+
+ AssertOneWindowWithOneTab(new_browser);
+
+ ASSERT_EQ(url1_, new_browser->GetSelectedWebContents()->GetURL());
+}
+
+// Make sure after a restore the number of processes matches that of the number
+// of processes running before the restore. This creates a new tab so that
+// we should have two new tabs running. (This test will pass in both
+// process-per-site and process-per-site-instance, because we treat the new tab
+// as a special case in process-per-site-instance so that it only ever uses one
+// process.)
+//
+// Flaky: http://code.google.com/p/chromium/issues/detail?id=52022
+// Unfortunately, the fix at http://codereview.chromium.org/6546078
+// breaks NTP background image refreshing, so ThemeSource had to revert to
+// replacing the existing data source.
+IN_PROC_BROWSER_TEST_F(SessionRestoreTest, ShareProcessesOnRestore) {
+ // Create two new tabs.
+ ui_test_utils::NavigateToURLWithDisposition(
+ browser(), GURL(chrome::kAboutBlankURL), NEW_FOREGROUND_TAB,
+ ui_test_utils::BROWSER_TEST_WAIT_FOR_NAVIGATION);
+ ui_test_utils::NavigateToURLWithDisposition(
+ browser(), GURL(chrome::kAboutBlankURL), NEW_FOREGROUND_TAB,
+ ui_test_utils::BROWSER_TEST_WAIT_FOR_NAVIGATION);
+
+ int expected_process_count = RenderProcessHostCount();
+
+ // Restart.
+ Browser* new_browser = QuitBrowserAndRestore(browser(), 3);
+
+ ASSERT_EQ(3, new_browser->tab_count());
+
+ ASSERT_EQ(expected_process_count, RenderProcessHostCount());
+}
diff --git a/chrome/browser/sessions/session_restore_uitest.cc b/chrome/browser/sessions/session_restore_uitest.cc
deleted file mode 100644
index d3d3a01..0000000
--- a/chrome/browser/sessions/session_restore_uitest.cc
+++ /dev/null
@@ -1,491 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "base/command_line.h"
-#include "base/file_path.h"
-#include "base/memory/scoped_ptr.h"
-#include "base/string_number_conversions.h"
-#include "base/test/test_timeouts.h"
-#include "chrome/app/chrome_command_ids.h"
-#include "chrome/browser/defaults.h"
-#include "chrome/common/chrome_paths.h"
-#include "chrome/common/chrome_switches.h"
-#include "chrome/common/url_constants.h"
-#include "chrome/test/automation/automation_proxy.h"
-#include "chrome/test/automation/browser_proxy.h"
-#include "chrome/test/automation/tab_proxy.h"
-#include "chrome/test/automation/window_proxy.h"
-#include "chrome/test/ui/ui_test.h"
-#include "googleurl/src/gurl.h"
-#include "net/base/net_util.h"
-#include "net/test/test_server.h"
-
-namespace {
-
-class SessionRestoreUITest : public UITest {
- protected:
- SessionRestoreUITest() : UITest() {
- FilePath path_prefix = test_data_directory_.AppendASCII("session_history");
-
- url1_ = net::FilePathToFileURL(path_prefix.AppendASCII("bot1.html"));
- url2_ = net::FilePathToFileURL(path_prefix.AppendASCII("bot2.html"));
- url3_ = net::FilePathToFileURL(path_prefix.AppendASCII("bot3.html"));
- }
-
- virtual void QuitBrowserAndRestore(int expected_tab_count) {
-#if defined(OS_CHROMEOS) || defined(OS_MACOSX)
- set_shutdown_type(ProxyLauncher::USER_QUIT);
-#endif
- UITest::TearDown();
-
- clear_profile_ = false;
-
- // Clear launch_arguments so that the URL arg doesn't get added on restart.
- launch_arguments_ = CommandLine(launch_arguments_.GetProgram());
-
- launch_arguments_.AppendSwitchASCII(switches::kRestoreLastSession,
- base::IntToString(expected_tab_count));
- UITest::SetUp();
- }
-
- void CloseWindow(int window_index, int initial_count) {
- scoped_refptr<BrowserProxy> browser_proxy(
- automation()->GetBrowserWindow(window_index));
- ASSERT_TRUE(browser_proxy.get());
- ASSERT_TRUE(browser_proxy->RunCommand(IDC_CLOSE_WINDOW));
- int window_count;
- ASSERT_TRUE(automation()->GetBrowserWindowCount(&window_count));
- ASSERT_EQ(initial_count - 1, window_count);
- }
-
- void AssertOneWindowWithOneTab() {
- int window_count;
- ASSERT_TRUE(automation()->GetBrowserWindowCount(&window_count));
- ASSERT_EQ(1, window_count);
- GURL url;
- AssertWindowHasOneTab(0, &url);
- }
-
- void AssertWindowHasOneTab(int window_index, GURL* url) {
- scoped_refptr<BrowserProxy> browser_proxy(
- automation()->GetBrowserWindow(window_index));
- ASSERT_TRUE(browser_proxy.get());
-
- int tab_count;
- ASSERT_TRUE(browser_proxy->GetTabCount(&tab_count));
- ASSERT_EQ(1, tab_count);
-
- int active_tab_index;
- ASSERT_TRUE(browser_proxy->GetActiveTabIndex(&active_tab_index));
- ASSERT_EQ(0, active_tab_index);
-
- scoped_refptr<TabProxy> tab_proxy(browser_proxy->GetActiveTab());
- ASSERT_TRUE(tab_proxy.get());
- ASSERT_TRUE(tab_proxy->WaitForTabToBeRestored(
- TestTimeouts::action_max_timeout_ms()));
-
- ASSERT_TRUE(tab_proxy->GetCurrentURL(url));
- }
-
- GURL url1_;
- GURL url2_;
- GURL url3_;
-
- private:
- DISALLOW_COPY_AND_ASSIGN(SessionRestoreUITest);
-};
-
-TEST_F(SessionRestoreUITest, Basic) {
- NavigateToURL(url1_);
- NavigateToURL(url2_);
-
- QuitBrowserAndRestore(1);
-
- // NOTE: Don't use GetActiveWindow here, when run with the screen locked
- // active windows returns NULL.
- int window_count;
- ASSERT_TRUE(automation()->GetBrowserWindowCount(&window_count));
- ASSERT_EQ(1, window_count);
- scoped_refptr<BrowserProxy> browser_proxy(automation()->GetBrowserWindow(0));
- ASSERT_TRUE(browser_proxy.get());
- scoped_refptr<TabProxy> tab_proxy(browser_proxy->GetTab(0));
- ASSERT_TRUE(tab_proxy->WaitForTabToBeRestored(
- TestTimeouts::action_max_timeout_ms()));
-
- ASSERT_EQ(url2_, GetActiveTabURL());
- ASSERT_EQ(AUTOMATION_MSG_NAVIGATION_SUCCESS, tab_proxy->GoBack());
- ASSERT_EQ(url1_, GetActiveTabURL());
-}
-
-TEST_F(SessionRestoreUITest, RestoresForwardAndBackwardNavs) {
- NavigateToURL(url1_);
- NavigateToURL(url2_);
- NavigateToURL(url3_);
-
- scoped_refptr<TabProxy> active_tab(GetActiveTab());
- ASSERT_TRUE(active_tab.get());
- ASSERT_TRUE(active_tab->GoBack());
-
- QuitBrowserAndRestore(1);
-
- // NOTE: Don't use GetActiveWindow here, when run with the screen locked
- // active windows returns NULL.
- int window_count;
- ASSERT_TRUE(automation()->GetBrowserWindowCount(&window_count));
- ASSERT_EQ(1, window_count);
- scoped_refptr<BrowserProxy> browser_proxy(automation()->GetBrowserWindow(0));
- ASSERT_TRUE(browser_proxy.get());
- scoped_refptr<TabProxy> tab_proxy(browser_proxy->GetTab(0));
- ASSERT_TRUE(tab_proxy->WaitForTabToBeRestored(
- TestTimeouts::action_max_timeout_ms()));
-
- ASSERT_TRUE(GetActiveTabURL() == url2_);
- ASSERT_TRUE(tab_proxy->GoForward());
- ASSERT_TRUE(GetActiveTabURL() == url3_);
- ASSERT_TRUE(tab_proxy->GoBack());
- ASSERT_TRUE(GetActiveTabURL() == url2_);
-
- // Test renderer-initiated back/forward as well.
- GURL go_back_url("javascript:history.back();");
- ASSERT_TRUE(tab_proxy->NavigateToURL(go_back_url));
- ASSERT_TRUE(GetActiveTabURL() == url1_);
-}
-
-// Tests that the SiteInstances used for entries in a restored tab's history
-// are given appropriate max page IDs, so that going back to a restored
-// cross-site page and then forward again works. (Bug 1204135)
-TEST_F(SessionRestoreUITest, RestoresCrossSiteForwardAndBackwardNavs) {
- net::TestServer test_server(net::TestServer::TYPE_HTTP,
- net::TestServer::kLocalhost,
- FilePath(FILE_PATH_LITERAL("chrome/test/data")));
- ASSERT_TRUE(test_server.Start());
-
- GURL cross_site_url(test_server.GetURL("files/title2.html"));
-
- // Visit URLs on different sites.
- NavigateToURL(url1_);
- NavigateToURL(cross_site_url);
- NavigateToURL(url2_);
-
- scoped_refptr<TabProxy> active_tab(GetActiveTab());
- ASSERT_TRUE(active_tab.get());
- ASSERT_TRUE(active_tab->GoBack());
-
- QuitBrowserAndRestore(1);
-
- // NOTE: Don't use GetActiveWindow here, when run with the screen locked
- // active windows returns NULL.
- int window_count;
- ASSERT_TRUE(automation()->GetBrowserWindowCount(&window_count));
- ASSERT_EQ(1, window_count);
- scoped_refptr<BrowserProxy> browser_proxy(automation()->GetBrowserWindow(0));
- ASSERT_TRUE(browser_proxy.get());
- int tab_count;
- ASSERT_TRUE(browser_proxy->GetTabCount(&tab_count));
- ASSERT_EQ(1, tab_count);
- scoped_refptr<TabProxy> tab_proxy(browser_proxy->GetTab(0));
- ASSERT_TRUE(tab_proxy.get());
- ASSERT_TRUE(tab_proxy->WaitForTabToBeRestored(
- TestTimeouts::action_max_timeout_ms()));
-
- // Check that back and forward work as expected.
- GURL url;
- ASSERT_TRUE(tab_proxy->GetCurrentURL(&url));
- ASSERT_EQ(cross_site_url, url);
-
- ASSERT_TRUE(tab_proxy->GoBack());
- ASSERT_TRUE(tab_proxy->GetCurrentURL(&url));
- ASSERT_EQ(url1_, url);
-
- ASSERT_TRUE(tab_proxy->GoForward());
- ASSERT_TRUE(tab_proxy->GetCurrentURL(&url));
- ASSERT_EQ(cross_site_url, url);
-
- // Test renderer-initiated back/forward as well.
- GURL go_forward_url("javascript:history.forward();");
- ASSERT_TRUE(tab_proxy->NavigateToURL(go_forward_url));
- ASSERT_TRUE(tab_proxy->GetCurrentURL(&url));
- ASSERT_EQ(url2_, url);
-}
-
-TEST_F(SessionRestoreUITest, TwoTabsSecondSelected) {
- NavigateToURL(url1_);
-
- // NOTE: Don't use GetActiveWindow here, when run with the screen locked
- // active windows returns NULL.
- int window_count;
- ASSERT_TRUE(automation()->GetBrowserWindowCount(&window_count));
- ASSERT_EQ(1, window_count);
- scoped_refptr<BrowserProxy> browser_proxy(automation()->GetBrowserWindow(0));
- ASSERT_TRUE(browser_proxy.get());
-
- ASSERT_TRUE(browser_proxy->AppendTab(url2_));
-
- QuitBrowserAndRestore(2);
- browser_proxy = NULL;
-
- ASSERT_TRUE(automation()->GetBrowserWindowCount(&window_count));
- ASSERT_EQ(1, window_count);
- browser_proxy = automation()->GetBrowserWindow(0);
-
- int tab_count;
- ASSERT_TRUE(browser_proxy->GetTabCount(&tab_count));
- ASSERT_EQ(2, tab_count);
-
- int active_tab_index;
- ASSERT_TRUE(browser_proxy->GetActiveTabIndex(&active_tab_index));
- ASSERT_EQ(1, active_tab_index);
-
- scoped_refptr<TabProxy> tab_proxy(browser_proxy->GetActiveTab());
- ASSERT_TRUE(tab_proxy.get());
- ASSERT_TRUE(tab_proxy->WaitForTabToBeRestored(
- TestTimeouts::action_max_timeout_ms()));
-
- ASSERT_EQ(url2_, GetActiveTabURL());
-
- ASSERT_TRUE(browser_proxy->ActivateTab(0));
- tab_proxy = browser_proxy->GetActiveTab();
- ASSERT_TRUE(tab_proxy.get());
- ASSERT_TRUE(tab_proxy->WaitForTabToBeRestored(
- TestTimeouts::action_max_timeout_ms()));
-
- ASSERT_EQ(url1_, GetActiveTabURL());
-}
-
-// Creates two tabs, closes one, quits and makes sure only one tab is restored.
-TEST_F(SessionRestoreUITest, ClosedTabStaysClosed) {
- NavigateToURL(url1_);
-
- // NOTE: Don't use GetActiveWindow here, when run with the screen locked
- // active windows returns NULL.
- int window_count;
- ASSERT_TRUE(automation()->GetBrowserWindowCount(&window_count));
- ASSERT_EQ(1, window_count);
- scoped_refptr<BrowserProxy> browser_proxy(automation()->GetBrowserWindow(0));
- ASSERT_TRUE(browser_proxy.get());
- scoped_refptr<TabProxy> tab_proxy(browser_proxy->GetTab(0));
- ASSERT_TRUE(tab_proxy.get());
-
- ASSERT_TRUE(browser_proxy->AppendTab(url2_));
-
- scoped_refptr<TabProxy> active_tab(browser_proxy->GetActiveTab());
- ASSERT_TRUE(active_tab.get());
- ASSERT_TRUE(active_tab->Close(true));
-
- QuitBrowserAndRestore(1);
- browser_proxy = NULL;
- tab_proxy = NULL;
-
- AssertOneWindowWithOneTab();
-
- ASSERT_EQ(url1_, GetActiveTabURL());
-}
-
-// Test to verify that the print preview tab is not restored.
-TEST_F(SessionRestoreUITest, DontRestorePrintPreviewTabTest) {
- NavigateToURL(url1_);
-
- int window_count;
- ASSERT_TRUE(automation()->GetBrowserWindowCount(&window_count));
- ASSERT_EQ(1, window_count);
- scoped_refptr<BrowserProxy> browser_proxy(automation()->GetBrowserWindow(0));
- ASSERT_TRUE(browser_proxy.get());
-
- // Append the print preview tab.
- GURL printPreviewURL(chrome::kChromeUIPrintURL);
- ASSERT_TRUE(browser_proxy->AppendTab(printPreviewURL));
-
- scoped_refptr<TabProxy> active_tab(browser_proxy->GetActiveTab());
- ASSERT_TRUE(active_tab.get());
- ASSERT_EQ(printPreviewURL, GetActiveTabURL());
-
- // Restart and make sure we have only one window with one tab and the url
- // is url1_.
- QuitBrowserAndRestore(1);
- browser_proxy = NULL;
-
- AssertOneWindowWithOneTab();
-
- ASSERT_EQ(url1_, GetActiveTabURL());
-}
-
-// Creates a tabbed browser and popup and makes sure we restore both.
-TEST_F(SessionRestoreUITest, NormalAndPopup) {
- if (!browser_defaults::kRestorePopups)
- return; // Test only applicable if restoring popups.
-
- NavigateToURL(url1_);
-
- // Make sure we have one window.
- int window_count;
- ASSERT_TRUE(automation()->GetBrowserWindowCount(&window_count));
- ASSERT_EQ(1, window_count);
-
- // Open a popup.
- ASSERT_TRUE(automation()->OpenNewBrowserWindow(Browser::TYPE_POPUP,
- true));
- ASSERT_TRUE(automation()->GetBrowserWindowCount(&window_count));
- ASSERT_EQ(2, window_count);
-
- scoped_refptr<BrowserProxy> popup(automation()->GetBrowserWindow(1));
- ASSERT_TRUE(popup.get());
-
- scoped_refptr<TabProxy> tab(popup->GetTab(0));
- ASSERT_TRUE(tab.get());
-
- ASSERT_EQ(AUTOMATION_MSG_NAVIGATION_SUCCESS, tab->NavigateToURL(url1_));
-
- // Simulate an exit by shuting down the session service. If we don't do this
- // the first window close is treated as though the user closed the window
- // and won't be restored.
- ASSERT_TRUE(popup->ShutdownSessionService());
-
- tab = NULL;
- popup = NULL;
-
- // Restart and make sure we have only one window with one tab and the url
- // is url1_.
- QuitBrowserAndRestore(1);
-
- ASSERT_TRUE(automation()->GetBrowserWindowCount(&window_count));
- ASSERT_EQ(2, window_count);
-
- scoped_refptr<BrowserProxy> browser_proxy1(
- automation()->GetBrowserWindow(0));
- ASSERT_TRUE(browser_proxy1.get());
-
- scoped_refptr<BrowserProxy> browser_proxy2(
- automation()->GetBrowserWindow(1));
- ASSERT_TRUE(browser_proxy2.get());
-
- Browser::Type type1, type2;
- ASSERT_TRUE(browser_proxy1->GetType(&type1));
- ASSERT_TRUE(browser_proxy2->GetType(&type2));
-
- // The order of whether the normal window or popup is first depends upon
- // activation order, which is not necessarily consistant across runs.
- if (type1 == Browser::TYPE_TABBED) {
- EXPECT_EQ(type2, Browser::TYPE_POPUP);
- } else {
- EXPECT_EQ(type1, Browser::TYPE_POPUP);
- EXPECT_EQ(type2, Browser::TYPE_TABBED);
- }
-}
-
-#if !defined(OS_MACOSX)
-// This test doesn't apply to the Mac version; see
-// LaunchAnotherBrowserBlockUntilClosed for details.
-
-// Launches an app window, closes tabbed browser, launches and makes sure
-// we restore the tabbed browser url.
-// Flaky: http://crbug.com/29110
-TEST_F(SessionRestoreUITest,
- DISABLED_RestoreAfterClosingTabbedBrowserWithAppAndLaunching) {
- NavigateToURL(url1_);
-
- // Launch an app.
-
- bool include_testing_id_orig = include_testing_id_;
- include_testing_id_ = false;
- clear_profile_ = false;
- CommandLine app_launch_arguments = launch_arguments_;
- app_launch_arguments.AppendSwitchASCII(switches::kApp, url2_.spec());
- LaunchAnotherBrowserBlockUntilClosed(app_launch_arguments);
- ASSERT_TRUE(automation()->WaitForWindowCountToBecome(2));
-
- // Close the first window. The only window left is the App window.
- CloseWindow(0, 2);
-
- // Restore the session, which should bring back the first window with url1_.
- // First restore the settings so we can connect to the browser.
- include_testing_id_ = include_testing_id_orig;
- // Restore the session with 1 tab.
- QuitBrowserAndRestore(1);
-
- AssertOneWindowWithOneTab();
-
- ASSERT_EQ(url1_, GetActiveTabURL());
-}
-
-#endif // !OS_MACOSX
-
-// Creates two windows, closes one, restores, make sure only one window open.
-TEST_F(SessionRestoreUITest, TwoWindowsCloseOneRestoreOnlyOne) {
- NavigateToURL(url1_);
-
- // Make sure we have one window.
- int window_count;
- ASSERT_TRUE(automation()->GetBrowserWindowCount(&window_count));
- ASSERT_EQ(1, window_count);
-
- // Open a second window.
- ASSERT_TRUE(automation()->OpenNewBrowserWindow(Browser::TYPE_TABBED,
- true));
- ASSERT_TRUE(automation()->GetBrowserWindowCount(&window_count));
- ASSERT_EQ(2, window_count);
-
- // Close it.
- CloseWindow(1, 2);
-
- // Restart and make sure we have only one window with one tab and the url
- // is url1_.
- QuitBrowserAndRestore(1);
-
- AssertOneWindowWithOneTab();
-
- ASSERT_EQ(url1_, GetActiveTabURL());
-}
-
-// Make sure after a restore the number of processes matches that of the number
-// of processes running before the restore. This creates a new tab so that
-// we should have two new tabs running. (This test will pass in both
-// process-per-site and process-per-site-instance, because we treat the new tab
-// as a special case in process-per-site-instance so that it only ever uses one
-// process.)
-//
-// Flaky: http://code.google.com/p/chromium/issues/detail?id=52022
-// Unfortunately, the fix at http://codereview.chromium.org/6546078
-// breaks NTP background image refreshing, so ThemeSource had to revert to
-// replacing the existing data source.
-TEST_F(SessionRestoreUITest, DISABLED_ShareProcessesOnRestore) {
- scoped_refptr<BrowserProxy> browser_proxy(automation()->GetBrowserWindow(0));
- ASSERT_TRUE(browser_proxy.get() != NULL);
- int tab_count;
- ASSERT_TRUE(browser_proxy->GetTabCount(&tab_count));
-
- // Create two new tabs.
- ASSERT_TRUE(browser_proxy->RunCommand(IDC_NEW_TAB));
- ASSERT_TRUE(browser_proxy->RunCommand(IDC_NEW_TAB));
- int new_tab_count;
- ASSERT_TRUE(browser_proxy->GetTabCount(&new_tab_count));
- ASSERT_EQ(tab_count + 2, new_tab_count);
-
- int expected_process_count = 0;
- ASSERT_TRUE(GetBrowserProcessCount(&expected_process_count));
- int expected_tab_count = new_tab_count;
-
- // Restart.
- browser_proxy = NULL;
- QuitBrowserAndRestore(3);
-
- // Wait for each tab to finish being restored, then make sure the process
- // count matches.
- browser_proxy = automation()->GetBrowserWindow(0);
- ASSERT_TRUE(browser_proxy.get() != NULL);
- ASSERT_TRUE(browser_proxy->GetTabCount(&tab_count));
- ASSERT_EQ(expected_tab_count, tab_count);
-
- for (int i = 0; i < expected_tab_count; ++i) {
- scoped_refptr<TabProxy> tab_proxy(browser_proxy->GetTab(i));
- ASSERT_TRUE(tab_proxy.get() != NULL);
- ASSERT_TRUE(tab_proxy->WaitForTabToBeRestored(
- TestTimeouts::action_max_timeout_ms()));
- }
-
- int process_count = 0;
- ASSERT_TRUE(GetBrowserProcessCount(&process_count));
- ASSERT_EQ(expected_process_count, process_count);
-}
-
-} // namespace
diff --git a/chrome/browser/sessions/session_service.cc b/chrome/browser/sessions/session_service.cc
index 4eb3f65..f39ec70 100644
--- a/chrome/browser/sessions/session_service.cc
+++ b/chrome/browser/sessions/session_service.cc
@@ -198,7 +198,8 @@ SessionService::SessionService(Profile* profile)
move_on_new_browser_(false),
save_delay_in_millis_(base::TimeDelta::FromMilliseconds(2500)),
save_delay_in_mins_(base::TimeDelta::FromMinutes(10)),
- save_delay_in_hrs_(base::TimeDelta::FromHours(8)) {
+ save_delay_in_hrs_(base::TimeDelta::FromHours(8)),
+ force_browser_not_alive_with_no_windows_(false) {
Init();
}
@@ -208,7 +209,8 @@ SessionService::SessionService(const FilePath& save_path)
move_on_new_browser_(false),
save_delay_in_millis_(base::TimeDelta::FromMilliseconds(2500)),
save_delay_in_mins_(base::TimeDelta::FromMinutes(10)),
- save_delay_in_hrs_(base::TimeDelta::FromHours(8)) {
+ save_delay_in_hrs_(base::TimeDelta::FromHours(8)),
+ force_browser_not_alive_with_no_windows_(false) {
Init();
}
@@ -525,7 +527,10 @@ bool SessionService::ShouldNewWindowStartSession() {
// ChromeOS and OSX have different ideas of application lifetime than
// the other platforms.
// On ChromeOS opening a new window should never start a new session.
-#if !defined(OS_CHROMEOS)
+#if defined(OS_CHROMEOS)
+ if (!force_browser_not_alive_with_no_windows_)
+ return false;
+#endif
if (!has_open_trackable_browsers_ &&
!BrowserInit::InSynchronousProfileLaunch() &&
!SessionRestore::IsRestoring(profile())
@@ -537,7 +542,6 @@ bool SessionService::ShouldNewWindowStartSession() {
) {
return true;
}
-#endif // !OS_CHROMEOS
return false;
}
diff --git a/chrome/browser/sessions/session_service.h b/chrome/browser/sessions/session_service.h
index b5c5a3f..781fa9c 100644
--- a/chrome/browser/sessions/session_service.h
+++ b/chrome/browser/sessions/session_service.h
@@ -53,7 +53,8 @@ class NavigationEntry;
// of the browser.
class SessionService : public BaseSessionService,
public content::NotificationObserver {
- friend class SessionServiceTestHelper;
+ friend class SessionRestoreTest;
+ friend class SessionServiceTestHelper;
public:
// Used to distinguish an application window from a normal one.
enum AppType {
@@ -387,6 +388,7 @@ class SessionService : public BaseSessionService,
// windows or similar. In this case, we record the close as pending.
return !has_open_trackable_browsers_ &&
(!browser_defaults::kBrowserAliveWithNoWindows ||
+ force_browser_not_alive_with_no_windows_ ||
BrowserList::size() > 1);
}
@@ -462,6 +464,10 @@ class SessionService : public BaseSessionService,
const base::TimeDelta save_delay_in_mins_;
const base::TimeDelta save_delay_in_hrs_;
+ // For browser_tests, since we want to simulate the browser shutting down
+ // without quitting.
+ bool force_browser_not_alive_with_no_windows_;
+
DISALLOW_COPY_AND_ASSIGN(SessionService);
};