Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2013 The Chromium Authors. All rights reserved. | 1 // Copyright 2017 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "content/shell/browser/shell_devtools_frontend.h" | 5 #include "content/shell/browser/shell_devtools_bindings.h" |
| 6 | 6 |
| 7 #include <stddef.h> | 7 #include <stddef.h> |
| 8 | 8 |
| 9 #include "base/json/json_reader.h" | 9 #include "base/json/json_reader.h" |
| 10 #include "base/json/json_writer.h" | 10 #include "base/json/json_writer.h" |
| 11 #include "base/json/string_escape.h" | 11 #include "base/json/string_escape.h" |
| 12 #include "base/macros.h" | 12 #include "base/macros.h" |
| 13 #include "base/strings/string_number_conversions.h" | 13 #include "base/strings/string_number_conversions.h" |
| 14 #include "base/strings/stringprintf.h" | 14 #include "base/strings/stringprintf.h" |
| 15 #include "base/strings/utf_string_conversions.h" | 15 #include "base/strings/utf_string_conversions.h" |
| (...skipping 12 matching lines...) Expand all Loading... | |
| 28 #include "net/base/io_buffer.h" | 28 #include "net/base/io_buffer.h" |
| 29 #include "net/base/net_errors.h" | 29 #include "net/base/net_errors.h" |
| 30 #include "net/http/http_response_headers.h" | 30 #include "net/http/http_response_headers.h" |
| 31 #include "net/url_request/url_fetcher.h" | 31 #include "net/url_request/url_fetcher.h" |
| 32 #include "net/url_request/url_fetcher_response_writer.h" | 32 #include "net/url_request/url_fetcher_response_writer.h" |
| 33 | 33 |
| 34 namespace content { | 34 namespace content { |
| 35 | 35 |
| 36 namespace { | 36 namespace { |
| 37 | 37 |
| 38 | |
| 39 // ResponseWriter ------------------------------------------------------------- | 38 // ResponseWriter ------------------------------------------------------------- |
| 40 | 39 |
| 41 class ResponseWriter : public net::URLFetcherResponseWriter { | 40 class ResponseWriter : public net::URLFetcherResponseWriter { |
| 42 public: | 41 public: |
| 43 ResponseWriter(base::WeakPtr<ShellDevToolsFrontend> shell_devtools_, | 42 ResponseWriter(base::WeakPtr<ShellDevToolsBindings> devtools_bindings_, |
| 44 int stream_id); | 43 int stream_id); |
| 45 ~ResponseWriter() override; | 44 ~ResponseWriter() override; |
| 46 | 45 |
| 47 // URLFetcherResponseWriter overrides: | 46 // URLFetcherResponseWriter overrides: |
| 48 int Initialize(const net::CompletionCallback& callback) override; | 47 int Initialize(const net::CompletionCallback& callback) override; |
| 49 int Write(net::IOBuffer* buffer, | 48 int Write(net::IOBuffer* buffer, |
| 50 int num_bytes, | 49 int num_bytes, |
| 51 const net::CompletionCallback& callback) override; | 50 const net::CompletionCallback& callback) override; |
| 52 int Finish(int net_error, const net::CompletionCallback& callback) override; | 51 int Finish(int net_error, const net::CompletionCallback& callback) override; |
| 53 | 52 |
| 54 private: | 53 private: |
| 55 base::WeakPtr<ShellDevToolsFrontend> shell_devtools_; | 54 base::WeakPtr<ShellDevToolsBindings> devtools_bindings_; |
| 56 int stream_id_; | 55 int stream_id_; |
| 57 | 56 |
| 58 DISALLOW_COPY_AND_ASSIGN(ResponseWriter); | 57 DISALLOW_COPY_AND_ASSIGN(ResponseWriter); |
| 59 }; | 58 }; |
| 60 | 59 |
| 61 ResponseWriter::ResponseWriter( | 60 ResponseWriter::ResponseWriter( |
| 62 base::WeakPtr<ShellDevToolsFrontend> shell_devtools, | 61 base::WeakPtr<ShellDevToolsBindings> shell_devtools, |
| 63 int stream_id) | 62 int stream_id) |
| 64 : shell_devtools_(shell_devtools), | 63 : devtools_bindings_(shell_devtools), stream_id_(stream_id) {} |
| 65 stream_id_(stream_id) { | |
| 66 } | |
| 67 | 64 |
| 68 ResponseWriter::~ResponseWriter() { | 65 ResponseWriter::~ResponseWriter() {} |
| 69 } | |
| 70 | 66 |
| 71 int ResponseWriter::Initialize(const net::CompletionCallback& callback) { | 67 int ResponseWriter::Initialize(const net::CompletionCallback& callback) { |
| 72 return net::OK; | 68 return net::OK; |
| 73 } | 69 } |
| 74 | 70 |
| 75 int ResponseWriter::Write(net::IOBuffer* buffer, | 71 int ResponseWriter::Write(net::IOBuffer* buffer, |
| 76 int num_bytes, | 72 int num_bytes, |
| 77 const net::CompletionCallback& callback) { | 73 const net::CompletionCallback& callback) { |
| 78 std::string chunk = std::string(buffer->data(), num_bytes); | 74 std::string chunk = std::string(buffer->data(), num_bytes); |
| 79 if (!base::IsStringUTF8(chunk)) | 75 if (!base::IsStringUTF8(chunk)) |
| 80 return num_bytes; | 76 return num_bytes; |
| 81 | 77 |
| 82 base::Value* id = new base::Value(stream_id_); | 78 base::Value* id = new base::Value(stream_id_); |
| 83 base::Value* chunkValue = new base::Value(chunk); | 79 base::Value* chunkValue = new base::Value(chunk); |
| 84 | 80 |
| 85 content::BrowserThread::PostTask( | 81 content::BrowserThread::PostTask( |
| 86 content::BrowserThread::UI, FROM_HERE, | 82 content::BrowserThread::UI, FROM_HERE, |
| 87 base::Bind(&ShellDevToolsFrontend::CallClientFunction, | 83 base::Bind(&ShellDevToolsBindings::CallClientFunction, devtools_bindings_, |
| 88 shell_devtools_, "DevToolsAPI.streamWrite", | 84 "DevToolsAPI.streamWrite", base::Owned(id), |
| 89 base::Owned(id), base::Owned(chunkValue), nullptr)); | 85 base::Owned(chunkValue), nullptr)); |
| 90 return num_bytes; | 86 return num_bytes; |
| 91 } | 87 } |
| 92 | 88 |
| 93 int ResponseWriter::Finish(int net_error, | 89 int ResponseWriter::Finish(int net_error, |
| 94 const net::CompletionCallback& callback) { | 90 const net::CompletionCallback& callback) { |
| 95 return net::OK; | 91 return net::OK; |
| 96 } | 92 } |
| 97 | 93 |
| 98 static GURL GetFrontendURL() { | |
| 99 int port = ShellDevToolsManagerDelegate::GetHttpHandlerPort(); | |
| 100 return GURL( | |
| 101 base::StringPrintf("http://127.0.0.1:%d/devtools/inspector.html", port)); | |
| 102 } | |
| 103 | |
| 104 } // namespace | 94 } // namespace |
| 105 | 95 |
| 106 // This constant should be in sync with | 96 // This constant should be in sync with |
| 107 // the constant at devtools_ui_bindings.cc. | 97 // the constant at devtools_ui_bindings.cc. |
| 108 const size_t kMaxMessageChunkSize = IPC::Channel::kMaximumMessageSize / 4; | 98 const size_t kMaxMessageChunkSize = IPC::Channel::kMaximumMessageSize / 4; |
| 109 | 99 |
| 110 // static | 100 void ShellDevToolsBindings::InspectElementAt(int x, int y) { |
| 111 ShellDevToolsFrontend* ShellDevToolsFrontend::Show( | |
| 112 WebContents* inspected_contents) { | |
| 113 Shell* shell = Shell::CreateNewWindow(inspected_contents->GetBrowserContext(), | |
| 114 GURL(), | |
| 115 NULL, | |
| 116 gfx::Size()); | |
| 117 ShellDevToolsFrontend* devtools_frontend = new ShellDevToolsFrontend( | |
| 118 shell, | |
| 119 inspected_contents); | |
| 120 shell->LoadURL(GetFrontendURL()); | |
| 121 return devtools_frontend; | |
| 122 } | |
| 123 | |
| 124 void ShellDevToolsFrontend::Activate() { | |
| 125 frontend_shell_->ActivateContents(web_contents()); | |
| 126 } | |
| 127 | |
| 128 void ShellDevToolsFrontend::Focus() { | |
| 129 web_contents()->Focus(); | |
| 130 } | |
| 131 | |
| 132 void ShellDevToolsFrontend::InspectElementAt(int x, int y) { | |
| 133 if (agent_host_) { | 101 if (agent_host_) { |
| 134 agent_host_->InspectElement(this, x, y); | 102 agent_host_->InspectElement(this, x, y); |
| 135 } else { | 103 } else { |
| 136 inspect_element_at_x_ = x; | 104 inspect_element_at_x_ = x; |
| 137 inspect_element_at_y_ = y; | 105 inspect_element_at_y_ = y; |
| 138 } | 106 } |
| 139 } | 107 } |
| 140 | 108 |
| 141 void ShellDevToolsFrontend::Close() { | 109 ShellDevToolsBindings::ShellDevToolsBindings(WebContents* devtools_contents, |
| 142 frontend_shell_->Close(); | 110 WebContents* inspected_contents, |
| 143 } | 111 ShellDevToolsDelegate* delegate, |
| 144 | 112 const std::string& settings, |
| 145 void ShellDevToolsFrontend::DisconnectFromTarget() { | 113 const GURL& devtools_url) |
| 146 if (!agent_host_) | 114 : WebContentsObserver(devtools_contents), |
| 147 return; | |
| 148 agent_host_->DetachClient(this); | |
| 149 agent_host_ = NULL; | |
| 150 } | |
| 151 | |
| 152 ShellDevToolsFrontend::ShellDevToolsFrontend(Shell* frontend_shell, | |
| 153 WebContents* inspected_contents) | |
| 154 : WebContentsObserver(frontend_shell->web_contents()), | |
| 155 frontend_shell_(frontend_shell), | |
| 156 inspected_contents_(inspected_contents), | 115 inspected_contents_(inspected_contents), |
| 116 delegate_(delegate), | |
| 157 inspect_element_at_x_(-1), | 117 inspect_element_at_x_(-1), |
| 158 inspect_element_at_y_(-1), | 118 inspect_element_at_y_(-1), |
| 159 weak_factory_(this) { | 119 weak_factory_(this) { |
| 120 SetPreferences(settings); | |
| 121 NavigationController::LoadURLParams params(devtools_url); | |
| 122 params.transition_type = ui::PageTransitionFromInt( | |
| 123 ui::PAGE_TRANSITION_TYPED | ui::PAGE_TRANSITION_FROM_ADDRESS_BAR); | |
| 124 web_contents()->GetController().LoadURLWithParams(params); | |
| 125 web_contents()->Focus(); | |
| 126 frontend_host_.reset(DevToolsFrontendHost::Create( | |
| 127 web_contents()->GetMainFrame(), | |
| 128 base::Bind(&ShellDevToolsBindings::HandleMessageFromDevToolsFrontend, | |
| 129 base::Unretained(this)))); | |
| 160 } | 130 } |
| 161 | 131 |
| 162 ShellDevToolsFrontend::~ShellDevToolsFrontend() { | 132 ShellDevToolsBindings::~ShellDevToolsBindings() { |
| 163 for (const auto& pair : pending_requests_) | 133 for (const auto& pair : pending_requests_) |
| 164 delete pair.first; | 134 delete pair.first; |
| 135 if (agent_host_) | |
| 136 agent_host_->DetachClient(this); | |
| 165 } | 137 } |
| 166 | 138 |
| 167 void ShellDevToolsFrontend::RenderViewCreated( | 139 void ShellDevToolsBindings::DocumentAvailableInMainFrame() { |
|
dgozman
2017/03/21 20:57:35
We still need this in case RenderFrameHost for mai
chenwilliam
2017/03/21 23:36:42
Done.
| |
| 168 RenderViewHost* render_view_host) { | |
| 169 if (!frontend_host_) { | |
| 170 frontend_host_.reset(DevToolsFrontendHost::Create( | |
| 171 web_contents()->GetMainFrame(), | |
| 172 base::Bind(&ShellDevToolsFrontend::HandleMessageFromDevToolsFrontend, | |
| 173 base::Unretained(this)))); | |
| 174 } | |
| 175 } | |
| 176 | |
| 177 void ShellDevToolsFrontend::DocumentAvailableInMainFrame() { | |
| 178 agent_host_ = DevToolsAgentHost::GetOrCreateFor(inspected_contents_); | 140 agent_host_ = DevToolsAgentHost::GetOrCreateFor(inspected_contents_); |
| 179 agent_host_->AttachClient(this); | 141 agent_host_->AttachClient(this); |
| 180 if (inspect_element_at_x_ != -1) { | 142 if (inspect_element_at_x_ != -1) { |
| 181 agent_host_->InspectElement( | 143 agent_host_->InspectElement(this, inspect_element_at_x_, |
| 182 this, inspect_element_at_x_, inspect_element_at_y_); | 144 inspect_element_at_y_); |
| 183 inspect_element_at_x_ = -1; | 145 inspect_element_at_x_ = -1; |
| 184 inspect_element_at_y_ = -1; | 146 inspect_element_at_y_ = -1; |
| 185 } | 147 } |
| 186 } | 148 } |
| 187 | 149 |
| 188 void ShellDevToolsFrontend::WebContentsDestroyed() { | 150 void ShellDevToolsBindings::WebContentsDestroyed() { |
| 189 if (agent_host_) | |
| 190 agent_host_->DetachClient(this); | |
| 191 delete this; | 151 delete this; |
|
dgozman
2017/03/21 20:57:35
Deleting this while being owned via std::unique_pt
chenwilliam
2017/03/21 23:36:43
Done.
| |
| 192 } | 152 } |
| 193 | 153 |
| 194 void ShellDevToolsFrontend::SetPreferences(const std::string& json) { | 154 void ShellDevToolsBindings::SetPreferences(const std::string& json) { |
| 195 preferences_.Clear(); | 155 preferences_.Clear(); |
| 196 if (json.empty()) | 156 if (json.empty()) |
| 197 return; | 157 return; |
| 198 base::DictionaryValue* dict = nullptr; | 158 base::DictionaryValue* dict = nullptr; |
| 199 std::unique_ptr<base::Value> parsed = base::JSONReader::Read(json); | 159 std::unique_ptr<base::Value> parsed = base::JSONReader::Read(json); |
| 200 if (!parsed || !parsed->GetAsDictionary(&dict)) | 160 if (!parsed || !parsed->GetAsDictionary(&dict)) |
| 201 return; | 161 return; |
| 202 for (base::DictionaryValue::Iterator it(*dict); !it.IsAtEnd(); it.Advance()) { | 162 for (base::DictionaryValue::Iterator it(*dict); !it.IsAtEnd(); it.Advance()) { |
| 203 if (!it.value().IsType(base::Value::Type::STRING)) | 163 if (!it.value().IsType(base::Value::Type::STRING)) |
| 204 continue; | 164 continue; |
| 205 preferences_.SetWithoutPathExpansion(it.key(), it.value().CreateDeepCopy()); | 165 preferences_.SetWithoutPathExpansion(it.key(), it.value().CreateDeepCopy()); |
| 206 } | 166 } |
| 207 } | 167 } |
| 208 | 168 |
| 209 void ShellDevToolsFrontend::HandleMessageFromDevToolsFrontend( | 169 void ShellDevToolsBindings::HandleMessageFromDevToolsFrontend( |
| 210 const std::string& message) { | 170 const std::string& message) { |
| 211 if (!agent_host_) | 171 if (!agent_host_) |
| 212 return; | 172 return; |
| 213 std::string method; | 173 std::string method; |
| 214 base::ListValue* params = NULL; | 174 base::ListValue* params = NULL; |
| 215 base::DictionaryValue* dict = NULL; | 175 base::DictionaryValue* dict = NULL; |
| 216 std::unique_ptr<base::Value> parsed_message = base::JSONReader::Read(message); | 176 std::unique_ptr<base::Value> parsed_message = base::JSONReader::Read(message); |
| 217 if (!parsed_message || | 177 if (!parsed_message || !parsed_message->GetAsDictionary(&dict) || |
| 218 !parsed_message->GetAsDictionary(&dict) || | |
| 219 !dict->GetString("method", &method)) { | 178 !dict->GetString("method", &method)) { |
| 220 return; | 179 return; |
| 221 } | 180 } |
| 222 int request_id = 0; | 181 int request_id = 0; |
| 223 dict->GetInteger("id", &request_id); | 182 dict->GetInteger("id", &request_id); |
| 224 dict->GetList("params", ¶ms); | 183 dict->GetList("params", ¶ms); |
| 225 | 184 |
| 226 if (method == "dispatchProtocolMessage" && params && params->GetSize() == 1) { | 185 if (method == "dispatchProtocolMessage" && params && params->GetSize() == 1) { |
| 227 if (!agent_host_ || !agent_host_->IsAttached()) | 186 if (!agent_host_ || !agent_host_->IsAttached()) |
| 228 return; | 187 return; |
| 229 std::string protocol_message; | 188 std::string protocol_message; |
| 230 if (!params->GetString(0, &protocol_message)) | 189 if (!params->GetString(0, &protocol_message)) |
| 231 return; | 190 return; |
| 232 agent_host_->DispatchProtocolMessage(this, protocol_message); | 191 agent_host_->DispatchProtocolMessage(this, protocol_message); |
| 233 } else if (method == "loadCompleted") { | 192 } else if (method == "loadCompleted") { |
| 234 web_contents()->GetMainFrame()->ExecuteJavaScriptForTests( | 193 web_contents()->GetMainFrame()->ExecuteJavaScriptForTests( |
| 235 base::ASCIIToUTF16("DevToolsAPI.setUseSoftMenu(true);")); | 194 base::ASCIIToUTF16("DevToolsAPI.setUseSoftMenu(true);")); |
| 236 } else if (method == "loadNetworkResource" && params->GetSize() == 3) { | 195 } else if (method == "loadNetworkResource" && params->GetSize() == 3) { |
| 237 // TODO(pfeldman): handle some of the embedder messages in content. | 196 // TODO(pfeldman): handle some of the embedder messages in content. |
| 238 std::string url; | 197 std::string url; |
| 239 std::string headers; | 198 std::string headers; |
| 240 int stream_id; | 199 int stream_id; |
| 241 if (!params->GetString(0, &url) || | 200 if (!params->GetString(0, &url) || !params->GetString(1, &headers) || |
| 242 !params->GetString(1, &headers) || | |
| 243 !params->GetInteger(2, &stream_id)) { | 201 !params->GetInteger(2, &stream_id)) { |
| 244 return; | 202 return; |
| 245 } | 203 } |
| 246 | 204 |
| 247 GURL gurl(url); | 205 GURL gurl(url); |
| 248 if (!gurl.is_valid()) { | 206 if (!gurl.is_valid()) { |
| 249 base::DictionaryValue response; | 207 base::DictionaryValue response; |
| 250 response.SetInteger("statusCode", 404); | 208 response.SetInteger("statusCode", 404); |
| 251 SendMessageAck(request_id, &response); | 209 SendMessageAck(request_id, &response); |
| 252 return; | 210 return; |
| 253 } | 211 } |
| 254 | 212 |
| 255 net::URLFetcher* fetcher = | 213 net::URLFetcher* fetcher = |
| 256 net::URLFetcher::Create(gurl, net::URLFetcher::GET, this).release(); | 214 net::URLFetcher::Create(gurl, net::URLFetcher::GET, this).release(); |
| 257 pending_requests_[fetcher] = request_id; | 215 pending_requests_[fetcher] = request_id; |
| 258 fetcher->SetRequestContext( | 216 fetcher->SetRequestContext(BrowserContext::GetDefaultStoragePartition( |
| 259 BrowserContext::GetDefaultStoragePartition( | 217 web_contents()->GetBrowserContext()) |
| 260 web_contents()->GetBrowserContext())-> | 218 ->GetURLRequestContext()); |
| 261 GetURLRequestContext()); | |
| 262 fetcher->SetExtraRequestHeaders(headers); | 219 fetcher->SetExtraRequestHeaders(headers); |
| 263 fetcher->SaveResponseWithWriter( | 220 fetcher->SaveResponseWithWriter( |
| 264 std::unique_ptr<net::URLFetcherResponseWriter>( | 221 std::unique_ptr<net::URLFetcherResponseWriter>( |
| 265 new ResponseWriter(weak_factory_.GetWeakPtr(), stream_id))); | 222 new ResponseWriter(weak_factory_.GetWeakPtr(), stream_id))); |
| 266 fetcher->Start(); | 223 fetcher->Start(); |
| 267 return; | 224 return; |
| 268 } else if (method == "getPreferences") { | 225 } else if (method == "getPreferences") { |
| 269 SendMessageAck(request_id, &preferences_); | 226 SendMessageAck(request_id, &preferences_); |
| 270 return; | 227 return; |
| 271 } else if (method == "setPreference") { | 228 } else if (method == "setPreference") { |
| 272 std::string name; | 229 std::string name; |
| 273 std::string value; | 230 std::string value; |
| 274 if (!params->GetString(0, &name) || | 231 if (!params->GetString(0, &name) || !params->GetString(1, &value)) { |
| 275 !params->GetString(1, &value)) { | |
| 276 return; | 232 return; |
| 277 } | 233 } |
| 278 preferences_.SetStringWithoutPathExpansion(name, value); | 234 preferences_.SetStringWithoutPathExpansion(name, value); |
| 279 } else if (method == "removePreference") { | 235 } else if (method == "removePreference") { |
| 280 std::string name; | 236 std::string name; |
| 281 if (!params->GetString(0, &name)) | 237 if (!params->GetString(0, &name)) |
| 282 return; | 238 return; |
| 283 preferences_.RemoveWithoutPathExpansion(name, nullptr); | 239 preferences_.RemoveWithoutPathExpansion(name, nullptr); |
| 284 } else if (method == "requestFileSystems") { | 240 } else if (method == "requestFileSystems") { |
| 285 web_contents()->GetMainFrame()->ExecuteJavaScriptForTests( | 241 web_contents()->GetMainFrame()->ExecuteJavaScriptForTests( |
| 286 base::ASCIIToUTF16("DevToolsAPI.fileSystemsLoaded([]);")); | 242 base::ASCIIToUTF16("DevToolsAPI.fileSystemsLoaded([]);")); |
| 287 } else if (method == "reattach") { | 243 } else if (method == "reattach") { |
| 288 agent_host_->DetachClient(this); | 244 agent_host_->DetachClient(this); |
| 289 agent_host_->AttachClient(this); | 245 agent_host_->AttachClient(this); |
| 290 } else { | 246 } else { |
| 291 return; | 247 return; |
| 292 } | 248 } |
| 293 | 249 |
| 294 if (request_id) | 250 if (request_id) |
| 295 SendMessageAck(request_id, nullptr); | 251 SendMessageAck(request_id, nullptr); |
| 296 } | 252 } |
| 297 | 253 |
| 298 void ShellDevToolsFrontend::DispatchProtocolMessage( | 254 void ShellDevToolsBindings::DispatchProtocolMessage( |
| 299 DevToolsAgentHost* agent_host, const std::string& message) { | 255 DevToolsAgentHost* agent_host, |
| 300 | 256 const std::string& message) { |
| 301 if (message.length() < kMaxMessageChunkSize) { | 257 if (message.length() < kMaxMessageChunkSize) { |
| 302 std::string param; | 258 std::string param; |
| 303 base::EscapeJSONString(message, true, ¶m); | 259 base::EscapeJSONString(message, true, ¶m); |
| 304 std::string code = "DevToolsAPI.dispatchMessage(" + param + ");"; | 260 std::string code = "DevToolsAPI.dispatchMessage(" + param + ");"; |
| 305 base::string16 javascript = base::UTF8ToUTF16(code); | 261 base::string16 javascript = base::UTF8ToUTF16(code); |
| 306 web_contents()->GetMainFrame()->ExecuteJavaScriptForTests(javascript); | 262 web_contents()->GetMainFrame()->ExecuteJavaScriptForTests(javascript); |
| 307 return; | 263 return; |
| 308 } | 264 } |
| 309 | 265 |
| 310 size_t total_size = message.length(); | 266 size_t total_size = message.length(); |
| 311 for (size_t pos = 0; pos < message.length(); pos += kMaxMessageChunkSize) { | 267 for (size_t pos = 0; pos < message.length(); pos += kMaxMessageChunkSize) { |
| 312 std::string param; | 268 std::string param; |
| 313 base::EscapeJSONString(message.substr(pos, kMaxMessageChunkSize), true, | 269 base::EscapeJSONString(message.substr(pos, kMaxMessageChunkSize), true, |
| 314 ¶m); | 270 ¶m); |
| 315 std::string code = "DevToolsAPI.dispatchMessageChunk(" + param + "," + | 271 std::string code = "DevToolsAPI.dispatchMessageChunk(" + param + "," + |
| 316 std::to_string(pos ? 0 : total_size) + ");"; | 272 std::to_string(pos ? 0 : total_size) + ");"; |
| 317 base::string16 javascript = base::UTF8ToUTF16(code); | 273 base::string16 javascript = base::UTF8ToUTF16(code); |
| 318 web_contents()->GetMainFrame()->ExecuteJavaScriptForTests(javascript); | 274 web_contents()->GetMainFrame()->ExecuteJavaScriptForTests(javascript); |
| 319 } | 275 } |
| 320 } | 276 } |
| 321 | 277 |
| 322 void ShellDevToolsFrontend::OnURLFetchComplete(const net::URLFetcher* source) { | 278 void ShellDevToolsBindings::OnURLFetchComplete(const net::URLFetcher* source) { |
| 323 // TODO(pfeldman): this is a copy of chrome's devtools_ui_bindings.cc. | 279 // TODO(pfeldman): this is a copy of chrome's devtools_ui_bindings.cc. |
| 324 // We should handle some of the commands including this one in content. | 280 // We should handle some of the commands including this one in content. |
| 325 DCHECK(source); | 281 DCHECK(source); |
| 326 PendingRequestsMap::iterator it = pending_requests_.find(source); | 282 PendingRequestsMap::iterator it = pending_requests_.find(source); |
| 327 DCHECK(it != pending_requests_.end()); | 283 DCHECK(it != pending_requests_.end()); |
| 328 | 284 |
| 329 base::DictionaryValue response; | 285 base::DictionaryValue response; |
| 330 base::DictionaryValue* headers = new base::DictionaryValue(); | 286 base::DictionaryValue* headers = new base::DictionaryValue(); |
| 331 net::HttpResponseHeaders* rh = source->GetResponseHeaders(); | 287 net::HttpResponseHeaders* rh = source->GetResponseHeaders(); |
| 332 response.SetInteger("statusCode", rh ? rh->response_code() : 200); | 288 response.SetInteger("statusCode", rh ? rh->response_code() : 200); |
| 333 response.Set("headers", headers); | 289 response.Set("headers", headers); |
| 334 | 290 |
| 335 size_t iterator = 0; | 291 size_t iterator = 0; |
| 336 std::string name; | 292 std::string name; |
| 337 std::string value; | 293 std::string value; |
| 338 while (rh && rh->EnumerateHeaderLines(&iterator, &name, &value)) | 294 while (rh && rh->EnumerateHeaderLines(&iterator, &name, &value)) |
| 339 headers->SetString(name, value); | 295 headers->SetString(name, value); |
| 340 | 296 |
| 341 SendMessageAck(it->second, &response); | 297 SendMessageAck(it->second, &response); |
| 342 pending_requests_.erase(it); | 298 pending_requests_.erase(it); |
| 343 delete source; | 299 delete source; |
| 344 } | 300 } |
| 345 | 301 |
| 346 void ShellDevToolsFrontend::CallClientFunction( | 302 void ShellDevToolsBindings::CallClientFunction(const std::string& function_name, |
| 347 const std::string& function_name, | 303 const base::Value* arg1, |
| 348 const base::Value* arg1, | 304 const base::Value* arg2, |
| 349 const base::Value* arg2, | 305 const base::Value* arg3) { |
| 350 const base::Value* arg3) { | |
| 351 std::string javascript = function_name + "("; | 306 std::string javascript = function_name + "("; |
| 352 if (arg1) { | 307 if (arg1) { |
| 353 std::string json; | 308 std::string json; |
| 354 base::JSONWriter::Write(*arg1, &json); | 309 base::JSONWriter::Write(*arg1, &json); |
| 355 javascript.append(json); | 310 javascript.append(json); |
| 356 if (arg2) { | 311 if (arg2) { |
| 357 base::JSONWriter::Write(*arg2, &json); | 312 base::JSONWriter::Write(*arg2, &json); |
| 358 javascript.append(", ").append(json); | 313 javascript.append(", ").append(json); |
| 359 if (arg3) { | 314 if (arg3) { |
| 360 base::JSONWriter::Write(*arg3, &json); | 315 base::JSONWriter::Write(*arg3, &json); |
| 361 javascript.append(", ").append(json); | 316 javascript.append(", ").append(json); |
| 362 } | 317 } |
| 363 } | 318 } |
| 364 } | 319 } |
| 365 javascript.append(");"); | 320 javascript.append(");"); |
| 366 web_contents()->GetMainFrame()->ExecuteJavaScriptForTests( | 321 web_contents()->GetMainFrame()->ExecuteJavaScriptForTests( |
| 367 base::UTF8ToUTF16(javascript)); | 322 base::UTF8ToUTF16(javascript)); |
| 368 } | 323 } |
| 369 | 324 |
| 370 void ShellDevToolsFrontend::SendMessageAck(int request_id, | 325 void ShellDevToolsBindings::SendMessageAck(int request_id, |
| 371 const base::Value* arg) { | 326 const base::Value* arg) { |
| 372 base::Value id_value(request_id); | 327 base::Value id_value(request_id); |
| 373 CallClientFunction("DevToolsAPI.embedderMessageAck", | 328 CallClientFunction("DevToolsAPI.embedderMessageAck", &id_value, arg, nullptr); |
| 374 &id_value, arg, nullptr); | |
| 375 } | 329 } |
| 376 | 330 |
| 377 void ShellDevToolsFrontend::AgentHostClosed( | 331 void ShellDevToolsBindings::AgentHostClosed(DevToolsAgentHost* agent_host, |
| 378 DevToolsAgentHost* agent_host, bool replaced) { | 332 bool replaced) { |
| 379 agent_host_ = nullptr; | 333 agent_host_ = nullptr; |
| 380 frontend_shell_->Close(); | 334 if (delegate_) |
| 335 delegate_->Close(); | |
| 381 } | 336 } |
| 382 | 337 |
| 383 } // namespace content | 338 } // namespace content |
| OLD | NEW |