Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2016 The Chromium Authors. All rights reserved. | 1 // Copyright 2016 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 <memory> | 5 #include <memory> |
| 6 #include <sstream> | 6 #include <sstream> |
| 7 #include <string> | 7 #include <string> |
| 8 | 8 |
| 9 #include "base/base64.h" | 9 #include "base/base64.h" |
| 10 #include "base/bind.h" | 10 #include "base/bind.h" |
| (...skipping 69 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 80 browser_->SetDefaultBrowserContext(browser_context_); | 80 browser_->SetDefaultBrowserContext(browser_context_); |
| 81 | 81 |
| 82 HeadlessWebContents::Builder builder( | 82 HeadlessWebContents::Builder builder( |
| 83 browser_context_->CreateWebContentsBuilder()); | 83 browser_context_->CreateWebContentsBuilder()); |
| 84 base::CommandLine::StringVector args = | 84 base::CommandLine::StringVector args = |
| 85 base::CommandLine::ForCurrentProcess()->GetArgs(); | 85 base::CommandLine::ForCurrentProcess()->GetArgs(); |
| 86 | 86 |
| 87 // TODO(alexclarke): Should we navigate to about:blank first if using | 87 // TODO(alexclarke): Should we navigate to about:blank first if using |
| 88 // virtual time? | 88 // virtual time? |
| 89 if (args.empty()) | 89 if (args.empty()) |
| 90 #if defined(OS_WIN) | |
| 91 args.push_back(L"about:blank"); | |
| 92 #else | |
| 90 args.push_back("about:blank"); | 93 args.push_back("about:blank"); |
| 94 #endif | |
| 91 for (auto it = args.rbegin(); it != args.rend(); ++it) { | 95 for (auto it = args.rbegin(); it != args.rend(); ++it) { |
| 92 GURL url(*it); | 96 GURL url(*it); |
| 93 HeadlessWebContents* web_contents = builder.SetInitialURL(url).Build(); | 97 HeadlessWebContents* web_contents = builder.SetInitialURL(url).Build(); |
| 94 if (!web_contents) { | 98 if (!web_contents) { |
| 95 LOG(ERROR) << "Navigation to " << url << " failed"; | 99 LOG(ERROR) << "Navigation to " << url << " failed"; |
| 96 browser_->Shutdown(); | 100 browser_->Shutdown(); |
| 97 return; | 101 return; |
| 98 } | 102 } |
| 99 if (!web_contents_ && !RemoteDebuggingEnabled()) { | 103 if (!web_contents_ && !RemoteDebuggingEnabled()) { |
| 100 // TODO(jzfeng): Support observing multiple targets. | 104 // TODO(jzfeng): Support observing multiple targets. |
| (...skipping 213 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 314 | 318 |
| 315 void HeadlessShell::OnScreenshotCaptured( | 319 void HeadlessShell::OnScreenshotCaptured( |
| 316 std::unique_ptr<page::CaptureScreenshotResult> result) { | 320 std::unique_ptr<page::CaptureScreenshotResult> result) { |
| 317 base::FilePath file_name = | 321 base::FilePath file_name = |
| 318 base::CommandLine::ForCurrentProcess()->GetSwitchValuePath( | 322 base::CommandLine::ForCurrentProcess()->GetSwitchValuePath( |
| 319 switches::kScreenshot); | 323 switches::kScreenshot); |
| 320 if (file_name.empty()) { | 324 if (file_name.empty()) { |
| 321 file_name = base::FilePath().AppendASCII(kDefaultScreenshotFileName); | 325 file_name = base::FilePath().AppendASCII(kDefaultScreenshotFileName); |
| 322 } | 326 } |
| 323 | 327 |
| 324 screenshot_file_stream_.reset( | 328 screenshot_file_proxy_.reset( |
| 325 new net::FileStream(browser_->BrowserFileThread())); | 329 new base::FileProxy(browser_->BrowserFileThread().get())); |
| 326 const int open_result = screenshot_file_stream_->Open( | 330 if (!screenshot_file_proxy_->CreateOrOpen( |
| 327 file_name, base::File::FLAG_CREATE_ALWAYS | base::File::FLAG_WRITE | | 331 file_name, base::File::FLAG_CREATE_ALWAYS | base::File::FLAG_WRITE, |
| 328 base::File::FLAG_ASYNC, | 332 base::Bind(&HeadlessShell::OnScreenshotFileOpened, |
| 329 base::Bind(&HeadlessShell::OnScreenshotFileOpened, | 333 weak_factory_.GetWeakPtr(), |
| 330 weak_factory_.GetWeakPtr(), base::Passed(std::move(result)), | 334 base::Passed(std::move(result)), file_name))) { |
| 331 file_name)); | |
| 332 if (open_result != net::ERR_IO_PENDING) { | |
| 333 // Operation could not be started. | 335 // Operation could not be started. |
| 334 OnScreenshotFileOpened(nullptr, file_name, open_result); | 336 OnScreenshotFileOpened(nullptr, file_name, base::File::FILE_ERROR_FAILED); |
| 335 } | 337 } |
| 336 } | 338 } |
| 337 | 339 |
| 338 void HeadlessShell::OnScreenshotFileOpened( | 340 void HeadlessShell::OnScreenshotFileOpened( |
| 339 std::unique_ptr<page::CaptureScreenshotResult> result, | 341 std::unique_ptr<page::CaptureScreenshotResult> result, |
| 340 const base::FilePath file_name, | 342 const base::FilePath file_name, |
| 341 const int open_result) { | 343 base::File::Error error_code) { |
| 342 if (open_result != net::OK) { | 344 if (!screenshot_file_proxy_->IsValid()) { |
| 343 LOG(ERROR) << "Writing screenshot to file " << file_name.value() | 345 LOG(ERROR) << "Writing screenshot to file " << file_name.value() |
| 344 << " was unsuccessful, could not open file: " | 346 << " was unsuccessful, could not open file: " |
| 345 << net::ErrorToString(open_result); | 347 << base::File::ErrorToString(error_code); |
| 346 return; | 348 return; |
| 347 } | 349 } |
| 348 | 350 |
| 349 std::string decoded_png; | 351 std::string decoded_png; |
| 350 base::Base64Decode(result->GetData(), &decoded_png); | 352 base::Base64Decode(result->GetData(), &decoded_png); |
| 351 scoped_refptr<net::IOBufferWithSize> buf = | 353 scoped_refptr<net::IOBufferWithSize> buf = |
| 352 new net::IOBufferWithSize(decoded_png.size()); | 354 new net::IOBufferWithSize(decoded_png.size()); |
| 353 memcpy(buf->data(), decoded_png.data(), decoded_png.size()); | 355 memcpy(buf->data(), decoded_png.data(), decoded_png.size()); |
| 354 const int write_result = screenshot_file_stream_->Write( | 356 LOG(ERROR) << "About to call write: " << screenshot_file_proxy_->IsValid(); |
|
Sami
2017/02/10 13:56:22
Probably don't want to land this :)
dvallet
2017/02/13 00:50:34
Good catch!
Probably not :)
| |
| 355 buf.get(), buf->size(), | 357 |
| 356 base::Bind(&HeadlessShell::OnScreenshotFileWritten, | 358 if (!screenshot_file_proxy_->Write( |
| 357 weak_factory_.GetWeakPtr(), file_name, buf->size())); | 359 0, buf->data(), buf->size(), |
| 358 if (write_result != net::ERR_IO_PENDING) { | 360 base::Bind(&HeadlessShell::OnScreenshotFileWritten, |
| 361 weak_factory_.GetWeakPtr(), file_name, buf->size()))) { | |
| 359 // Operation may have completed successfully or failed. | 362 // Operation may have completed successfully or failed. |
| 360 OnScreenshotFileWritten(file_name, buf->size(), write_result); | 363 OnScreenshotFileWritten(file_name, buf->size(), |
| 364 base::File::FILE_ERROR_FAILED, 0); | |
| 361 } | 365 } |
| 362 } | 366 } |
| 363 | 367 |
| 364 void HeadlessShell::OnScreenshotFileWritten(const base::FilePath file_name, | 368 void HeadlessShell::OnScreenshotFileWritten(const base::FilePath file_name, |
| 365 const int length, | 369 const int length, |
| 366 const int write_result) { | 370 base::File::Error error_code, |
| 371 int write_result) { | |
| 367 if (write_result < length) { | 372 if (write_result < length) { |
| 368 // TODO(eseckler): Support recovering from partial writes. | 373 // TODO(eseckler): Support recovering from partial writes. |
| 369 LOG(ERROR) << "Writing screenshot to file " << file_name.value() | 374 LOG(ERROR) << "Writing screenshot to file " << file_name.value() |
| 370 << " was unsuccessful: " << net::ErrorToString(write_result); | 375 << " was unsuccessful: " << net::ErrorToString(write_result); |
| 371 } else { | 376 } else { |
| 372 LOG(INFO) << "Screenshot written to file " << file_name.value() << "." | 377 LOG(INFO) << "Screenshot written to file " << file_name.value() << "." |
| 373 << std::endl; | 378 << std::endl; |
| 374 } | 379 } |
| 375 int close_result = screenshot_file_stream_->Close(base::Bind( | 380 if (!screenshot_file_proxy_->Close( |
| 376 &HeadlessShell::OnScreenshotFileClosed, weak_factory_.GetWeakPtr())); | 381 base::Bind(&HeadlessShell::OnScreenshotFileClosed, |
| 377 if (close_result != net::ERR_IO_PENDING) { | 382 weak_factory_.GetWeakPtr()))) { |
| 378 // Operation could not be started. | 383 // Operation could not be started. |
| 379 OnScreenshotFileClosed(close_result); | 384 OnScreenshotFileClosed(base::File::FILE_ERROR_FAILED); |
| 380 } | 385 } |
| 381 } | 386 } |
| 382 | 387 |
| 383 void HeadlessShell::OnScreenshotFileClosed(const int close_result) { | 388 void HeadlessShell::OnScreenshotFileClosed(base::File::Error error_code) { |
| 384 Shutdown(); | 389 Shutdown(); |
| 385 } | 390 } |
| 386 | 391 |
| 387 bool HeadlessShell::RemoteDebuggingEnabled() const { | 392 bool HeadlessShell::RemoteDebuggingEnabled() const { |
| 388 const base::CommandLine& command_line = | 393 const base::CommandLine& command_line = |
| 389 *base::CommandLine::ForCurrentProcess(); | 394 *base::CommandLine::ForCurrentProcess(); |
| 390 return command_line.HasSwitch(switches::kRemoteDebuggingPort); | 395 return command_line.HasSwitch(switches::kRemoteDebuggingPort); |
| 391 } | 396 } |
| 392 | 397 |
| 393 bool ValidateCommandLine(const base::CommandLine& command_line) { | 398 bool ValidateCommandLine(const base::CommandLine& command_line) { |
| (...skipping 112 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 506 builder.SetOverrideWebPreferencesCallback(base::Bind([]( | 511 builder.SetOverrideWebPreferencesCallback(base::Bind([]( |
| 507 WebPreferences* preferences) { preferences->hide_scrollbars = true; })); | 512 WebPreferences* preferences) { preferences->hide_scrollbars = true; })); |
| 508 } | 513 } |
| 509 | 514 |
| 510 return HeadlessBrowserMain( | 515 return HeadlessBrowserMain( |
| 511 builder.Build(), | 516 builder.Build(), |
| 512 base::Bind(&HeadlessShell::OnStart, base::Unretained(&shell))); | 517 base::Bind(&HeadlessShell::OnStart, base::Unretained(&shell))); |
| 513 } | 518 } |
| 514 | 519 |
| 515 } // namespace headless | 520 } // namespace headless |
| OLD | NEW |