Torne (Richard Coles) | 5821806 | 2012-11-14 11:43:16 +0000 | [diff] [blame] | 1 | // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
| 2 | // Use of this source code is governed by a BSD-style license that can be |
| 3 | // found in the LICENSE file. |
| 4 | |
| 5 | #include "content/public/test/render_view_fake_resources_test.h" |
| 6 | |
| 7 | #include <string.h> |
| 8 | |
Ben Murdoch | eb525c5 | 2013-07-10 11:40:50 +0100 | [diff] [blame] | 9 | #include "base/command_line.h" |
Ben Murdoch | ca12bfa | 2013-07-23 11:17:05 +0100 | [diff] [blame] | 10 | #include "base/memory/shared_memory.h" |
Ben Murdoch | 58e6fbe | 2013-07-26 10:20:38 +0100 | [diff] [blame] | 11 | #include "base/process/process.h" |
Torne (Richard Coles) | 2a99a7e | 2013-03-28 15:31:22 +0000 | [diff] [blame] | 12 | #include "base/run_loop.h" |
Ben Murdoch | eb525c5 | 2013-07-10 11:40:50 +0100 | [diff] [blame] | 13 | #include "base/time/time.h" |
Ben Murdoch | bb1529c | 2013-08-08 10:24:53 +0100 | [diff] [blame^] | 14 | #include "content/common/dom_storage/dom_storage_types.h" |
Torne (Richard Coles) | 5821806 | 2012-11-14 11:43:16 +0000 | [diff] [blame] | 15 | #include "content/common/resource_messages.h" |
| 16 | #include "content/common/view_messages.h" |
| 17 | #include "content/public/common/resource_response.h" |
Torne (Richard Coles) | 90dce4d | 2013-05-29 14:40:03 +0100 | [diff] [blame] | 18 | #include "content/public/renderer/history_item_serialization.h" |
Torne (Richard Coles) | 5821806 | 2012-11-14 11:43:16 +0000 | [diff] [blame] | 19 | #include "content/renderer/render_thread_impl.h" |
| 20 | #include "content/renderer/render_view_impl.h" |
| 21 | #include "content/renderer/renderer_webkitplatformsupport_impl.h" |
| 22 | #include "content/test/mock_render_process.h" |
Torne (Richard Coles) | 5821806 | 2012-11-14 11:43:16 +0000 | [diff] [blame] | 23 | #include "net/base/net_errors.h" |
| 24 | #include "net/base/upload_data.h" |
| 25 | #include "net/http/http_response_headers.h" |
| 26 | #include "net/url_request/url_request_status.h" |
Torne (Richard Coles) | 868fa2f | 2013-06-11 10:57:03 +0100 | [diff] [blame] | 27 | #include "third_party/WebKit/public/platform/WebString.h" |
| 28 | #include "third_party/WebKit/public/platform/WebURLRequest.h" |
Torne (Richard Coles) | 7d4cd47 | 2013-06-19 11:58:07 +0100 | [diff] [blame] | 29 | #include "third_party/WebKit/public/web/WebFrame.h" |
| 30 | #include "third_party/WebKit/public/web/WebHistoryItem.h" |
| 31 | #include "third_party/WebKit/public/web/WebView.h" |
Ben Murdoch | eb525c5 | 2013-07-10 11:40:50 +0100 | [diff] [blame] | 32 | #include "ui/base/ui_base_switches.h" |
Ben Murdoch | 7dbb3d5 | 2013-07-17 14:55:54 +0100 | [diff] [blame] | 33 | #include "url/gurl.h" |
Torne (Richard Coles) | 5821806 | 2012-11-14 11:43:16 +0000 | [diff] [blame] | 34 | #include "webkit/glue/webkit_glue.h" |
| 35 | |
| 36 | namespace content { |
| 37 | |
| 38 | const int32 RenderViewFakeResourcesTest::kViewId = 5; |
| 39 | |
| 40 | RenderViewFakeResourcesTest::RenderViewFakeResourcesTest() {} |
| 41 | RenderViewFakeResourcesTest::~RenderViewFakeResourcesTest() {} |
| 42 | |
| 43 | bool RenderViewFakeResourcesTest::OnMessageReceived( |
| 44 | const IPC::Message& message) { |
| 45 | IPC_BEGIN_MESSAGE_MAP(RenderViewFakeResourcesTest, message) |
| 46 | IPC_MESSAGE_HANDLER(ViewHostMsg_RenderViewReady, OnRenderViewReady) |
| 47 | IPC_MESSAGE_HANDLER(ViewHostMsg_DidStopLoading, OnDidStopLoading) |
| 48 | IPC_MESSAGE_HANDLER(ResourceHostMsg_RequestResource, OnRequestResource) |
| 49 | IPC_END_MESSAGE_MAP() |
| 50 | return true; |
| 51 | } |
| 52 | |
| 53 | bool RenderViewFakeResourcesTest::Visit(RenderView* render_view) { |
| 54 | view_ = render_view; |
| 55 | return false; |
| 56 | } |
| 57 | |
| 58 | void RenderViewFakeResourcesTest::SetUp() { |
| 59 | // Set up the renderer. This code is largely adapted from |
| 60 | // render_view_test.cc and renderer_main.cc. Note that we use a |
| 61 | // MockRenderProcess (because we don't need to use IPC for painting), |
| 62 | // but we use a real RenderThread so that we can use the ResourceDispatcher |
| 63 | // to fetch network resources. These are then served canned content |
| 64 | // in OnRequestResource(). |
Torne (Richard Coles) | c2e0dbd | 2013-05-09 18:35:53 +0100 | [diff] [blame] | 65 | SetRendererClientForTesting(&content_renderer_client_); |
Torne (Richard Coles) | 5821806 | 2012-11-14 11:43:16 +0000 | [diff] [blame] | 66 | // Generate a unique channel id so that multiple instances of the test can |
| 67 | // run in parallel. |
| 68 | std::string channel_id = IPC::Channel::GenerateVerifiedChannelID( |
| 69 | std::string()); |
| 70 | channel_.reset(new IPC::Channel(channel_id, |
| 71 | IPC::Channel::MODE_SERVER, this)); |
| 72 | ASSERT_TRUE(channel_->Connect()); |
| 73 | |
Ben Murdoch | eb525c5 | 2013-07-10 11:40:50 +0100 | [diff] [blame] | 74 | CommandLine& command_line = *CommandLine::ForCurrentProcess(); |
| 75 | command_line.AppendSwitchASCII(switches::kLang, "en-us"); |
| 76 | |
Torne (Richard Coles) | 5821806 | 2012-11-14 11:43:16 +0000 | [diff] [blame] | 77 | webkit_glue::SetJavaScriptFlags("--expose-gc"); |
| 78 | mock_process_.reset(new MockRenderProcess); |
| 79 | sandbox_was_enabled_ = |
| 80 | RendererWebKitPlatformSupportImpl::SetSandboxEnabledForTesting(false); |
| 81 | render_thread_ = new RenderThreadImpl(channel_id); |
| 82 | |
| 83 | // Tell the renderer to create a view, then wait until it's ready. |
| 84 | // We can't call View::Create() directly here or else we won't get |
| 85 | // RenderProcess's lazy initialization of WebKit. |
| 86 | view_ = NULL; |
| 87 | ViewMsg_New_Params params; |
| 88 | params.view_id = kViewId; |
| 89 | params.opener_route_id = MSG_ROUTING_NONE; |
Ben Murdoch | bb1529c | 2013-08-08 10:24:53 +0100 | [diff] [blame^] | 90 | params.session_storage_namespace_id = kInvalidSessionStorageNamespaceId; |
Torne (Richard Coles) | 5821806 | 2012-11-14 11:43:16 +0000 | [diff] [blame] | 91 | ASSERT_TRUE(channel_->Send(new ViewMsg_New(params))); |
| 92 | message_loop_.Run(); |
| 93 | } |
| 94 | |
| 95 | void RenderViewFakeResourcesTest::TearDown() { |
| 96 | // Try very hard to collect garbage before shutting down. |
| 97 | GetMainFrame()->collectGarbage(); |
| 98 | GetMainFrame()->collectGarbage(); |
| 99 | |
| 100 | ASSERT_TRUE(channel_->Send(new ViewMsg_Close(kViewId))); |
| 101 | do { |
Torne (Richard Coles) | 2a99a7e | 2013-03-28 15:31:22 +0000 | [diff] [blame] | 102 | base::RunLoop().RunUntilIdle(); |
Torne (Richard Coles) | 5821806 | 2012-11-14 11:43:16 +0000 | [diff] [blame] | 103 | view_ = NULL; |
| 104 | RenderView::ForEach(this); |
| 105 | } while (view_); |
| 106 | |
| 107 | mock_process_.reset(); |
| 108 | RendererWebKitPlatformSupportImpl::SetSandboxEnabledForTesting( |
| 109 | sandbox_was_enabled_); |
| 110 | } |
| 111 | |
| 112 | RenderView* RenderViewFakeResourcesTest::view() { |
| 113 | return view_; |
| 114 | } |
| 115 | |
| 116 | WebKit::WebFrame* RenderViewFakeResourcesTest::GetMainFrame() { |
| 117 | return view_->GetWebView()->mainFrame(); |
| 118 | } |
| 119 | |
| 120 | void RenderViewFakeResourcesTest::LoadURL(const std::string& url) { |
| 121 | GURL g_url(url); |
| 122 | GetMainFrame()->loadRequest(WebKit::WebURLRequest(g_url)); |
| 123 | message_loop_.Run(); |
| 124 | } |
| 125 | |
| 126 | void RenderViewFakeResourcesTest::LoadURLWithPost(const std::string& url) { |
| 127 | GURL g_url(url); |
| 128 | WebKit::WebURLRequest request(g_url); |
| 129 | request.setHTTPMethod(WebKit::WebString::fromUTF8("POST")); |
| 130 | GetMainFrame()->loadRequest(request); |
| 131 | message_loop_.Run(); |
| 132 | } |
| 133 | |
| 134 | void RenderViewFakeResourcesTest::GoBack() { |
| 135 | GoToOffset(-1, GetMainFrame()->previousHistoryItem()); |
| 136 | } |
| 137 | |
| 138 | void RenderViewFakeResourcesTest::GoForward( |
| 139 | const WebKit::WebHistoryItem& history_item) { |
| 140 | GoToOffset(1, history_item); |
| 141 | } |
| 142 | |
| 143 | void RenderViewFakeResourcesTest::OnDidStopLoading() { |
| 144 | message_loop_.Quit(); |
| 145 | } |
| 146 | |
| 147 | void RenderViewFakeResourcesTest::OnRequestResource( |
| 148 | const IPC::Message& message, |
| 149 | int request_id, |
| 150 | const ResourceHostMsg_Request& request_data) { |
| 151 | std::string headers, body; |
| 152 | std::map<std::string, std::string>::const_iterator it = |
| 153 | responses_.find(request_data.url.spec()); |
| 154 | if (it == responses_.end()) { |
| 155 | headers = "HTTP/1.1 404 Not Found\0Content-Type:text/html\0\0"; |
| 156 | body = "content not found"; |
| 157 | } else { |
| 158 | headers = "HTTP/1.1 200 OK\0Content-Type:text/html\0\0"; |
| 159 | body = it->second; |
| 160 | } |
| 161 | |
| 162 | ResourceResponseHead response_head; |
| 163 | response_head.headers = new net::HttpResponseHeaders(headers); |
| 164 | response_head.mime_type = "text/html"; |
| 165 | ASSERT_TRUE(channel_->Send(new ResourceMsg_ReceivedResponse( |
| 166 | message.routing_id(), request_id, response_head))); |
| 167 | |
| 168 | base::SharedMemory shared_memory; |
| 169 | ASSERT_TRUE(shared_memory.CreateAndMapAnonymous(body.size())); |
| 170 | memcpy(shared_memory.memory(), body.data(), body.size()); |
| 171 | |
| 172 | base::SharedMemoryHandle handle; |
| 173 | ASSERT_TRUE(shared_memory.GiveToProcess(base::Process::Current().handle(), |
| 174 | &handle)); |
| 175 | |
| 176 | ASSERT_TRUE(channel_->Send(new ResourceMsg_SetDataBuffer( |
| 177 | message.routing_id(), |
| 178 | request_id, |
| 179 | handle, |
Torne (Richard Coles) | 2a99a7e | 2013-03-28 15:31:22 +0000 | [diff] [blame] | 180 | body.size(), |
| 181 | 0))); |
Torne (Richard Coles) | 5821806 | 2012-11-14 11:43:16 +0000 | [diff] [blame] | 182 | |
| 183 | ASSERT_TRUE(channel_->Send(new ResourceMsg_DataReceived( |
| 184 | message.routing_id(), |
| 185 | request_id, |
| 186 | 0, |
| 187 | body.size(), |
| 188 | body.size()))); |
| 189 | |
| 190 | ASSERT_TRUE(channel_->Send(new ResourceMsg_RequestComplete( |
| 191 | message.routing_id(), |
| 192 | request_id, |
| 193 | net::OK, |
| 194 | false, |
| 195 | std::string(), |
| 196 | base::TimeTicks()))); |
| 197 | } |
| 198 | |
| 199 | void RenderViewFakeResourcesTest::OnRenderViewReady() { |
| 200 | // Grab a pointer to the new view using RenderViewVisitor. |
| 201 | ASSERT_TRUE(!view_); |
| 202 | RenderView::ForEach(this); |
| 203 | ASSERT_TRUE(view_); |
| 204 | message_loop_.Quit(); |
| 205 | } |
| 206 | |
| 207 | void RenderViewFakeResourcesTest::GoToOffset( |
| 208 | int offset, |
| 209 | const WebKit::WebHistoryItem& history_item) { |
| 210 | RenderViewImpl* impl = static_cast<RenderViewImpl*>(view_); |
| 211 | ViewMsg_Navigate_Params params; |
| 212 | params.page_id = impl->GetPageId() + offset; |
| 213 | params.pending_history_list_offset = |
| 214 | impl->history_list_offset() + offset; |
| 215 | params.current_history_list_offset = impl->history_list_offset(); |
| 216 | params.current_history_list_length = (impl->historyBackListCount() + |
| 217 | impl->historyForwardListCount() + 1); |
| 218 | params.url = GURL(history_item.urlString()); |
| 219 | params.transition = PAGE_TRANSITION_FORWARD_BACK; |
Torne (Richard Coles) | 90dce4d | 2013-05-29 14:40:03 +0100 | [diff] [blame] | 220 | params.page_state = HistoryItemToPageState(history_item); |
Torne (Richard Coles) | 5821806 | 2012-11-14 11:43:16 +0000 | [diff] [blame] | 221 | params.navigation_type = ViewMsg_Navigate_Type::NORMAL; |
| 222 | params.request_time = base::Time::Now(); |
| 223 | channel_->Send(new ViewMsg_Navigate(impl->routing_id(), params)); |
| 224 | message_loop_.Run(); |
| 225 | } |
| 226 | |
| 227 | } // namespace content |