diff options
author | tommi@chromium.org <tommi@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2010-03-29 23:59:42 +0000 |
---|---|---|
committer | tommi@chromium.org <tommi@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2010-03-29 23:59:42 +0000 |
commit | 49cffd6276c6decb35dbf2db1b07f581d7c9d5e8 (patch) | |
tree | ce7fabac8485f4e69fa8fdce23a97cf6e58468e1 /chrome_frame | |
parent | 2af51006181a9e32aca6511b0a1b73f813098a0f (diff) | |
download | chromium_src-49cffd6276c6decb35dbf2db1b07f581d7c9d5e8.zip chromium_src-49cffd6276c6decb35dbf2db1b07f581d7c9d5e8.tar.gz chromium_src-49cffd6276c6decb35dbf2db1b07f581d7c9d5e8.tar.bz2 |
Unit test for form download (POST). This replicates the issue reported in bug 36694. Test will be disabled until we fix the issue.
TEST=none. (test is disabled for now)
BUG=36694
Review URL: http://codereview.chromium.org/1541003
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@43019 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'chrome_frame')
-rw-r--r-- | chrome_frame/test/test_mock_with_web_server.cc | 146 | ||||
-rw-r--r-- | chrome_frame/test/test_server.h | 2 | ||||
-rw-r--r-- | chrome_frame/test/test_with_web_server.cc | 36 | ||||
-rw-r--r-- | chrome_frame/test/test_with_web_server.h | 7 | ||||
-rw-r--r-- | chrome_frame/urlmon_url_request.cc | 2 |
5 files changed, 167 insertions, 26 deletions
diff --git a/chrome_frame/test/test_mock_with_web_server.cc b/chrome_frame/test/test_mock_with_web_server.cc index cedaf87..bb25afe 100644 --- a/chrome_frame/test/test_mock_with_web_server.cc +++ b/chrome_frame/test/test_mock_with_web_server.cc @@ -1306,3 +1306,149 @@ TEST(IEPrivacy, NavigationToRestrictedSite) { ASSERT_HRESULT_SUCCEEDED(security_manager->SetZoneMapping(URLZONE_UNTRUSTED, L"http://localhost:1337", SZM_DELETE)); } + +// See bug 36694 for details. http://crbug.com/36694 +TEST_F(ChromeFrameTestWithWebServer, + DISABLED_FullTabModeIE_TestDownloadFromForm) { + if (!MonikerPatchEnabled()) + return; + + CloseIeAtEndOfScope last_resort_close_ie; + + // The content of our HTML test page. This will be returned whenever + // we reply to a GET request. + static const char kHtml[] = + "<html><head>\n" + "<title>ChromeFrame Form Download Test</title>\n" + // To see how this test runs with only IE (no CF in the picture), comment + // out this meta tag. The outcome of the test should be identical. + "<meta http-equiv=\"X-UA-Compatible\" content=\"chrome=1\" />\n" + "</head>\n" + "<script language=\"javascript\">\n" + "function SubmitForm() {\n" + " var form = document.forms['myform'];\n" + " form.action = document.location;\n" + " form.submit();\n" + " return true;\n" + "}\n" + "</script>\n" + "<body onload=\"SubmitForm();\">\n" + "<form method=\"post\" action=\"foo.html\" id=\"myform\">\n" + " <input type=\"hidden\" name=\"Field1\" value=\"myvalue\" />\n" + " <input type=\"button\" name=\"btn\" value=\"Test Download\" " + "onclick=\"return SubmitForm();\" id=\"Button1\"/>\n" + "</form></body></html>\n"; + + // The content of our HTML test page. This will be returned whenever + // we reply to a POST request. + static const char kText[] = + "This is a text file (in case you were wondering)."; + + // This http response class will return an HTML document that contains + // a form whenever it receives a GET request. Whenever it gets a POST + // request, it will respond with a text file that needs to be downloaded + // (content-disposition is "attachment"). + class CustomResponse : public test_server::ResponseForPath { + public: + CustomResponse(const char* path) + : test_server::ResponseForPath(path), is_post_(false), + post_requests_(0), get_requests_(0) { + } + + virtual bool GetContentType(std::string* content_type) const { + DCHECK(!is_post_); + return false; + } + + virtual size_t ContentLength() const { + DCHECK(!is_post_); + return sizeof(kHtml) - 1; + } + + virtual bool GetCustomHeaders(std::string* headers) const { + if (!is_post_) + return false; + *headers = StringPrintf( + "HTTP/1.1 200 OK\r\n" + "Content-Disposition: attachment;filename=\"test.txt\"\r\n" + "Content-Type: application/text\r\n" + "Connection: close\r\n" + "Content-Length: %i\r\n\r\n", sizeof(kText) - 1); + return true; + } + + virtual bool Matches(const test_server::Request& r) const { + bool match = __super::Matches(r); + if (match) { + is_post_ = LowerCaseEqualsASCII(r.method().c_str(), "post"); + } + return match; + } + + virtual void WriteContents(ListenSocket* socket) const { + if (is_post_) { + socket->Send(kText, sizeof(kText) - 1, false); + } else { + socket->Send(kHtml, sizeof(kHtml) - 1, false); + } + } + + virtual void IncrementAccessCounter() { + __super::IncrementAccessCounter(); + if (is_post_) { + post_requests_++; + } else { + get_requests_++; + } + } + + size_t get_request_count() const { + return get_requests_; + } + + size_t post_request_count() const { + return get_requests_; + } + + protected: + mutable bool is_post_; + size_t post_requests_; + size_t get_requests_; + }; + + chrome_frame_test::TimedMsgLoop loop; // must come before the server. + SimpleWebServerTest server(46664); + CustomResponse* response = new CustomResponse("/form.html"); + server.web_server()->AddResponse(response); + + std::wstring url(server.FormatHttpPath(L"form.html")); + + ComStackObjectWithUninitialize<MockWebBrowserEventSink> mock; + + // Will get called twice. Once for HTML, once for the download. + EXPECT_CALL(mock, OnBeforeNavigate2(_, + testing::Field(&VARIANT::bstrVal, + testing::StrCaseEq(url)), _, _, _, _, _)).Times(2); + // Will get called twice in the case of CF, once if no CF. + EXPECT_CALL(mock, OnFileDownload(VARIANT_TRUE, _)) + .Times(testing::AnyNumber()); + EXPECT_CALL(mock, OnNavigateComplete2(_, + testing::Field(&VARIANT::bstrVal, testing::StrCaseEq(url)))) + .Times(testing::AnyNumber()); + EXPECT_CALL(mock, OnFileDownload(VARIANT_FALSE, _)) + .Times(testing::AnyNumber()) + .WillRepeatedly(CloseBrowserMock(&mock)); + + EXPECT_CALL(mock, OnQuit()).WillOnce(QUIT_LOOP(loop)); + + HRESULT hr = mock.LaunchIEAndNavigate(url); + ASSERT_HRESULT_SUCCEEDED(hr); + if (hr == S_OK) { + ASSERT_TRUE(mock.web_browser2() != NULL); + loop.RunFor(kChromeFrameLongNavigationTimeoutInSeconds * 2); + } + + EXPECT_EQ(1, response->get_request_count()); + EXPECT_EQ(1, response->post_request_count()); +} + diff --git a/chrome_frame/test/test_server.h b/chrome_frame/test/test_server.h index 462d7aa..58fd160 100644 --- a/chrome_frame/test/test_server.h +++ b/chrome_frame/test/test_server.h @@ -163,7 +163,7 @@ class Response { virtual void WriteContents(ListenSocket* socket) const { } - void IncrementAccessCounter() { + virtual void IncrementAccessCounter() { accessed_++; } diff --git a/chrome_frame/test/test_with_web_server.cc b/chrome_frame/test/test_with_web_server.cc index 229d3ad..67904a8 100644 --- a/chrome_frame/test/test_with_web_server.cc +++ b/chrome_frame/test/test_with_web_server.cc @@ -16,6 +16,15 @@ const int kShortWaitTimeout = 25 * 1000; const int kChromeFrameLaunchDelay = 5; const int kChromeFrameLongNavigationTimeoutInSeconds = 10; +bool MonikerPatchEnabled() { + ProtocolPatchMethod patch_method = + static_cast<ProtocolPatchMethod>( + GetConfigInt(PATCH_METHOD_IBROWSER_AND_MONIKER, kPatchProtocols)); + LOG_IF(ERROR, patch_method != PATCH_METHOD_IBROWSER_AND_MONIKER) + << "Not running test. Moniker patch not enabled."; + return patch_method == PATCH_METHOD_IBROWSER_AND_MONIKER; +} + class ChromeFrameTestEnvironment: public testing::Environment { public: ~ChromeFrameTestEnvironment() {} @@ -694,15 +703,8 @@ TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_NavigateOut) { const wchar_t kReferrerMainTest[] = L"files/referrer_main.html"; TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_ReferrerTest) { - // At the moment the moniker patch is only enabled if the below - // registry config value is set to PATCH_METHOD_IBROWSER_AND_MONIKER. - ProtocolPatchMethod patch_method = - static_cast<ProtocolPatchMethod>( - GetConfigInt(PATCH_METHOD_IBROWSER_AND_MONIKER, kPatchProtocols)); - if (patch_method != PATCH_METHOD_IBROWSER_AND_MONIKER) { - LOG(ERROR) << "Not running test. Moniker patch not enabled."; + if (!MonikerPatchEnabled()) return; - } SimpleBrowserTest(IE, kReferrerMainTest, L"FullTab_ReferrerTest"); } @@ -790,15 +792,8 @@ TEST_F(ChromeFrameTestWithWebServer, // Test whether POST-ing a form from an mshtml page to a CF page will cause // the request to get reissued. It should not. TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_TestPostReissue) { - // At the moment the moniker patch is only enabled if the below - // registry config value is set to PATCH_METHOD_IBROWSER_AND_MONIKER. - ProtocolPatchMethod patch_method = - static_cast<ProtocolPatchMethod>( - GetConfigInt(PATCH_METHOD_IBROWSER_AND_MONIKER, kPatchProtocols)); - if (patch_method != PATCH_METHOD_IBROWSER_AND_MONIKER) { - LOG(ERROR) << "Not running test. Moniker patch not enabled."; + if (!MonikerPatchEnabled()) return; - } MessageLoopForUI loop; // must come before the server. @@ -831,15 +826,8 @@ TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_TestPostReissue) { // Test whether following a link from an mshtml page to a CF page will cause // multiple network requests. It should not. TEST_F(ChromeFrameTestWithWebServer, FullTabModeIE_TestMultipleGet) { - // At the moment the moniker patch is only enabled if the below - // registry config value is set to PATCH_METHOD_IBROWSER_AND_MONIKER. - ProtocolPatchMethod patch_method = - static_cast<ProtocolPatchMethod>( - GetConfigInt(PATCH_METHOD_IBROWSER_AND_MONIKER, kPatchProtocols)); - if (patch_method != PATCH_METHOD_IBROWSER_AND_MONIKER) { - LOG(ERROR) << "Not running test. Moniker patch not enabled."; + if (!MonikerPatchEnabled()) return; - } MessageLoopForUI loop; // must come before the server. diff --git a/chrome_frame/test/test_with_web_server.h b/chrome_frame/test/test_with_web_server.h index d68a6b3..baba20c 100644 --- a/chrome_frame/test/test_with_web_server.h +++ b/chrome_frame/test/test_with_web_server.h @@ -150,10 +150,17 @@ class SimpleWebServerTest { return requests; } + test_server::SimpleWebServer* web_server() { + return &server_; + } + protected: test_server::SimpleWebServer server_; int port_; }; +// TODO(tommi): Remove when this is the only option. +bool MonikerPatchEnabled(); + #endif // CHROME_FRAME_TEST_WITH_WEB_SERVER_H_ diff --git a/chrome_frame/urlmon_url_request.cc b/chrome_frame/urlmon_url_request.cc index 3b15628..9d6ff10 100644 --- a/chrome_frame/urlmon_url_request.cc +++ b/chrome_frame/urlmon_url_request.cc @@ -953,7 +953,7 @@ void UrlmonUrlRequestManager::DownloadRequestInHost(int request_id) { if (request) { ScopedComPtr<IMoniker> moniker; request->StealMoniker(moniker.Receive()); - DCHECK(moniker); + DLOG_IF(ERROR, moniker == NULL) << __FUNCTION__ << " No moniker!"; if (moniker) { // We use SendMessage and not PostMessage to make sure that if the // notification window does not handle the message we won't leak |