summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--chrome_frame/chrome_frame.gyp10
-rw-r--r--chrome_frame/test/automation_client_mock.cc269
-rw-r--r--chrome_frame/test/automation_client_mock.h176
-rw-r--r--chrome_frame/test/chrome_frame_unittests.cc2088
-rw-r--r--chrome_frame/test/function_stub_unittest.cc3
-rw-r--r--chrome_frame/test/html_util_unittests.cc1
-rw-r--r--chrome_frame/test/proxy_factory_mock.cc86
-rw-r--r--chrome_frame/test/proxy_factory_mock.h43
-rw-r--r--chrome_frame/test/test_mock_with_web_server.cc684
-rw-r--r--chrome_frame/test/test_mock_with_web_server.h64
-rw-r--r--chrome_frame/test/test_with_web_server.cc825
-rw-r--r--chrome_frame/test/test_with_web_server.h (renamed from chrome_frame/test/chrome_frame_unittests.h)26
12 files changed, 2162 insertions, 2113 deletions
diff --git a/chrome_frame/chrome_frame.gyp b/chrome_frame/chrome_frame.gyp
index 7f844cf..6032ad6 100644
--- a/chrome_frame/chrome_frame.gyp
+++ b/chrome_frame/chrome_frame.gyp
@@ -191,19 +191,25 @@
],
'sources': [
'../base/test_suite.h',
+ 'test/automation_client_mock.cc',
+ 'test/automation_client_mock.h',
'test/chrome_frame_test_utils.cc',
'test/chrome_frame_test_utils.h',
'test/chrome_frame_automation_mock.cc',
'test/chrome_frame_automation_mock.h',
- 'test/chrome_frame_unittests.cc',
- 'test/chrome_frame_unittests.h',
'test/function_stub_unittest.cc',
'test/http_server.cc',
'test/http_server.h',
+ 'test/proxy_factory_mock.cc',
+ 'test/proxy_factory_mock.h',
'test/run_all_unittests.cc',
+ 'test/test_mock_with_web_server.cc',
+ 'test/test_mock_with_web_server.h',
'test/test_server.cc',
'test/test_server.h',
'test/test_server_test.cc',
+ 'test/test_with_web_server.cc',
+ 'test/test_with_web_server.h',
'test/url_request_test.cc',
'chrome_frame_automation.cc',
'chrome_frame_histograms.h',
diff --git a/chrome_frame/test/automation_client_mock.cc b/chrome_frame/test/automation_client_mock.cc
new file mode 100644
index 0000000..83d2b6a
--- /dev/null
+++ b/chrome_frame/test/automation_client_mock.cc
@@ -0,0 +1,269 @@
+// Copyright (c) 2006-2010 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 "chrome_frame/test/automation_client_mock.h"
+
+#include "net/base/net_errors.h"
+#include "chrome_frame/test/chrome_frame_test_utils.h"
+
+#define GMOCK_MUTANT_INCLUDE_LATE_OBJECT_BINDING
+#include "testing/gmock_mutant.h"
+
+using testing::CreateFunctor;
+using testing::_;
+
+template <> struct RunnableMethodTraits<ProxyFactory::LaunchDelegate> {
+ void RetainCallee(ProxyFactory::LaunchDelegate* obj) {}
+ void ReleaseCallee(ProxyFactory::LaunchDelegate* obj) {}
+};
+
+template <> struct RunnableMethodTraits<ChromeFrameAutomationClient> {
+ void RetainCallee(ChromeFrameAutomationClient* obj) {}
+ void ReleaseCallee(ChromeFrameAutomationClient* obj) {}
+};
+
+template <> struct RunnableMethodTraits<chrome_frame_test::TimedMsgLoop> {
+ void RetainCallee(chrome_frame_test::TimedMsgLoop* obj) {}
+ void ReleaseCallee(chrome_frame_test::TimedMsgLoop* obj) {}
+};
+
+void MockProxyFactory::GetServerImpl(ChromeFrameAutomationProxy* pxy,
+ void* proxy_id,
+ AutomationLaunchResult result,
+ LaunchDelegate* d,
+ const ChromeFrameLaunchParams& params,
+ void** automation_server_id) {
+ *automation_server_id = proxy_id;
+ Task* task = NewRunnableMethod(d,
+ &ProxyFactory::LaunchDelegate::LaunchComplete, pxy, result);
+ loop_->PostDelayedTask(FROM_HERE, task,
+ params.automation_server_launch_timeout/2);
+}
+
+void CFACMockTest::SetAutomationServerOk() {
+ EXPECT_CALL(factory_, GetAutomationServer(testing::NotNull(),
+ testing::Field(&ChromeFrameLaunchParams::profile_name,
+ testing::StrEq(profile_)),
+ testing::NotNull()))
+ .Times(1)
+ .WillOnce(testing::Invoke(CreateFunctor(&factory_,
+ &MockProxyFactory::GetServerImpl,
+ get_proxy(), id_,
+ AUTOMATION_SUCCESS)));
+
+ EXPECT_CALL(factory_, ReleaseAutomationServer(testing::Eq(id_))).Times(1);
+}
+
+void CFACMockTest::Set_CFD_LaunchFailed(AutomationLaunchResult result) {
+ EXPECT_CALL(cfd_, OnAutomationServerLaunchFailed(testing::Eq(result),
+ testing::_))
+ .Times(1)
+ .WillOnce(QUIT_LOOP(loop_));
+}
+
+MATCHER_P(MsgType, msg_type, "IPC::Message::type()") {
+ const IPC::Message& m = arg;
+ return (m.type() == msg_type);
+}
+
+MATCHER_P(EqNavigationInfoUrl, url, "IPC::NavigationInfo matcher") {
+ if (url.is_valid() && url != arg.url)
+ return false;
+ // TODO(stevet): other members
+ return true;
+}
+
+// Could be implemented as MockAutomationProxy member (we have WithArgs<>!)
+ACTION_P3(HandleCreateTab, tab_handle, external_tab_container, tab_wnd) {
+ // arg0 - message
+ // arg1 - callback
+ // arg2 - key
+ CallbackRunner<Tuple3<HWND, HWND, int> >* c =
+ reinterpret_cast<CallbackRunner<Tuple3<HWND, HWND, int> >*>(arg1);
+ c->Run(external_tab_container, tab_wnd, tab_handle);
+ delete c;
+ delete arg0;
+}
+
+// We mock ChromeFrameDelegate only. The rest is with real AutomationProxy
+TEST(CFACWithChrome, CreateTooFast) {
+ MockCFDelegate cfd;
+ chrome_frame_test::TimedMsgLoop loop;
+ int timeout = 0; // Chrome cannot send Hello message so fast.
+ const std::wstring profile = L"Adam.N.Epilinter";
+
+ scoped_refptr<ChromeFrameAutomationClient> client;
+ client = new ChromeFrameAutomationClient();
+
+ EXPECT_CALL(cfd, OnAutomationServerLaunchFailed(AUTOMATION_TIMEOUT, _))
+ .Times(1)
+ .WillOnce(QUIT_LOOP(loop));
+
+ EXPECT_TRUE(client->Initialize(&cfd, timeout, false, profile, L"", false));
+ loop.RunFor(10);
+ client->Uninitialize();
+}
+
+// This test may fail if Chrome take more that 10 seconds (timeout var) to
+// launch. In this case GMock shall print something like "unexpected call to
+// OnAutomationServerLaunchFailed". I'm yet to find out how to specify
+// that this is an unexpected call, and still to execute and action.
+TEST(CFACWithChrome, CreateNotSoFast) {
+ MockCFDelegate cfd;
+ chrome_frame_test::TimedMsgLoop loop;
+ const std::wstring profile = L"Adam.N.Epilinter";
+ int timeout = 10000;
+
+ scoped_refptr<ChromeFrameAutomationClient> client;
+ client = new ChromeFrameAutomationClient;
+
+ EXPECT_CALL(cfd, OnAutomationServerReady())
+ .Times(1)
+ .WillOnce(QUIT_LOOP(loop));
+
+ EXPECT_CALL(cfd, OnAutomationServerLaunchFailed(_, _))
+ .Times(0);
+
+ EXPECT_TRUE(client->Initialize(&cfd, timeout, false, profile, L"", false));
+
+ loop.RunFor(11);
+ client->Uninitialize();
+ client = NULL;
+}
+
+TEST(CFACWithChrome, NavigateOk) {
+ MockCFDelegate cfd;
+ chrome_frame_test::TimedMsgLoop loop;
+ const std::wstring profile = L"Adam.N.Epilinter";
+ const std::string url = "about:version";
+ int timeout = 10000;
+
+ scoped_refptr<ChromeFrameAutomationClient> client;
+ client = new ChromeFrameAutomationClient;
+
+ EXPECT_CALL(cfd, OnAutomationServerReady())
+ .WillOnce(testing::IgnoreResult(testing::InvokeWithoutArgs(CreateFunctor(
+ client.get(), &ChromeFrameAutomationClient::InitiateNavigation,
+ url, std::string(), false))));
+
+ EXPECT_CALL(cfd, GetBounds(_)).Times(testing::AnyNumber());
+
+ EXPECT_CALL(cfd, OnNavigationStateChanged(_, _))
+ .Times(testing::AnyNumber());
+
+ {
+ testing::InSequence s;
+
+ EXPECT_CALL(cfd, OnDidNavigate(_, EqNavigationInfoUrl(GURL())))
+ .Times(1);
+
+ EXPECT_CALL(cfd, OnUpdateTargetUrl(_, _)).Times(1);
+
+ EXPECT_CALL(cfd, OnLoad(_, _))
+ .Times(1)
+ .WillOnce(QUIT_LOOP(loop));
+ }
+
+ EXPECT_TRUE(client->Initialize(&cfd, timeout, false, profile, L"", false));
+ loop.RunFor(10);
+ client->Uninitialize();
+ client = NULL;
+}
+
+TEST(CFACWithChrome, NavigateFailed) {
+ MockCFDelegate cfd;
+ chrome_frame_test::TimedMsgLoop loop;
+ const std::wstring profile = L"Adam.N.Epilinter";
+ const std::string url = "http://127.0.0.3:65412/";
+ const URLRequestStatus connection_failed(URLRequestStatus::FAILED,
+ net::ERR_INVALID_URL);
+
+ scoped_refptr<ChromeFrameAutomationClient> client;
+ client = new ChromeFrameAutomationClient;
+ cfd.SetRequestDelegate(client);
+
+ EXPECT_CALL(cfd, OnAutomationServerReady())
+ .WillOnce(testing::IgnoreResult(testing::InvokeWithoutArgs(CreateFunctor(
+ client.get(), &ChromeFrameAutomationClient::InitiateNavigation,
+ url, std::string(), false))));
+
+ EXPECT_CALL(cfd, GetBounds(_)).Times(testing::AnyNumber());
+ EXPECT_CALL(cfd, OnNavigationStateChanged(_, _)).Times(testing::AnyNumber());
+
+ EXPECT_CALL(cfd, OnRequestStart(_, _, _))
+ // Often there's another request for the error page
+ .Times(testing::Between(1, 2))
+ .WillRepeatedly(testing::WithArgs<1>(testing::Invoke(CreateFunctor(&cfd,
+ &MockCFDelegate::Reply, connection_failed))));
+
+ EXPECT_CALL(cfd, OnUpdateTargetUrl(_, _)).Times(testing::AnyNumber());
+ EXPECT_CALL(cfd, OnLoad(_, _)).Times(testing::AtMost(1));
+
+ EXPECT_CALL(cfd, OnNavigationFailed(_, _, GURL(url)))
+ .Times(1)
+ .WillOnce(QUIT_LOOP_SOON(loop, 2));
+
+ EXPECT_TRUE(client->Initialize(&cfd, 10000, false, profile, L"", false));
+
+ loop.RunFor(10);
+ client->Uninitialize();
+ client = NULL;
+}
+
+TEST_F(CFACMockTest, MockedCreateTabOk) {
+ int timeout = 500;
+ CreateTab();
+ SetAutomationServerOk();
+
+ EXPECT_CALL(proxy_, server_version()).Times(testing::AnyNumber())
+ .WillRepeatedly(testing::Return(""));
+
+ // We need some valid HWNDs, when responding to CreateExternalTab
+ HWND h1 = ::GetDesktopWindow();
+ HWND h2 = ::GetDesktopWindow();
+ EXPECT_CALL(proxy_, SendAsAsync(testing::Property(&IPC::SyncMessage::type,
+ AutomationMsg_CreateExternalTab__ID),
+ testing::NotNull(), _))
+ .Times(1)
+ .WillOnce(HandleCreateTab(tab_handle_, h1, h2));
+
+ EXPECT_CALL(proxy_, CreateTabProxy(testing::Eq(tab_handle_)))
+ .WillOnce(testing::Return(tab_));
+
+ EXPECT_CALL(cfd_, OnAutomationServerReady())
+ .WillOnce(QUIT_LOOP(loop_));
+
+ EXPECT_CALL(proxy_, CancelAsync(_)).Times(testing::AnyNumber());
+
+ // Here we go!
+ EXPECT_TRUE(client_->Initialize(&cfd_, timeout, false, profile_, L"", false));
+ loop_.RunFor(10);
+ client_->Uninitialize();
+}
+
+TEST_F(CFACMockTest, MockedCreateTabFailed) {
+ HWND null_wnd = NULL;
+ SetAutomationServerOk();
+
+ EXPECT_CALL(proxy_, server_version()).Times(testing::AnyNumber())
+ .WillRepeatedly(testing::Return(""));
+
+ EXPECT_CALL(proxy_, SendAsAsync(testing::Property(&IPC::SyncMessage::type,
+ AutomationMsg_CreateExternalTab__ID),
+ testing::NotNull(), _))
+ .Times(1)
+ .WillOnce(HandleCreateTab(tab_handle_, null_wnd, null_wnd));
+
+ EXPECT_CALL(proxy_, CreateTabProxy(_)).Times(0);
+
+ EXPECT_CALL(proxy_, CancelAsync(_)).Times(testing::AnyNumber());
+
+ Set_CFD_LaunchFailed(AUTOMATION_CREATE_TAB_FAILED);
+
+ // Here we go!
+ EXPECT_TRUE(client_->Initialize(&cfd_, timeout_, false, profile_, L"",
+ false));
+ loop_.RunFor(4);
+ client_->Uninitialize();
+}
+
diff --git a/chrome_frame/test/automation_client_mock.h b/chrome_frame/test/automation_client_mock.h
new file mode 100644
index 0000000..aa17937
--- /dev/null
+++ b/chrome_frame/test/automation_client_mock.h
@@ -0,0 +1,176 @@
+// Copyright (c) 2006-2010 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.
+#ifndef CHROME_FRAME_AUTOMATION_CLIENT_MOCK_H_
+#define CHROME_FRAME_AUTOMATION_CLIENT_MOCK_H_
+
+#include <windows.h>
+#include <string>
+
+#include "chrome_frame/chrome_frame_automation.h"
+#include "chrome_frame/test/chrome_frame_test_utils.h"
+#include "chrome_frame/test/proxy_factory_mock.h"
+#include "gmock/gmock.h"
+
+// ChromeFrameAutomationClient [CFAC] tests.
+struct MockCFDelegate : public ChromeFrameDelegateImpl {
+ MOCK_CONST_METHOD0(GetWindow, WindowType());
+ MOCK_METHOD1(GetBounds, void(RECT* bounds));
+ MOCK_METHOD0(GetDocumentUrl, std::string());
+ MOCK_METHOD2(ExecuteScript, bool(const std::string& script,
+ std::string* result));
+ MOCK_METHOD0(OnAutomationServerReady, void());
+ MOCK_METHOD2(OnAutomationServerLaunchFailed, void(
+ AutomationLaunchResult reason, const std::string& server_version));
+ // This remains in interface since we call it if Navigate()
+ // returns immediate error.
+ MOCK_METHOD2(OnLoadFailed, void(int error_code, const std::string& url));
+
+ // Do not mock this method. :) Use it as message demuxer and dispatcher
+ // to the following methods (which we mock)
+ // MOCK_METHOD1(OnMessageReceived, void(const IPC::Message&));
+
+ MOCK_METHOD2(OnNavigationStateChanged, void(int tab_handle, int flags));
+ MOCK_METHOD2(OnUpdateTargetUrl, void(int tab_handle,
+ const std::wstring& new_target_url));
+ MOCK_METHOD2(OnAcceleratorPressed, void(int tab_handle,
+ const MSG& accel_message));
+ MOCK_METHOD2(OnTabbedOut, void(int tab_handle, bool reverse));
+ MOCK_METHOD3(OnOpenURL, void(int tab_handle, const GURL& url,
+ int open_disposition));
+ MOCK_METHOD2(OnDidNavigate, void(int tab_handle,
+ const IPC::NavigationInfo& navigation_info));
+ MOCK_METHOD3(OnNavigationFailed, void(int tab_handle, int error_code,
+ const GURL& gurl));
+ MOCK_METHOD2(OnLoad, void(int tab_handle, const GURL& url));
+ MOCK_METHOD4(OnMessageFromChromeFrame, void(int tab_handle,
+ const std::string& message,
+ const std::string& origin,
+ const std::string& target));
+ MOCK_METHOD4(OnHandleContextMenu, void(int tab_handle, HANDLE menu_handle,
+ int align_flags, const IPC::ContextMenuParams& params));
+ MOCK_METHOD3(OnRequestStart, void(int tab_handle, int request_id,
+ const IPC::AutomationURLRequest& request));
+ MOCK_METHOD3(OnRequestRead, void(int tab_handle, int request_id,
+ int bytes_to_read));
+ MOCK_METHOD3(OnRequestEnd, void(int tab_handle, int request_id,
+ const URLRequestStatus& status));
+ MOCK_METHOD3(OnSetCookieAsync, void(int tab_handle, const GURL& url,
+ const std::string& cookie));
+
+ // Use for sending network responses
+ void SetRequestDelegate(PluginUrlRequestDelegate* request_delegate) {
+ request_delegate_ = request_delegate;
+ }
+
+ void ReplyStarted(int request_id, const char* headers) {
+ request_delegate_->OnResponseStarted(request_id, "text/html", headers,
+ 0, base::Time::Now(), EmptyString(), EmptyString(), 0);
+ }
+
+ void ReplyData(int request_id, const std::string* data) {
+ request_delegate_->OnReadComplete(request_id, data->c_str(), data->size());
+ }
+
+ void Reply(const URLRequestStatus& status, int request_id) {
+ request_delegate_->OnResponseEnd(request_id, status);
+ }
+
+ void Reply404(int request_id) {
+ ReplyStarted(request_id, "HTTP/1.1 404\r\n\r\n");
+ Reply(URLRequestStatus(), request_id);
+ }
+
+ PluginUrlRequestDelegate* request_delegate_;
+};
+
+class MockAutomationProxy : public ChromeFrameAutomationProxy {
+ public:
+ MOCK_METHOD1(Send, bool(IPC::Message*));
+ MOCK_METHOD3(SendAsAsync, void(IPC::SyncMessage* msg, void* callback,
+ void* key));
+ MOCK_METHOD1(CancelAsync, void(void* key));
+ MOCK_METHOD1(CreateTabProxy, scoped_refptr<TabProxy>(int handle));
+ MOCK_METHOD0(server_version, std::string(void));
+ MOCK_METHOD1(SendProxyConfig, void(const std::string&));
+ MOCK_METHOD1(SetEnableExtensionAutomation, void(bool enable));
+
+ ~MockAutomationProxy() {}
+};
+
+struct MockAutomationMessageSender : public AutomationMessageSender {
+ MOCK_METHOD1(Send, bool(IPC::Message*));
+ MOCK_METHOD3(SendWithTimeout, bool(IPC::Message* , int , bool*));
+
+ void ForwardTo(MockAutomationProxy *p) {
+ proxy_ = p;
+ ON_CALL(*this, Send(testing::_))
+ .WillByDefault(testing::Invoke(proxy_, &MockAutomationProxy::Send));
+ }
+
+ MockAutomationProxy* proxy_;
+};
+
+// [CFAC] -- uses a ProxyFactory for creation of ChromeFrameAutomationProxy
+// -- uses ChromeFrameAutomationProxy
+// -- uses TabProxy obtained from ChromeFrameAutomationProxy
+// -- uses ChromeFrameDelegate as outgoing interface
+//
+// We mock ProxyFactory to return mock object (MockAutomationProxy) implementing
+// ChromeFrameAutomationProxy interface.
+// Since CFAC uses TabProxy for few calls and TabProxy is not easy mockable,
+// we create 'real' TabProxy but with fake AutomationSender (the one responsible
+// for sending messages over channel).
+// Additionally we have mock implementation ChromeFrameDelagate interface -
+// MockCFDelegate.
+
+// Test fixture, saves typing all of it's members.
+class CFACMockTest : public testing::Test {
+ public:
+ MockProxyFactory factory_;
+ MockCFDelegate cfd_;
+ chrome_frame_test::TimedMsgLoop loop_;
+ MockAutomationProxy proxy_;
+ scoped_ptr<AutomationHandleTracker> tracker_;
+ MockAutomationMessageSender dummy_sender_;
+ scoped_refptr<TabProxy> tab_;
+ // the victim of all tests
+ scoped_refptr<ChromeFrameAutomationClient> client_;
+
+ std::wstring profile_;
+ int timeout_;
+ void* id_; // Automation server id we are going to return
+ int tab_handle_; // Tab handle. Any non-zero value is Ok.
+
+ inline ChromeFrameAutomationProxy* get_proxy() {
+ return static_cast<ChromeFrameAutomationProxy*>(&proxy_);
+ }
+
+ inline void CreateTab() {
+ ASSERT_EQ(NULL, tab_.get());
+ tab_ = new TabProxy(&dummy_sender_, tracker_.get(), tab_handle_);
+ }
+
+ // Easy methods to set expectations.
+ void SetAutomationServerOk();
+ void Set_CFD_LaunchFailed(AutomationLaunchResult result);
+
+ protected:
+ CFACMockTest() : tracker_(NULL), timeout_(500),
+ profile_(L"Adam.N.Epilinter") {
+ id_ = reinterpret_cast<void*>(5);
+ tab_handle_ = 3;
+ }
+
+ virtual void SetUp() {
+ dummy_sender_.ForwardTo(&proxy_);
+ tracker_.reset(new AutomationHandleTracker(&dummy_sender_));
+
+ client_ = new ChromeFrameAutomationClient;
+ client_->set_proxy_factory(&factory_);
+ }
+};
+
+
+#endif // CHROME_FRAME_AUTOMATION_CLIENT_MOCK_H_
+
diff --git a/chrome_frame/test/chrome_frame_unittests.cc b/chrome_frame/test/chrome_frame_unittests.cc
deleted file mode 100644
index c530766..0000000
--- a/chrome_frame/test/chrome_frame_unittests.cc
+++ /dev/null
@@ -1,2088 +0,0 @@
-// Copyright (c) 2006-2008 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 <windows.h>
-#include <stdarg.h>
-
-// IShellWindows includes. Unfortunately we can't keep these in
-// alphabetic order since exdisp will bark if some interfaces aren't fully
-// defined.
-#include <mshtml.h>
-#include <exdisp.h>
-#include <mshtmcid.h>
-
-#include "base/basictypes.h"
-#include "base/file_version_info.h"
-#include "base/file_util.h"
-#include "base/scoped_bstr_win.h"
-#include "base/scoped_variant_win.h"
-#include "base/win_util.h"
-#include "gmock/gmock.h"
-#include "net/url_request/url_request_unittest.h"
-#include "chrome_frame/test/chrome_frame_unittests.h"
-#include "chrome_frame/chrome_frame_automation.h"
-#include "chrome_frame/chrome_frame_delegate.h"
-#include "chrome_frame/test/chrome_frame_test_utils.h"
-#include "chrome_frame/test_utils.h"
-#include "chrome/common/chrome_switches.h"
-#include "chrome/common/url_constants.h"
-#include "chrome/installer/util/install_util.h"
-#include "chrome/installer/util/helper.h"
-
-#define GMOCK_MUTANT_INCLUDE_LATE_OBJECT_BINDING
-#include "testing/gmock_mutant.h"
-
-using testing::CreateFunctor;
-using testing::_;
-
-const wchar_t kDocRoot[] = L"chrome_frame\\test\\data";
-const int kLongWaitTimeout = 60 * 1000;
-const int kShortWaitTimeout = 25 * 1000;
-
-void ChromeFrameTestWithWebServer::CloseAllBrowsers() {
- // Web browsers tend to relaunch themselves in other processes, meaning the
- // KillProcess stuff above might not have actually cleaned up all our browser
- // instances, so make really sure browsers are dead.
- base::KillProcesses(chrome_frame_test::kIEImageName, 0, NULL);
- base::KillProcesses(chrome_frame_test::kIEBrokerImageName, 0, NULL);
- base::KillProcesses(chrome_frame_test::kFirefoxImageName, 0, NULL);
- base::KillProcesses(chrome_frame_test::kSafariImageName, 0, NULL);
-
- // Endeavour to only kill off Chrome Frame derived Chrome processes.
- KillAllNamedProcessesWithArgument(chrome_frame_test::kChromeImageName,
- UTF8ToWide(switches::kChromeFrame));
-}
-
-void ChromeFrameTestWithWebServer::SetUp() {
- // Make sure our playground is clean before we start.
- CloseAllBrowsers();
-
- // Make sure that we are not accidently enabling gcf protocol.
- SetConfigBool(kEnableGCFProtocol, false);
-
- server_.SetUp();
- results_dir_ = server_.GetDataDir();
- file_util::AppendToPath(&results_dir_, L"dump");
-}
-
-void ChromeFrameTestWithWebServer::TearDown() {
- CloseBrowser();
-
- CloseAllBrowsers();
-
- server_.TearDown();
-}
-
-bool ChromeFrameTestWithWebServer::LaunchBrowser(BrowserKind browser,
- const wchar_t* page) {
- std::wstring url = page;
- if (url.find(L"files/") != std::wstring::npos)
- url = UTF8ToWide(server_.Resolve(page).spec());
-
- browser_ = browser;
- if (browser == IE) {
- browser_handle_.Set(chrome_frame_test::LaunchIE(url));
- } else if (browser == FIREFOX) {
- browser_handle_.Set(chrome_frame_test::LaunchFirefox(url));
- } else if (browser == OPERA) {
- browser_handle_.Set(chrome_frame_test::LaunchOpera(url));
- } else if (browser == SAFARI) {
- browser_handle_.Set(chrome_frame_test::LaunchSafari(url));
- } else if (browser == CHROME) {
- browser_handle_.Set(chrome_frame_test::LaunchChrome(url));
- } else {
- NOTREACHED();
- }
-
- return browser_handle_.IsValid();
-}
-
-void ChromeFrameTestWithWebServer::CloseBrowser() {
- if (!browser_handle_.IsValid())
- return;
-
- int attempts = 0;
- if (browser_ == IE) {
- attempts = chrome_frame_test::CloseAllIEWindows();
- } else {
- attempts = chrome_frame_test::CloseVisibleWindowsOnAllThreads(
- browser_handle_);
- }
-
- if (attempts > 0) {
- DWORD wait = ::WaitForSingleObject(browser_handle_, 20000);
- if (wait == WAIT_OBJECT_0) {
- browser_handle_.Close();
- } else {
- DLOG(ERROR) << "WaitForSingleObject returned " << wait;
- }
- } else {
- DLOG(ERROR) << "No attempts to close browser windows";
- }
-
- if (browser_handle_.IsValid()) {
- DWORD exit_code = 0;
- if (!::GetExitCodeProcess(browser_handle_, &exit_code) ||
- exit_code == STILL_ACTIVE) {
- LOG(ERROR) << L"Forcefully killing browser process. Exit:" << exit_code;
- base::KillProcess(browser_handle_, 0, true);
- }
- browser_handle_.Close();
- }
-}
-
-bool ChromeFrameTestWithWebServer::BringBrowserToTop() {
- return chrome_frame_test::EnsureProcessInForeground(GetProcessId(
- browser_handle_));
-}
-
-bool ChromeFrameTestWithWebServer::WaitForTestToComplete(int milliseconds) {
- return server_.WaitToFinish(milliseconds);
-}
-
-bool ChromeFrameTestWithWebServer::WaitForOnLoad(int milliseconds) {
- DWORD start = ::GetTickCount();
- std::string data;
- while (!ReadResultFile(L"OnLoadEvent", &data) || data.length() == 0) {
- DWORD now = ::GetTickCount();
- if (start > now) {
- // Very simple check for overflow. In that case we just restart the
- // wait.
- start = now;
- } else if (static_cast<int>(now - start) > milliseconds) {
- break;
- }
- Sleep(100);
- }
-
- return data.compare("loaded") == 0;
-}
-
-bool ChromeFrameTestWithWebServer::ReadResultFile(const std::wstring& file_name,
- std::string* data) {
- std::wstring full_path = results_dir_;
- file_util::AppendToPath(&full_path, file_name);
- return file_util::ReadFileToString(full_path, data);
-}
-
-bool ChromeFrameTestWithWebServer::CheckResultFile(
- const std::wstring& file_name, const std::string& expected_result) {
- std::string data;
- bool ret = ReadResultFile(file_name, &data);
- if (ret)
- ret = (data == expected_result);
-
- if (!ret) {
- LOG(ERROR) << "Error text: " << (data.empty() ? "<empty>" : data.c_str());
- }
-
- return ret;
-}
-
-void ChromeFrameTestWithWebServer::SimpleBrowserTest(BrowserKind browser,
- const wchar_t* page, const wchar_t* result_file_to_check) {
- ASSERT_TRUE(LaunchBrowser(browser, page));
- ASSERT_TRUE(WaitForTestToComplete(kLongWaitTimeout));
- ASSERT_TRUE(CheckResultFile(result_file_to_check, "OK"));
-}
-
-void ChromeFrameTestWithWebServer::OptionalBrowserTest(BrowserKind browser,
- const wchar_t* page, const wchar_t* result_file_to_check) {
- if (!LaunchBrowser(browser, page)) {
- LOG(ERROR) << "Failed to launch browser " << ToString(browser);
- } else {
- ASSERT_TRUE(WaitForTestToComplete(kLongWaitTimeout));
- ASSERT_TRUE(CheckResultFile(result_file_to_check, "OK"));
- }
-}
-
-void ChromeFrameTestWithWebServer::VersionTest(BrowserKind browser,
- const wchar_t* page, const wchar_t* result_file_to_check) {
- std::wstring plugin_path;
- PathService::Get(base::DIR_MODULE, &plugin_path);
- file_util::AppendToPath(&plugin_path, L"servers");
- file_util::AppendToPath(&plugin_path, kChromeFrameDllName);
-
- static FileVersionInfo* version_info =
- FileVersionInfo::CreateFileVersionInfo(plugin_path);
-
- std::wstring version;
- if (version_info)
- version = version_info->product_version();
-
- // If we can't find the Chrome Frame DLL in the src tree, we turn to
- // the directory where chrome is installed.
- if (!version_info) {
- installer::Version* ver_system = InstallUtil::GetChromeVersion(true);
- installer::Version* ver_user = InstallUtil::GetChromeVersion(false);
- ASSERT_TRUE(ver_system || ver_user);
-
- bool system_install = ver_system ? true : false;
- std::wstring cf_dll_path(installer::GetChromeInstallPath(system_install));
- file_util::AppendToPath(&cf_dll_path,
- ver_system ? ver_system->GetString() : ver_user->GetString());
- file_util::AppendToPath(&cf_dll_path, kChromeFrameDllName);
- version_info = FileVersionInfo::CreateFileVersionInfo(cf_dll_path);
- if (version_info)
- version = version_info->product_version();
- }
-
- EXPECT_TRUE(version_info);
- EXPECT_FALSE(version.empty());
- EXPECT_TRUE(LaunchBrowser(browser, page));
- ASSERT_TRUE(WaitForTestToComplete(kLongWaitTimeout));
- ASSERT_TRUE(CheckResultFile(result_file_to_check, WideToUTF8(version)));
-}
-
-const wchar_t kPostMessageBasicPage[] = L"files/postmessage_basic_host.html";
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_PostMessageBasic) {
- SimpleBrowserTest(IE, kPostMessageBasicPage, L"PostMessage");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_PostMessageBasic) {
- SimpleBrowserTest(FIREFOX, kPostMessageBasicPage, L"PostMessage");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_PostMessageBasic) {
- OptionalBrowserTest(OPERA, kPostMessageBasicPage, L"PostMessage");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, FullTabIE_MIMEFilterBasic) {
- const wchar_t kMIMEFilterBasicPage[] =
- L"files/chrome_frame_mime_filter_test.html";
-
- // If this test fails for IE8 then it is possible that prebinding is enabled.
- // A known workaround is to disable it until CF properly handles it.
- //
- // HKCU\Software\Microsoft\Internet Explorer\Main
- // Value name: EnablePreBinding (REG_DWORD)
- // Value: 0
- SimpleBrowserTest(IE, kMIMEFilterBasicPage, L"MIMEFilter");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_Resize) {
- SimpleBrowserTest(IE, L"files/chrome_frame_resize.html", L"Resize");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_Resize) {
- SimpleBrowserTest(FIREFOX, L"files/chrome_frame_resize.html", L"Resize");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_Resize) {
- OptionalBrowserTest(OPERA, L"files/chrome_frame_resize.html", L"Resize");
-}
-
-const wchar_t kNavigateURLAbsolutePage[] =
- L"files/navigateurl_absolute_host.html";
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_NavigateURLAbsolute) {
- SimpleBrowserTest(IE, kNavigateURLAbsolutePage, L"NavigateURL");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_NavigateURLAbsolute) {
- SimpleBrowserTest(FIREFOX, kNavigateURLAbsolutePage, L"NavigateURL");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_NavigateURLAbsolute) {
- OptionalBrowserTest(OPERA, kNavigateURLAbsolutePage, L"NavigateURL");
-}
-
-const wchar_t kNavigateURLRelativePage[] =
- L"files/navigateurl_relative_host.html";
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_NavigateURLRelative) {
- SimpleBrowserTest(IE, kNavigateURLRelativePage, L"NavigateURL");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_NavigateURLRelative) {
- SimpleBrowserTest(FIREFOX, kNavigateURLRelativePage, L"NavigateURL");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_NavigateURLRelative) {
- OptionalBrowserTest(OPERA, kNavigateURLRelativePage, L"NavigateURL");
-}
-
-const wchar_t kNavigateSimpleObjectFocus[] = L"files/simple_object_focus.html";
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_ObjectFocus) {
- SimpleBrowserTest(FIREFOX, kNavigateSimpleObjectFocus, L"ObjectFocus");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_ObjectFocus) {
- SimpleBrowserTest(IE, kNavigateSimpleObjectFocus, L"ObjectFocus");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_ObjectFocus) {
- if (!LaunchBrowser(OPERA, kNavigateSimpleObjectFocus)) {
- LOG(ERROR) << "Failed to launch browser " << ToString(OPERA);
- } else {
- ASSERT_TRUE(WaitForOnLoad(kLongWaitTimeout));
- BringBrowserToTop();
- // Tab through a couple of times. Once should be enough in theory
- // but in practice activating the browser can take a few milliseconds more.
- bool ok;
- for (int i = 0;
- i < 5 && (ok = CheckResultFile(L"ObjectFocus", "OK")) == false;
- ++i) {
- Sleep(300);
- chrome_frame_test::SendMnemonic(VK_TAB, false, false, false);
- }
- ASSERT_TRUE(ok);
- }
-}
-
-const wchar_t kiframeBasicPage[] = L"files/iframe_basic_host.html";
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_iframeBasic) {
- SimpleBrowserTest(IE, kiframeBasicPage, L"PostMessage");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_iframeBasic) {
- SimpleBrowserTest(FIREFOX, kiframeBasicPage, L"PostMessage");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_iframeBasic) {
- OptionalBrowserTest(OPERA, kiframeBasicPage, L"PostMessage");
-}
-
-const wchar_t kSrcPropertyTestPage[] = L"files/src_property_host.html";
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_SrcProperty) {
- SimpleBrowserTest(IE, kSrcPropertyTestPage, L"SrcProperty");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_SrcProperty) {
- SimpleBrowserTest(FIREFOX, kSrcPropertyTestPage, L"SrcProperty");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_SrcProperty) {
- OptionalBrowserTest(OPERA, kSrcPropertyTestPage, L"SrcProperty");
-}
-
-const wchar_t kCFInstanceBasicTestPage[] = L"files/CFInstance_basic_host.html";
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_CFInstanceBasic) {
- SimpleBrowserTest(IE, kCFInstanceBasicTestPage, L"CFInstanceBasic");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_CFInstanceBasic) {
- SimpleBrowserTest(FIREFOX, kCFInstanceBasicTestPage, L"CFInstanceBasic");
-}
-
-const wchar_t kCFISingletonPage[] = L"files/CFInstance_singleton_host.html";
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_CFInstanceSingleton) {
- SimpleBrowserTest(IE, kCFISingletonPage, L"CFInstanceSingleton");
-}
-
-// This test randomly fails on the ChromeFrame builder.
-// Bug http://code.google.com/p/chromium/issues/detail?id=31532
-TEST_F(ChromeFrameTestWithWebServer, FLAKY_WidgetModeFF_CFInstanceSingleton) {
- SimpleBrowserTest(FIREFOX, kCFISingletonPage, L"CFInstanceSingleton");
-}
-
-const wchar_t kCFIDelayPage[] = L"files/CFInstance_delay_host.html";
-
-TEST_F(ChromeFrameTestWithWebServer, DISABLED_WidgetModeIE_CFInstanceDelay) {
- SimpleBrowserTest(IE, kCFIDelayPage, L"CFInstanceDelay");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, DISABLED_WidgetModeFF_CFInstanceDelay) {
- SimpleBrowserTest(FIREFOX, kCFIDelayPage, L"CFInstanceDelay");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, DISABLED_WidgetModeOpera_CFInstanceDelay) {
- OptionalBrowserTest(OPERA, kCFIDelayPage, L"CFInstanceDelay");
-}
-
-const wchar_t kCFIFallbackPage[] = L"files/CFInstance_fallback_host.html";
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_CFInstanceFallback) {
- SimpleBrowserTest(IE, kCFIFallbackPage, L"CFInstanceFallback");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_CFInstanceFallback) {
- SimpleBrowserTest(FIREFOX, kCFIFallbackPage, L"CFInstanceFallback");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_CFInstanceFallback) {
- OptionalBrowserTest(OPERA, kCFIFallbackPage, L"CFInstanceFallback");
-}
-
-const wchar_t kCFINoSrcPage[] = L"files/CFInstance_no_src_host.html";
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_CFInstanceNoSrc) {
- SimpleBrowserTest(IE, kCFINoSrcPage, L"CFInstanceNoSrc");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_CFInstanceNoSrc) {
- SimpleBrowserTest(FIREFOX, kCFINoSrcPage, L"CFInstanceNoSrc");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_CFInstanceNoSrc) {
- OptionalBrowserTest(OPERA, kCFINoSrcPage, L"CFInstanceNoSrc");
-}
-
-const wchar_t kCFIIfrOnLoadPage[] = L"files/CFInstance_iframe_onload_host.html";
-
-// disabled since it's unlikely that we care about this case
-TEST_F(ChromeFrameTestWithWebServer,
- DISABLED_WidgetModeIE_CFInstanceIfrOnLoad) {
- SimpleBrowserTest(IE, kCFIIfrOnLoadPage, L"CFInstanceIfrOnLoad");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_CFInstanceIfrOnLoad) {
- SimpleBrowserTest(FIREFOX, kCFIIfrOnLoadPage, L"CFInstanceIfrOnLoad");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_CFInstanceIfrOnLoad) {
- OptionalBrowserTest(OPERA, kCFIIfrOnLoadPage, L"CFInstanceIfrOnLoad");
-}
-
-const wchar_t kCFIZeroSizePage[] = L"files/CFInstance_zero_size_host.html";
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_CFInstanceZeroSize) {
- SimpleBrowserTest(IE, kCFIZeroSizePage, L"CFInstanceZeroSize");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_CFInstanceZeroSize) {
- SimpleBrowserTest(FIREFOX, kCFIZeroSizePage, L"CFInstanceZeroSize");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_CFInstanceZeroSize) {
- OptionalBrowserTest(OPERA, kCFIZeroSizePage, L"CFInstanceZeroSize");
-}
-
-const wchar_t kCFIIfrPostPage[] = L"files/CFInstance_iframe_post_host.html";
-
-// http://crbug.com/32321
-TEST_F(ChromeFrameTestWithWebServer, FLAKY_WidgetModeIE_CFInstanceIfrPost) {
- SimpleBrowserTest(IE, kCFIIfrPostPage, L"CFInstanceIfrPost");
-}
-
-// Flakes out on the bots, http://crbug.com/26372
-TEST_F(ChromeFrameTestWithWebServer,
- FLAKY_WidgetModeFF_CFInstanceIfrPost) {
- SimpleBrowserTest(FIREFOX, kCFIIfrPostPage, L"CFInstanceIfrPost");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeChrome_CFInstanceIfrPost) {
- OptionalBrowserTest(CHROME, kCFIIfrPostPage, L"CFInstanceIfrPost");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeSafari_CFInstanceIfrPost) {
- OptionalBrowserTest(SAFARI, kCFIIfrPostPage, L"CFInstanceIfrPost");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_CFInstanceIfrPost) {
- OptionalBrowserTest(OPERA, kCFIIfrPostPage, L"CFInstanceIfrPost");
-}
-
-const wchar_t kCFIPostPage[] = L"files/CFInstance_post_host.html";
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_CFInstancePost) {
- SimpleBrowserTest(IE, kCFIPostPage, L"CFInstancePost");
-}
-
-// This test randomly fails on the ChromeFrame builder.
-// Bug http://code.google.com/p/chromium/issues/detail?id=31532
-TEST_F(ChromeFrameTestWithWebServer, FLAKY_WidgetModeFF_CFInstancePost) {
- SimpleBrowserTest(FIREFOX, kCFIPostPage, L"CFInstancePost");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeChrome_CFInstancePost) {
- OptionalBrowserTest(CHROME, kCFIPostPage, L"CFInstancePost");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeSafari_CFInstancePost) {
- OptionalBrowserTest(SAFARI, kCFIPostPage, L"CFInstancePost");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, DISABLED_WidgetModeOpera_CFInstancePost) {
- OptionalBrowserTest(OPERA, kCFIPostPage, L"CFInstancePost");
-}
-
-const wchar_t kCFIRPCPage[] = L"files/CFInstance_rpc_host.html";
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_CFInstanceRPC) {
- SimpleBrowserTest(IE, kCFIRPCPage, L"CFInstanceRPC");
-}
-
-// This test randomly fails on the ChromeFrame builder.
-// Bug http://code.google.com/p/chromium/issues/detail?id=31532
-TEST_F(ChromeFrameTestWithWebServer, FLAKY_WidgetModeFF_CFInstanceRPC) {
- SimpleBrowserTest(FIREFOX, kCFIRPCPage, L"CFInstanceRPC");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeChrome_CFInstanceRPC) {
- OptionalBrowserTest(CHROME, kCFIRPCPage, L"CFInstanceRPC");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeSafari_CFInstanceRPC) {
- OptionalBrowserTest(SAFARI, kCFIRPCPage, L"CFInstanceRPC");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, DISABLED_WidgetModeOpera_CFInstanceRPC) {
- OptionalBrowserTest(OPERA, kCFIRPCPage, L"CFInstanceRPC");
-}
-
-const wchar_t kCFIRPCInternalPage[] =
- L"files/CFInstance_rpc_internal_host.html";
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_CFInstanceRPCInternal) {
- SimpleBrowserTest(IE, kCFIRPCInternalPage, L"CFInstanceRPCInternal");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_CFInstanceRPCInternal) {
- SimpleBrowserTest(FIREFOX, kCFIRPCInternalPage, L"CFInstanceRPCInternal");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeChrome_CFInstanceRPCInternal) {
- OptionalBrowserTest(CHROME, kCFIRPCInternalPage, L"CFInstanceRPCInternal");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeSafari_CFInstanceRPCInternal) {
- OptionalBrowserTest(SAFARI, kCFIRPCInternalPage, L"CFInstanceRPCInternal");
-}
-
-const wchar_t kCFIDefaultCtorPage[] =
- L"files/CFInstance_default_ctor_host.html";
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_CFInstanceDefaultCtor) {
- SimpleBrowserTest(IE, kCFIDefaultCtorPage, L"CFInstanceDefaultCtor");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_CFInstanceDefaultCtor) {
- SimpleBrowserTest(FIREFOX, kCFIDefaultCtorPage, L"CFInstanceDefaultCtor");
-}
-
-const wchar_t kCFInstallBasicTestPage[] = L"files/CFInstall_basic.html";
-
-TEST_F(ChromeFrameTestWithWebServer, FullTabIE_CFInstallBasic) {
- SimpleBrowserTest(IE, kCFInstallBasicTestPage, L"CFInstallBasic");
-}
-
-const wchar_t kCFInstallPlaceTestPage[] = L"files/CFInstall_place.html";
-
-TEST_F(ChromeFrameTestWithWebServer, FullTabIE_CFInstallPlace) {
- SimpleBrowserTest(IE, kCFInstallPlaceTestPage, L"CFInstallPlace");
-}
-
-const wchar_t kCFInstallOverlayTestPage[] = L"files/CFInstall_overlay.html";
-
-TEST_F(ChromeFrameTestWithWebServer, FullTabIE_CFInstallOverlay) {
- SimpleBrowserTest(IE, kCFInstallOverlayTestPage, L"CFInstallOverlay");
-}
-
-const wchar_t kCFInstallDismissTestPage[] = L"files/CFInstall_dismiss.html";
-
-TEST_F(ChromeFrameTestWithWebServer, FullTabIE_CFInstallDismiss) {
- SimpleBrowserTest(IE, kCFInstallDismissTestPage, L"CFInstallDismiss");
-}
-
-const wchar_t kInitializeHiddenPage[] = L"files/initialize_hidden.html";
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_InitializeHidden) {
- SimpleBrowserTest(IE, kInitializeHiddenPage, L"InitializeHidden");
-}
-
-const wchar_t kFullTabHttpHeaderPage[] = L"files/chrome_frame_http_header.html";
-
-TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_CFHttpHeaderBasic) {
- SimpleBrowserTest(IE, kFullTabHttpHeaderPage, L"FullTabHttpHeader");
-}
-
-const wchar_t kFullTabHttpHeaderPageIFrame[] =
- L"files/chrome_frame_http_header_host.html";
-
-TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_CFHttpHeaderIFrame) {
- SimpleBrowserTest(IE, kFullTabHttpHeaderPageIFrame,
- L"FullTabHttpHeaderIFrame");
-}
-
-const wchar_t kFullTabHttpHeaderPageFrameset[] =
- L"files/chrome_frame_http_header_frameset.html";
-
-TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_CFHttpHeaderFrameSet) {
- SimpleBrowserTest(IE, kFullTabHttpHeaderPageFrameset,
- L"FullTabHttpHeaderFrameset");
-}
-
-// Flaky on the build bots. See http://crbug.com/30622
-TEST_F(ChromeFrameTestWithWebServer, FLAKY_WidgetModeFF_InitializeHidden) {
- SimpleBrowserTest(FIREFOX, kInitializeHiddenPage, L"InitializeHidden");
-}
-
-// Disabled due to a problem with Opera.
-// http://b/issue?id=1708275
-TEST_F(ChromeFrameTestWithWebServer,
- DISABLED_WidgetModeOpera_InitializeHidden) {
- OptionalBrowserTest(OPERA, kInitializeHiddenPage, L"InitializeHidden");
-}
-
-const wchar_t kInHeadPage[] = L"files/in_head.html";
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_InHead) {
- SimpleBrowserTest(FIREFOX, kInHeadPage, L"InHead");
-}
-
-const wchar_t kVersionPage[] = L"files/version.html";
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_Version) {
- VersionTest(IE, kVersionPage, L"version");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_Version) {
- VersionTest(FIREFOX, kVersionPage, L"version");
-}
-
-const wchar_t kEventListenerPage[] = L"files/event_listener.html";
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_EventListener) {
- SimpleBrowserTest(IE, kEventListenerPage, L"EventListener");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_EventListener) {
- SimpleBrowserTest(FIREFOX, kEventListenerPage, L"EventListener");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_EventListener) {
- OptionalBrowserTest(OPERA, kEventListenerPage, L"EventListener");
-}
-
-const wchar_t kPrivilegedApisPage[] = L"files/privileged_apis_host.html";
-
-// http://crbug.com/32321
-TEST_F(ChromeFrameTestWithWebServer, FLAKY_WidgetModeIE_PrivilegedApis) {
- SimpleBrowserTest(IE, kPrivilegedApisPage, L"PrivilegedApis");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_PrivilegedApis) {
- SimpleBrowserTest(FIREFOX, kPrivilegedApisPage, L"PrivilegedApis");
-}
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_PrivilegedApis) {
- OptionalBrowserTest(OPERA, kPrivilegedApisPage, L"PrivilegedApis");
-}
-
-class ChromeFrameTestEnvironment: public testing::Environment {
- public:
- ~ChromeFrameTestEnvironment() {
- }
-
- void SetUp() {
- ScopedChromeFrameRegistrar::RegisterDefaults();
- }
-
- void TearDown() {
- }
-};
-
-::testing::Environment* const chrome_frame_env =
- ::testing::AddGlobalTestEnvironment(new ChromeFrameTestEnvironment);
-
-// TODO(stoyan): - Move everything below in separate file(s).
-struct LaunchDelegateMock : public ProxyFactory::LaunchDelegate {
- MOCK_METHOD2(LaunchComplete, void(ChromeFrameAutomationProxy*,
- AutomationLaunchResult));
-};
-
-TEST(ProxyFactoryTest, CreateDestroy) {
- ProxyFactory f;
- LaunchDelegateMock d;
- EXPECT_CALL(d, LaunchComplete(testing::NotNull(), testing::_)).Times(1);
-
- ChromeFrameLaunchParams params;
- params.automation_server_launch_timeout = 0;
- params.profile_name = L"Adam.N.Epilinter";
- params.extra_chrome_arguments = L"";
- params.perform_version_check = false;
- params.incognito_mode = false;
-
- void* id = NULL;
- f.GetAutomationServer(&d, params, &id);
- f.ReleaseAutomationServer(id);
-}
-
-TEST(ProxyFactoryTest, CreateSameProfile) {
- ProxyFactory f;
- LaunchDelegateMock d;
- EXPECT_CALL(d, LaunchComplete(testing::NotNull(), testing::_)).Times(2);
-
- ChromeFrameLaunchParams params;
- params.automation_server_launch_timeout = 0;
- params.profile_name = L"Dr. Gratiano Forbeson";
- params.extra_chrome_arguments = L"";
- params.perform_version_check = false;
- params.incognito_mode = false;
-
- void* i1 = NULL;
- void* i2 = NULL;
-
- f.GetAutomationServer(&d, params, &i1);
- f.GetAutomationServer(&d, params, &i2);
-
- EXPECT_EQ(i1, i2);
- f.ReleaseAutomationServer(i2);
- f.ReleaseAutomationServer(i1);
-}
-
-TEST(ProxyFactoryTest, CreateDifferentProfiles) {
- ProxyFactory f;
- LaunchDelegateMock d;
- EXPECT_CALL(d, LaunchComplete(testing::NotNull(), testing::_)).Times(2);
-
- ChromeFrameLaunchParams params1;
- params1.automation_server_launch_timeout = 0;
- params1.profile_name = L"Adam.N.Epilinter";
- params1.extra_chrome_arguments = L"";
- params1.perform_version_check = false;
- params1.incognito_mode = false;
-
- ChromeFrameLaunchParams params2;
- params2.automation_server_launch_timeout = 0;
- params2.profile_name = L"Dr. Gratiano Forbeson";
- params2.extra_chrome_arguments = L"";
- params2.perform_version_check = false;
- params2.incognito_mode = false;
-
- void* i1 = NULL;
- void* i2 = NULL;
-
- f.GetAutomationServer(&d, params1, &i1);
- f.GetAutomationServer(&d, params2, &i2);
-
- EXPECT_NE(i1, i2);
- f.ReleaseAutomationServer(i2);
- f.ReleaseAutomationServer(i1);
-}
-
-// ChromeFrameAutomationClient [CFAC] tests.
-struct MockCFDelegate : public ChromeFrameDelegateImpl {
- MOCK_CONST_METHOD0(GetWindow, WindowType());
- MOCK_METHOD1(GetBounds, void(RECT* bounds));
- MOCK_METHOD0(GetDocumentUrl, std::string());
- MOCK_METHOD2(ExecuteScript, bool(const std::string& script,
- std::string* result));
- MOCK_METHOD0(OnAutomationServerReady, void());
- MOCK_METHOD2(OnAutomationServerLaunchFailed, void(
- AutomationLaunchResult reason, const std::string& server_version));
- // This remains in interface since we call it if Navigate()
- // returns immediate error.
- MOCK_METHOD2(OnLoadFailed, void(int error_code, const std::string& url));
-
- // Do not mock this method. :) Use it as message demuxer and dispatcher
- // to the following methods (which we mock)
- // MOCK_METHOD1(OnMessageReceived, void(const IPC::Message&));
-
-
- MOCK_METHOD2(OnNavigationStateChanged, void(int tab_handle, int flags));
- MOCK_METHOD2(OnUpdateTargetUrl, void(int tab_handle,
- const std::wstring& new_target_url));
- MOCK_METHOD2(OnAcceleratorPressed, void(int tab_handle,
- const MSG& accel_message));
- MOCK_METHOD2(OnTabbedOut, void(int tab_handle, bool reverse));
- MOCK_METHOD3(OnOpenURL, void(int tab_handle, const GURL& url,
- int open_disposition));
- MOCK_METHOD2(OnDidNavigate, void(int tab_handle,
- const IPC::NavigationInfo& navigation_info));
- MOCK_METHOD3(OnNavigationFailed, void(int tab_handle, int error_code,
- const GURL& gurl));
- MOCK_METHOD2(OnLoad, void(int tab_handle, const GURL& url));
- MOCK_METHOD4(OnMessageFromChromeFrame, void(int tab_handle,
- const std::string& message,
- const std::string& origin,
- const std::string& target));
- MOCK_METHOD4(OnHandleContextMenu, void(int tab_handle, HANDLE menu_handle,
- int align_flags, const IPC::ContextMenuParams& params));
- MOCK_METHOD3(OnRequestStart, void(int tab_handle, int request_id,
- const IPC::AutomationURLRequest& request));
- MOCK_METHOD3(OnRequestRead, void(int tab_handle, int request_id,
- int bytes_to_read));
- MOCK_METHOD3(OnRequestEnd, void(int tab_handle, int request_id,
- const URLRequestStatus& status));
- MOCK_METHOD3(OnSetCookieAsync, void(int tab_handle, const GURL& url,
- const std::string& cookie));
-
- // Use for sending network responses
- void SetRequestDelegate(PluginUrlRequestDelegate* request_delegate) {
- request_delegate_ = request_delegate;
- }
-
- void ReplyStarted(int request_id, const char* headers) {
- request_delegate_->OnResponseStarted(request_id, "text/html", headers,
- 0, base::Time::Now(), EmptyString(), EmptyString(), 0);
- }
-
- void ReplyData(int request_id, const std::string* data) {
- request_delegate_->OnReadComplete(request_id, data->c_str(), data->size());
- }
-
- void Reply(const URLRequestStatus& status, int request_id) {
- request_delegate_->OnResponseEnd(request_id, status);
- }
-
- void Reply404(int request_id) {
- ReplyStarted(request_id, "HTTP/1.1 404\r\n\r\n");
- Reply(URLRequestStatus(), request_id);
- }
-
- // Set-expectation helpers
- void SetOnNavigationStateChanged(int tab_handle) {
- EXPECT_CALL(*this,
- OnNavigationStateChanged(testing::Eq(tab_handle), testing::_))
- .Times(testing::AnyNumber());
- }
-
- PluginUrlRequestDelegate* request_delegate_;
-};
-
-class MockProxyFactory : public ProxyFactory {
- public:
- MOCK_METHOD3(GetAutomationServer, void (ProxyFactory::LaunchDelegate*,
- const ChromeFrameLaunchParams& params, void** automation_server_id));
- MOCK_METHOD1(ReleaseAutomationServer, bool(void* id));
-
- MockProxyFactory() : thread_("mock factory worker") {
- thread_.Start();
- loop_ = thread_.message_loop();
- }
-
- // Fake implementation
- void GetServerImpl(ChromeFrameAutomationProxy* pxy,
- void* proxy_id,
- AutomationLaunchResult result,
- LaunchDelegate* d,
- const ChromeFrameLaunchParams& params,
- void** automation_server_id) {
- *automation_server_id = proxy_id;
- Task* task = NewRunnableMethod(d,
- &ProxyFactory::LaunchDelegate::LaunchComplete, pxy, result);
- loop_->PostDelayedTask(FROM_HERE, task,
- params.automation_server_launch_timeout/2);
- }
-
- base::Thread thread_;
- MessageLoop* loop_;
-};
-
-class MockAutomationProxy : public ChromeFrameAutomationProxy {
- public:
- MOCK_METHOD1(Send, bool(IPC::Message*));
- MOCK_METHOD3(SendAsAsync, void(IPC::SyncMessage* msg, void* callback,
- void* key));
- MOCK_METHOD1(CancelAsync, void(void* key));
- MOCK_METHOD1(CreateTabProxy, scoped_refptr<TabProxy>(int handle));
- MOCK_METHOD0(server_version, std::string(void));
- MOCK_METHOD1(SendProxyConfig, void(const std::string&));
- MOCK_METHOD1(SetEnableExtensionAutomation,
- void(const std::vector<std::string>&));
-
- ~MockAutomationProxy() {}
-};
-
-struct MockAutomationMessageSender : public AutomationMessageSender {
- MOCK_METHOD1(Send, bool(IPC::Message*));
- MOCK_METHOD3(SendWithTimeout, bool(IPC::Message* , int , bool*));
-
- void ForwardTo(MockAutomationProxy *p) {
- proxy_ = p;
- ON_CALL(*this, Send(testing::_))
- .WillByDefault(testing::Invoke(proxy_, &MockAutomationProxy::Send));
- }
-
- MockAutomationProxy* proxy_;
-};
-
-template <> struct RunnableMethodTraits<ProxyFactory::LaunchDelegate> {
- void RetainCallee(ProxyFactory::LaunchDelegate* obj) {}
- void ReleaseCallee(ProxyFactory::LaunchDelegate* obj) {}
-};
-
-template <> struct RunnableMethodTraits<MockProxyFactory> {
- void RetainCallee(MockProxyFactory* obj) {}
- void ReleaseCallee(MockProxyFactory* obj) {}
-};
-
-template <> struct RunnableMethodTraits<ChromeFrameAutomationClient> {
- void RetainCallee(ChromeFrameAutomationClient* obj) {}
- void ReleaseCallee(ChromeFrameAutomationClient* obj) {}
-};
-
-template <> struct RunnableMethodTraits<chrome_frame_test::TimedMsgLoop> {
- void RetainCallee(chrome_frame_test::TimedMsgLoop* obj) {}
- void ReleaseCallee(chrome_frame_test::TimedMsgLoop* obj) {}
-};
-
-// We mock ChromeFrameDelegate only. The rest is with real AutomationProxy
-TEST(CFACWithChrome, CreateTooFast) {
- MockCFDelegate cfd;
- chrome_frame_test::TimedMsgLoop loop;
- int timeout = 0; // Chrome cannot send Hello message so fast.
- const std::wstring profile = L"Adam.N.Epilinter";
-
- scoped_refptr<ChromeFrameAutomationClient> client;
- client = new ChromeFrameAutomationClient();
-
- EXPECT_CALL(cfd, OnAutomationServerLaunchFailed(AUTOMATION_TIMEOUT,
- testing::_))
- .Times(1)
- .WillOnce(QUIT_LOOP(loop));
-
- EXPECT_TRUE(client->Initialize(&cfd, timeout, false, profile, L"", false));
- loop.RunFor(10);
- client->Uninitialize();
-}
-
-// This test may fail if Chrome take more that 10 seconds (timeout var) to
-// launch. In this case GMock shall print something like "unexpected call to
-// OnAutomationServerLaunchFailed". I'm yet to find out how to specify
-// that this is an unexpected call, and still to execute and action.
-TEST(CFACWithChrome, CreateNotSoFast) {
- MockCFDelegate cfd;
- chrome_frame_test::TimedMsgLoop loop;
- const std::wstring profile = L"Adam.N.Epilinter";
- int timeout = 10000;
-
- scoped_refptr<ChromeFrameAutomationClient> client;
- client = new ChromeFrameAutomationClient;
-
- EXPECT_CALL(cfd, OnAutomationServerReady())
- .Times(1)
- .WillOnce(QUIT_LOOP(loop));
-
- EXPECT_CALL(cfd, OnAutomationServerLaunchFailed(testing::_, testing::_))
- .Times(0);
-
- EXPECT_TRUE(client->Initialize(&cfd, timeout, false, profile, L"", false));
-
- loop.RunFor(11);
- client->Uninitialize();
- client = NULL;
-}
-
-MATCHER_P(MsgType, msg_type, "IPC::Message::type()") {
- const IPC::Message& m = arg;
- return (m.type() == msg_type);
-}
-
-MATCHER_P(EqNavigationInfoUrl, url, "IPC::NavigationInfo matcher") {
- if (url.is_valid() && url != arg.url)
- return false;
- // TODO(stevet): other members
- return true;
-}
-
-TEST(CFACWithChrome, NavigateOk) {
- MockCFDelegate cfd;
- chrome_frame_test::TimedMsgLoop loop;
- const std::wstring profile = L"Adam.N.Epilinter";
- const std::string url = "about:version";
- int timeout = 10000;
-
- scoped_refptr<ChromeFrameAutomationClient> client;
- client = new ChromeFrameAutomationClient;
-
- EXPECT_CALL(cfd, OnAutomationServerReady())
- .WillOnce(testing::IgnoreResult(testing::InvokeWithoutArgs(CreateFunctor(
- client.get(), &ChromeFrameAutomationClient::InitiateNavigation,
- url, std::string(), false))));
-
- EXPECT_CALL(cfd, GetBounds(testing::_)).Times(testing::AnyNumber());
-
-// cfd.SetOnNavigationStateChanged();
- EXPECT_CALL(cfd,
- OnNavigationStateChanged(testing::_, testing::_))
- .Times(testing::AnyNumber());
-
- {
- testing::InSequence s;
-
- EXPECT_CALL(cfd, OnDidNavigate(testing::_, EqNavigationInfoUrl(GURL())))
- .Times(1);
-
- EXPECT_CALL(cfd, OnUpdateTargetUrl(testing::_, testing::_)).Times(1);
-
- EXPECT_CALL(cfd, OnLoad(testing::_, testing::_))
- .Times(1)
- .WillOnce(QUIT_LOOP(loop));
- }
-
- EXPECT_TRUE(client->Initialize(&cfd, timeout, false, profile, L"", false));
- loop.RunFor(10);
- client->Uninitialize();
- client = NULL;
-}
-
-TEST(CFACWithChrome, NavigateFailed) {
- MockCFDelegate cfd;
- chrome_frame_test::TimedMsgLoop loop;
- const std::wstring profile = L"Adam.N.Epilinter";
- const std::string url = "http://127.0.0.3:65412/";
- const URLRequestStatus connection_failed(URLRequestStatus::FAILED,
- net::ERR_INVALID_URL);
-
- scoped_refptr<ChromeFrameAutomationClient> client;
- client = new ChromeFrameAutomationClient;
- cfd.SetRequestDelegate(client);
-
- EXPECT_CALL(cfd, OnAutomationServerReady())
- .WillOnce(testing::IgnoreResult(testing::InvokeWithoutArgs(CreateFunctor(
- client.get(), &ChromeFrameAutomationClient::InitiateNavigation,
- url, std::string(), false))));
-
- EXPECT_CALL(cfd, GetBounds(_)).Times(testing::AnyNumber());
- EXPECT_CALL(cfd, OnNavigationStateChanged(_, _)).Times(testing::AnyNumber());
-
- EXPECT_CALL(cfd, OnRequestStart(_, _, _))
- // Often there's another request for the error page
- .Times(testing::Between(1, 2))
- .WillRepeatedly(testing::WithArgs<1>(testing::Invoke(CreateFunctor(&cfd,
- &MockCFDelegate::Reply, connection_failed))));
-
- EXPECT_CALL(cfd, OnUpdateTargetUrl(_, _)).Times(testing::AnyNumber());
- EXPECT_CALL(cfd, OnLoad(_, _)).Times(testing::AtMost(1));
-
- EXPECT_CALL(cfd, OnNavigationFailed(_, _, GURL(url)))
- .Times(1)
- .WillOnce(QUIT_LOOP_SOON(loop, 2));
-
- EXPECT_TRUE(client->Initialize(&cfd, 10000, false, profile, L"", false));
-
- loop.RunFor(10);
- client->Uninitialize();
- client = NULL;
-}
-
-// [CFAC] -- uses a ProxyFactory for creation of ChromeFrameAutomationProxy
-// -- uses ChromeFrameAutomationProxy
-// -- uses TabProxy obtained from ChromeFrameAutomationProxy
-// -- uses ChromeFrameDelegate as outgoing interface
-//
-// We mock ProxyFactory to return mock object (MockAutomationProxy) implementing
-// ChromeFrameAutomationProxy interface.
-// Since CFAC uses TabProxy for few calls and TabProxy is not easy mockable,
-// we create 'real' TabProxy but with fake AutomationSender (the one responsible
-// for sending messages over channel).
-// Additionally we have mock implementation ChromeFrameDelagate interface -
-// MockCFDelegate.
-
-// Test fixture, saves typing all of it's members.
-class CFACMockTest : public testing::Test {
- public:
- MockProxyFactory factory_;
- MockCFDelegate cfd_;
- chrome_frame_test::TimedMsgLoop loop_;
- MockAutomationProxy proxy_;
- scoped_ptr<AutomationHandleTracker> tracker_;
- MockAutomationMessageSender dummy_sender_;
- scoped_refptr<TabProxy> tab_;
- // the victim of all tests
- scoped_refptr<ChromeFrameAutomationClient> client_;
-
- std::wstring profile_;
- int timeout_;
- void* id_; // Automation server id we are going to return
- int tab_handle_; // Tab handle. Any non-zero value is Ok.
-
- inline ChromeFrameAutomationProxy* get_proxy() {
- return static_cast<ChromeFrameAutomationProxy*>(&proxy_);
- }
-
- inline void CreateTab() {
- ASSERT_EQ(NULL, tab_.get());
- tab_ = new TabProxy(&dummy_sender_, tracker_.get(), tab_handle_);
- }
-
- // Easy methods to set expectations.
- void SetAutomationServerOk() {
- EXPECT_CALL(factory_, GetAutomationServer(testing::NotNull(),
- testing::Field(&ChromeFrameLaunchParams::profile_name,
- testing::StrEq(profile_)),
- testing::NotNull()))
- .Times(1)
- .WillOnce(testing::Invoke(
- CreateFunctor(&factory_, &MockProxyFactory::GetServerImpl,
- get_proxy(),
- id_,
- AUTOMATION_SUCCESS)));
-
- EXPECT_CALL(factory_, ReleaseAutomationServer(testing::Eq(id_))).Times(1);
- }
-
- void Set_CFD_LaunchFailed(AutomationLaunchResult result) {
- EXPECT_CALL(cfd_, OnAutomationServerLaunchFailed(
- testing::Eq(result), testing::_))
- .Times(1)
- .WillOnce(QUIT_LOOP(loop_));
- }
-
- protected:
- CFACMockTest() : tracker_(NULL), timeout_(500),
- profile_(L"Adam.N.Epilinter") {
- id_ = reinterpret_cast<void*>(5);
- tab_handle_ = 3;
- }
-
- virtual void SetUp() {
- dummy_sender_.ForwardTo(&proxy_);
- tracker_.reset(new AutomationHandleTracker(&dummy_sender_));
-
- client_ = new ChromeFrameAutomationClient;
- client_->set_proxy_factory(&factory_);
- }
-};
-
-// Could be implemented as MockAutomationProxy member (we have WithArgs<>!)
-ACTION_P3(HandleCreateTab, tab_handle, external_tab_container, tab_wnd) {
- // arg0 - message
- // arg1 - callback
- // arg2 - key
- CallbackRunner<Tuple3<HWND, HWND, int> >* c =
- reinterpret_cast<CallbackRunner<Tuple3<HWND, HWND, int> >*>(arg1);
- c->Run(external_tab_container, tab_wnd, tab_handle);
- delete c;
- delete arg0;
-}
-
-TEST_F(CFACMockTest, MockedCreateTabOk) {
- int timeout = 500;
- CreateTab();
- SetAutomationServerOk();
-
- EXPECT_CALL(proxy_, server_version()).Times(testing::AnyNumber())
- .WillRepeatedly(testing::Return(""));
-
- // We need some valid HWNDs, when responding to CreateExternalTab
- HWND h1 = ::GetDesktopWindow();
- HWND h2 = ::GetDesktopWindow();
- EXPECT_CALL(proxy_, SendAsAsync(testing::Property(&IPC::SyncMessage::type,
- AutomationMsg_CreateExternalTab__ID),
- testing::NotNull(), testing::_))
- .Times(1)
- .WillOnce(HandleCreateTab(tab_handle_, h1, h2));
-
- EXPECT_CALL(proxy_, CreateTabProxy(testing::Eq(tab_handle_)))
- .WillOnce(testing::Return(tab_));
-
- EXPECT_CALL(cfd_, OnAutomationServerReady())
- .WillOnce(QUIT_LOOP(loop_));
-
- EXPECT_CALL(proxy_, CancelAsync(testing::_)).Times(testing::AnyNumber());
-
- // Here we go!
- EXPECT_TRUE(client_->Initialize(&cfd_, timeout, false, profile_, L"", false));
- loop_.RunFor(10);
- client_->Uninitialize();
-}
-
-TEST_F(CFACMockTest, MockedCreateTabFailed) {
- HWND null_wnd = NULL;
- SetAutomationServerOk();
-
- EXPECT_CALL(proxy_, server_version()).Times(testing::AnyNumber())
- .WillRepeatedly(testing::Return(""));
-
- EXPECT_CALL(proxy_, SendAsAsync(testing::Property(&IPC::SyncMessage::type,
- AutomationMsg_CreateExternalTab__ID),
- testing::NotNull(), testing::_))
- .Times(1)
- .WillOnce(HandleCreateTab(tab_handle_, null_wnd, null_wnd));
-
- EXPECT_CALL(proxy_, CreateTabProxy(testing::_)).Times(0);
-
- EXPECT_CALL(proxy_, CancelAsync(testing::_)).Times(testing::AnyNumber());
-
- Set_CFD_LaunchFailed(AUTOMATION_CREATE_TAB_FAILED);
-
- // Here we go!
- EXPECT_TRUE(client_->Initialize(&cfd_, timeout_, false, profile_, L"",
- false));
- loop_.RunFor(4);
- client_->Uninitialize();
-}
-
-const wchar_t kMetaTagPage[] = L"files/meta_tag.html";
-TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_MetaTag) {
- SimpleBrowserTest(IE, kMetaTagPage, L"meta_tag");
-}
-
-const wchar_t kCFProtocolPage[] = L"files/cf_protocol.html";
-TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_CFProtocol) {
- // Temporarily enable gcf: protocol for this test.
- SetConfigBool(kEnableGCFProtocol, true);
- SimpleBrowserTest(IE, kCFProtocolPage, L"chrome_frame_protocol");
- SetConfigBool(kEnableGCFProtocol, false);
-}
-
-const wchar_t kPersistentCookieTest[] =
- L"files/persistent_cookie_test_page.html";
-TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_PersistentCookieTest) {
- // Temporarily enable gcf: protocol for this test.
- SetConfigBool(kEnableGCFProtocol, true);
- SimpleBrowserTest(IE, kPersistentCookieTest, L"PersistentCookieTest");
- SetConfigBool(kEnableGCFProtocol, false);
-}
-
-const wchar_t kNavigateOutPage[] = L"files/navigate_out.html";
-TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_NavigateOut) {
- SimpleBrowserTest(IE, kNavigateOutPage, L"navigate_out");
-}
-
-const wchar_t kReferrerMainTest[] = L"files/referrer_main.html";
-TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_ReferrerTest) {
- SimpleBrowserTest(IE, kReferrerMainTest, L"FullTab_ReferrerTest");
-}
-
-const wchar_t kSubFrameTestPage[] = L"files/full_tab_sub_frame_main.html";
-TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_SubFrame) {
- SimpleBrowserTest(IE, kSubFrameTestPage, L"sub_frame");
-}
-
-const wchar_t kSubIFrameTestPage[] = L"files/full_tab_sub_iframe_main.html";
-TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_SubIFrame) {
- SimpleBrowserTest(IE, kSubIFrameTestPage, L"sub_frame");
-}
-
-const int kChromeFrameLaunchDelay = 5;
-const int kChromeFrameLongNavigationTimeoutInSeconds = 10;
-
-// This class provides functionality to add expectations to IE full tab mode
-// tests.
-class MockWebBrowserEventSink : public chrome_frame_test::WebBrowserEventSink {
- public:
- // Needed to support PostTask.
- static bool ImplementsThreadSafeReferenceCounting() {
- return true;
- }
-
- MOCK_METHOD7_WITH_CALLTYPE(__stdcall, OnBeforeNavigate2,
- HRESULT (IDispatch* dispatch, // NOLINT
- VARIANT* url,
- VARIANT* flags,
- VARIANT* target_frame_name,
- VARIANT* post_data,
- VARIANT* headers,
- VARIANT_BOOL* cancel));
-
- MOCK_METHOD2_WITH_CALLTYPE(__stdcall, OnNavigateComplete2,
- void (IDispatch* dispatch, // NOLINT
- VARIANT* url));
-
- MOCK_METHOD5_WITH_CALLTYPE(__stdcall, OnNewWindow3,
- void (IDispatch** dispatch, // NOLINT
- VARIANT_BOOL* cancel,
- DWORD flags,
- BSTR url_context,
- BSTR url));
-
- MOCK_METHOD2_WITH_CALLTYPE(__stdcall, OnNewWindow2,
- void (IDispatch** dispatch, // NOLINT
- VARIANT_BOOL* cancel));
-
- MOCK_METHOD5_WITH_CALLTYPE(__stdcall, OnNavigateError,
- void (IDispatch* dispatch, // NOLINT
- VARIANT* url,
- VARIANT* frame_name,
- VARIANT* status_code,
- VARIANT* cancel));
-
- MOCK_METHOD1(OnLoad, void (const wchar_t* url)); // NOLINT
- MOCK_METHOD1(OnLoadError, void (const wchar_t* url)); // NOLINT
- MOCK_METHOD1(OnMessage, void (const wchar_t* message)); // NOLINT
- MOCK_METHOD2(OnNewBrowserWindow, void (IDispatch* dispatch, // NOLINT
- const wchar_t* url));
-};
-
-const wchar_t kChromeFrameFileUrl[] = L"gcf:file:///C:/";
-
-TEST(ChromeFrameTest, FullTabModeIE_DisallowedUrls) {
- chrome_frame_test::TimedMsgLoop loop;
- // If a navigation fails then IE issues a navigation to an interstitial
- // page. Catch this to track navigation errors as the NavigateError
- // notification does not seem to fire reliably.
- CComObjectStackEx<MockWebBrowserEventSink> mock;
-
- EXPECT_CALL(mock,
- OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kChromeFrameFileUrl)),
- _, _, _, _, _))
- .Times(1)
- .WillOnce(testing::Return(S_OK));
-
- EXPECT_CALL(mock,
- OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
- testing::StartsWith(L"res:")),
- _, _, _, _, _))
- .Times(1)
- .WillOnce(testing::DoAll(
- QUIT_LOOP(loop),
- testing::Return(S_OK)));
-
- HRESULT hr = mock.LaunchIEAndNavigate(kChromeFrameFileUrl);
- ASSERT_HRESULT_SUCCEEDED(hr);
- if (hr == S_FALSE)
- return;
-
- ASSERT_TRUE(mock.web_browser2() != NULL);
-
- loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
-
- mock.Uninitialize();
- chrome_frame_test::CloseAllIEWindows();
-}
-
-const wchar_t kChromeFrameFullTabWindowOpenTestUrl[] =
- L"http://localhost:1337/files/chrome_frame_window_open.html";
-
-const wchar_t kChromeFrameFullTabWindowOpenPopupUrl[] =
- L"http://localhost:1337/files/chrome_frame_window_open_popup.html";
-
-// This test checks if window.open calls issued by a full tab mode ChromeFrame
-// instance make it back to IE and then transitions back to Chrome as the
-// window.open target page is supposed to render within Chrome.
-// Marking this test as FLAKY initially as it relies on getting focus and user
-// input which don't work correctly at times.
-// http://code.google.com/p/chromium/issues/detail?id=26549
-TEST_F(ChromeFrameTestWithWebServer, FLAKY_FullTabModeIE_WindowOpenInChrome) {
- chrome_frame_test::TimedMsgLoop loop;
- CComObjectStackEx<MockWebBrowserEventSink> mock;
-
- // NOTE:
- // Intentionally not in sequence since we have just one navigation
- // per mock, it's OK to be not in sequence as long as all the expections
- // are satisfied. Moreover, since the second mock expects a new window,
- // its events happen in random order.
- EXPECT_CALL(mock,
- OnBeforeNavigate2(
- _, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kChromeFrameFullTabWindowOpenTestUrl)),
- _, _, _, _, _))
- .Times(testing::AnyNumber()).WillRepeatedly(testing::Return(S_OK));
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .Times(testing::AnyNumber()).WillRepeatedly(testing::Return());
-
- EXPECT_CALL(mock,
- OnLoad(testing::StrEq(kChromeFrameFullTabWindowOpenTestUrl)))
- .WillOnce(testing::DoAll(
- testing::InvokeWithoutArgs(CreateFunctor(&mock,
- &chrome_frame_test::WebBrowserEventSink::SetFocusToChrome)),
- testing::InvokeWithoutArgs(CreateFunctor(&loop,
- &chrome_frame_test::TimedMsgLoop::PostDelayedTask, FROM_HERE,
- NewRunnableMethod(
- &mock,
- &chrome_frame_test::WebBrowserEventSink::SendInputToChrome,
- std::string("A")), 0))));
-
- // Watch for new window
- CComObjectStackEx<MockWebBrowserEventSink> new_window_mock;
- // Can't really check URL here since it will be of the form gcf:attach...
- EXPECT_CALL(mock, OnNewWindow3(_, _, _, _, _));
- EXPECT_CALL(mock, OnNewBrowserWindow(_, _))
- .WillOnce(testing::WithArgs<0>(
- testing::Invoke(CreateFunctor(&new_window_mock,
- &MockWebBrowserEventSink::Attach))));
-
- // Expect navigations on the new mock
- EXPECT_CALL(new_window_mock, OnBeforeNavigate2(_, _, _, _, _, _, _))
- .Times(testing::AnyNumber()).WillRepeatedly(testing::Return(S_OK));
- EXPECT_CALL(new_window_mock, OnNavigateComplete2(_, _))
- .Times(testing::AnyNumber()).WillRepeatedly(testing::Return());
- EXPECT_CALL(new_window_mock,
- OnLoad(testing::StrEq(kChromeFrameFullTabWindowOpenPopupUrl)))
- .WillOnce(testing::DoAll(
- testing::InvokeWithoutArgs(CreateFunctor(&mock,
- &MockWebBrowserEventSink::Uninitialize)),
- testing::InvokeWithoutArgs(CreateFunctor(&new_window_mock,
- &MockWebBrowserEventSink::Uninitialize)),
- testing::IgnoreResult(testing::InvokeWithoutArgs(
- &chrome_frame_test::CloseAllIEWindows)),
- QUIT_LOOP_SOON(loop, 2)));
-
- HRESULT hr = mock.LaunchIEAndNavigate(kChromeFrameFullTabWindowOpenTestUrl);
- ASSERT_HRESULT_SUCCEEDED(hr);
- if (hr == S_FALSE)
- return;
-
- ASSERT_TRUE(mock.web_browser2() != NULL);
-
- loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
-
- mock.Uninitialize();
- chrome_frame_test::CloseAllIEWindows();
- ASSERT_TRUE(CheckResultFile(L"ChromeFrameWindowOpenPopup", "OK"));
-}
-
-const wchar_t kSubFrameUrl1[] =
- L"http://localhost:1337/files/sub_frame1.html";
-
-const wchar_t kChromeFrameAboutVersion[] =
- L"gcf:about:version";
-
-// This test launches chrome frame in full tab mode in IE by having IE navigate
-// to gcf:about:blank. It then looks for the chrome renderer window and posts
-// the WM_RBUTTONDOWN/WM_RBUTTONUP messages to it, which bring up the context
-// menu. This is followed by keyboard messages sent via SendInput to select
-// the About chrome frame menu option, which would then bring up a new window
-// with the chrome revision. The test finally checks for success by comparing
-// the URL of the window being opened with cf:about:version, which indicates
-// that the operation succeeded.
-// Marking this test FLAKY as it fails at times on the buildbot.
-// http://code.google.com/p/chromium/issues/detail?id=26549
-TEST_F(ChromeFrameTestWithWebServer, FLAKY_FullTabModeIE_AboutChromeFrame) {
- chrome_frame_test::TimedMsgLoop loop;
- CComObjectStackEx<MockWebBrowserEventSink> mock;
-
- EXPECT_CALL(mock,
- OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kSubFrameUrl1)),
- _, _, _, _, _))
- .Times(testing::AnyNumber()).WillRepeatedly(testing::Return(S_OK));
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .Times(testing::AnyNumber()).WillRepeatedly(testing::Return());
-
- EXPECT_CALL(mock, OnLoad(testing::StrEq(kSubFrameUrl1)))
- .WillOnce(testing::InvokeWithoutArgs(
- &chrome_frame_test::ShowChromeFrameContextMenu));
-
- EXPECT_CALL(mock,
- OnNewWindow3(_, _, _, _,
- testing::StrCaseEq(kChromeFrameAboutVersion)))
- .WillOnce(QUIT_LOOP(loop));
-
- HRESULT hr = mock.LaunchIEAndNavigate(kSubFrameUrl1);
- ASSERT_HRESULT_SUCCEEDED(hr);
- if (hr == S_FALSE)
- return;
-
- ASSERT_TRUE(mock.web_browser2() != NULL);
-
- loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
-
- mock.Uninitialize();
- chrome_frame_test::CloseAllIEWindows();
-}
-
-const wchar_t kChromeFrameFullTabModeKeyEventUrl[] = L"files/keyevent.html";
-
-// Marking this test FLAKY as it fails at times on the buildbot.
-// http://code.google.com/p/chromium/issues/detail?id=26549
-TEST_F(ChromeFrameTestWithWebServer, FLAKY_FullTabModeIE_ChromeFrameKeyboardTest) {
- chrome_frame_test::TimedMsgLoop loop;
-
- ASSERT_TRUE(LaunchBrowser(IE, kChromeFrameFullTabModeKeyEventUrl));
-
- // Allow some time for chrome to be launched.
- loop.RunFor(kChromeFrameLaunchDelay);
-
- HWND renderer_window = chrome_frame_test::GetChromeRendererWindow();
- EXPECT_TRUE(IsWindow(renderer_window));
-
- chrome_frame_test::SetKeyboardFocusToWindow(renderer_window, 1, 1);
- chrome_frame_test::SendInputToWindow(renderer_window, "Chrome");
-
- loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
-
- chrome_frame_test::CloseAllIEWindows();
- ASSERT_TRUE(CheckResultFile(L"FullTab_KeyboardTest", "OK"));
-}
-
-const wchar_t kSubFrameUrl2[] =
- L"http://localhost:1337/files/sub_frame2.html";
-const wchar_t kSubFrameUrl3[] =
- L"http://localhost:1337/files/sub_frame3.html";
-
-// Hack to pass a reference to the argument instead of value. Passing by
-// value evaluates the argument at the mock specification time which is
-// not always ideal. For e.g. At the time of mock creation, web_browser2_
-// pointer is not set up yet so by passing a reference to it instead of
-// a value we allow it to be created later.
-template <typename T> T** ReceivePointer(scoped_refptr<T>& p) { // NOLINT
- return reinterpret_cast<T**>(&p);
-}
-
-// Full tab mode back/forward test
-// Launch and navigate chrome frame to a set of URLs and test back forward
-TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_BackForward) {
- chrome_frame_test::TimedMsgLoop loop;
- CComObjectStackEx<MockWebBrowserEventSink> mock;
- ::testing::InSequence sequence; // Everything in sequence
-
- // When the onhttpequiv patch is enabled, we will get two
- // BeforeNavigate2/OnNavigateComplete2 notifications due to
- // switching from IE to CF.
- // Note that when going backwards, we don't expect that since the extra
- // navigational entries in the travel log should have been removed.
-
- EXPECT_CALL(mock,
- OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kSubFrameUrl1)),
- _, _, _, _, _))
- .WillOnce(testing::Return(S_OK));
-
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .WillOnce(testing::Return());
-
- EXPECT_CALL(mock,
- OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kSubFrameUrl1)),
- _, _, _, _, _))
- .Times(testing::AnyNumber()).WillRepeatedly(testing::Return(S_OK));
-
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .Times(testing::AnyNumber()).WillRepeatedly(testing::Return());
-
- // Navigate to url 2 after the previous navigation is complete.
- EXPECT_CALL(mock, OnLoad(testing::StrEq(kSubFrameUrl1)))
- .WillOnce(testing::IgnoreResult(testing::InvokeWithoutArgs(
- CreateFunctor(
- &mock, &chrome_frame_test::WebBrowserEventSink::Navigate,
- std::wstring(kSubFrameUrl2)))));
-
- // Expect BeforeNavigate/NavigateComplete twice here as well.
- EXPECT_CALL(mock,
- OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kSubFrameUrl2)),
- _, _, _, _, _))
- .WillOnce(testing::Return(S_OK));
-
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .WillOnce(testing::Return());
-
- EXPECT_CALL(mock,
- OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kSubFrameUrl2)),
- _, _, _, _, _))
- .Times(testing::AnyNumber()).WillRepeatedly(testing::Return(S_OK));
-
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .Times(testing::AnyNumber()).WillRepeatedly(testing::Return());
-
- // Navigate to url 3 after the previous navigation is complete
- EXPECT_CALL(mock, OnLoad(testing::StrEq(kSubFrameUrl2)))
- .WillOnce(testing::IgnoreResult(testing::InvokeWithoutArgs(
- CreateFunctor(
- &mock, &chrome_frame_test::WebBrowserEventSink::Navigate,
- std::wstring(kSubFrameUrl3)))));
-
- // We have reached url 3 and have two back entries for url 1 & 2
- // Go back to url 2 now
- EXPECT_CALL(mock,
- OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kSubFrameUrl3)),
- _, _, _, _, _))
- .WillOnce(testing::Return(S_OK));
-
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .WillOnce(testing::Return());
-
- EXPECT_CALL(mock,
- OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kSubFrameUrl3)),
- _, _, _, _, _))
- .Times(testing::AnyNumber()).WillRepeatedly(testing::Return(S_OK));
-
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .Times(testing::AnyNumber()).WillRepeatedly(testing::Return());
-
- // Go back.
- EXPECT_CALL(mock, OnLoad(testing::StrEq(kSubFrameUrl3)))
- .WillOnce(testing::IgnoreResult(testing::InvokeWithoutArgs(
- CreateFunctor(ReceivePointer(mock.web_browser2_),
- &IWebBrowser::GoBack))));
-
- // We have reached url 2 and have 1 back & 1 forward entries for url 1 & 3
- // Go back to url 1 now
- EXPECT_CALL(mock,
- OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kSubFrameUrl2)),
- _, _, _, _, _))
- .WillOnce(testing::Return(S_OK));
-
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .WillOnce(testing::Return());
-
- EXPECT_CALL(mock, OnLoad(testing::StrEq(kSubFrameUrl2)))
- .WillOnce(testing::IgnoreResult(testing::InvokeWithoutArgs(
- CreateFunctor(ReceivePointer(mock.web_browser2_),
- &IWebBrowser::GoBack))));
-
- // We have reached url 1 and have 0 back & 2 forward entries for url 2 & 3
- // Go back to url 1 now
- EXPECT_CALL(mock,
- OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kSubFrameUrl1)),
- _, _, _, _, _));
-
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .WillOnce(testing::Return());
-
- EXPECT_CALL(mock, OnLoad(testing::StrEq(kSubFrameUrl1)))
- .WillOnce(testing::DoAll(
- testing::InvokeWithoutArgs(CreateFunctor(&mock,
- &chrome_frame_test::WebBrowserEventSink::Uninitialize)),
- testing::IgnoreResult(testing::InvokeWithoutArgs(
- &chrome_frame_test::CloseAllIEWindows)),
- QUIT_LOOP_SOON(loop, 2)));
-
- HRESULT hr = mock.LaunchIEAndNavigate(kSubFrameUrl1);
- ASSERT_HRESULT_SUCCEEDED(hr);
- if (hr == S_FALSE)
- return;
-
- ASSERT_TRUE(mock.web_browser2() != NULL);
- loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
- mock.Uninitialize();
- chrome_frame_test::CloseAllIEWindows();
-}
-
-
-const wchar_t kChromeFrameAboutBlankUrl[] = L"gcf:about:blank";
-
-TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_ChromeFrameFocusTest) {
- chrome_frame_test::TimedMsgLoop loop;
-
- ASSERT_TRUE(LaunchBrowser(IE, kChromeFrameAboutBlankUrl));
-
- // Allow some time for chrome to be launched.
- loop.RunFor(kChromeFrameLaunchDelay);
-
- HWND renderer_window = chrome_frame_test::GetChromeRendererWindow();
- EXPECT_TRUE(IsWindow(renderer_window));
-
- DWORD renderer_thread_id = 0;
- DWORD renderer_process_id = 0;
- renderer_thread_id = GetWindowThreadProcessId(renderer_window,
- &renderer_process_id);
-
- AttachThreadInput(GetCurrentThreadId(), renderer_thread_id, TRUE);
- HWND focus_window = GetFocus();
- EXPECT_TRUE(focus_window == renderer_window);
- AttachThreadInput(GetCurrentThreadId(), renderer_thread_id, FALSE);
-
- chrome_frame_test::CloseAllIEWindows();
-}
-
-const wchar_t kAnchorUrl[] = L"http://localhost:1337/files/anchor.html";
-const wchar_t kAnchor1Url[] = L"http://localhost:1337/files/anchor.html#a1";
-const wchar_t kAnchor2Url[] = L"http://localhost:1337/files/anchor.html#a2";
-const wchar_t kAnchor3Url[] = L"http://localhost:1337/files/anchor.html#a3";
-
-// Full tab mode back/forward test
-// Launch and navigate chrome frame to a set of URLs and test back forward
-// Marking this test FLAKY as it fails at times on the buildbot.
-// http://code.google.com/p/chromium/issues/detail?id=26549
-TEST_F(ChromeFrameTestWithWebServer, FLAKY_FullTabModeIE_BackForwardAnchor) {
- const char tab_enter_keystrokes[] = { VK_TAB, VK_RETURN, 0 };
- static const std::string tab_enter(tab_enter_keystrokes);
- chrome_frame_test::TimedMsgLoop loop;
- CComObjectStackEx<MockWebBrowserEventSink> mock;
- ::testing::InSequence sequence; // Everything in sequence
-
- // When the onhttpequiv patch is enabled, we will get two
- // BeforeNavigate2/OnNavigateComplete2 notifications due to
- // switching from IE to CF.
- // Note that when going backwards, we don't expect that since the extra
- // navigational entries in the travel log should have been removed.
- // Same for navigating to anchors within a page that's already loaded.
-
- // Back/Forward state at this point:
- // Back: 0
- // Forward: 0
- EXPECT_CALL(mock, OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kAnchorUrl)),
- _, _, _, _, _))
- .WillOnce(testing::Return(S_OK));
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .WillOnce(testing::Return());
- EXPECT_CALL(mock, OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kAnchorUrl)),
- _, _, _, _, _))
- .Times(testing::AnyNumber()).WillRepeatedly(testing::Return(S_OK));
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .Times(testing::AnyNumber()).WillRepeatedly(testing::Return());
-
- // Navigate to anchor 1:
- // - First set focus to chrome renderer window
- // Call WebBrowserEventSink::SetFocusToChrome only once
- // in the beginning. Calling it again will change focus from the
- // current location to an element near the simulated mouse.click.
- // - Then send keyboard input of TAB + ENTER to cause navigation.
- // It's better to send input as PostDelayedTask since the Activex
- // message loop on the other side might be blocked when we get
- // called in Onload.
- EXPECT_CALL(mock, OnLoad(testing::StrEq(kAnchorUrl)))
- .WillOnce(testing::DoAll(
- testing::InvokeWithoutArgs(CreateFunctor(&mock,
- &chrome_frame_test::WebBrowserEventSink::SetFocusToChrome)),
- testing::InvokeWithoutArgs(CreateFunctor(&loop,
- &chrome_frame_test::TimedMsgLoop::PostDelayedTask, FROM_HERE,
- NewRunnableMethod(
- &mock,
- &chrome_frame_test::WebBrowserEventSink::SendInputToChrome,
- std::string(tab_enter)), 0))));
- EXPECT_CALL(mock, OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kAnchor1Url)),
- _, _, _, _, _))
- .WillOnce(testing::Return(S_OK));
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .WillOnce(testing::Return());
-
- // Navigate to anchor 2 after the previous navigation is complete
- // Back/Forward state at this point:
- // Back: 1 (kAnchorUrl)
- // Forward: 0
- EXPECT_CALL(mock, OnLoad(testing::StrEq(kAnchor1Url)))
- .WillOnce(testing::InvokeWithoutArgs(
- CreateFunctor(
- &loop, &chrome_frame_test::TimedMsgLoop::PostDelayedTask,
- FROM_HERE,
- NewRunnableMethod(
- &mock,
- &chrome_frame_test::WebBrowserEventSink::SendInputToChrome,
- std::string(tab_enter)), 0)));
- EXPECT_CALL(mock, OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kAnchor2Url)),
- _, _, _, _, _))
- .WillOnce(testing::Return(S_OK));
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .WillOnce(testing::Return());
-
- // Navigate to anchor 3 after the previous navigation is complete
- // Back/Forward state at this point:
- // Back: 2 (kAnchorUrl, kAnchor1Url)
- // Forward: 0
- EXPECT_CALL(mock, OnLoad(testing::StrEq(kAnchor2Url)))
- .WillOnce(testing::InvokeWithoutArgs(
- CreateFunctor(
- &loop, &chrome_frame_test::TimedMsgLoop::PostDelayedTask,
- FROM_HERE,
- NewRunnableMethod(
- &mock,
- &chrome_frame_test::WebBrowserEventSink::SendInputToChrome,
- std::string(tab_enter)), 0)));
- EXPECT_CALL(mock, OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kAnchor3Url)),
- _, _, _, _, _))
- .WillOnce(testing::Return(S_OK));
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .WillOnce(testing::Return());
-
- // We will reach anchor 3 once the navigation is complete,
- // then go back to anchor 2
- // Back/Forward state at this point:
- // Back: 3 (kAnchorUrl, kAnchor1Url, kAnchor2Url)
- // Forward: 0
- EXPECT_CALL(mock, OnLoad(testing::StrEq(kAnchor3Url)))
- .WillOnce(testing::IgnoreResult(testing::InvokeWithoutArgs(
- CreateFunctor(ReceivePointer(mock.web_browser2_),
- &IWebBrowser::GoBack))));
- EXPECT_CALL(mock, OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kAnchor2Url)),
- _, _, _, _, _))
- .WillOnce(testing::Return(S_OK));
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .WillOnce(testing::Return());
-
- // We will reach anchor 2 once the navigation is complete,
- // then go back to anchor 1
- // Back/Forward state at this point:
- // Back: 3 (kAnchorUrl, kAnchor1Url, kAnchor2Url)
- // Forward: 1 (kAnchor3Url)
- EXPECT_CALL(mock, OnLoad(testing::StrEq(kAnchor2Url)))
- .WillOnce(testing::IgnoreResult(testing::InvokeWithoutArgs(
- CreateFunctor(ReceivePointer(mock.web_browser2_),
- &IWebBrowser::GoBack))));
- EXPECT_CALL(mock, OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kAnchor1Url)),
- _, _, _, _, _))
- .WillOnce(testing::Return(S_OK));
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .WillOnce(testing::Return());
-
- // We will reach anchor 1 once the navigation is complete,
- // now go forward to anchor 2
- // Back/Forward state at this point:
- // Back: 2 (kAnchorUrl, kAnchor1Url)
- // Forward: 2 (kAnchor2Url, kAnchor3Url)
- EXPECT_CALL(mock, OnLoad(testing::StrEq(kAnchor1Url)))
- .WillOnce(testing::IgnoreResult(testing::InvokeWithoutArgs(
- CreateFunctor(ReceivePointer(mock.web_browser2_),
- &IWebBrowser::GoForward))));
- EXPECT_CALL(mock, OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kAnchor2Url)),
- _, _, _, _, _))
- .WillOnce(testing::Return(S_OK));
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .WillOnce(testing::Return());
-
- // We have reached anchor 2, go forward to anchor 3 again
- // Back/Forward state at this point:
- // Back: 3 (kAnchorUrl, kAnchor1Url, kAnchor2Url)
- // Forward: 1 (kAnchor3Url)
- EXPECT_CALL(mock, OnLoad(testing::StrEq(kAnchor2Url)))
- .WillOnce(testing::IgnoreResult(testing::InvokeWithoutArgs(
- CreateFunctor(ReceivePointer(mock.web_browser2_),
- &IWebBrowser::GoForward))));
- EXPECT_CALL(mock, OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kAnchor3Url)),
- _, _, _, _, _))
- .WillOnce(testing::Return(S_OK));
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .WillOnce(testing::Return());
-
- // We have gone a few steps back and forward, this should be enough for now.
- EXPECT_CALL(mock, OnLoad(testing::StrEq(kAnchor3Url)))
- .WillOnce(testing::DoAll(
- testing::InvokeWithoutArgs(CreateFunctor(&mock,
- &chrome_frame_test::WebBrowserEventSink::Uninitialize)),
- testing::IgnoreResult(testing::InvokeWithoutArgs(
- &chrome_frame_test::CloseAllIEWindows)),
- QUIT_LOOP_SOON(loop, 2)));
-
- HRESULT hr = mock.LaunchIEAndNavigate(kAnchorUrl);
- ASSERT_HRESULT_SUCCEEDED(hr);
- if (hr == S_FALSE)
- return;
-
- ASSERT_TRUE(mock.web_browser2() != NULL);
- loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
- mock.Uninitialize();
- chrome_frame_test::CloseAllIEWindows();
-}
-
-// Full tab mode view source test
-// Launch and navigate chrome frame and invoke view source functionality
-TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_ViewSource) {
- chrome_frame_test::TimedMsgLoop loop;
- CComObjectStackEx<MockWebBrowserEventSink> mock;
- CComObjectStackEx<MockWebBrowserEventSink> view_source_mock;
- ::testing::InSequence sequence; // Everything in sequence
-
- // After navigation invoke view soruce action using IWebBrowser2::ExecWB
- EXPECT_CALL(mock, OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kAnchorUrl)),
- _, _, _, _, _))
- .WillOnce(testing::Return(S_OK));
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .WillOnce(testing::Return());
- EXPECT_CALL(mock, OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kAnchorUrl)),
- _, _, _, _, _))
- .Times(testing::AnyNumber()).WillRepeatedly(testing::Return(S_OK));
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .Times(testing::AnyNumber()).WillRepeatedly(testing::Return());
-
- VARIANT empty = ScopedVariant::kEmptyVariant;
- EXPECT_CALL(mock, OnLoad(testing::StrEq(kAnchorUrl)))
- .WillOnce(testing::IgnoreResult(testing::InvokeWithoutArgs(
- CreateFunctor(ReceivePointer(mock.web_browser2_),
- &IWebBrowser2::ExecWB,
- static_cast<OLECMDID>(IDM_VIEWSOURCE),
- OLECMDEXECOPT_DONTPROMPTUSER, &empty, &empty))));
-
- // Expect notification for view-source window, handle new window event
- // and attach a new mock to the received web browser
- std::wstring view_source_url;
- view_source_url += UTF8ToWide(chrome::kViewSourceScheme);
- view_source_url += L":";
- view_source_url += kAnchorUrl;
- std::wstring url_in_new_window = kChromeProtocolPrefix;
- url_in_new_window += view_source_url;
-
- EXPECT_CALL(mock, OnNewWindow3(_, _, _, _,
- testing::StrCaseEq(url_in_new_window)));
- EXPECT_CALL(mock, OnNewBrowserWindow(_, _))
- .WillOnce(testing::WithArgs<0>(
- testing::Invoke(CreateFunctor(&view_source_mock,
- &MockWebBrowserEventSink::Attach))));
-
- // Expect navigations on the new mock
- EXPECT_CALL(view_source_mock, OnBeforeNavigate2(_,
- testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(url_in_new_window)), _, _, _, _, _))
- .Times(testing::AnyNumber()).WillRepeatedly(testing::Return(S_OK));
- EXPECT_CALL(view_source_mock, OnNavigateComplete2(_, _))
- .WillOnce(testing::Return());
- EXPECT_CALL(view_source_mock, OnLoad(testing::StrEq(view_source_url)))
- .WillOnce(testing::DoAll(
- testing::InvokeWithoutArgs(CreateFunctor(&mock,
- &MockWebBrowserEventSink::Uninitialize)),
- testing::InvokeWithoutArgs(CreateFunctor(&view_source_mock,
- &MockWebBrowserEventSink::Uninitialize)),
- testing::IgnoreResult(testing::InvokeWithoutArgs(
- &chrome_frame_test::CloseAllIEWindows)),
- QUIT_LOOP_SOON(loop, 2)));
-
- HRESULT hr = mock.LaunchIEAndNavigate(kAnchorUrl);
- ASSERT_HRESULT_SUCCEEDED(hr);
- if (hr == S_FALSE)
- return;
-
- ASSERT_TRUE(mock.web_browser2() != NULL);
- loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
- mock.Uninitialize();
- chrome_frame_test::CloseAllIEWindows();
-}
-
-const wchar_t kChromeFrameFullTabModeXMLHttpRequestTestUrl[] =
- L"files/xmlhttprequest_test.html";
-
-TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_ChromeFrameXHRTest) {
- chrome_frame_test::TimedMsgLoop loop;
-
- ASSERT_TRUE(LaunchBrowser(IE, kChromeFrameFullTabModeXMLHttpRequestTestUrl));
-
- loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
-
- chrome_frame_test::CloseAllIEWindows();
- ASSERT_TRUE(CheckResultFile(L"FullTab_XMLHttpRequestTest", "OK"));
-}
-
-const wchar_t kMultipleCFInstancesTestUrl[] =
- L"files/multiple_cf_instances_main.html";
-
-TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_MultipleCFInstances) {
- SimpleBrowserTest(IE, kMultipleCFInstancesTestUrl,
- L"WidgetMode_MultipleInstancesTest");
-}
-
-// TODO(ananta)
-// Disabled until I figure out why this does not work on Firefox.
-TEST_F(ChromeFrameTestWithWebServer,
- DISABLED_WidgetModeFF_MultipleCFInstances) {
- SimpleBrowserTest(FIREFOX, kMultipleCFInstancesTestUrl,
- L"WidgetMode_MultipleInstancesTest");
-}
-
-const wchar_t kChromeFrameFullTabModeXMLHttpRequestAuthHeaderTestUrl[] =
- L"files/xmlhttprequest_authorization_header_test.html";
-
-TEST_F(ChromeFrameTestWithWebServer,
- FullTabModeIE_ChromeFrameXHRAuthHeaderTest) {
- chrome_frame_test::TimedMsgLoop loop;
-
- ASSERT_TRUE(LaunchBrowser(
- IE, kChromeFrameFullTabModeXMLHttpRequestAuthHeaderTestUrl));
-
- loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
-
- chrome_frame_test::CloseAllIEWindows();
- ASSERT_TRUE(
- CheckResultFile(L"FullTab_XMLHttpRequestAuthorizationHeaderTest", "OK"));
-}
-
-const wchar_t kChromeFrameFullTabModeDeleteCookieTest[] =
- L"files/fulltab_delete_cookie_test.html";
-
-TEST_F(ChromeFrameTestWithWebServer,
- FullTabModeIE_ChromeFrameDeleteCookieTest) {
- chrome_frame_test::TimedMsgLoop loop;
-
- ASSERT_TRUE(LaunchBrowser(IE, kChromeFrameFullTabModeDeleteCookieTest));
-
- loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
-
- chrome_frame_test::CloseAllIEWindows();
- ASSERT_TRUE(CheckResultFile(L"FullTab_DeleteCookieTest", "OK"));
-}
-
-const wchar_t kChromeFrameFullTabModeAnchorUrlNavigate[] =
- L"files/fulltab_anchor_url_navigate.html#chrome_frame";
-
-TEST_F(ChromeFrameTestWithWebServer,
- FullTabModeIE_ChromeFrameAnchorUrlNavigateTest) {
- chrome_frame_test::TimedMsgLoop loop;
-
- ASSERT_TRUE(LaunchBrowser(IE, kChromeFrameFullTabModeAnchorUrlNavigate));
-
- loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
-
- chrome_frame_test::CloseAllIEWindows();
- ASSERT_TRUE(CheckResultFile(L"FullTab_AnchorURLNavigateTest", "OK"));
-}
-
-const wchar_t kChromeFrameFullTabModeBeforeUnloadEventTest[] =
- L"http://localhost:1337/files/fulltab_before_unload_event_test.html";
-
-const wchar_t kChromeFrameFullTabModeBeforeUnloadEventMain[] =
- L"http://localhost:1337/files/fulltab_before_unload_event_main.html";
-
-TEST_F(ChromeFrameTestWithWebServer,
- FullTabModeIE_ChromeFrameUnloadEventTest) {
- chrome_frame_test::TimedMsgLoop loop;
- CComObjectStackEx<MockWebBrowserEventSink> mock;
- ::testing::InSequence sequence; // Everything in sequence
-
- // We will get two BeforeNavigate2/OnNavigateComplete2 notifications due to
- // switching from IE to CF.
- EXPECT_CALL(
- mock,
- OnBeforeNavigate2(
- _, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kChromeFrameFullTabModeBeforeUnloadEventTest)),
- _, _, _, _, _))
- .WillOnce(testing::Return(S_OK));
-
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .WillOnce(testing::Return());
-
- EXPECT_CALL(
- mock,
- OnBeforeNavigate2(
- _, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kChromeFrameFullTabModeBeforeUnloadEventTest)),
- _, _, _, _, _))
- .Times(testing::AnyNumber()).WillRepeatedly(testing::Return(S_OK));
-
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .Times(testing::AnyNumber()).WillRepeatedly(testing::Return());
-
- EXPECT_CALL(mock, OnLoad(_)).WillOnce(testing::Return());
-
- // We will get two BeforeNavigate2/OnNavigateComplete2 notifications due to
- // switching from IE to CF.
- EXPECT_CALL(
- mock,
- OnBeforeNavigate2(
- _, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kChromeFrameFullTabModeBeforeUnloadEventMain)),
- _, _, _, _, _))
- .WillOnce(testing::Return(S_OK));
-
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .WillOnce(testing::Return());
-
- EXPECT_CALL(
- mock,
- OnBeforeNavigate2(
- _, testing::Field(&VARIANT::bstrVal,
- testing::StrCaseEq(kChromeFrameFullTabModeBeforeUnloadEventMain)),
- _, _, _, _, _))
- .Times(testing::AnyNumber()).WillRepeatedly(testing::Return(S_OK));
-
- EXPECT_CALL(mock, OnNavigateComplete2(_, _))
- .Times(testing::AnyNumber()).WillRepeatedly(testing::Return());
-
- EXPECT_CALL(mock, OnLoad(_)).WillOnce(testing::Return());
-
- EXPECT_CALL(mock, OnMessage(_))
- .WillOnce(testing::DoAll(
- testing::InvokeWithoutArgs(CreateFunctor(&mock,
- &chrome_frame_test::WebBrowserEventSink::Uninitialize)),
- testing::IgnoreResult(testing::InvokeWithoutArgs(
- &chrome_frame_test::CloseAllIEWindows)),
- QUIT_LOOP_SOON(loop, 2)));
-
- HRESULT hr =
- mock.LaunchIEAndNavigate(kChromeFrameFullTabModeBeforeUnloadEventTest);
- ASSERT_HRESULT_SUCCEEDED(hr);
- if (hr == S_FALSE)
- return;
-
- ASSERT_TRUE(mock.web_browser2() != NULL);
- loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
- mock.Uninitialize();
- chrome_frame_test::CloseAllIEWindows();
-}
diff --git a/chrome_frame/test/function_stub_unittest.cc b/chrome_frame/test/function_stub_unittest.cc
index 6ef6f36..8ac107c 100644
--- a/chrome_frame/test/function_stub_unittest.cc
+++ b/chrome_frame/test/function_stub_unittest.cc
@@ -3,8 +3,7 @@
// found in the LICENSE file.
#include "chrome_frame/function_stub.h"
-
-#include "chrome_frame/test/chrome_frame_unittests.h"
+#include "testing/gtest/include/gtest/gtest.h"
#define NO_INLINE __declspec(noinline)
diff --git a/chrome_frame/test/html_util_unittests.cc b/chrome_frame/test/html_util_unittests.cc
index 90cdd4f..b993129 100644
--- a/chrome_frame/test/html_util_unittests.cc
+++ b/chrome_frame/test/html_util_unittests.cc
@@ -19,7 +19,6 @@
#include "base/win_util.h"
#include "net/base/net_util.h"
-#include "chrome_frame/test/chrome_frame_unittests.h"
#include "chrome_frame/chrome_frame_automation.h"
#include "chrome_frame/chrome_frame_delegate.h"
#include "chrome_frame/html_utils.h"
diff --git a/chrome_frame/test/proxy_factory_mock.cc b/chrome_frame/test/proxy_factory_mock.cc
new file mode 100644
index 0000000..a50dc33
--- /dev/null
+++ b/chrome_frame/test/proxy_factory_mock.cc
@@ -0,0 +1,86 @@
+// Copyright (c) 2006-2010 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 "chrome_frame/test/proxy_factory_mock.h"
+
+#define GMOCK_MUTANT_INCLUDE_LATE_OBJECT_BINDING
+#include "testing/gmock_mutant.h"
+
+using testing::CreateFunctor;
+using testing::_;
+
+template <> struct RunnableMethodTraits<MockProxyFactory> {
+ void RetainCallee(MockProxyFactory* obj) {}
+ void ReleaseCallee(MockProxyFactory* obj) {}
+};
+
+TEST(ProxyFactoryTest, CreateDestroy) {
+ ProxyFactory f;
+ LaunchDelegateMock d;
+ EXPECT_CALL(d, LaunchComplete(testing::NotNull(), testing::_)).Times(1);
+
+ ChromeFrameLaunchParams params;
+ params.automation_server_launch_timeout = 0;
+ params.profile_name = L"Adam.N.Epilinter";
+ params.extra_chrome_arguments = L"";
+ params.perform_version_check = false;
+ params.incognito_mode = false;
+
+ void* id = NULL;
+ f.GetAutomationServer(&d, params, &id);
+ f.ReleaseAutomationServer(id);
+}
+
+TEST(ProxyFactoryTest, CreateSameProfile) {
+ ProxyFactory f;
+ LaunchDelegateMock d;
+ EXPECT_CALL(d, LaunchComplete(testing::NotNull(), testing::_)).Times(2);
+
+ ChromeFrameLaunchParams params;
+ params.automation_server_launch_timeout = 0;
+ params.profile_name = L"Dr. Gratiano Forbeson";
+ params.extra_chrome_arguments = L"";
+ params.perform_version_check = false;
+ params.incognito_mode = false;
+
+ void* i1 = NULL;
+ void* i2 = NULL;
+
+ f.GetAutomationServer(&d, params, &i1);
+ f.GetAutomationServer(&d, params, &i2);
+
+ EXPECT_EQ(i1, i2);
+ f.ReleaseAutomationServer(i2);
+ f.ReleaseAutomationServer(i1);
+}
+
+TEST(ProxyFactoryTest, CreateDifferentProfiles) {
+ ProxyFactory f;
+ LaunchDelegateMock d;
+ EXPECT_CALL(d, LaunchComplete(testing::NotNull(), testing::_)).Times(2);
+
+ ChromeFrameLaunchParams params1;
+ params1.automation_server_launch_timeout = 0;
+ params1.profile_name = L"Adam.N.Epilinter";
+ params1.extra_chrome_arguments = L"";
+ params1.perform_version_check = false;
+ params1.incognito_mode = false;
+
+ ChromeFrameLaunchParams params2;
+ params2.automation_server_launch_timeout = 0;
+ params2.profile_name = L"Dr. Gratiano Forbeson";
+ params2.extra_chrome_arguments = L"";
+ params2.perform_version_check = false;
+ params2.incognito_mode = false;
+
+ void* i1 = NULL;
+ void* i2 = NULL;
+
+ f.GetAutomationServer(&d, params1, &i1);
+ f.GetAutomationServer(&d, params2, &i2);
+
+ EXPECT_NE(i1, i2);
+ f.ReleaseAutomationServer(i2);
+ f.ReleaseAutomationServer(i1);
+}
+
diff --git a/chrome_frame/test/proxy_factory_mock.h b/chrome_frame/test/proxy_factory_mock.h
new file mode 100644
index 0000000..8f2bb2e
--- /dev/null
+++ b/chrome_frame/test/proxy_factory_mock.h
@@ -0,0 +1,43 @@
+// Copyright (c) 2006-2010 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.
+#ifndef CHROME_FRAME_PROXY_FACTORY_MOCK_H_
+#define CHROME_FRAME_PROXY_FACTORY_MOCK_H_
+
+#include <windows.h>
+#include <string>
+
+#include "gmock/gmock.h"
+#include "chrome_frame/chrome_frame_automation.h"
+
+struct LaunchDelegateMock : public ProxyFactory::LaunchDelegate {
+ MOCK_METHOD2(LaunchComplete, void(ChromeFrameAutomationProxy*,
+ AutomationLaunchResult));
+};
+
+class MockProxyFactory : public ProxyFactory {
+ public:
+ MOCK_METHOD3(GetAutomationServer, void (ProxyFactory::LaunchDelegate*,
+ const ChromeFrameLaunchParams& params, void** automation_server_id));
+ MOCK_METHOD1(ReleaseAutomationServer, bool(void* id));
+
+ MockProxyFactory() : thread_("mock factory worker") {
+ thread_.Start();
+ loop_ = thread_.message_loop();
+ }
+
+ // Fake implementation
+ void GetServerImpl(ChromeFrameAutomationProxy* pxy,
+ void* proxy_id,
+ AutomationLaunchResult result,
+ LaunchDelegate* d,
+ const ChromeFrameLaunchParams& params,
+ void** automation_server_id);
+
+ base::Thread thread_;
+ MessageLoop* loop_;
+};
+
+
+#endif // CHROME_FRAME_PROXY_FACTORY_MOCK_H_
+
diff --git a/chrome_frame/test/test_mock_with_web_server.cc b/chrome_frame/test/test_mock_with_web_server.cc
new file mode 100644
index 0000000..0e30433
--- /dev/null
+++ b/chrome_frame/test/test_mock_with_web_server.cc
@@ -0,0 +1,684 @@
+// Copyright (c) 2006-2010 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 "chrome_frame/test/test_mock_with_web_server.h"
+
+#include <mshtmcid.h>
+
+#include "chrome/common/url_constants.h"
+#include "chrome_frame/utils.h"
+#include "chrome_frame/test/test_with_web_server.h"
+
+#define GMOCK_MUTANT_INCLUDE_LATE_OBJECT_BINDING
+#include "testing/gmock_mutant.h"
+
+using testing::CreateFunctor;
+using testing::_;
+
+const int kChromeFrameLaunchDelay = 5;
+const int kChromeFrameLongNavigationTimeoutInSeconds = 10;
+
+const wchar_t kChromeFrameFileUrl[] = L"gcf:file:///C:/";
+
+TEST(ChromeFrameTest, FullTabModeIE_DisallowedUrls) {
+ chrome_frame_test::TimedMsgLoop loop;
+ // If a navigation fails then IE issues a navigation to an interstitial
+ // page. Catch this to track navigation errors as the NavigateError
+ // notification does not seem to fire reliably.
+ CComObjectStackEx<MockWebBrowserEventSink> mock;
+
+ EXPECT_CALL(mock,
+ OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kChromeFrameFileUrl)),
+ _, _, _, _, _))
+ .Times(1)
+ .WillOnce(testing::Return(S_OK));
+
+ EXPECT_CALL(mock,
+ OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
+ testing::StartsWith(L"res:")),
+ _, _, _, _, _))
+ .Times(1)
+ .WillOnce(testing::DoAll(
+ QUIT_LOOP(loop),
+ testing::Return(S_OK)));
+
+ HRESULT hr = mock.LaunchIEAndNavigate(kChromeFrameFileUrl);
+ ASSERT_HRESULT_SUCCEEDED(hr);
+ if (hr == S_FALSE)
+ return;
+
+ ASSERT_TRUE(mock.web_browser2() != NULL);
+
+ loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
+
+ mock.Uninitialize();
+ chrome_frame_test::CloseAllIEWindows();
+}
+
+const wchar_t kChromeFrameFullTabWindowOpenTestUrl[] =
+ L"http://localhost:1337/files/chrome_frame_window_open.html";
+
+const wchar_t kChromeFrameFullTabWindowOpenPopupUrl[] =
+ L"http://localhost:1337/files/chrome_frame_window_open_popup.html";
+
+// This test checks if window.open calls issued by a full tab mode ChromeFrame
+// instance make it back to IE and then transitions back to Chrome as the
+// window.open target page is supposed to render within Chrome.
+// Marking this test as FLAKY initially as it relies on getting focus and user
+// input which don't work correctly at times.
+// http://code.google.com/p/chromium/issues/detail?id=26549
+TEST_F(ChromeFrameTestWithWebServer, FLAKY_FullTabModeIE_WindowOpenInChrome) {
+ chrome_frame_test::TimedMsgLoop loop;
+ CComObjectStackEx<MockWebBrowserEventSink> mock;
+
+ // NOTE:
+ // Intentionally not in sequence since we have just one navigation
+ // per mock, it's OK to be not in sequence as long as all the expections
+ // are satisfied. Moreover, since the second mock expects a new window,
+ // its events happen in random order.
+ EXPECT_CALL(mock,
+ OnBeforeNavigate2(
+ _, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kChromeFrameFullTabWindowOpenTestUrl)),
+ _, _, _, _, _))
+ .Times(testing::AnyNumber()).WillRepeatedly(testing::Return(S_OK));
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .Times(testing::AnyNumber()).WillRepeatedly(testing::Return());
+
+ EXPECT_CALL(mock,
+ OnLoad(testing::StrEq(kChromeFrameFullTabWindowOpenTestUrl)))
+ .WillOnce(testing::DoAll(
+ testing::InvokeWithoutArgs(CreateFunctor(&mock,
+ &chrome_frame_test::WebBrowserEventSink::SetFocusToChrome)),
+ testing::InvokeWithoutArgs(CreateFunctor(&loop,
+ &chrome_frame_test::TimedMsgLoop::PostDelayedTask, FROM_HERE,
+ NewRunnableMethod(
+ &mock,
+ &chrome_frame_test::WebBrowserEventSink::SendInputToChrome,
+ std::string("A")), 0))));
+
+ // Watch for new window
+ CComObjectStackEx<MockWebBrowserEventSink> new_window_mock;
+ // Can't really check URL here since it will be of the form gcf:attach...
+ EXPECT_CALL(mock, OnNewWindow3(_, _, _, _, _));
+ EXPECT_CALL(mock, OnNewBrowserWindow(_, _))
+ .WillOnce(testing::WithArgs<0>(
+ testing::Invoke(CreateFunctor(&new_window_mock,
+ &MockWebBrowserEventSink::Attach))));
+
+ // Expect navigations on the new mock
+ EXPECT_CALL(new_window_mock, OnBeforeNavigate2(_, _, _, _, _, _, _))
+ .Times(testing::AnyNumber()).WillRepeatedly(testing::Return(S_OK));
+ EXPECT_CALL(new_window_mock, OnNavigateComplete2(_, _))
+ .Times(testing::AnyNumber()).WillRepeatedly(testing::Return());
+ EXPECT_CALL(new_window_mock,
+ OnLoad(testing::StrEq(kChromeFrameFullTabWindowOpenPopupUrl)))
+ .WillOnce(testing::DoAll(
+ testing::InvokeWithoutArgs(CreateFunctor(&mock,
+ &MockWebBrowserEventSink::Uninitialize)),
+ testing::InvokeWithoutArgs(CreateFunctor(&new_window_mock,
+ &MockWebBrowserEventSink::Uninitialize)),
+ testing::IgnoreResult(testing::InvokeWithoutArgs(
+ &chrome_frame_test::CloseAllIEWindows)),
+ QUIT_LOOP_SOON(loop, 2)));
+
+ HRESULT hr = mock.LaunchIEAndNavigate(kChromeFrameFullTabWindowOpenTestUrl);
+ ASSERT_HRESULT_SUCCEEDED(hr);
+ if (hr == S_FALSE)
+ return;
+
+ ASSERT_TRUE(mock.web_browser2() != NULL);
+
+ loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
+
+ mock.Uninitialize();
+ chrome_frame_test::CloseAllIEWindows();
+ ASSERT_TRUE(CheckResultFile(L"ChromeFrameWindowOpenPopup", "OK"));
+}
+
+const wchar_t kSubFrameUrl1[] =
+ L"http://localhost:1337/files/sub_frame1.html";
+
+const wchar_t kChromeFrameAboutVersion[] =
+ L"gcf:about:version";
+
+// This test launches chrome frame in full tab mode in IE by having IE navigate
+// to gcf:about:blank. It then looks for the chrome renderer window and posts
+// the WM_RBUTTONDOWN/WM_RBUTTONUP messages to it, which bring up the context
+// menu. This is followed by keyboard messages sent via SendInput to select
+// the About chrome frame menu option, which would then bring up a new window
+// with the chrome revision. The test finally checks for success by comparing
+// the URL of the window being opened with cf:about:version, which indicates
+// that the operation succeeded.
+// Marking this test FLAKY as it fails at times on the buildbot.
+// http://code.google.com/p/chromium/issues/detail?id=26549
+TEST_F(ChromeFrameTestWithWebServer, FLAKY_FullTabModeIE_AboutChromeFrame) {
+ chrome_frame_test::TimedMsgLoop loop;
+ CComObjectStackEx<MockWebBrowserEventSink> mock;
+
+ EXPECT_CALL(mock,
+ OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kSubFrameUrl1)),
+ _, _, _, _, _))
+ .Times(testing::AnyNumber()).WillRepeatedly(testing::Return(S_OK));
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .Times(testing::AnyNumber()).WillRepeatedly(testing::Return());
+
+ EXPECT_CALL(mock, OnLoad(testing::StrEq(kSubFrameUrl1)))
+ .WillOnce(testing::InvokeWithoutArgs(
+ &chrome_frame_test::ShowChromeFrameContextMenu));
+
+ EXPECT_CALL(mock,
+ OnNewWindow3(_, _, _, _,
+ testing::StrCaseEq(kChromeFrameAboutVersion)))
+ .WillOnce(QUIT_LOOP(loop));
+
+ HRESULT hr = mock.LaunchIEAndNavigate(kSubFrameUrl1);
+ ASSERT_HRESULT_SUCCEEDED(hr);
+ if (hr == S_FALSE)
+ return;
+
+ ASSERT_TRUE(mock.web_browser2() != NULL);
+
+ loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
+
+ mock.Uninitialize();
+ chrome_frame_test::CloseAllIEWindows();
+}
+
+const wchar_t kSubFrameUrl2[] =
+ L"http://localhost:1337/files/sub_frame2.html";
+const wchar_t kSubFrameUrl3[] =
+ L"http://localhost:1337/files/sub_frame3.html";
+
+// Hack to pass a reference to the argument instead of value. Passing by
+// value evaluates the argument at the mock specification time which is
+// not always ideal. For e.g. At the time of mock creation, web_browser2_
+// pointer is not set up yet so by passing a reference to it instead of
+// a value we allow it to be created later.
+template <typename T> T** ReceivePointer(scoped_refptr<T>& p) { // NOLINT
+ return reinterpret_cast<T**>(&p);
+}
+
+// Full tab mode back/forward test
+// Launch and navigate chrome frame to a set of URLs and test back forward
+TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_BackForward) {
+ chrome_frame_test::TimedMsgLoop loop;
+ CComObjectStackEx<MockWebBrowserEventSink> mock;
+ ::testing::InSequence sequence; // Everything in sequence
+
+ // When the onhttpequiv patch is enabled, we will get two
+ // BeforeNavigate2/OnNavigateComplete2 notifications due to
+ // switching from IE to CF.
+ // Note that when going backwards, we don't expect that since the extra
+ // navigational entries in the travel log should have been removed.
+
+ EXPECT_CALL(mock,
+ OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kSubFrameUrl1)),
+ _, _, _, _, _))
+ .WillOnce(testing::Return(S_OK));
+
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .WillOnce(testing::Return());
+
+ EXPECT_CALL(mock,
+ OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kSubFrameUrl1)),
+ _, _, _, _, _))
+ .Times(testing::AnyNumber()).WillRepeatedly(testing::Return(S_OK));
+
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .Times(testing::AnyNumber()).WillRepeatedly(testing::Return());
+
+ // Navigate to url 2 after the previous navigation is complete.
+ EXPECT_CALL(mock, OnLoad(testing::StrEq(kSubFrameUrl1)))
+ .WillOnce(testing::IgnoreResult(testing::InvokeWithoutArgs(
+ CreateFunctor(
+ &mock, &chrome_frame_test::WebBrowserEventSink::Navigate,
+ std::wstring(kSubFrameUrl2)))));
+
+ // Expect BeforeNavigate/NavigateComplete twice here as well.
+ EXPECT_CALL(mock,
+ OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kSubFrameUrl2)),
+ _, _, _, _, _))
+ .WillOnce(testing::Return(S_OK));
+
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .WillOnce(testing::Return());
+
+ EXPECT_CALL(mock,
+ OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kSubFrameUrl2)),
+ _, _, _, _, _))
+ .Times(testing::AnyNumber()).WillRepeatedly(testing::Return(S_OK));
+
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .Times(testing::AnyNumber()).WillRepeatedly(testing::Return());
+
+ // Navigate to url 3 after the previous navigation is complete
+ EXPECT_CALL(mock, OnLoad(testing::StrEq(kSubFrameUrl2)))
+ .WillOnce(testing::IgnoreResult(testing::InvokeWithoutArgs(
+ CreateFunctor(
+ &mock, &chrome_frame_test::WebBrowserEventSink::Navigate,
+ std::wstring(kSubFrameUrl3)))));
+
+ // We have reached url 3 and have two back entries for url 1 & 2
+ // Go back to url 2 now
+ EXPECT_CALL(mock,
+ OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kSubFrameUrl3)),
+ _, _, _, _, _))
+ .WillOnce(testing::Return(S_OK));
+
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .WillOnce(testing::Return());
+
+ EXPECT_CALL(mock,
+ OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kSubFrameUrl3)),
+ _, _, _, _, _))
+ .Times(testing::AnyNumber()).WillRepeatedly(testing::Return(S_OK));
+
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .Times(testing::AnyNumber()).WillRepeatedly(testing::Return());
+
+ // Go back.
+ EXPECT_CALL(mock, OnLoad(testing::StrEq(kSubFrameUrl3)))
+ .WillOnce(testing::IgnoreResult(testing::InvokeWithoutArgs(
+ CreateFunctor(ReceivePointer(mock.web_browser2_),
+ &IWebBrowser::GoBack))));
+
+ // We have reached url 2 and have 1 back & 1 forward entries for url 1 & 3
+ // Go back to url 1 now
+ EXPECT_CALL(mock,
+ OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kSubFrameUrl2)),
+ _, _, _, _, _))
+ .WillOnce(testing::Return(S_OK));
+
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .WillOnce(testing::Return());
+
+ EXPECT_CALL(mock, OnLoad(testing::StrEq(kSubFrameUrl2)))
+ .WillOnce(testing::IgnoreResult(testing::InvokeWithoutArgs(
+ CreateFunctor(ReceivePointer(mock.web_browser2_),
+ &IWebBrowser::GoBack))));
+
+ // We have reached url 1 and have 0 back & 2 forward entries for url 2 & 3
+ // Go back to url 1 now
+ EXPECT_CALL(mock,
+ OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kSubFrameUrl1)),
+ _, _, _, _, _));
+
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .WillOnce(testing::Return());
+
+ EXPECT_CALL(mock, OnLoad(testing::StrEq(kSubFrameUrl1)))
+ .WillOnce(testing::DoAll(
+ testing::InvokeWithoutArgs(CreateFunctor(&mock,
+ &chrome_frame_test::WebBrowserEventSink::Uninitialize)),
+ testing::IgnoreResult(testing::InvokeWithoutArgs(
+ &chrome_frame_test::CloseAllIEWindows)),
+ QUIT_LOOP_SOON(loop, 2)));
+
+ HRESULT hr = mock.LaunchIEAndNavigate(kSubFrameUrl1);
+ ASSERT_HRESULT_SUCCEEDED(hr);
+ if (hr == S_FALSE)
+ return;
+
+ ASSERT_TRUE(mock.web_browser2() != NULL);
+ loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
+ mock.Uninitialize();
+ chrome_frame_test::CloseAllIEWindows();
+}
+
+const wchar_t kAnchorUrl[] = L"http://localhost:1337/files/anchor.html";
+const wchar_t kAnchor1Url[] = L"http://localhost:1337/files/anchor.html#a1";
+const wchar_t kAnchor2Url[] = L"http://localhost:1337/files/anchor.html#a2";
+const wchar_t kAnchor3Url[] = L"http://localhost:1337/files/anchor.html#a3";
+
+// Full tab mode back/forward test
+// Launch and navigate chrome frame to a set of URLs and test back forward
+// Marking this test FLAKY as it fails at times on the buildbot.
+// http://code.google.com/p/chromium/issues/detail?id=26549
+TEST_F(ChromeFrameTestWithWebServer, FLAKY_FullTabModeIE_BackForwardAnchor) {
+ const char tab_enter_keystrokes[] = { VK_TAB, VK_RETURN, 0 };
+ static const std::string tab_enter(tab_enter_keystrokes);
+ chrome_frame_test::TimedMsgLoop loop;
+ CComObjectStackEx<MockWebBrowserEventSink> mock;
+ ::testing::InSequence sequence; // Everything in sequence
+
+ // When the onhttpequiv patch is enabled, we will get two
+ // BeforeNavigate2/OnNavigateComplete2 notifications due to
+ // switching from IE to CF.
+ // Note that when going backwards, we don't expect that since the extra
+ // navigational entries in the travel log should have been removed.
+ // Same for navigating to anchors within a page that's already loaded.
+
+ // Back/Forward state at this point:
+ // Back: 0
+ // Forward: 0
+ EXPECT_CALL(mock, OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kAnchorUrl)),
+ _, _, _, _, _))
+ .WillOnce(testing::Return(S_OK));
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .WillOnce(testing::Return());
+ EXPECT_CALL(mock, OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kAnchorUrl)),
+ _, _, _, _, _))
+ .Times(testing::AnyNumber()).WillRepeatedly(testing::Return(S_OK));
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .Times(testing::AnyNumber()).WillRepeatedly(testing::Return());
+
+ // Navigate to anchor 1:
+ // - First set focus to chrome renderer window
+ // Call WebBrowserEventSink::SetFocusToChrome only once
+ // in the beginning. Calling it again will change focus from the
+ // current location to an element near the simulated mouse.click.
+ // - Then send keyboard input of TAB + ENTER to cause navigation.
+ // It's better to send input as PostDelayedTask since the Activex
+ // message loop on the other side might be blocked when we get
+ // called in Onload.
+ EXPECT_CALL(mock, OnLoad(testing::StrEq(kAnchorUrl)))
+ .WillOnce(testing::DoAll(
+ testing::InvokeWithoutArgs(CreateFunctor(&mock,
+ &chrome_frame_test::WebBrowserEventSink::SetFocusToChrome)),
+ testing::InvokeWithoutArgs(CreateFunctor(&loop,
+ &chrome_frame_test::TimedMsgLoop::PostDelayedTask, FROM_HERE,
+ NewRunnableMethod(
+ &mock,
+ &chrome_frame_test::WebBrowserEventSink::SendInputToChrome,
+ std::string(tab_enter)), 0))));
+ EXPECT_CALL(mock, OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kAnchor1Url)),
+ _, _, _, _, _))
+ .WillOnce(testing::Return(S_OK));
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .WillOnce(testing::Return());
+
+ // Navigate to anchor 2 after the previous navigation is complete
+ // Back/Forward state at this point:
+ // Back: 1 (kAnchorUrl)
+ // Forward: 0
+ EXPECT_CALL(mock, OnLoad(testing::StrEq(kAnchor1Url)))
+ .WillOnce(testing::InvokeWithoutArgs(
+ CreateFunctor(
+ &loop, &chrome_frame_test::TimedMsgLoop::PostDelayedTask,
+ FROM_HERE,
+ NewRunnableMethod(
+ &mock,
+ &chrome_frame_test::WebBrowserEventSink::SendInputToChrome,
+ std::string(tab_enter)), 0)));
+ EXPECT_CALL(mock, OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kAnchor2Url)),
+ _, _, _, _, _))
+ .WillOnce(testing::Return(S_OK));
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .WillOnce(testing::Return());
+
+ // Navigate to anchor 3 after the previous navigation is complete
+ // Back/Forward state at this point:
+ // Back: 2 (kAnchorUrl, kAnchor1Url)
+ // Forward: 0
+ EXPECT_CALL(mock, OnLoad(testing::StrEq(kAnchor2Url)))
+ .WillOnce(testing::InvokeWithoutArgs(
+ CreateFunctor(
+ &loop, &chrome_frame_test::TimedMsgLoop::PostDelayedTask,
+ FROM_HERE,
+ NewRunnableMethod(
+ &mock,
+ &chrome_frame_test::WebBrowserEventSink::SendInputToChrome,
+ std::string(tab_enter)), 0)));
+ EXPECT_CALL(mock, OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kAnchor3Url)),
+ _, _, _, _, _))
+ .WillOnce(testing::Return(S_OK));
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .WillOnce(testing::Return());
+
+ // We will reach anchor 3 once the navigation is complete,
+ // then go back to anchor 2
+ // Back/Forward state at this point:
+ // Back: 3 (kAnchorUrl, kAnchor1Url, kAnchor2Url)
+ // Forward: 0
+ EXPECT_CALL(mock, OnLoad(testing::StrEq(kAnchor3Url)))
+ .WillOnce(testing::IgnoreResult(testing::InvokeWithoutArgs(
+ CreateFunctor(ReceivePointer(mock.web_browser2_),
+ &IWebBrowser::GoBack))));
+ EXPECT_CALL(mock, OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kAnchor2Url)),
+ _, _, _, _, _))
+ .WillOnce(testing::Return(S_OK));
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .WillOnce(testing::Return());
+
+ // We will reach anchor 2 once the navigation is complete,
+ // then go back to anchor 1
+ // Back/Forward state at this point:
+ // Back: 3 (kAnchorUrl, kAnchor1Url, kAnchor2Url)
+ // Forward: 1 (kAnchor3Url)
+ EXPECT_CALL(mock, OnLoad(testing::StrEq(kAnchor2Url)))
+ .WillOnce(testing::IgnoreResult(testing::InvokeWithoutArgs(
+ CreateFunctor(ReceivePointer(mock.web_browser2_),
+ &IWebBrowser::GoBack))));
+ EXPECT_CALL(mock, OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kAnchor1Url)),
+ _, _, _, _, _))
+ .WillOnce(testing::Return(S_OK));
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .WillOnce(testing::Return());
+
+ // We will reach anchor 1 once the navigation is complete,
+ // now go forward to anchor 2
+ // Back/Forward state at this point:
+ // Back: 2 (kAnchorUrl, kAnchor1Url)
+ // Forward: 2 (kAnchor2Url, kAnchor3Url)
+ EXPECT_CALL(mock, OnLoad(testing::StrEq(kAnchor1Url)))
+ .WillOnce(testing::IgnoreResult(testing::InvokeWithoutArgs(
+ CreateFunctor(ReceivePointer(mock.web_browser2_),
+ &IWebBrowser::GoForward))));
+ EXPECT_CALL(mock, OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kAnchor2Url)),
+ _, _, _, _, _))
+ .WillOnce(testing::Return(S_OK));
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .WillOnce(testing::Return());
+
+ // We have reached anchor 2, go forward to anchor 3 again
+ // Back/Forward state at this point:
+ // Back: 3 (kAnchorUrl, kAnchor1Url, kAnchor2Url)
+ // Forward: 1 (kAnchor3Url)
+ EXPECT_CALL(mock, OnLoad(testing::StrEq(kAnchor2Url)))
+ .WillOnce(testing::IgnoreResult(testing::InvokeWithoutArgs(
+ CreateFunctor(ReceivePointer(mock.web_browser2_),
+ &IWebBrowser::GoForward))));
+ EXPECT_CALL(mock, OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kAnchor3Url)),
+ _, _, _, _, _))
+ .WillOnce(testing::Return(S_OK));
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .WillOnce(testing::Return());
+
+ // We have gone a few steps back and forward, this should be enough for now.
+ EXPECT_CALL(mock, OnLoad(testing::StrEq(kAnchor3Url)))
+ .WillOnce(testing::DoAll(
+ testing::InvokeWithoutArgs(CreateFunctor(&mock,
+ &chrome_frame_test::WebBrowserEventSink::Uninitialize)),
+ testing::IgnoreResult(testing::InvokeWithoutArgs(
+ &chrome_frame_test::CloseAllIEWindows)),
+ QUIT_LOOP_SOON(loop, 2)));
+
+ HRESULT hr = mock.LaunchIEAndNavigate(kAnchorUrl);
+ ASSERT_HRESULT_SUCCEEDED(hr);
+ if (hr == S_FALSE)
+ return;
+
+ ASSERT_TRUE(mock.web_browser2() != NULL);
+ loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
+ mock.Uninitialize();
+ chrome_frame_test::CloseAllIEWindows();
+}
+
+// Full tab mode view source test
+// Launch and navigate chrome frame and invoke view source functionality
+TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_ViewSource) {
+ chrome_frame_test::TimedMsgLoop loop;
+ CComObjectStackEx<MockWebBrowserEventSink> mock;
+ CComObjectStackEx<MockWebBrowserEventSink> view_source_mock;
+ ::testing::InSequence sequence; // Everything in sequence
+
+ // After navigation invoke view soruce action using IWebBrowser2::ExecWB
+ EXPECT_CALL(mock, OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kAnchorUrl)),
+ _, _, _, _, _))
+ .WillOnce(testing::Return(S_OK));
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .WillOnce(testing::Return());
+ EXPECT_CALL(mock, OnBeforeNavigate2(_, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kAnchorUrl)),
+ _, _, _, _, _))
+ .Times(testing::AnyNumber()).WillRepeatedly(testing::Return(S_OK));
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .Times(testing::AnyNumber()).WillRepeatedly(testing::Return());
+
+ VARIANT empty = ScopedVariant::kEmptyVariant;
+ EXPECT_CALL(mock, OnLoad(testing::StrEq(kAnchorUrl)))
+ .WillOnce(testing::IgnoreResult(testing::InvokeWithoutArgs(
+ CreateFunctor(ReceivePointer(mock.web_browser2_),
+ &IWebBrowser2::ExecWB,
+ static_cast<OLECMDID>(IDM_VIEWSOURCE),
+ OLECMDEXECOPT_DONTPROMPTUSER, &empty, &empty))));
+
+ // Expect notification for view-source window, handle new window event
+ // and attach a new mock to the received web browser
+ std::wstring view_source_url;
+ view_source_url += UTF8ToWide(chrome::kViewSourceScheme);
+ view_source_url += L":";
+ view_source_url += kAnchorUrl;
+ std::wstring url_in_new_window = kChromeProtocolPrefix;
+ url_in_new_window += view_source_url;
+
+ EXPECT_CALL(mock, OnNewWindow3(_, _, _, _,
+ testing::StrCaseEq(url_in_new_window)));
+ EXPECT_CALL(mock, OnNewBrowserWindow(_, _))
+ .WillOnce(testing::WithArgs<0>(
+ testing::Invoke(CreateFunctor(&view_source_mock,
+ &MockWebBrowserEventSink::Attach))));
+
+ // Expect navigations on the new mock
+ EXPECT_CALL(view_source_mock, OnBeforeNavigate2(_,
+ testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(url_in_new_window)), _, _, _, _, _))
+ .Times(testing::AnyNumber()).WillRepeatedly(testing::Return(S_OK));
+ EXPECT_CALL(view_source_mock, OnNavigateComplete2(_, _))
+ .WillOnce(testing::Return());
+ EXPECT_CALL(view_source_mock, OnLoad(testing::StrEq(view_source_url)))
+ .WillOnce(testing::DoAll(
+ testing::InvokeWithoutArgs(CreateFunctor(&mock,
+ &MockWebBrowserEventSink::Uninitialize)),
+ testing::InvokeWithoutArgs(CreateFunctor(&view_source_mock,
+ &MockWebBrowserEventSink::Uninitialize)),
+ testing::IgnoreResult(testing::InvokeWithoutArgs(
+ &chrome_frame_test::CloseAllIEWindows)),
+ QUIT_LOOP_SOON(loop, 2)));
+
+ HRESULT hr = mock.LaunchIEAndNavigate(kAnchorUrl);
+ ASSERT_HRESULT_SUCCEEDED(hr);
+ if (hr == S_FALSE)
+ return;
+
+ ASSERT_TRUE(mock.web_browser2() != NULL);
+ loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
+ mock.Uninitialize();
+ chrome_frame_test::CloseAllIEWindows();
+}
+
+const wchar_t kChromeFrameFullTabModeBeforeUnloadEventTest[] =
+ L"http://localhost:1337/files/fulltab_before_unload_event_test.html";
+
+const wchar_t kChromeFrameFullTabModeBeforeUnloadEventMain[] =
+ L"http://localhost:1337/files/fulltab_before_unload_event_main.html";
+
+TEST_F(ChromeFrameTestWithWebServer,
+ FullTabModeIE_ChromeFrameUnloadEventTest) {
+ chrome_frame_test::TimedMsgLoop loop;
+ CComObjectStackEx<MockWebBrowserEventSink> mock;
+ ::testing::InSequence sequence; // Everything in sequence
+
+ // We will get two BeforeNavigate2/OnNavigateComplete2 notifications due to
+ // switching from IE to CF.
+ EXPECT_CALL(
+ mock,
+ OnBeforeNavigate2(
+ _, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kChromeFrameFullTabModeBeforeUnloadEventTest)),
+ _, _, _, _, _))
+ .WillOnce(testing::Return(S_OK));
+
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .WillOnce(testing::Return());
+
+ EXPECT_CALL(
+ mock,
+ OnBeforeNavigate2(
+ _, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kChromeFrameFullTabModeBeforeUnloadEventTest)),
+ _, _, _, _, _))
+ .Times(testing::AnyNumber()).WillRepeatedly(testing::Return(S_OK));
+
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .Times(testing::AnyNumber()).WillRepeatedly(testing::Return());
+
+ EXPECT_CALL(mock, OnLoad(_)).WillOnce(testing::Return());
+
+ // We will get two BeforeNavigate2/OnNavigateComplete2 notifications due to
+ // switching from IE to CF.
+ EXPECT_CALL(
+ mock,
+ OnBeforeNavigate2(
+ _, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kChromeFrameFullTabModeBeforeUnloadEventMain)),
+ _, _, _, _, _))
+ .WillOnce(testing::Return(S_OK));
+
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .WillOnce(testing::Return());
+
+ EXPECT_CALL(
+ mock,
+ OnBeforeNavigate2(
+ _, testing::Field(&VARIANT::bstrVal,
+ testing::StrCaseEq(kChromeFrameFullTabModeBeforeUnloadEventMain)),
+ _, _, _, _, _))
+ .Times(testing::AnyNumber()).WillRepeatedly(testing::Return(S_OK));
+
+ EXPECT_CALL(mock, OnNavigateComplete2(_, _))
+ .Times(testing::AnyNumber()).WillRepeatedly(testing::Return());
+
+ EXPECT_CALL(mock, OnLoad(_)).WillOnce(testing::Return());
+
+ EXPECT_CALL(mock, OnMessage(_))
+ .WillOnce(testing::DoAll(
+ testing::InvokeWithoutArgs(CreateFunctor(&mock,
+ &chrome_frame_test::WebBrowserEventSink::Uninitialize)),
+ testing::IgnoreResult(testing::InvokeWithoutArgs(
+ &chrome_frame_test::CloseAllIEWindows)),
+ QUIT_LOOP_SOON(loop, 2)));
+
+ HRESULT hr =
+ mock.LaunchIEAndNavigate(kChromeFrameFullTabModeBeforeUnloadEventTest);
+ ASSERT_HRESULT_SUCCEEDED(hr);
+ if (hr == S_FALSE)
+ return;
+
+ ASSERT_TRUE(mock.web_browser2() != NULL);
+ loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
+ mock.Uninitialize();
+ chrome_frame_test::CloseAllIEWindows();
+}
+
diff --git a/chrome_frame/test/test_mock_with_web_server.h b/chrome_frame/test/test_mock_with_web_server.h
new file mode 100644
index 0000000..346e38d
--- /dev/null
+++ b/chrome_frame/test/test_mock_with_web_server.h
@@ -0,0 +1,64 @@
+// Copyright (c) 2006-2010 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.
+#ifndef CHROME_FRAME_TEST_MOCK_WITH_WEB_SERVER_H_
+#define CHROME_FRAME_TEST_MOCK_WITH_WEB_SERVER_H_
+
+#include <windows.h>
+
+#include "gmock/gmock.h"
+#include "chrome_frame/chrome_frame_automation.h"
+#include "chrome_frame/test/chrome_frame_test_utils.h"
+
+#define GMOCK_MUTANT_INCLUDE_LATE_OBJECT_BINDING
+#include "testing/gmock_mutant.h"
+
+// This class provides functionality to add expectations to IE full tab mode
+// tests.
+class MockWebBrowserEventSink : public chrome_frame_test::WebBrowserEventSink {
+ public:
+ // Needed to support PostTask.
+ static bool ImplementsThreadSafeReferenceCounting() {
+ return true;
+ }
+
+ MOCK_METHOD7_WITH_CALLTYPE(__stdcall, OnBeforeNavigate2,
+ HRESULT (IDispatch* dispatch, // NOLINT
+ VARIANT* url,
+ VARIANT* flags,
+ VARIANT* target_frame_name,
+ VARIANT* post_data,
+ VARIANT* headers,
+ VARIANT_BOOL* cancel));
+
+ MOCK_METHOD2_WITH_CALLTYPE(__stdcall, OnNavigateComplete2,
+ void (IDispatch* dispatch, // NOLINT
+ VARIANT* url));
+
+ MOCK_METHOD5_WITH_CALLTYPE(__stdcall, OnNewWindow3,
+ void (IDispatch** dispatch, // NOLINT
+ VARIANT_BOOL* cancel,
+ DWORD flags,
+ BSTR url_context,
+ BSTR url));
+
+ MOCK_METHOD2_WITH_CALLTYPE(__stdcall, OnNewWindow2,
+ void (IDispatch** dispatch, // NOLINT
+ VARIANT_BOOL* cancel));
+
+ MOCK_METHOD5_WITH_CALLTYPE(__stdcall, OnNavigateError,
+ void (IDispatch* dispatch, // NOLINT
+ VARIANT* url,
+ VARIANT* frame_name,
+ VARIANT* status_code,
+ VARIANT* cancel));
+
+ MOCK_METHOD1(OnLoad, void (const wchar_t* url)); // NOLINT
+ MOCK_METHOD1(OnLoadError, void (const wchar_t* url)); // NOLINT
+ MOCK_METHOD1(OnMessage, void (const wchar_t* message)); // NOLINT
+ MOCK_METHOD2(OnNewBrowserWindow, void (IDispatch* dispatch, // NOLINT
+ const wchar_t* url));
+};
+
+#endif // CHROME_FRAME_TEST_MOCK_WITH_WEB_SERVER_H_
+
diff --git a/chrome_frame/test/test_with_web_server.cc b/chrome_frame/test/test_with_web_server.cc
new file mode 100644
index 0000000..d0f0068
--- /dev/null
+++ b/chrome_frame/test/test_with_web_server.cc
@@ -0,0 +1,825 @@
+// Copyright (c) 2006-2010 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 "chrome_frame/test/test_with_web_server.h"
+
+#include "base/file_version_info.h"
+#include "chrome/common/chrome_switches.h"
+#include "chrome/installer/util/install_util.h"
+#include "chrome/installer/util/helper.h"
+#include "chrome_frame/utils.h"
+#include "chrome_frame/test/chrome_frame_test_utils.h"
+
+const wchar_t kDocRoot[] = L"chrome_frame\\test\\data";
+const int kLongWaitTimeout = 60 * 1000;
+const int kShortWaitTimeout = 25 * 1000;
+const int kChromeFrameLaunchDelay = 5;
+const int kChromeFrameLongNavigationTimeoutInSeconds = 10;
+
+class ChromeFrameTestEnvironment: public testing::Environment {
+ public:
+ ~ChromeFrameTestEnvironment() {}
+ void SetUp() {
+ ScopedChromeFrameRegistrar::RegisterDefaults();
+ }
+ void TearDown() {}
+};
+
+::testing::Environment* const chrome_frame_env =
+ ::testing::AddGlobalTestEnvironment(new ChromeFrameTestEnvironment);
+
+void ChromeFrameTestWithWebServer::CloseAllBrowsers() {
+ // Web browsers tend to relaunch themselves in other processes, meaning the
+ // KillProcess stuff above might not have actually cleaned up all our browser
+ // instances, so make really sure browsers are dead.
+ base::KillProcesses(chrome_frame_test::kIEImageName, 0, NULL);
+ base::KillProcesses(chrome_frame_test::kIEBrokerImageName, 0, NULL);
+ base::KillProcesses(chrome_frame_test::kFirefoxImageName, 0, NULL);
+ base::KillProcesses(chrome_frame_test::kSafariImageName, 0, NULL);
+
+ // Endeavour to only kill off Chrome Frame derived Chrome processes.
+ KillAllNamedProcessesWithArgument(chrome_frame_test::kChromeImageName,
+ UTF8ToWide(switches::kChromeFrame));
+}
+
+void ChromeFrameTestWithWebServer::SetUp() {
+ // Make sure our playground is clean before we start.
+ CloseAllBrowsers();
+
+ // Make sure that we are not accidently enabling gcf protocol.
+ SetConfigBool(kEnableGCFProtocol, false);
+
+ server_.SetUp();
+ results_dir_ = server_.GetDataDir();
+ file_util::AppendToPath(&results_dir_, L"dump");
+}
+
+void ChromeFrameTestWithWebServer::TearDown() {
+ CloseBrowser();
+ CloseAllBrowsers();
+ server_.TearDown();
+}
+
+bool ChromeFrameTestWithWebServer::LaunchBrowser(BrowserKind browser,
+ const wchar_t* page) {
+ std::wstring url = page;
+ if (url.find(L"files/") != std::wstring::npos)
+ url = UTF8ToWide(server_.Resolve(page).spec());
+
+ browser_ = browser;
+ if (browser == IE) {
+ browser_handle_.Set(chrome_frame_test::LaunchIE(url));
+ } else if (browser == FIREFOX) {
+ browser_handle_.Set(chrome_frame_test::LaunchFirefox(url));
+ } else if (browser == OPERA) {
+ browser_handle_.Set(chrome_frame_test::LaunchOpera(url));
+ } else if (browser == SAFARI) {
+ browser_handle_.Set(chrome_frame_test::LaunchSafari(url));
+ } else if (browser == CHROME) {
+ browser_handle_.Set(chrome_frame_test::LaunchChrome(url));
+ } else {
+ NOTREACHED();
+ }
+
+ return browser_handle_.IsValid();
+}
+
+void ChromeFrameTestWithWebServer::CloseBrowser() {
+ if (!browser_handle_.IsValid())
+ return;
+
+ int attempts = 0;
+ if (browser_ == IE) {
+ attempts = chrome_frame_test::CloseAllIEWindows();
+ } else {
+ attempts = chrome_frame_test::CloseVisibleWindowsOnAllThreads(
+ browser_handle_);
+ }
+
+ if (attempts > 0) {
+ DWORD wait = ::WaitForSingleObject(browser_handle_, 20000);
+ if (wait == WAIT_OBJECT_0) {
+ browser_handle_.Close();
+ } else {
+ DLOG(ERROR) << "WaitForSingleObject returned " << wait;
+ }
+ } else {
+ DLOG(ERROR) << "No attempts to close browser windows";
+ }
+
+ if (browser_handle_.IsValid()) {
+ DWORD exit_code = 0;
+ if (!::GetExitCodeProcess(browser_handle_, &exit_code) ||
+ exit_code == STILL_ACTIVE) {
+ LOG(ERROR) << L"Forcefully killing browser process. Exit:" << exit_code;
+ base::KillProcess(browser_handle_, 0, true);
+ }
+ browser_handle_.Close();
+ }
+}
+
+bool ChromeFrameTestWithWebServer::BringBrowserToTop() {
+ return chrome_frame_test::EnsureProcessInForeground(
+ GetProcessId(browser_handle_));
+}
+
+bool ChromeFrameTestWithWebServer::WaitForTestToComplete(int milliseconds) {
+ return server_.WaitToFinish(milliseconds);
+}
+
+bool ChromeFrameTestWithWebServer::WaitForOnLoad(int milliseconds) {
+ DWORD start = ::GetTickCount();
+ std::string data;
+ while (!ReadResultFile(L"OnLoadEvent", &data) || data.length() == 0) {
+ DWORD now = ::GetTickCount();
+ if (start > now) {
+ // Very simple check for overflow. In that case we just restart the
+ // wait.
+ start = now;
+ } else if (static_cast<int>(now - start) > milliseconds) {
+ break;
+ }
+ Sleep(100);
+ }
+
+ return data.compare("loaded") == 0;
+}
+
+bool ChromeFrameTestWithWebServer::ReadResultFile(const std::wstring& file_name,
+ std::string* data) {
+ std::wstring full_path = results_dir_;
+ file_util::AppendToPath(&full_path, file_name);
+ return file_util::ReadFileToString(full_path, data);
+}
+
+bool ChromeFrameTestWithWebServer::CheckResultFile(
+ const std::wstring& file_name, const std::string& expected_result) {
+ std::string data;
+ bool ret = ReadResultFile(file_name, &data);
+ if (ret)
+ ret = (data == expected_result);
+
+ if (!ret) {
+ LOG(ERROR) << "Error text: " << (data.empty() ? "<empty>" : data.c_str());
+ }
+
+ return ret;
+}
+
+void ChromeFrameTestWithWebServer::SimpleBrowserTest(BrowserKind browser,
+ const wchar_t* page, const wchar_t* result_file_to_check) {
+ ASSERT_TRUE(LaunchBrowser(browser, page));
+ ASSERT_TRUE(WaitForTestToComplete(kLongWaitTimeout));
+ ASSERT_TRUE(CheckResultFile(result_file_to_check, "OK"));
+}
+
+void ChromeFrameTestWithWebServer::OptionalBrowserTest(BrowserKind browser,
+ const wchar_t* page, const wchar_t* result_file_to_check) {
+ if (!LaunchBrowser(browser, page)) {
+ LOG(ERROR) << "Failed to launch browser " << ToString(browser);
+ } else {
+ ASSERT_TRUE(WaitForTestToComplete(kLongWaitTimeout));
+ ASSERT_TRUE(CheckResultFile(result_file_to_check, "OK"));
+ }
+}
+
+void ChromeFrameTestWithWebServer::VersionTest(BrowserKind browser,
+ const wchar_t* page, const wchar_t* result_file_to_check) {
+ std::wstring plugin_path;
+ PathService::Get(base::DIR_MODULE, &plugin_path);
+ file_util::AppendToPath(&plugin_path, L"servers");
+ file_util::AppendToPath(&plugin_path, kChromeFrameDllName);
+
+ static FileVersionInfo* version_info =
+ FileVersionInfo::CreateFileVersionInfo(plugin_path);
+
+ std::wstring version;
+ if (version_info)
+ version = version_info->product_version();
+
+ // If we can't find the Chrome Frame DLL in the src tree, we turn to
+ // the directory where chrome is installed.
+ if (!version_info) {
+ installer::Version* ver_system = InstallUtil::GetChromeVersion(true);
+ installer::Version* ver_user = InstallUtil::GetChromeVersion(false);
+ ASSERT_TRUE(ver_system || ver_user);
+
+ bool system_install = ver_system ? true : false;
+ std::wstring cf_dll_path(installer::GetChromeInstallPath(system_install));
+ file_util::AppendToPath(&cf_dll_path,
+ ver_system ? ver_system->GetString() : ver_user->GetString());
+ file_util::AppendToPath(&cf_dll_path, kChromeFrameDllName);
+ version_info = FileVersionInfo::CreateFileVersionInfo(cf_dll_path);
+ if (version_info)
+ version = version_info->product_version();
+ }
+
+ EXPECT_TRUE(version_info);
+ EXPECT_FALSE(version.empty());
+ EXPECT_TRUE(LaunchBrowser(browser, page));
+ ASSERT_TRUE(WaitForTestToComplete(kLongWaitTimeout));
+ ASSERT_TRUE(CheckResultFile(result_file_to_check, WideToUTF8(version)));
+}
+
+const wchar_t kPostMessageBasicPage[] = L"files/postmessage_basic_host.html";
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_PostMessageBasic) {
+ SimpleBrowserTest(IE, kPostMessageBasicPage, L"PostMessage");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_PostMessageBasic) {
+ SimpleBrowserTest(FIREFOX, kPostMessageBasicPage, L"PostMessage");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_PostMessageBasic) {
+ OptionalBrowserTest(OPERA, kPostMessageBasicPage, L"PostMessage");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, FullTabIE_MIMEFilterBasic) {
+ const wchar_t kMIMEFilterBasicPage[] =
+ L"files/chrome_frame_mime_filter_test.html";
+
+ // If this test fails for IE8 then it is possible that prebinding is enabled.
+ // A known workaround is to disable it until CF properly handles it.
+ //
+ // HKCU\Software\Microsoft\Internet Explorer\Main
+ // Value name: EnablePreBinding (REG_DWORD)
+ // Value: 0
+ SimpleBrowserTest(IE, kMIMEFilterBasicPage, L"MIMEFilter");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_Resize) {
+ SimpleBrowserTest(IE, L"files/chrome_frame_resize.html", L"Resize");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_Resize) {
+ SimpleBrowserTest(FIREFOX, L"files/chrome_frame_resize.html", L"Resize");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_Resize) {
+ OptionalBrowserTest(OPERA, L"files/chrome_frame_resize.html", L"Resize");
+}
+
+const wchar_t kNavigateURLAbsolutePage[] =
+ L"files/navigateurl_absolute_host.html";
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_NavigateURLAbsolute) {
+ SimpleBrowserTest(IE, kNavigateURLAbsolutePage, L"NavigateURL");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_NavigateURLAbsolute) {
+ SimpleBrowserTest(FIREFOX, kNavigateURLAbsolutePage, L"NavigateURL");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_NavigateURLAbsolute) {
+ OptionalBrowserTest(OPERA, kNavigateURLAbsolutePage, L"NavigateURL");
+}
+
+const wchar_t kNavigateURLRelativePage[] =
+ L"files/navigateurl_relative_host.html";
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_NavigateURLRelative) {
+ SimpleBrowserTest(IE, kNavigateURLRelativePage, L"NavigateURL");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_NavigateURLRelative) {
+ SimpleBrowserTest(FIREFOX, kNavigateURLRelativePage, L"NavigateURL");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_NavigateURLRelative) {
+ OptionalBrowserTest(OPERA, kNavigateURLRelativePage, L"NavigateURL");
+}
+
+const wchar_t kNavigateSimpleObjectFocus[] = L"files/simple_object_focus.html";
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_ObjectFocus) {
+ SimpleBrowserTest(FIREFOX, kNavigateSimpleObjectFocus, L"ObjectFocus");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_ObjectFocus) {
+ SimpleBrowserTest(IE, kNavigateSimpleObjectFocus, L"ObjectFocus");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_ObjectFocus) {
+ if (!LaunchBrowser(OPERA, kNavigateSimpleObjectFocus)) {
+ LOG(ERROR) << "Failed to launch browser " << ToString(OPERA);
+ } else {
+ ASSERT_TRUE(WaitForOnLoad(kLongWaitTimeout));
+ BringBrowserToTop();
+ // Tab through a couple of times. Once should be enough in theory
+ // but in practice activating the browser can take a few milliseconds more.
+ bool ok;
+ for (int i = 0;
+ i < 5 && (ok = CheckResultFile(L"ObjectFocus", "OK")) == false;
+ ++i) {
+ Sleep(300);
+ chrome_frame_test::SendMnemonic(VK_TAB, false, false, false);
+ }
+ ASSERT_TRUE(ok);
+ }
+}
+
+const wchar_t kiframeBasicPage[] = L"files/iframe_basic_host.html";
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_iframeBasic) {
+ SimpleBrowserTest(IE, kiframeBasicPage, L"PostMessage");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_iframeBasic) {
+ SimpleBrowserTest(FIREFOX, kiframeBasicPage, L"PostMessage");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_iframeBasic) {
+ OptionalBrowserTest(OPERA, kiframeBasicPage, L"PostMessage");
+}
+
+const wchar_t kSrcPropertyTestPage[] = L"files/src_property_host.html";
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_SrcProperty) {
+ SimpleBrowserTest(IE, kSrcPropertyTestPage, L"SrcProperty");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_SrcProperty) {
+ SimpleBrowserTest(FIREFOX, kSrcPropertyTestPage, L"SrcProperty");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_SrcProperty) {
+ OptionalBrowserTest(OPERA, kSrcPropertyTestPage, L"SrcProperty");
+}
+
+const wchar_t kCFInstanceBasicTestPage[] = L"files/CFInstance_basic_host.html";
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_CFInstanceBasic) {
+ SimpleBrowserTest(IE, kCFInstanceBasicTestPage, L"CFInstanceBasic");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_CFInstanceBasic) {
+ SimpleBrowserTest(FIREFOX, kCFInstanceBasicTestPage, L"CFInstanceBasic");
+}
+
+const wchar_t kCFISingletonPage[] = L"files/CFInstance_singleton_host.html";
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_CFInstanceSingleton) {
+ SimpleBrowserTest(IE, kCFISingletonPage, L"CFInstanceSingleton");
+}
+
+// This test randomly fails on the ChromeFrame builder.
+// Bug http://code.google.com/p/chromium/issues/detail?id=31532
+TEST_F(ChromeFrameTestWithWebServer, FLAKY_WidgetModeFF_CFInstanceSingleton) {
+ SimpleBrowserTest(FIREFOX, kCFISingletonPage, L"CFInstanceSingleton");
+}
+
+const wchar_t kCFIDelayPage[] = L"files/CFInstance_delay_host.html";
+
+TEST_F(ChromeFrameTestWithWebServer, DISABLED_WidgetModeIE_CFInstanceDelay) {
+ SimpleBrowserTest(IE, kCFIDelayPage, L"CFInstanceDelay");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, DISABLED_WidgetModeFF_CFInstanceDelay) {
+ SimpleBrowserTest(FIREFOX, kCFIDelayPage, L"CFInstanceDelay");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, DISABLED_WidgetModeOpera_CFInstanceDelay) {
+ OptionalBrowserTest(OPERA, kCFIDelayPage, L"CFInstanceDelay");
+}
+
+const wchar_t kCFIFallbackPage[] = L"files/CFInstance_fallback_host.html";
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_CFInstanceFallback) {
+ SimpleBrowserTest(IE, kCFIFallbackPage, L"CFInstanceFallback");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_CFInstanceFallback) {
+ SimpleBrowserTest(FIREFOX, kCFIFallbackPage, L"CFInstanceFallback");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_CFInstanceFallback) {
+ OptionalBrowserTest(OPERA, kCFIFallbackPage, L"CFInstanceFallback");
+}
+
+const wchar_t kCFINoSrcPage[] = L"files/CFInstance_no_src_host.html";
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_CFInstanceNoSrc) {
+ SimpleBrowserTest(IE, kCFINoSrcPage, L"CFInstanceNoSrc");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_CFInstanceNoSrc) {
+ SimpleBrowserTest(FIREFOX, kCFINoSrcPage, L"CFInstanceNoSrc");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_CFInstanceNoSrc) {
+ OptionalBrowserTest(OPERA, kCFINoSrcPage, L"CFInstanceNoSrc");
+}
+
+const wchar_t kCFIIfrOnLoadPage[] = L"files/CFInstance_iframe_onload_host.html";
+
+// disabled since it's unlikely that we care about this case
+TEST_F(ChromeFrameTestWithWebServer,
+ DISABLED_WidgetModeIE_CFInstanceIfrOnLoad) {
+ SimpleBrowserTest(IE, kCFIIfrOnLoadPage, L"CFInstanceIfrOnLoad");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_CFInstanceIfrOnLoad) {
+ SimpleBrowserTest(FIREFOX, kCFIIfrOnLoadPage, L"CFInstanceIfrOnLoad");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_CFInstanceIfrOnLoad) {
+ OptionalBrowserTest(OPERA, kCFIIfrOnLoadPage, L"CFInstanceIfrOnLoad");
+}
+
+const wchar_t kCFIZeroSizePage[] = L"files/CFInstance_zero_size_host.html";
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_CFInstanceZeroSize) {
+ SimpleBrowserTest(IE, kCFIZeroSizePage, L"CFInstanceZeroSize");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_CFInstanceZeroSize) {
+ SimpleBrowserTest(FIREFOX, kCFIZeroSizePage, L"CFInstanceZeroSize");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_CFInstanceZeroSize) {
+ OptionalBrowserTest(OPERA, kCFIZeroSizePage, L"CFInstanceZeroSize");
+}
+
+const wchar_t kCFIIfrPostPage[] = L"files/CFInstance_iframe_post_host.html";
+
+// http://crbug.com/32321
+TEST_F(ChromeFrameTestWithWebServer, FLAKY_WidgetModeIE_CFInstanceIfrPost) {
+ SimpleBrowserTest(IE, kCFIIfrPostPage, L"CFInstanceIfrPost");
+}
+
+// Flakes out on the bots, http://crbug.com/26372
+TEST_F(ChromeFrameTestWithWebServer,
+ FLAKY_WidgetModeFF_CFInstanceIfrPost) {
+ SimpleBrowserTest(FIREFOX, kCFIIfrPostPage, L"CFInstanceIfrPost");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeChrome_CFInstanceIfrPost) {
+ OptionalBrowserTest(CHROME, kCFIIfrPostPage, L"CFInstanceIfrPost");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeSafari_CFInstanceIfrPost) {
+ OptionalBrowserTest(SAFARI, kCFIIfrPostPage, L"CFInstanceIfrPost");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_CFInstanceIfrPost) {
+ OptionalBrowserTest(OPERA, kCFIIfrPostPage, L"CFInstanceIfrPost");
+}
+
+const wchar_t kCFIPostPage[] = L"files/CFInstance_post_host.html";
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_CFInstancePost) {
+ SimpleBrowserTest(IE, kCFIPostPage, L"CFInstancePost");
+}
+
+// This test randomly fails on the ChromeFrame builder.
+// Bug http://code.google.com/p/chromium/issues/detail?id=31532
+TEST_F(ChromeFrameTestWithWebServer, FLAKY_WidgetModeFF_CFInstancePost) {
+ SimpleBrowserTest(FIREFOX, kCFIPostPage, L"CFInstancePost");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeChrome_CFInstancePost) {
+ OptionalBrowserTest(CHROME, kCFIPostPage, L"CFInstancePost");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeSafari_CFInstancePost) {
+ OptionalBrowserTest(SAFARI, kCFIPostPage, L"CFInstancePost");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, DISABLED_WidgetModeOpera_CFInstancePost) {
+ OptionalBrowserTest(OPERA, kCFIPostPage, L"CFInstancePost");
+}
+
+const wchar_t kCFIRPCPage[] = L"files/CFInstance_rpc_host.html";
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_CFInstanceRPC) {
+ SimpleBrowserTest(IE, kCFIRPCPage, L"CFInstanceRPC");
+}
+
+// This test randomly fails on the ChromeFrame builder.
+// Bug http://code.google.com/p/chromium/issues/detail?id=31532
+TEST_F(ChromeFrameTestWithWebServer, FLAKY_WidgetModeFF_CFInstanceRPC) {
+ SimpleBrowserTest(FIREFOX, kCFIRPCPage, L"CFInstanceRPC");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeChrome_CFInstanceRPC) {
+ OptionalBrowserTest(CHROME, kCFIRPCPage, L"CFInstanceRPC");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeSafari_CFInstanceRPC) {
+ OptionalBrowserTest(SAFARI, kCFIRPCPage, L"CFInstanceRPC");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, DISABLED_WidgetModeOpera_CFInstanceRPC) {
+ OptionalBrowserTest(OPERA, kCFIRPCPage, L"CFInstanceRPC");
+}
+
+const wchar_t kCFIRPCInternalPage[] =
+ L"files/CFInstance_rpc_internal_host.html";
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_CFInstanceRPCInternal) {
+ SimpleBrowserTest(IE, kCFIRPCInternalPage, L"CFInstanceRPCInternal");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_CFInstanceRPCInternal) {
+ SimpleBrowserTest(FIREFOX, kCFIRPCInternalPage, L"CFInstanceRPCInternal");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeChrome_CFInstanceRPCInternal) {
+ OptionalBrowserTest(CHROME, kCFIRPCInternalPage, L"CFInstanceRPCInternal");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeSafari_CFInstanceRPCInternal) {
+ OptionalBrowserTest(SAFARI, kCFIRPCInternalPage, L"CFInstanceRPCInternal");
+}
+
+const wchar_t kCFIDefaultCtorPage[] =
+ L"files/CFInstance_default_ctor_host.html";
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_CFInstanceDefaultCtor) {
+ SimpleBrowserTest(IE, kCFIDefaultCtorPage, L"CFInstanceDefaultCtor");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_CFInstanceDefaultCtor) {
+ SimpleBrowserTest(FIREFOX, kCFIDefaultCtorPage, L"CFInstanceDefaultCtor");
+}
+
+const wchar_t kCFInstallBasicTestPage[] = L"files/CFInstall_basic.html";
+
+TEST_F(ChromeFrameTestWithWebServer, FullTabIE_CFInstallBasic) {
+ SimpleBrowserTest(IE, kCFInstallBasicTestPage, L"CFInstallBasic");
+}
+
+const wchar_t kCFInstallPlaceTestPage[] = L"files/CFInstall_place.html";
+
+TEST_F(ChromeFrameTestWithWebServer, FullTabIE_CFInstallPlace) {
+ SimpleBrowserTest(IE, kCFInstallPlaceTestPage, L"CFInstallPlace");
+}
+
+const wchar_t kCFInstallOverlayTestPage[] = L"files/CFInstall_overlay.html";
+
+TEST_F(ChromeFrameTestWithWebServer, FullTabIE_CFInstallOverlay) {
+ SimpleBrowserTest(IE, kCFInstallOverlayTestPage, L"CFInstallOverlay");
+}
+
+const wchar_t kCFInstallDismissTestPage[] = L"files/CFInstall_dismiss.html";
+
+TEST_F(ChromeFrameTestWithWebServer, FullTabIE_CFInstallDismiss) {
+ SimpleBrowserTest(IE, kCFInstallDismissTestPage, L"CFInstallDismiss");
+}
+
+const wchar_t kInitializeHiddenPage[] = L"files/initialize_hidden.html";
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_InitializeHidden) {
+ SimpleBrowserTest(IE, kInitializeHiddenPage, L"InitializeHidden");
+}
+
+const wchar_t kFullTabHttpHeaderPage[] = L"files/chrome_frame_http_header.html";
+
+TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_CFHttpHeaderBasic) {
+ SimpleBrowserTest(IE, kFullTabHttpHeaderPage, L"FullTabHttpHeader");
+}
+
+const wchar_t kFullTabHttpHeaderPageIFrame[] =
+ L"files/chrome_frame_http_header_host.html";
+
+TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_CFHttpHeaderIFrame) {
+ SimpleBrowserTest(IE, kFullTabHttpHeaderPageIFrame,
+ L"FullTabHttpHeaderIFrame");
+}
+
+const wchar_t kFullTabHttpHeaderPageFrameset[] =
+ L"files/chrome_frame_http_header_frameset.html";
+
+TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_CFHttpHeaderFrameSet) {
+ SimpleBrowserTest(IE, kFullTabHttpHeaderPageFrameset,
+ L"FullTabHttpHeaderFrameset");
+}
+
+// Flaky on the build bots. See http://crbug.com/30622
+TEST_F(ChromeFrameTestWithWebServer, FLAKY_WidgetModeFF_InitializeHidden) {
+ SimpleBrowserTest(FIREFOX, kInitializeHiddenPage, L"InitializeHidden");
+}
+
+// Disabled due to a problem with Opera.
+// http://b/issue?id=1708275
+TEST_F(ChromeFrameTestWithWebServer,
+ DISABLED_WidgetModeOpera_InitializeHidden) {
+ OptionalBrowserTest(OPERA, kInitializeHiddenPage, L"InitializeHidden");
+}
+
+const wchar_t kInHeadPage[] = L"files/in_head.html";
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_InHead) {
+ SimpleBrowserTest(FIREFOX, kInHeadPage, L"InHead");
+}
+
+const wchar_t kVersionPage[] = L"files/version.html";
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_Version) {
+ VersionTest(IE, kVersionPage, L"version");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_Version) {
+ VersionTest(FIREFOX, kVersionPage, L"version");
+}
+
+const wchar_t kEventListenerPage[] = L"files/event_listener.html";
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_EventListener) {
+ SimpleBrowserTest(IE, kEventListenerPage, L"EventListener");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_EventListener) {
+ SimpleBrowserTest(FIREFOX, kEventListenerPage, L"EventListener");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_EventListener) {
+ OptionalBrowserTest(OPERA, kEventListenerPage, L"EventListener");
+}
+
+const wchar_t kPrivilegedApisPage[] = L"files/privileged_apis_host.html";
+
+// http://crbug.com/32321
+TEST_F(ChromeFrameTestWithWebServer, FLAKY_WidgetModeIE_PrivilegedApis) {
+ SimpleBrowserTest(IE, kPrivilegedApisPage, L"PrivilegedApis");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeFF_PrivilegedApis) {
+ SimpleBrowserTest(FIREFOX, kPrivilegedApisPage, L"PrivilegedApis");
+}
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeOpera_PrivilegedApis) {
+ OptionalBrowserTest(OPERA, kPrivilegedApisPage, L"PrivilegedApis");
+}
+
+const wchar_t kMetaTagPage[] = L"files/meta_tag.html";
+TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_MetaTag) {
+ SimpleBrowserTest(IE, kMetaTagPage, L"meta_tag");
+}
+
+const wchar_t kCFProtocolPage[] = L"files/cf_protocol.html";
+TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_CFProtocol) {
+ // Temporarily enable gcf: protocol for this test.
+ SetConfigBool(kEnableGCFProtocol, true);
+ SimpleBrowserTest(IE, kCFProtocolPage, L"chrome_frame_protocol");
+ SetConfigBool(kEnableGCFProtocol, false);
+}
+
+const wchar_t kPersistentCookieTest[] =
+ L"files/persistent_cookie_test_page.html";
+TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_PersistentCookieTest) {
+ // Temporarily enable gcf: protocol for this test.
+ SetConfigBool(kEnableGCFProtocol, true);
+ SimpleBrowserTest(IE, kPersistentCookieTest, L"PersistentCookieTest");
+ SetConfigBool(kEnableGCFProtocol, false);
+}
+
+const wchar_t kNavigateOutPage[] = L"files/navigate_out.html";
+TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_NavigateOut) {
+ SimpleBrowserTest(IE, kNavigateOutPage, L"navigate_out");
+}
+
+const wchar_t kReferrerMainTest[] = L"files/referrer_main.html";
+TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_ReferrerTest) {
+ SimpleBrowserTest(IE, kReferrerMainTest, L"FullTab_ReferrerTest");
+}
+
+const wchar_t kSubFrameTestPage[] = L"files/full_tab_sub_frame_main.html";
+TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_SubFrame) {
+ SimpleBrowserTest(IE, kSubFrameTestPage, L"sub_frame");
+}
+
+const wchar_t kSubIFrameTestPage[] = L"files/full_tab_sub_iframe_main.html";
+TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_SubIFrame) {
+ SimpleBrowserTest(IE, kSubIFrameTestPage, L"sub_frame");
+}
+
+const wchar_t kChromeFrameFullTabModeKeyEventUrl[] = L"files/keyevent.html";
+
+// Marking this test FLAKY as it fails at times on the buildbot.
+// http://code.google.com/p/chromium/issues/detail?id=26549
+TEST_F(ChromeFrameTestWithWebServer,
+ FLAKY_FullTabModeIE_ChromeFrameKeyboardTest) {
+ chrome_frame_test::TimedMsgLoop loop;
+
+ ASSERT_TRUE(LaunchBrowser(IE, kChromeFrameFullTabModeKeyEventUrl));
+
+ // Allow some time for chrome to be launched.
+ loop.RunFor(kChromeFrameLaunchDelay);
+
+ HWND renderer_window = chrome_frame_test::GetChromeRendererWindow();
+ EXPECT_TRUE(IsWindow(renderer_window));
+
+ chrome_frame_test::SetKeyboardFocusToWindow(renderer_window, 1, 1);
+ chrome_frame_test::SendInputToWindow(renderer_window, "Chrome");
+
+ loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
+
+ chrome_frame_test::CloseAllIEWindows();
+ ASSERT_TRUE(CheckResultFile(L"FullTab_KeyboardTest", "OK"));
+}
+
+const wchar_t kChromeFrameAboutBlankUrl[] = L"gcf:about:blank";
+
+TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_ChromeFrameFocusTest) {
+ chrome_frame_test::TimedMsgLoop loop;
+
+ ASSERT_TRUE(LaunchBrowser(IE, kChromeFrameAboutBlankUrl));
+
+ // Allow some time for chrome to be launched.
+ loop.RunFor(kChromeFrameLaunchDelay);
+
+ HWND renderer_window = chrome_frame_test::GetChromeRendererWindow();
+ EXPECT_TRUE(IsWindow(renderer_window));
+
+ DWORD renderer_thread_id = 0;
+ DWORD renderer_process_id = 0;
+ renderer_thread_id = GetWindowThreadProcessId(renderer_window,
+ &renderer_process_id);
+
+ AttachThreadInput(GetCurrentThreadId(), renderer_thread_id, TRUE);
+ HWND focus_window = GetFocus();
+ EXPECT_TRUE(focus_window == renderer_window);
+ AttachThreadInput(GetCurrentThreadId(), renderer_thread_id, FALSE);
+
+ chrome_frame_test::CloseAllIEWindows();
+}
+
+const wchar_t kChromeFrameFullTabModeXMLHttpRequestTestUrl[] =
+ L"files/xmlhttprequest_test.html";
+
+TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_ChromeFrameXHRTest) {
+ chrome_frame_test::TimedMsgLoop loop;
+
+ ASSERT_TRUE(LaunchBrowser(IE, kChromeFrameFullTabModeXMLHttpRequestTestUrl));
+
+ loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
+
+ chrome_frame_test::CloseAllIEWindows();
+ ASSERT_TRUE(CheckResultFile(L"FullTab_XMLHttpRequestTest", "OK"));
+}
+
+const wchar_t kMultipleCFInstancesTestUrl[] =
+ L"files/multiple_cf_instances_main.html";
+
+TEST_F(ChromeFrameTestWithWebServer, WidgetModeIE_MultipleCFInstances) {
+ SimpleBrowserTest(IE, kMultipleCFInstancesTestUrl,
+ L"WidgetMode_MultipleInstancesTest");
+}
+
+// TODO(ananta)
+// Disabled until I figure out why this does not work on Firefox.
+TEST_F(ChromeFrameTestWithWebServer,
+ DISABLED_WidgetModeFF_MultipleCFInstances) {
+ SimpleBrowserTest(FIREFOX, kMultipleCFInstancesTestUrl,
+ L"WidgetMode_MultipleInstancesTest");
+}
+
+const wchar_t kChromeFrameFullTabModeXMLHttpRequestAuthHeaderTestUrl[] =
+ L"files/xmlhttprequest_authorization_header_test.html";
+
+TEST_F(ChromeFrameTestWithWebServer,
+ FullTabModeIE_ChromeFrameXHRAuthHeaderTest) {
+ chrome_frame_test::TimedMsgLoop loop;
+
+ ASSERT_TRUE(LaunchBrowser(
+ IE, kChromeFrameFullTabModeXMLHttpRequestAuthHeaderTestUrl));
+
+ loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
+
+ chrome_frame_test::CloseAllIEWindows();
+ ASSERT_TRUE(
+ CheckResultFile(L"FullTab_XMLHttpRequestAuthorizationHeaderTest", "OK"));
+}
+
+const wchar_t kChromeFrameFullTabModeDeleteCookieTest[] =
+ L"files/fulltab_delete_cookie_test.html";
+
+TEST_F(ChromeFrameTestWithWebServer,
+ FullTabModeIE_ChromeFrameDeleteCookieTest) {
+ chrome_frame_test::TimedMsgLoop loop;
+
+ ASSERT_TRUE(LaunchBrowser(IE, kChromeFrameFullTabModeDeleteCookieTest));
+
+ loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
+
+ chrome_frame_test::CloseAllIEWindows();
+ ASSERT_TRUE(CheckResultFile(L"FullTab_DeleteCookieTest", "OK"));
+}
+
+const wchar_t kChromeFrameFullTabModeAnchorUrlNavigate[] =
+ L"files/fulltab_anchor_url_navigate.html#chrome_frame";
+
+TEST_F(ChromeFrameTestWithWebServer,
+ FullTabModeIE_ChromeFrameAnchorUrlNavigateTest) {
+ chrome_frame_test::TimedMsgLoop loop;
+
+ ASSERT_TRUE(LaunchBrowser(IE, kChromeFrameFullTabModeAnchorUrlNavigate));
+
+ loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds);
+
+ chrome_frame_test::CloseAllIEWindows();
+ ASSERT_TRUE(CheckResultFile(L"FullTab_AnchorURLNavigateTest", "OK"));
+}
+
diff --git a/chrome_frame/test/chrome_frame_unittests.h b/chrome_frame/test/test_with_web_server.h
index f5bd3cb..baf3471 100644
--- a/chrome_frame/test/chrome_frame_unittests.h
+++ b/chrome_frame/test/test_with_web_server.h
@@ -1,27 +1,13 @@
-// Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
+// Copyright (c) 2006-2010 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.
-#ifndef CHROME_FRAME_TEST_CHROME_FRAME_UNITTESTS_H_
-#define CHROME_FRAME_TEST_CHROME_FRAME_UNITTESTS_H_
+#ifndef CHROME_FRAME_TEST_WITH_WEB_SERVER_H_
+#define CHROME_FRAME_TEST_WITH_WEB_SERVER_H_
-#include <atlbase.h>
-#include <atlcom.h>
+#include <windows.h>
#include <string>
-#include <exdisp.h>
-#include <exdispid.h>
-#include <mshtml.h>
-#include <shlguid.h>
-#include <shobjidl.h>
-
-#include "base/compiler_specific.h"
-#include "base/ref_counted.h"
-#include "base/scoped_comptr_win.h"
-#include "base/scoped_variant_win.h"
-#include "base/scoped_handle_win.h"
-#include "googleurl/src/gurl.h"
+
#include "chrome_frame/test/http_server.h"
-#include "chrome_frame/test_utils.h"
-#include "chrome_frame/utils.h"
#include "testing/gtest/include/gtest/gtest.h"
// Include without path to make GYP build see it.
@@ -104,5 +90,5 @@ class ChromeFrameTestWithWebServer: public testing::Test {
ChromeFrameHTTPServer server_;
};
-#endif // CHROME_FRAME_TEST_CHROME_FRAME_UNITTESTS_H_
+#endif // CHROME_FRAME_TEST_WITH_WEB_SERVER_H_