summaryrefslogtreecommitdiffstats
path: root/chrome/browser/ui/browser_browsertest.cc
diff options
context:
space:
mode:
authorsky@chromium.org <sky@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2011-07-28 16:25:14 +0000
committersky@chromium.org <sky@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2011-07-28 16:25:14 +0000
commitde4943f2cb9c8ce44812b94efa878bfb1c0f5e97 (patch)
tree95646f1151727c6f6df63df3189ed8b55a7ab8ac /chrome/browser/ui/browser_browsertest.cc
parent03b2dba54bfbc9cc9cce3ff08f8ca8101d891956 (diff)
downloadchromium_src-de4943f2cb9c8ce44812b94efa878bfb1c0f5e97.zip
chromium_src-de4943f2cb9c8ce44812b94efa878bfb1c0f5e97.tar.gz
chromium_src-de4943f2cb9c8ce44812b94efa878bfb1c0f5e97.tar.bz2
Attempt 2 at:
Adds a test to make sure Chrome doesn't crash on startup when configure to open maximized. Also, I'm making OnWidgetMove a little less error prone. BUG=89843 TEST=none R=pkasting@chromium.org TBR=pkasting@chromium.org Review URL: http://codereview.chromium.org/7514044 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@94476 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'chrome/browser/ui/browser_browsertest.cc')
-rw-r--r--chrome/browser/ui/browser_browsertest.cc871
1 files changed, 871 insertions, 0 deletions
diff --git a/chrome/browser/ui/browser_browsertest.cc b/chrome/browser/ui/browser_browsertest.cc
new file mode 100644
index 0000000..0b20a83
--- /dev/null
+++ b/chrome/browser/ui/browser_browsertest.cc
@@ -0,0 +1,871 @@
+// Copyright (c) 2011 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 <string>
+
+#include "base/compiler_specific.h"
+#include "base/file_path.h"
+#include "base/sys_info.h"
+#include "base/utf_string_conversions.h"
+#include "chrome/app/chrome_command_ids.h"
+#include "chrome/browser/defaults.h"
+#include "chrome/browser/extensions/extension_browsertest.h"
+#include "chrome/browser/extensions/extension_service.h"
+#include "chrome/browser/extensions/extension_tab_helper.h"
+#include "chrome/browser/profiles/profile.h"
+#include "chrome/browser/tabs/pinned_tab_codec.h"
+#include "chrome/browser/tabs/tab_strip_model.h"
+#include "chrome/browser/translate/translate_tab_helper.h"
+#include "chrome/browser/ui/app_modal_dialogs/app_modal_dialog.h"
+#include "chrome/browser/ui/app_modal_dialogs/js_modal_dialog.h"
+#include "chrome/browser/ui/app_modal_dialogs/native_app_modal_dialog.h"
+#include "chrome/browser/ui/browser.h"
+#include "chrome/browser/ui/browser_init.h"
+#include "chrome/browser/ui/browser_list.h"
+#include "chrome/browser/ui/browser_navigator.h"
+#include "chrome/browser/ui/browser_window.h"
+#include "chrome/browser/ui/tab_contents/tab_contents_wrapper.h"
+#include "chrome/common/chrome_notification_types.h"
+#include "chrome/common/chrome_switches.h"
+#include "chrome/common/extensions/extension.h"
+#include "chrome/common/url_constants.h"
+#include "chrome/test/in_process_browser_test.h"
+#include "chrome/test/ui_test_utils.h"
+#include "content/browser/renderer_host/render_process_host.h"
+#include "content/browser/renderer_host/render_view_host.h"
+#include "content/browser/tab_contents/tab_contents.h"
+#include "content/common/notification_source.h"
+#include "content/common/page_transition_types.h"
+#include "grit/chromium_strings.h"
+#include "grit/generated_resources.h"
+#include "net/base/mock_host_resolver.h"
+#include "net/test/test_server.h"
+#include "ui/base/l10n/l10n_util.h"
+
+#if defined(OS_WIN)
+#include "base/i18n/rtl.h"
+#include "chrome/browser/browser_process.h"
+#endif
+
+namespace {
+
+const char* kBeforeUnloadHTML =
+ "<html><head><title>beforeunload</title></head><body>"
+ "<script>window.onbeforeunload=function(e){return 'foo'}</script>"
+ "</body></html>";
+
+const char* kOpenNewBeforeUnloadPage =
+ "w=window.open(); w.onbeforeunload=function(e){return 'foo'};";
+
+const FilePath::CharType* kBeforeUnloadFile =
+ FILE_PATH_LITERAL("beforeunload.html");
+
+const FilePath::CharType* kTitle1File = FILE_PATH_LITERAL("title1.html");
+const FilePath::CharType* kTitle2File = FILE_PATH_LITERAL("title2.html");
+
+const FilePath::CharType kDocRoot[] = FILE_PATH_LITERAL("chrome/test/data");
+
+// Given a page title, returns the expected window caption string.
+std::wstring WindowCaptionFromPageTitle(std::wstring page_title) {
+#if defined(OS_MACOSX) || defined(OS_CHROMEOS)
+ // On Mac or ChromeOS, we don't want to suffix the page title with
+ // the application name.
+ if (page_title.empty()) {
+ return UTF16ToWideHack(
+ l10n_util::GetStringUTF16(IDS_BROWSER_WINDOW_MAC_TAB_UNTITLED));
+ }
+ return page_title;
+#else
+ if (page_title.empty())
+ return UTF16ToWideHack(l10n_util::GetStringUTF16(IDS_PRODUCT_NAME));
+
+ return UTF16ToWideHack(
+ l10n_util::GetStringFUTF16(IDS_BROWSER_WINDOW_TITLE_FORMAT,
+ WideToUTF16Hack(page_title)));
+#endif
+}
+
+// Returns the number of active RenderProcessHosts.
+int CountRenderProcessHosts() {
+ int result = 0;
+ for (RenderProcessHost::iterator i(RenderProcessHost::AllHostsIterator());
+ !i.IsAtEnd(); i.Advance())
+ ++result;
+ return result;
+}
+
+class MockTabStripModelObserver : public TabStripModelObserver {
+ public:
+ MockTabStripModelObserver() : closing_count_(0) {}
+
+ virtual void TabClosingAt(TabStripModel* tab_strip_model,
+ TabContentsWrapper* contents,
+ int index) {
+ closing_count_++;
+ }
+
+ int closing_count() const { return closing_count_; }
+
+ private:
+ int closing_count_;
+
+ DISALLOW_COPY_AND_ASSIGN(MockTabStripModelObserver);
+};
+
+// Used by CloseWithAppMenuOpen. Invokes CloseWindow on the supplied browser.
+class CloseWindowTask : public Task {
+ public:
+ explicit CloseWindowTask(Browser* browser) : browser_(browser) {}
+
+ virtual void Run() {
+ browser_->CloseWindow();
+ }
+
+ private:
+ Browser* browser_;
+
+ DISALLOW_COPY_AND_ASSIGN(CloseWindowTask);
+};
+
+// Used by CloseWithAppMenuOpen. Posts a CloseWindowTask and shows the app menu.
+class RunCloseWithAppMenuTask : public Task {
+ public:
+ explicit RunCloseWithAppMenuTask(Browser* browser) : browser_(browser) {}
+
+ virtual void Run() {
+ // ShowAppMenu is modal under views. Schedule a task that closes the window.
+ MessageLoop::current()->PostTask(FROM_HERE, new CloseWindowTask(browser_));
+ browser_->ShowAppMenu();
+ }
+
+ private:
+ Browser* browser_;
+
+ DISALLOW_COPY_AND_ASSIGN(RunCloseWithAppMenuTask);
+};
+
+} // namespace
+
+class BrowserTest : public ExtensionBrowserTest {
+ protected:
+ // In RTL locales wrap the page title with RTL embedding characters so that it
+ // matches the value returned by GetWindowTitle().
+ std::wstring LocaleWindowCaptionFromPageTitle(
+ const std::wstring& expected_title) {
+ std::wstring page_title = WindowCaptionFromPageTitle(expected_title);
+#if defined(OS_WIN)
+ std::string locale = g_browser_process->GetApplicationLocale();
+ if (base::i18n::GetTextDirectionForLocale(locale.c_str()) ==
+ base::i18n::RIGHT_TO_LEFT) {
+ base::i18n::WrapStringWithLTRFormatting(&page_title);
+ }
+
+ return page_title;
+#else
+ // Do we need to use the above code on POSIX as well?
+ return page_title;
+#endif
+ }
+
+ // Returns the app extension aptly named "App Test".
+ const Extension* GetExtension() {
+ const ExtensionList* extensions =
+ browser()->profile()->GetExtensionService()->extensions();
+ for (size_t i = 0; i < extensions->size(); ++i) {
+ if ((*extensions)[i]->name() == "App Test")
+ return (*extensions)[i];
+ }
+ NOTREACHED();
+ return NULL;
+ }
+};
+
+// Launch the app on a page with no title, check that the app title was set
+// correctly.
+IN_PROC_BROWSER_TEST_F(BrowserTest, NoTitle) {
+ ui_test_utils::NavigateToURL(browser(),
+ ui_test_utils::GetTestUrl(FilePath(FilePath::kCurrentDirectory),
+ FilePath(kTitle1File)));
+ EXPECT_EQ(LocaleWindowCaptionFromPageTitle(L"title1.html"),
+ UTF16ToWideHack(browser()->GetWindowTitleForCurrentTab()));
+ string16 tab_title;
+ ASSERT_TRUE(ui_test_utils::GetCurrentTabTitle(browser(), &tab_title));
+ EXPECT_EQ(ASCIIToUTF16("title1.html"), tab_title);
+}
+
+// Launch the app, navigate to a page with a title, check that the app title
+// was set correctly.
+IN_PROC_BROWSER_TEST_F(BrowserTest, Title) {
+ ui_test_utils::NavigateToURL(browser(),
+ ui_test_utils::GetTestUrl(FilePath(FilePath::kCurrentDirectory),
+ FilePath(kTitle2File)));
+ const std::wstring test_title(L"Title Of Awesomeness");
+ EXPECT_EQ(LocaleWindowCaptionFromPageTitle(test_title),
+ UTF16ToWideHack(browser()->GetWindowTitleForCurrentTab()));
+ string16 tab_title;
+ ASSERT_TRUE(ui_test_utils::GetCurrentTabTitle(browser(), &tab_title));
+ EXPECT_EQ(WideToUTF16(test_title), tab_title);
+}
+
+IN_PROC_BROWSER_TEST_F(BrowserTest, JavascriptAlertActivatesTab) {
+ GURL url(ui_test_utils::GetTestUrl(FilePath(FilePath::kCurrentDirectory),
+ FilePath(kTitle1File)));
+ ui_test_utils::NavigateToURL(browser(), url);
+ AddTabAtIndex(0, url, PageTransition::TYPED);
+ EXPECT_EQ(2, browser()->tab_count());
+ EXPECT_EQ(0, browser()->active_index());
+ TabContents* second_tab = browser()->GetTabContentsAt(1);
+ ASSERT_TRUE(second_tab);
+ second_tab->render_view_host()->ExecuteJavascriptInWebFrame(
+ string16(),
+ ASCIIToUTF16("alert('Activate!');"));
+ AppModalDialog* alert = ui_test_utils::WaitForAppModalDialog();
+ alert->CloseModalDialog();
+ EXPECT_EQ(2, browser()->tab_count());
+ EXPECT_EQ(1, browser()->active_index());
+}
+
+
+
+#if defined(OS_WIN)
+// http://crbug.com/75274. On XP crashes inside
+// URLFetcher::Core::Registry::RemoveURLFetcherCore.
+#define MAYBE_ThirtyFourTabs FLAKY_ThirtyFourTabs
+#else
+#define MAYBE_ThirtyFourTabs ThirtyFourTabs
+#endif
+
+// Create 34 tabs and verify that a lot of processes have been created. The
+// exact number of processes depends on the amount of memory. Previously we
+// had a hard limit of 31 processes and this test is mainly directed at
+// verifying that we don't crash when we pass this limit.
+// Warning: this test can take >30 seconds when running on a slow (low
+// memory?) Mac builder.
+IN_PROC_BROWSER_TEST_F(BrowserTest, MAYBE_ThirtyFourTabs) {
+ GURL url(ui_test_utils::GetTestUrl(FilePath(FilePath::kCurrentDirectory),
+ FilePath(kTitle2File)));
+
+ // There is one initial tab.
+ for (int ix = 0; ix != 33; ++ix)
+ browser()->AddSelectedTabWithURL(url, PageTransition::TYPED);
+ EXPECT_EQ(34, browser()->tab_count());
+
+ // See browser\renderer_host\render_process_host.cc for the algorithm to
+ // decide how many processes to create.
+ if (base::SysInfo::AmountOfPhysicalMemoryMB() >= 2048) {
+ EXPECT_GE(CountRenderProcessHosts(), 24);
+ } else {
+ EXPECT_LE(CountRenderProcessHosts(), 23);
+ }
+}
+
+// Test for crbug.com/22004. Reloading a page with a before unload handler and
+// then canceling the dialog should not leave the throbber spinning.
+IN_PROC_BROWSER_TEST_F(BrowserTest, ReloadThenCancelBeforeUnload) {
+ GURL url(std::string("data:text/html,") + kBeforeUnloadHTML);
+ ui_test_utils::NavigateToURL(browser(), url);
+
+ // Navigate to another page, but click cancel in the dialog. Make sure that
+ // the throbber stops spinning.
+ browser()->Reload(CURRENT_TAB);
+ AppModalDialog* alert = ui_test_utils::WaitForAppModalDialog();
+ alert->CloseModalDialog();
+ EXPECT_FALSE(browser()->GetSelectedTabContents()->IsLoading());
+
+ // Clear the beforeunload handler so the test can easily exit.
+ browser()->GetSelectedTabContents()->render_view_host()->
+ ExecuteJavascriptInWebFrame(string16(),
+ ASCIIToUTF16("onbeforeunload=null;"));
+}
+
+// Test for crbug.com/80401. Canceling a before unload dialog should reset
+// the URL to the previous page's URL.
+IN_PROC_BROWSER_TEST_F(BrowserTest, CancelBeforeUnloadResetsURL) {
+ GURL url(ui_test_utils::GetTestUrl(FilePath(FilePath::kCurrentDirectory),
+ FilePath(kBeforeUnloadFile)));
+ ui_test_utils::NavigateToURL(browser(), url);
+
+ // Navigate to a page that triggers a cross-site transition.
+ ASSERT_TRUE(test_server()->Start());
+ GURL url2(test_server()->GetURL("files/title1.html"));
+ browser()->OpenURL(url2, GURL(), CURRENT_TAB, PageTransition::TYPED);
+
+ // Cancel the dialog.
+ AppModalDialog* alert = ui_test_utils::WaitForAppModalDialog();
+ alert->CloseModalDialog();
+ EXPECT_FALSE(browser()->GetSelectedTabContents()->IsLoading());
+
+ // Wait for the ShouldClose_ACK to arrive. We can detect it by waiting for
+ // the pending RVH to be destroyed.
+ ui_test_utils::WaitForNotification(
+ content::NOTIFICATION_RENDER_WIDGET_HOST_DESTROYED);
+ EXPECT_EQ(url.spec(), WideToUTF8(browser()->toolbar_model()->GetText()));
+
+ // Clear the beforeunload handler so the test can easily exit.
+ browser()->GetSelectedTabContents()->render_view_host()->
+ ExecuteJavascriptInWebFrame(string16(),
+ ASCIIToUTF16("onbeforeunload=null;"));
+}
+
+// Crashy on mac. http://crbug.com/38522
+#if defined(OS_MACOSX)
+#define MAYBE_SingleBeforeUnloadAfterWindowClose \
+ DISABLED_SingleBeforeUnloadAfterWindowClose
+#else
+#define MAYBE_SingleBeforeUnloadAfterWindowClose \
+ SingleBeforeUnloadAfterWindowClose
+#endif
+
+// Test for crbug.com/11647. A page closed with window.close() should not have
+// two beforeunload dialogs shown.
+IN_PROC_BROWSER_TEST_F(BrowserTest, MAYBE_SingleBeforeUnloadAfterWindowClose) {
+ browser()->GetSelectedTabContents()->render_view_host()->
+ ExecuteJavascriptInWebFrame(string16(),
+ ASCIIToUTF16(kOpenNewBeforeUnloadPage));
+
+ // Close the new window with JavaScript, which should show a single
+ // beforeunload dialog. Then show another alert, to make it easy to verify
+ // that a second beforeunload dialog isn't shown.
+ browser()->GetTabContentsAt(0)->render_view_host()->
+ ExecuteJavascriptInWebFrame(string16(),
+ ASCIIToUTF16("w.close(); alert('bar');"));
+ AppModalDialog* alert = ui_test_utils::WaitForAppModalDialog();
+ alert->native_dialog()->AcceptAppModalDialog();
+
+ alert = ui_test_utils::WaitForAppModalDialog();
+ EXPECT_FALSE(static_cast<JavaScriptAppModalDialog*>(alert)->
+ is_before_unload_dialog());
+ alert->native_dialog()->AcceptAppModalDialog();
+}
+
+// Test that get_process_idle_time() returns reasonable values when compared
+// with time deltas measured locally.
+IN_PROC_BROWSER_TEST_F(BrowserTest, RenderIdleTime) {
+ base::TimeTicks start = base::TimeTicks::Now();
+ ui_test_utils::NavigateToURL(browser(),
+ ui_test_utils::GetTestUrl(FilePath(FilePath::kCurrentDirectory),
+ FilePath(kTitle1File)));
+ RenderProcessHost::iterator it(RenderProcessHost::AllHostsIterator());
+ for (; !it.IsAtEnd(); it.Advance()) {
+ base::TimeDelta renderer_td =
+ it.GetCurrentValue()->get_child_process_idle_time();
+ base::TimeDelta browser_td = base::TimeTicks::Now() - start;
+ EXPECT_TRUE(browser_td >= renderer_td);
+ }
+}
+
+// Test IDC_CREATE_SHORTCUTS command is enabled for url scheme file, ftp, http
+// and https and disabled for chrome://, about:// etc.
+// TODO(pinkerton): Disable app-mode in the model until we implement it
+// on the Mac. http://crbug.com/13148
+#if !defined(OS_MACOSX)
+IN_PROC_BROWSER_TEST_F(BrowserTest, CommandCreateAppShortcutFile) {
+ CommandUpdater* command_updater = browser()->command_updater();
+
+ static const FilePath::CharType* kEmptyFile = FILE_PATH_LITERAL("empty.html");
+ GURL file_url(ui_test_utils::GetTestUrl(FilePath(FilePath::kCurrentDirectory),
+ FilePath(kEmptyFile)));
+ ASSERT_TRUE(file_url.SchemeIs(chrome::kFileScheme));
+ ui_test_utils::NavigateToURL(browser(), file_url);
+ EXPECT_TRUE(command_updater->IsCommandEnabled(IDC_CREATE_SHORTCUTS));
+}
+
+IN_PROC_BROWSER_TEST_F(BrowserTest, CommandCreateAppShortcutHttp) {
+ CommandUpdater* command_updater = browser()->command_updater();
+
+ ASSERT_TRUE(test_server()->Start());
+ GURL http_url(test_server()->GetURL(""));
+ ASSERT_TRUE(http_url.SchemeIs(chrome::kHttpScheme));
+ ui_test_utils::NavigateToURL(browser(), http_url);
+ EXPECT_TRUE(command_updater->IsCommandEnabled(IDC_CREATE_SHORTCUTS));
+}
+
+IN_PROC_BROWSER_TEST_F(BrowserTest, CommandCreateAppShortcutHttps) {
+ CommandUpdater* command_updater = browser()->command_updater();
+
+ net::TestServer test_server(net::TestServer::TYPE_HTTPS, FilePath(kDocRoot));
+ ASSERT_TRUE(test_server.Start());
+ GURL https_url(test_server.GetURL("/"));
+ ASSERT_TRUE(https_url.SchemeIs(chrome::kHttpsScheme));
+ ui_test_utils::NavigateToURL(browser(), https_url);
+ EXPECT_TRUE(command_updater->IsCommandEnabled(IDC_CREATE_SHORTCUTS));
+}
+
+IN_PROC_BROWSER_TEST_F(BrowserTest, CommandCreateAppShortcutFtp) {
+ CommandUpdater* command_updater = browser()->command_updater();
+
+ net::TestServer test_server(net::TestServer::TYPE_FTP, FilePath(kDocRoot));
+ ASSERT_TRUE(test_server.Start());
+ GURL ftp_url(test_server.GetURL(""));
+ ASSERT_TRUE(ftp_url.SchemeIs(chrome::kFtpScheme));
+ ui_test_utils::NavigateToURL(browser(), ftp_url);
+ EXPECT_TRUE(command_updater->IsCommandEnabled(IDC_CREATE_SHORTCUTS));
+}
+
+IN_PROC_BROWSER_TEST_F(BrowserTest, CommandCreateAppShortcutInvalid) {
+ CommandUpdater* command_updater = browser()->command_updater();
+
+ // Urls that should not have shortcuts.
+ GURL new_tab_url(chrome::kChromeUINewTabURL);
+ ui_test_utils::NavigateToURL(browser(), new_tab_url);
+ EXPECT_FALSE(command_updater->IsCommandEnabled(IDC_CREATE_SHORTCUTS));
+
+ GURL history_url(chrome::kChromeUIHistoryURL);
+ ui_test_utils::NavigateToURL(browser(), history_url);
+ EXPECT_FALSE(command_updater->IsCommandEnabled(IDC_CREATE_SHORTCUTS));
+
+ GURL downloads_url(chrome::kChromeUIDownloadsURL);
+ ui_test_utils::NavigateToURL(browser(), downloads_url);
+ EXPECT_FALSE(command_updater->IsCommandEnabled(IDC_CREATE_SHORTCUTS));
+
+ GURL blank_url(chrome::kAboutBlankURL);
+ ui_test_utils::NavigateToURL(browser(), blank_url);
+ EXPECT_FALSE(command_updater->IsCommandEnabled(IDC_CREATE_SHORTCUTS));
+}
+
+// Change a tab into an application window.
+// DISABLED: http://crbug.com/72310
+IN_PROC_BROWSER_TEST_F(BrowserTest, DISABLED_ConvertTabToAppShortcut) {
+ ASSERT_TRUE(test_server()->Start());
+ GURL http_url(test_server()->GetURL(""));
+ ASSERT_TRUE(http_url.SchemeIs(chrome::kHttpScheme));
+
+ ASSERT_EQ(1, browser()->tab_count());
+ TabContents* initial_tab = browser()->GetTabContentsAt(0);
+ TabContents* app_tab = browser()->AddSelectedTabWithURL(
+ http_url, PageTransition::TYPED)->tab_contents();
+ ASSERT_EQ(2, browser()->tab_count());
+ ASSERT_EQ(1u, BrowserList::GetBrowserCount(browser()->profile()));
+
+ // Normal tabs should accept load drops.
+ EXPECT_TRUE(initial_tab->GetMutableRendererPrefs()->can_accept_load_drops);
+ EXPECT_TRUE(app_tab->GetMutableRendererPrefs()->can_accept_load_drops);
+
+ // Turn |app_tab| into a tab in an app panel.
+ browser()->ConvertContentsToApplication(app_tab);
+
+ // The launch should have created a new browser.
+ ASSERT_EQ(2u, BrowserList::GetBrowserCount(browser()->profile()));
+
+ // Find the new browser.
+ Browser* app_browser = NULL;
+ for (BrowserList::const_iterator i = BrowserList::begin();
+ i != BrowserList::end() && !app_browser; ++i) {
+ if (*i != browser())
+ app_browser = *i;
+ }
+ ASSERT_TRUE(app_browser);
+
+ // Check that the tab contents is in the new browser, and not in the old.
+ ASSERT_EQ(1, browser()->tab_count());
+ ASSERT_EQ(initial_tab, browser()->GetTabContentsAt(0));
+
+ // Check that the appliaction browser has a single tab, and that tab contains
+ // the content that we app-ified.
+ ASSERT_EQ(1, app_browser->tab_count());
+ ASSERT_EQ(app_tab, app_browser->GetTabContentsAt(0));
+
+ // Normal tabs should accept load drops.
+ EXPECT_TRUE(initial_tab->GetMutableRendererPrefs()->can_accept_load_drops);
+
+ // The tab in an app window should not.
+ EXPECT_FALSE(app_tab->GetMutableRendererPrefs()->can_accept_load_drops);
+}
+
+#endif // !defined(OS_MACOSX)
+
+// Test RenderView correctly send back favicon url for web page that redirects
+// to an anchor in javascript body.onload handler.
+IN_PROC_BROWSER_TEST_F(BrowserTest,
+ DISABLED_FaviconOfOnloadRedirectToAnchorPage) {
+ ASSERT_TRUE(test_server()->Start());
+ GURL url(test_server()->GetURL("files/onload_redirect_to_anchor.html"));
+ GURL expected_favicon_url(test_server()->GetURL("files/test.png"));
+
+ ui_test_utils::NavigateToURL(browser(), url);
+
+ NavigationEntry* entry = browser()->GetSelectedTabContents()->
+ controller().GetActiveEntry();
+ EXPECT_EQ(expected_favicon_url.spec(), entry->favicon().url().spec());
+}
+
+#if defined(OS_MACOSX) || defined(OS_LINUX)
+// http://crbug.com/83828. On Mac 10.6, the failure rate is 14%
+#define MAYBE_FaviconChange FLAKY_FaviconChange
+#else
+#define MAYBE_FaviconChange FaviconChange
+#endif
+// Test that an icon can be changed from JS.
+IN_PROC_BROWSER_TEST_F(BrowserTest, MAYBE_FaviconChange) {
+ static const FilePath::CharType* kFile =
+ FILE_PATH_LITERAL("onload_change_favicon.html");
+ GURL file_url(ui_test_utils::GetTestUrl(FilePath(FilePath::kCurrentDirectory),
+ FilePath(kFile)));
+ ASSERT_TRUE(file_url.SchemeIs(chrome::kFileScheme));
+ ui_test_utils::NavigateToURL(browser(), file_url);
+
+ NavigationEntry* entry = browser()->GetSelectedTabContents()->
+ controller().GetActiveEntry();
+ static const FilePath::CharType* kIcon =
+ FILE_PATH_LITERAL("test1.png");
+ GURL expected_favicon_url(
+ ui_test_utils::GetTestUrl(FilePath(FilePath::kCurrentDirectory),
+ FilePath(kIcon)));
+ EXPECT_EQ(expected_favicon_url.spec(), entry->favicon().url().spec());
+}
+
+// Makes sure TabClosing is sent when uninstalling an extension that is an app
+// tab.
+IN_PROC_BROWSER_TEST_F(BrowserTest, TabClosingWhenRemovingExtension) {
+ ASSERT_TRUE(test_server()->Start());
+ host_resolver()->AddRule("www.example.com", "127.0.0.1");
+ GURL url(test_server()->GetURL("empty.html"));
+ TabStripModel* model = browser()->tabstrip_model();
+
+ ASSERT_TRUE(LoadExtension(test_data_dir_.AppendASCII("app/")));
+
+ const Extension* extension_app = GetExtension();
+
+ ui_test_utils::NavigateToURL(browser(), url);
+
+ TabContentsWrapper* app_contents =
+ Browser::TabContentsFactory(browser()->profile(), NULL,
+ MSG_ROUTING_NONE, NULL, NULL);
+ app_contents->extension_tab_helper()->SetExtensionApp(extension_app);
+
+ model->AddTabContents(app_contents, 0, 0, TabStripModel::ADD_NONE);
+ model->SetTabPinned(0, true);
+ ui_test_utils::NavigateToURL(browser(), url);
+
+ MockTabStripModelObserver observer;
+ model->AddObserver(&observer);
+
+ // Uninstall the extension and make sure TabClosing is sent.
+ ExtensionService* service = browser()->profile()->GetExtensionService();
+ service->UninstallExtension(GetExtension()->id(), false, NULL);
+ EXPECT_EQ(1, observer.closing_count());
+
+ model->RemoveObserver(&observer);
+
+ // There should only be one tab now.
+ ASSERT_EQ(1, browser()->tab_count());
+}
+
+#if !defined(OS_MACOSX)
+// Open with --app-id=<id>, and see that an app window opens.
+IN_PROC_BROWSER_TEST_F(BrowserTest, AppIdSwitch) {
+ ASSERT_TRUE(test_server()->Start());
+
+ // Load an app.
+ host_resolver()->AddRule("www.example.com", "127.0.0.1");
+ ASSERT_TRUE(LoadExtension(test_data_dir_.AppendASCII("app/")));
+ const Extension* extension_app = GetExtension();
+
+ CommandLine command_line(CommandLine::NO_PROGRAM);
+ command_line.AppendSwitchASCII(switches::kAppId, extension_app->id());
+
+ BrowserInit::LaunchWithProfile launch(FilePath(), command_line);
+ ASSERT_TRUE(launch.OpenApplicationWindow(browser()->profile()));
+
+ // Check that the new browser has an app name.
+ // The launch should have created a new browser.
+ ASSERT_EQ(2u, BrowserList::GetBrowserCount(browser()->profile()));
+
+ // Find the new browser.
+ Browser* new_browser = NULL;
+ for (BrowserList::const_iterator i = BrowserList::begin();
+ i != BrowserList::end() && !new_browser; ++i) {
+ if (*i != browser())
+ new_browser = *i;
+ }
+ ASSERT_TRUE(new_browser);
+ ASSERT_TRUE(new_browser != browser());
+
+ // The browser's app_name should include the app's ID.
+ ASSERT_NE(
+ new_browser->app_name_.find(extension_app->id()),
+ std::string::npos) << new_browser->app_name_;
+}
+#endif
+
+#if defined(OS_WIN) || defined(OS_MACOSX)
+// http://crbug.com/46198: On XP/Vista, the failure rate is 5 ~ 6%.
+// On OS 10.5 it's 1%, 10.6 currently 4%.
+#define MAYBE_PageLanguageDetection FLAKY_PageLanguageDetection
+#else
+#define MAYBE_PageLanguageDetection PageLanguageDetection
+#endif
+// Tests that the CLD (Compact Language Detection) works properly.
+IN_PROC_BROWSER_TEST_F(BrowserTest, MAYBE_PageLanguageDetection) {
+ ASSERT_TRUE(test_server()->Start());
+
+ std::string lang;
+
+ // Open a new tab with a page in English.
+ AddTabAtIndex(0, GURL(test_server()->GetURL("files/english_page.html")),
+ PageTransition::TYPED);
+
+ TabContents* current_tab = browser()->GetSelectedTabContents();
+ TabContentsWrapper* wrapper = browser()->GetSelectedTabContentsWrapper();
+ TranslateTabHelper* helper = wrapper->translate_tab_helper();
+ Source<TabContents> source(current_tab);
+
+ ui_test_utils::WindowedNotificationObserverWithDetails<std::string>
+ en_language_detected_signal(chrome::NOTIFICATION_TAB_LANGUAGE_DETERMINED,
+ source);
+ EXPECT_EQ("", helper->language_state().original_language());
+ en_language_detected_signal.Wait();
+ EXPECT_TRUE(en_language_detected_signal.GetDetailsFor(
+ source.map_key(), &lang));
+ EXPECT_EQ("en", lang);
+ EXPECT_EQ("en", helper->language_state().original_language());
+
+ // Now navigate to a page in French.
+ ui_test_utils::WindowedNotificationObserverWithDetails<std::string>
+ fr_language_detected_signal(chrome::NOTIFICATION_TAB_LANGUAGE_DETERMINED,
+ source);
+ ui_test_utils::NavigateToURL(
+ browser(), GURL(test_server()->GetURL("files/french_page.html")));
+ fr_language_detected_signal.Wait();
+ lang.clear();
+ EXPECT_TRUE(fr_language_detected_signal.GetDetailsFor(
+ source.map_key(), &lang));
+ EXPECT_EQ("fr", lang);
+ EXPECT_EQ("fr", helper->language_state().original_language());
+}
+
+// Chromeos defaults to restoring the last session, so this test isn't
+// applicable.
+#if !defined(OS_CHROMEOS)
+#if defined(OS_MACOSX)
+// Crashy, http://crbug.com/38522
+#define RestorePinnedTabs DISABLED_RestorePinnedTabs
+#endif
+// Makes sure pinned tabs are restored correctly on start.
+IN_PROC_BROWSER_TEST_F(BrowserTest, RestorePinnedTabs) {
+ ASSERT_TRUE(test_server()->Start());
+
+ // Add an pinned app tab.
+ host_resolver()->AddRule("www.example.com", "127.0.0.1");
+ GURL url(test_server()->GetURL("empty.html"));
+ TabStripModel* model = browser()->tabstrip_model();
+ ASSERT_TRUE(LoadExtension(test_data_dir_.AppendASCII("app/")));
+ const Extension* extension_app = GetExtension();
+ ui_test_utils::NavigateToURL(browser(), url);
+ TabContentsWrapper* app_contents =
+ Browser::TabContentsFactory(browser()->profile(), NULL,
+ MSG_ROUTING_NONE, NULL, NULL);
+ app_contents->extension_tab_helper()->SetExtensionApp(extension_app);
+ model->AddTabContents(app_contents, 0, 0, TabStripModel::ADD_NONE);
+ model->SetTabPinned(0, true);
+ ui_test_utils::NavigateToURL(browser(), url);
+
+ // Add a non pinned tab.
+ browser()->NewTab();
+
+ // Add a pinned non-app tab.
+ browser()->NewTab();
+ ui_test_utils::NavigateToURL(browser(), GURL("about:blank"));
+ model->SetTabPinned(2, true);
+
+ // Write out the pinned tabs.
+ PinnedTabCodec::WritePinnedTabs(browser()->profile());
+
+ // Simulate launching again.
+ CommandLine dummy(CommandLine::NO_PROGRAM);
+ BrowserInit::LaunchWithProfile launch(FilePath(), dummy);
+ launch.profile_ = browser()->profile();
+ launch.ProcessStartupURLs(std::vector<GURL>());
+
+ // The launch should have created a new browser.
+ ASSERT_EQ(2u, BrowserList::GetBrowserCount(browser()->profile()));
+
+ // Find the new browser.
+ Browser* new_browser = NULL;
+ for (BrowserList::const_iterator i = BrowserList::begin();
+ i != BrowserList::end() && !new_browser; ++i) {
+ if (*i != browser())
+ new_browser = *i;
+ }
+ ASSERT_TRUE(new_browser);
+ ASSERT_TRUE(new_browser != browser());
+
+ // We should get back an additional tab for the app, and another for the
+ // default home page.
+ ASSERT_EQ(3, new_browser->tab_count());
+
+ // Make sure the state matches.
+ TabStripModel* new_model = new_browser->tabstrip_model();
+ EXPECT_TRUE(new_model->IsAppTab(0));
+ EXPECT_FALSE(new_model->IsAppTab(1));
+ EXPECT_FALSE(new_model->IsAppTab(2));
+
+ EXPECT_TRUE(new_model->IsTabPinned(0));
+ EXPECT_TRUE(new_model->IsTabPinned(1));
+ EXPECT_FALSE(new_model->IsTabPinned(2));
+
+ EXPECT_EQ(browser()->GetHomePage(),
+ new_model->GetTabContentsAt(2)->tab_contents()->GetURL());
+
+ EXPECT_TRUE(
+ new_model->GetTabContentsAt(0)->extension_tab_helper()->extension_app() ==
+ extension_app);
+}
+#endif // !defined(OS_CHROMEOS)
+
+// This test verifies we don't crash when closing the last window and the app
+// menu is showing.
+IN_PROC_BROWSER_TEST_F(BrowserTest, CloseWithAppMenuOpen) {
+ if (browser_defaults::kBrowserAliveWithNoWindows)
+ return;
+
+ // We need a message loop running for menus on windows.
+ MessageLoop::current()->PostTask(FROM_HERE,
+ new RunCloseWithAppMenuTask(browser()));
+}
+
+#if !defined(OS_MACOSX)
+IN_PROC_BROWSER_TEST_F(BrowserTest, OpenAppWindowLikeNtp) {
+ ASSERT_TRUE(test_server()->Start());
+
+ // Load an app
+ host_resolver()->AddRule("www.example.com", "127.0.0.1");
+ ASSERT_TRUE(LoadExtension(test_data_dir_.AppendASCII("app/")));
+ const Extension* extension_app = GetExtension();
+
+ // Launch it in a window, as AppLauncherHandler::HandleLaunchApp() would.
+ TabContents* app_window =
+ Browser::OpenApplication(browser()->profile(),
+ extension_app,
+ extension_misc::LAUNCH_WINDOW,
+ NEW_WINDOW);
+ ASSERT_TRUE(app_window);
+
+ // Apps launched in a window from the NTP do not have extension_app set in
+ // tab contents.
+ TabContentsWrapper* wrapper =
+ TabContentsWrapper::GetCurrentWrapperForContents(app_window);
+ EXPECT_FALSE(wrapper->extension_tab_helper()->extension_app());
+ EXPECT_EQ(extension_app->GetFullLaunchURL(), app_window->GetURL());
+
+ // The launch should have created a new browser.
+ ASSERT_EQ(2u, BrowserList::GetBrowserCount(browser()->profile()));
+
+ // Find the new browser.
+ Browser* new_browser = NULL;
+ for (BrowserList::const_iterator i = BrowserList::begin();
+ i != BrowserList::end() && !new_browser; ++i) {
+ if (*i != browser())
+ new_browser = *i;
+ }
+ ASSERT_TRUE(new_browser);
+ ASSERT_TRUE(new_browser != browser());
+
+ EXPECT_TRUE(new_browser->is_app());
+
+ // The browser's app name should include the extension's id.
+ std::string app_name = new_browser->app_name_;
+ EXPECT_NE(app_name.find(extension_app->id()), std::string::npos)
+ << "Name " << app_name << " should contain id "<< extension_app->id();
+}
+#endif // !defined(OS_MACOSX)
+
+// Makes sure the browser doesn't crash when
+// set_maximized_state(MAXIMIZED_STATE_MAXIMIZED) has been invoked.
+IN_PROC_BROWSER_TEST_F(BrowserTest, StartMaximized) {
+ // Can't test TYPE_PANEL as they are currently created differently (and can't
+ // end up maximized).
+ Browser::Type types[] = { Browser::TYPE_TABBED, Browser::TYPE_POPUP };
+ for (size_t i = 0; i < ARRAYSIZE_UNSAFE(types); ++i) {
+ Browser* max_browser = new Browser(types[i], browser()->profile());
+ max_browser->set_maximized_state(Browser::MAXIMIZED_STATE_MAXIMIZED);
+ max_browser->InitBrowserWindow();
+ AddBlankTabAndShow(max_browser);
+ }
+}
+
+// TODO(ben): this test was never enabled. It has bit-rotted since being added.
+// It originally lived in browser_unittest.cc, but has been moved here to make
+// room for real browser unit tests.
+#if 0
+class BrowserTest2 : public InProcessBrowserTest {
+ public:
+ BrowserTest2() {
+ host_resolver_proc_ = new net::RuleBasedHostResolverProc(NULL);
+ // Avoid making external DNS lookups. In this test we don't need this
+ // to succeed.
+ host_resolver_proc_->AddSimulatedFailure("*.google.com");
+ scoped_host_resolver_proc_.Init(host_resolver_proc_.get());
+ }
+
+ private:
+ scoped_refptr<net::RuleBasedHostResolverProc> host_resolver_proc_;
+ net::ScopedDefaultHostResolverProc scoped_host_resolver_proc_;
+};
+
+IN_PROC_BROWSER_TEST_F(BrowserTest2, NoTabsInPopups) {
+ Browser::RegisterAppPrefs(L"Test");
+
+ // We start with a normal browser with one tab.
+ EXPECT_EQ(1, browser()->tab_count());
+
+ // Open a popup browser with a single blank foreground tab.
+ Browser* popup_browser = browser()->CreateForType(Browser::TYPE_POPUP,
+ browser()->profile());
+ popup_browser->AddBlankTab(true);
+ EXPECT_EQ(1, popup_browser->tab_count());
+
+ // Now try opening another tab in the popup browser.
+ AddTabWithURLParams params1(url, PageTransition::TYPED);
+ popup_browser->AddTabWithURL(&params1);
+ EXPECT_EQ(popup_browser, params1.target);
+
+ // The popup should still only have one tab.
+ EXPECT_EQ(1, popup_browser->tab_count());
+
+ // The normal browser should now have two.
+ EXPECT_EQ(2, browser()->tab_count());
+
+ // Open an app frame browser with a single blank foreground tab.
+ Browser* app_browser =
+ browser()->CreateForApp(L"Test", browser()->profile(), false);
+ app_browser->AddBlankTab(true);
+ EXPECT_EQ(1, app_browser->tab_count());
+
+ // Now try opening another tab in the app browser.
+ AddTabWithURLParams params2(GURL(chrome::kAboutBlankURL),
+ PageTransition::TYPED);
+ app_browser->AddTabWithURL(&params2);
+ EXPECT_EQ(app_browser, params2.target);
+
+ // The popup should still only have one tab.
+ EXPECT_EQ(1, app_browser->tab_count());
+
+ // The normal browser should now have three.
+ EXPECT_EQ(3, browser()->tab_count());
+
+ // Open an app frame popup browser with a single blank foreground tab.
+ Browser* app_popup_browser =
+ browser()->CreateForApp(L"Test", browser()->profile(), false);
+ app_popup_browser->AddBlankTab(true);
+ EXPECT_EQ(1, app_popup_browser->tab_count());
+
+ // Now try opening another tab in the app popup browser.
+ AddTabWithURLParams params3(GURL(chrome::kAboutBlankURL),
+ PageTransition::TYPED);
+ app_popup_browser->AddTabWithURL(&params3);
+ EXPECT_EQ(app_popup_browser, params3.target);
+
+ // The popup should still only have one tab.
+ EXPECT_EQ(1, app_popup_browser->tab_count());
+
+ // The normal browser should now have four.
+ EXPECT_EQ(4, browser()->tab_count());
+
+ // Close the additional browsers.
+ popup_browser->CloseAllTabs();
+ app_browser->CloseAllTabs();
+ app_popup_browser->CloseAllTabs();
+}
+#endif