From 8dafad32e63d4f8657aa88f0b17254d8a91727d6 Mon Sep 17 00:00:00 2001 From: "jochen@chromium.org" Date: Mon, 10 Dec 2012 14:11:45 +0000 Subject: [content shell] remove WebKitTestRunnerHost. Instead of having an observer per WebContents, only observe the main window. In a previous patch, all IPC messages were already routed to this one main window. Also, rename webkit_test_runner_host.* to webkit_test_controller.* BUG=111316 TEST=nothing breaks R=marja@chromium.org Review URL: https://chromiumcodereview.appspot.com/11494004 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@172054 0039d316-1c4b-4281-b951-d872f2087c98 --- content/shell/shell.cc | 2 +- content/shell/shell_browser_main.cc | 2 +- content/shell/shell_content_browser_client.cc | 9 +- content/shell/shell_content_browser_client.h | 2 - content/shell/shell_javascript_dialog_creator.cc | 2 +- content/shell/webkit_test_controller.cc | 386 +++++++++++++++++++++ content/shell/webkit_test_controller.h | 147 ++++++++ content/shell/webkit_test_runner_host.cc | 422 ----------------------- content/shell/webkit_test_runner_host.h | 181 ---------- 9 files changed, 537 insertions(+), 616 deletions(-) create mode 100644 content/shell/webkit_test_controller.cc create mode 100644 content/shell/webkit_test_controller.h delete mode 100644 content/shell/webkit_test_runner_host.cc delete mode 100644 content/shell/webkit_test_runner_host.h (limited to 'content/shell') diff --git a/content/shell/shell.cc b/content/shell/shell.cc index fd27d15..db6b856 100644 --- a/content/shell/shell.cc +++ b/content/shell/shell.cc @@ -26,7 +26,7 @@ #include "content/shell/shell_javascript_dialog_creator.h" #include "content/shell/shell_messages.h" #include "content/shell/shell_switches.h" -#include "content/shell/webkit_test_runner_host.h" +#include "content/shell/webkit_test_controller.h" #include "ui/gfx/size.h" // Content area size for newly created windows. diff --git a/content/shell/shell_browser_main.cc b/content/shell/shell_browser_main.cc index bfa2e0e..283617c 100644 --- a/content/shell/shell_browser_main.cc +++ b/content/shell/shell_browser_main.cc @@ -17,7 +17,7 @@ #include "base/utf_string_conversions.h" #include "content/public/browser/browser_main_runner.h" #include "content/shell/shell_switches.h" -#include "content/shell/webkit_test_runner_host.h" +#include "content/shell/webkit_test_controller.h" #include "net/base/net_util.h" #include "webkit/support/webkit_support.h" diff --git a/content/shell/shell_content_browser_client.cc b/content/shell/shell_content_browser_client.cc index 4019199..ee4fd62 100644 --- a/content/shell/shell_content_browser_client.cc +++ b/content/shell/shell_content_browser_client.cc @@ -18,7 +18,7 @@ #include "content/shell/shell_resource_dispatcher_host_delegate.h" #include "content/shell/shell_switches.h" #include "content/shell/shell_web_contents_view_delegate_creator.h" -#include "content/shell/webkit_test_runner_host.h" +#include "content/shell/webkit_test_controller.h" #include "googleurl/src/gurl.h" #include "webkit/glue/webpreferences.h" @@ -79,13 +79,6 @@ void ShellContentBrowserClient::RenderProcessHostCreated( host->Send(new ShellViewMsg_SetWebKitSourceDir(webkit_source_dir_)); } -void ShellContentBrowserClient::RenderViewHostCreated( - RenderViewHost* render_view_host) { - if (!CommandLine::ForCurrentProcess()->HasSwitch(switches::kDumpRenderTree)) - return; - new WebKitTestRunnerHost(render_view_host); -} - void ShellContentBrowserClient::AppendExtraCommandLineSwitches( CommandLine* command_line, int child_process_id) { if (CommandLine::ForCurrentProcess()->HasSwitch(switches::kDumpRenderTree)) diff --git a/content/shell/shell_content_browser_client.h b/content/shell/shell_content_browser_client.h index 06f6516..f5652a9 100644 --- a/content/shell/shell_content_browser_client.h +++ b/content/shell/shell_content_browser_client.h @@ -27,8 +27,6 @@ class ShellContentBrowserClient : public ContentBrowserClient { virtual BrowserMainParts* CreateBrowserMainParts( const MainFunctionParams& parameters) OVERRIDE; virtual void RenderProcessHostCreated(RenderProcessHost* host) OVERRIDE; - virtual void RenderViewHostCreated( - RenderViewHost* render_view_host) OVERRIDE; virtual void AppendExtraCommandLineSwitches(CommandLine* command_line, int child_process_id) OVERRIDE; virtual void OverrideWebkitPrefs(RenderViewHost* render_view_host, diff --git a/content/shell/shell_javascript_dialog_creator.cc b/content/shell/shell_javascript_dialog_creator.cc index 00342a4..6b97dc4 100644 --- a/content/shell/shell_javascript_dialog_creator.cc +++ b/content/shell/shell_javascript_dialog_creator.cc @@ -11,7 +11,7 @@ #include "content/public/browser/web_contents_view.h" #include "content/shell/shell_javascript_dialog.h" #include "content/shell/shell_switches.h" -#include "content/shell/webkit_test_runner_host.h" +#include "content/shell/webkit_test_controller.h" #include "net/base/net_util.h" namespace content { diff --git a/content/shell/webkit_test_controller.cc b/content/shell/webkit_test_controller.cc new file mode 100644 index 0000000..893ee31 --- /dev/null +++ b/content/shell/webkit_test_controller.cc @@ -0,0 +1,386 @@ +// Copyright (c) 2012 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 "content/shell/webkit_test_controller.h" + +#include + +#include "base/command_line.h" +#include "base/file_util.h" +#include "base/message_loop.h" +#include "base/run_loop.h" +#include "content/public/browser/navigation_controller.h" +#include "content/public/browser/render_view_host.h" +#include "content/public/browser/web_contents.h" +#include "content/shell/shell.h" +#include "content/shell/shell_browser_context.h" +#include "content/shell/shell_content_browser_client.h" +#include "content/shell/shell_messages.h" +#include "content/shell/shell_switches.h" +#include "webkit/support/webkit_support_gfx.h" + +namespace content { + +namespace { +const int kTestTimeoutMilliseconds = 30 * 1000; +} // namespace + +// WebKitTestResultPrinter ---------------------------------------------------- + +WebKitTestResultPrinter::WebKitTestResultPrinter( + std::ostream* output, std::ostream* error) + : state_(BEFORE_TEST), + capture_text_only_(false), + output_(output), + error_(error) { +} + +WebKitTestResultPrinter::~WebKitTestResultPrinter() { +} + +void WebKitTestResultPrinter::PrintTextHeader() { + DCHECK_EQ(state_, BEFORE_TEST); + if (!capture_text_only_) + *output_ << "Content-Type: text/plain\n"; + state_ = IN_TEXT_BLOCK; +} + +void WebKitTestResultPrinter::PrintTextBlock(const std::string& block) { + DCHECK_EQ(state_, IN_TEXT_BLOCK); + *output_ << block; +} + +void WebKitTestResultPrinter::PrintTextFooter() { + if (state_ != IN_TEXT_BLOCK) + return; + if (!capture_text_only_) { + *output_ << "#EOF\n"; + *error_ << "#EOF\n"; + output_->flush(); + error_->flush(); + } + state_ = IN_IMAGE_BLOCK; +} + +void WebKitTestResultPrinter::PrintImageHeader( + const std::string& actual_hash, + const std::string& expected_hash) { + if (state_ != IN_IMAGE_BLOCK || capture_text_only_) + return; + *output_ << "\nActualHash: " << actual_hash << "\n"; + if (!expected_hash.empty()) + *output_ << "\nExpectedHash: " << expected_hash << "\n"; +} + +void WebKitTestResultPrinter::PrintImageBlock( + const std::vector& png_image) { + if (state_ != IN_IMAGE_BLOCK || capture_text_only_) + return; + *output_ << "Content-Type: image/png\n"; + *output_ << "Content-Length: " << png_image.size() << "\n"; + output_->write( + reinterpret_cast(&png_image[0]), png_image.size()); +} + +void WebKitTestResultPrinter::PrintImageFooter() { + if (state_ != IN_IMAGE_BLOCK) + return; + if (!capture_text_only_) { + *output_ << "#EOF\n"; + output_->flush(); + } + state_ = AFTER_TEST; +} + +void WebKitTestResultPrinter::AddMessage(const std::string& message) { + AddMessageRaw(message + "\n"); +} + +void WebKitTestResultPrinter::AddMessageRaw(const std::string& message) { + if (state_ != IN_TEXT_BLOCK) + return; + *output_ << message; +} + +void WebKitTestResultPrinter::AddErrorMessage(const std::string& message) { + if (state_ != IN_TEXT_BLOCK) + return; + *output_ << message << "\n"; + if (!capture_text_only_) + *error_ << message << "\n"; + PrintTextFooter(); + PrintImageFooter(); + MessageLoop::current()->PostTask(FROM_HERE, MessageLoop::QuitClosure()); +} + +// WebKitTestController ------------------------------------------------------- + +WebKitTestController* WebKitTestController::instance_ = NULL; + +// static +WebKitTestController* WebKitTestController::Get() { + DCHECK(!instance_ || instance_->CalledOnValidThread()); + return instance_; +} + +WebKitTestController::WebKitTestController() { + CHECK(!instance_); + instance_ = this; + printer_.reset(new WebKitTestResultPrinter(&std::cout, &std::cerr)); + ResetAfterLayoutTest(); +} + +WebKitTestController::~WebKitTestController() { + DCHECK(CalledOnValidThread()); + CHECK(instance_ == this); + if (main_window_) + main_window_->Close(); + instance_ = NULL; +} + +bool WebKitTestController::PrepareForLayoutTest( + const GURL& test_url, + const FilePath& current_working_directory, + bool enable_pixel_dumping, + const std::string& expected_pixel_hash) { + DCHECK(CalledOnValidThread()); + current_working_directory_ = current_working_directory; + enable_pixel_dumping_ = enable_pixel_dumping; + expected_pixel_hash_ = expected_pixel_hash; + if (test_url.spec().find("/dumpAsText/") != std::string::npos || + test_url.spec().find("\\dumpAsText\\") != std::string::npos) { + dump_as_text_ = true; + enable_pixel_dumping_ = false; + } + printer_->reset(); + printer_->PrintTextHeader(); + content::ShellBrowserContext* browser_context = + static_cast( + content::GetContentClient()->browser())->browser_context(); + main_window_ = content::Shell::CreateNewWindow( + browser_context, + test_url, + NULL, + MSG_ROUTING_NONE, + NULL); + Observe(main_window_->web_contents()); + return true; +} + +bool WebKitTestController::ResetAfterLayoutTest() { + DCHECK(CalledOnValidThread()); + printer_->PrintTextFooter(); + printer_->PrintImageFooter(); + enable_pixel_dumping_ = false; + expected_pixel_hash_.clear(); + captured_dump_ = false; + dump_as_text_ = false; + dump_child_frames_ = false; + is_printing_ = false; + should_stay_on_page_after_handling_before_unload_ = false; + wait_until_done_ = false; + prefs_ = ShellWebPreferences(); + watchdog_.Cancel(); + if (main_window_) { + Observe(NULL); + main_window_ = NULL; + } + Shell::CloseAllWindows(); + Send(new ShellViewMsg_ResetAll); + return true; +} + +void WebKitTestController::RendererUnresponsive() { + if (!CommandLine::ForCurrentProcess()->HasSwitch(switches::kNoTimeout)) + printer_->AddErrorMessage("#PROCESS UNRESPONSIVE - renderer"); +} + +bool WebKitTestController::OnMessageReceived(const IPC::Message& message) { + bool handled = true; + IPC_BEGIN_MESSAGE_MAP(WebKitTestController, message) + IPC_MESSAGE_HANDLER(ShellViewHostMsg_DidFinishLoad, OnDidFinishLoad) + IPC_MESSAGE_HANDLER(ShellViewHostMsg_PrintMessage, OnPrintMessage) + IPC_MESSAGE_HANDLER(ShellViewHostMsg_TextDump, OnTextDump) + IPC_MESSAGE_HANDLER(ShellViewHostMsg_ImageDump, OnImageDump) + IPC_MESSAGE_HANDLER(ShellViewHostMsg_OverridePreferences, + OnOverridePreferences) + IPC_MESSAGE_HANDLER(ShellViewHostMsg_NotifyDone, OnNotifyDone) + IPC_MESSAGE_HANDLER(ShellViewHostMsg_DumpAsText, OnDumpAsText) + IPC_MESSAGE_HANDLER(ShellViewHostMsg_DumpChildFramesAsText, + OnDumpChildFramesAsText) + IPC_MESSAGE_HANDLER(ShellViewHostMsg_SetPrinting, OnSetPrinting) + IPC_MESSAGE_HANDLER( + ShellViewHostMsg_SetShouldStayOnPageAfterHandlingBeforeUnload, + OnSetShouldStayOnPageAfterHandlingBeforeUnload) + IPC_MESSAGE_HANDLER(ShellViewHostMsg_WaitUntilDone, OnWaitUntilDone) + IPC_MESSAGE_HANDLER(ShellViewHostMsg_NotImplemented, OnNotImplemented) + IPC_MESSAGE_UNHANDLED(handled = false) + IPC_END_MESSAGE_MAP() + + return handled; +} + +void WebKitTestController::PluginCrashed(const FilePath& plugin_path) { + printer_->AddErrorMessage("#CRASHED - plugin"); +} + +void WebKitTestController::RenderViewCreated(RenderViewHost* render_view_host) { + render_view_host->Send(new ShellViewMsg_SetCurrentWorkingDirectory( + render_view_host->GetRoutingID(), current_working_directory_)); +} + +void WebKitTestController::RenderViewGone(base::TerminationStatus status) { + if (status == base::TERMINATION_STATUS_PROCESS_CRASHED || + status == base::TERMINATION_STATUS_ABNORMAL_TERMINATION) { + printer_->AddErrorMessage("#CRASHED - renderer"); + } +} + +void WebKitTestController::WebContentsDestroyed(WebContents* web_contents) { + main_window_ = NULL; + printer_->AddErrorMessage("FAIL: main window was destroyed"); +} + +void WebKitTestController::CaptureDump() { + if (captured_dump_ || !main_window_ || !printer_->in_text_block()) + return; + captured_dump_ = true; + + RenderViewHost* render_view_host = + main_window_->web_contents()->GetRenderViewHost(); + + render_view_host->Send(new ShellViewMsg_CaptureTextDump( + render_view_host->GetRoutingID(), + dump_as_text_, + is_printing_, + dump_child_frames_)); + if (!dump_as_text_ && enable_pixel_dumping_) { + render_view_host->Send(new ShellViewMsg_CaptureImageDump( + render_view_host->GetRoutingID(), + expected_pixel_hash_)); + } +} + +void WebKitTestController::TimeoutHandler() { + printer_->AddErrorMessage( + "FAIL: Timed out waiting for notifyDone to be called"); +} + +void WebKitTestController::OnDidFinishLoad() { + if (wait_until_done_) + return; + CaptureDump(); +} + +void WebKitTestController::OnImageDump( + const std::string& actual_pixel_hash, + const SkBitmap& image) { + SkAutoLockPixels image_lock(image); + + printer_->PrintImageHeader(actual_pixel_hash, expected_pixel_hash_); + + // Only encode and dump the png if the hashes don't match. Encoding the + // image is really expensive. + if (actual_pixel_hash != expected_pixel_hash_) { + std::vector png; + + // Only the expected PNGs for Mac have a valid alpha channel. +#if defined(OS_MACOSX) + bool discard_transparency = false; +#else + bool discard_transparency = true; +#endif + + bool success = false; +#if defined(OS_ANDROID) + success = webkit_support::EncodeRGBAPNGWithChecksum( + reinterpret_cast(image.getPixels()), + image.width(), + image.height(), + static_cast(image.rowBytes()), + discard_transparency, + actual_pixel_hash, + &png); +#else + success = webkit_support::EncodeBGRAPNGWithChecksum( + reinterpret_cast(image.getPixels()), + image.width(), + image.height(), + static_cast(image.rowBytes()), + discard_transparency, + actual_pixel_hash, + &png); +#endif + if (success) + printer_->PrintImageBlock(png); + } + printer_->PrintImageFooter(); + MessageLoop::current()->PostTask(FROM_HERE, MessageLoop::QuitClosure()); +} + +void WebKitTestController::OnTextDump(const std::string& dump) { + printer_->PrintTextBlock(dump); + printer_->PrintTextFooter(); + if (dump_as_text_ || !enable_pixel_dumping_) { + printer_->PrintImageFooter(); + MessageLoop::current()->PostTask(FROM_HERE, MessageLoop::QuitClosure()); + } +} + +void WebKitTestController::OnPrintMessage(const std::string& message) { + printer_->AddMessageRaw(message); +} + +void WebKitTestController::OnOverridePreferences( + const ShellWebPreferences& prefs) { + prefs_ = prefs; +} + +void WebKitTestController::OnNotifyDone() { + if (!wait_until_done_) + return; + watchdog_.Cancel(); + CaptureDump(); +} + +void WebKitTestController::OnDumpAsText() { + dump_as_text_ = true; +} + +void WebKitTestController::OnSetPrinting() { + is_printing_ = true; +} + +void WebKitTestController::OnSetShouldStayOnPageAfterHandlingBeforeUnload( + bool should_stay_on_page) { + should_stay_on_page_after_handling_before_unload_ = should_stay_on_page; +} + +void WebKitTestController::OnDumpChildFramesAsText() { + dump_child_frames_ = true; +} + +void WebKitTestController::OnWaitUntilDone() { + if (wait_until_done_) + return; + if (!CommandLine::ForCurrentProcess()->HasSwitch(switches::kNoTimeout)) { + watchdog_.Reset(base::Bind(&WebKitTestController::TimeoutHandler, + base::Unretained(this))); + MessageLoop::current()->PostDelayedTask( + FROM_HERE, + watchdog_.callback(), + base::TimeDelta::FromMilliseconds(kTestTimeoutMilliseconds)); + } + wait_until_done_ = true; +} + +void WebKitTestController::OnNotImplemented( + const std::string& object_name, + const std::string& property_name) { + printer_->AddErrorMessage( + std::string("FAIL: NOT IMPLEMENTED: ") + + object_name + "." + property_name); +} + +} // namespace content diff --git a/content/shell/webkit_test_controller.h b/content/shell/webkit_test_controller.h new file mode 100644 index 0000000..03de47b --- /dev/null +++ b/content/shell/webkit_test_controller.h @@ -0,0 +1,147 @@ +// Copyright (c) 2012 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 CONTENT_SHELL_WEBKIT_TEST_CONTROLLER_H_ +#define CONTENT_SHELL_WEBKIT_TEST_CONTROLLER_H_ + +#include +#include + +#include "base/cancelable_callback.h" +#include "base/file_path.h" +#include "base/threading/non_thread_safe.h" +#include "content/public/browser/render_view_host_observer.h" +#include "content/public/browser/web_contents_observer.h" +#include "content/shell/shell_webpreferences.h" + +class SkBitmap; + +namespace content { + +class Shell; + +class WebKitTestResultPrinter { + public: + WebKitTestResultPrinter(std::ostream* output, std::ostream* error); + ~WebKitTestResultPrinter(); + + void reset() { + state_ = BEFORE_TEST; + } + bool in_text_block() const { return state_ == IN_TEXT_BLOCK; } + void set_capture_text_only(bool capture_text_only) { + capture_text_only_ = capture_text_only; + } + + void PrintTextHeader(); + void PrintTextBlock(const std::string& block); + void PrintTextFooter(); + + void PrintImageHeader(const std::string& actual_hash, + const std::string& expected_hash); + void PrintImageBlock(const std::vector& png_image); + void PrintImageFooter(); + + void AddMessage(const std::string& message); + void AddMessageRaw(const std::string& message); + void AddErrorMessage(const std::string& message); + + private: + enum State { + BEFORE_TEST, + IN_TEXT_BLOCK, + IN_IMAGE_BLOCK, + AFTER_TEST + }; + State state_; + bool capture_text_only_; + + std::ostream* output_; + std::ostream* error_; + + DISALLOW_COPY_AND_ASSIGN(WebKitTestResultPrinter); +}; + +class WebKitTestController : public base::NonThreadSafe, + public WebContentsObserver { + public: + static WebKitTestController* Get(); + + WebKitTestController(); + virtual ~WebKitTestController(); + + // True if the controller is ready for testing. + bool PrepareForLayoutTest(const GURL& test_url, + const FilePath& current_working_directory, + bool enable_pixel_dumping, + const std::string& expected_pixel_hash); + // True if the controller was reset successfully. + bool ResetAfterLayoutTest(); + + void RendererUnresponsive(); + + WebKitTestResultPrinter* printer() { return printer_.get(); } + void set_printer(WebKitTestResultPrinter* printer) { + printer_.reset(printer); + } + const ShellWebPreferences& web_preferences() const { return prefs_; } + bool should_stay_on_page_after_handling_before_unload() const { + return should_stay_on_page_after_handling_before_unload_; + } + + // WebContentsObserver implementation. + virtual bool OnMessageReceived(const IPC::Message& message) OVERRIDE; + virtual void PluginCrashed(const FilePath& plugin_path) OVERRIDE; + virtual void RenderViewCreated(RenderViewHost* render_view_host) OVERRIDE; + virtual void RenderViewGone(base::TerminationStatus status) OVERRIDE; + virtual void WebContentsDestroyed(WebContents* web_contents) OVERRIDE; + + private: + static WebKitTestController* instance_; + + void CaptureDump(); + void TimeoutHandler(); + + // Message handlers. + void OnDidFinishLoad(); + void OnImageDump(const std::string& actual_pixel_hash, const SkBitmap& image); + void OnTextDump(const std::string& dump); + void OnPrintMessage(const std::string& message); + void OnOverridePreferences(const ShellWebPreferences& prefs); + void OnNotifyDone(); + void OnDumpAsText(); + void OnDumpChildFramesAsText(); + void OnSetPrinting(); + void OnSetShouldStayOnPageAfterHandlingBeforeUnload(bool should_stay_on_page); + void OnWaitUntilDone(); + + void OnNotImplemented(const std::string& object_name, + const std::string& method_name); + + scoped_ptr printer_; + + FilePath current_working_directory_; + + Shell* main_window_; + + bool enable_pixel_dumping_; + std::string expected_pixel_hash_; + + bool captured_dump_; + + bool dump_as_text_; + bool dump_child_frames_; + bool is_printing_; + bool should_stay_on_page_after_handling_before_unload_; + bool wait_until_done_; + ShellWebPreferences prefs_; + + base::CancelableClosure watchdog_; + + DISALLOW_COPY_AND_ASSIGN(WebKitTestController); +}; + +} // namespace content + +#endif // CONTENT_SHELL_WEBKIT_TEST_CONTROLLER_H_ diff --git a/content/shell/webkit_test_runner_host.cc b/content/shell/webkit_test_runner_host.cc deleted file mode 100644 index 5eef32d..0000000 --- a/content/shell/webkit_test_runner_host.cc +++ /dev/null @@ -1,422 +0,0 @@ -// Copyright (c) 2012 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 "content/shell/webkit_test_runner_host.h" - -#include - -#include "base/command_line.h" -#include "base/file_util.h" -#include "base/message_loop.h" -#include "base/run_loop.h" -#include "content/public/browser/navigation_controller.h" -#include "content/public/browser/render_view_host.h" -#include "content/public/browser/web_contents.h" -#include "content/shell/shell.h" -#include "content/shell/shell_browser_context.h" -#include "content/shell/shell_content_browser_client.h" -#include "content/shell/shell_messages.h" -#include "content/shell/shell_switches.h" -#include "webkit/support/webkit_support_gfx.h" - -namespace content { - -namespace { -const int kTestTimeoutMilliseconds = 30 * 1000; -} // namespace - -// WebKitTestResultPrinter ---------------------------------------------------- - -WebKitTestResultPrinter::WebKitTestResultPrinter( - std::ostream* output, std::ostream* error) - : state_(BEFORE_TEST), - capture_text_only_(false), - output_(output), - error_(error) { -} - -WebKitTestResultPrinter::~WebKitTestResultPrinter() { -} - -void WebKitTestResultPrinter::PrintTextHeader() { - DCHECK_EQ(state_, BEFORE_TEST); - if (!capture_text_only_) - *output_ << "Content-Type: text/plain\n"; - state_ = IN_TEXT_BLOCK; -} - -void WebKitTestResultPrinter::PrintTextBlock(const std::string& block) { - DCHECK_EQ(state_, IN_TEXT_BLOCK); - *output_ << block; -} - -void WebKitTestResultPrinter::PrintTextFooter() { - if (state_ != IN_TEXT_BLOCK) - return; - if (!capture_text_only_) { - *output_ << "#EOF\n"; - *error_ << "#EOF\n"; - output_->flush(); - error_->flush(); - } - state_ = IN_IMAGE_BLOCK; -} - -void WebKitTestResultPrinter::PrintImageHeader( - const std::string& actual_hash, - const std::string& expected_hash) { - if (state_ != IN_IMAGE_BLOCK || capture_text_only_) - return; - *output_ << "\nActualHash: " << actual_hash << "\n"; - if (!expected_hash.empty()) - *output_ << "\nExpectedHash: " << expected_hash << "\n"; -} - -void WebKitTestResultPrinter::PrintImageBlock( - const std::vector& png_image) { - if (state_ != IN_IMAGE_BLOCK || capture_text_only_) - return; - *output_ << "Content-Type: image/png\n"; - *output_ << "Content-Length: " << png_image.size() << "\n"; - output_->write( - reinterpret_cast(&png_image[0]), png_image.size()); -} - -void WebKitTestResultPrinter::PrintImageFooter() { - if (state_ != IN_IMAGE_BLOCK) - return; - if (!capture_text_only_) { - *output_ << "#EOF\n"; - output_->flush(); - } - state_ = AFTER_TEST; -} - -void WebKitTestResultPrinter::AddMessage(const std::string& message) { - AddMessageRaw(message + "\n"); -} - -void WebKitTestResultPrinter::AddMessageRaw(const std::string& message) { - if (state_ != IN_TEXT_BLOCK) - return; - *output_ << message; -} - -void WebKitTestResultPrinter::AddErrorMessage(const std::string& message) { - if (state_ != IN_TEXT_BLOCK) - return; - *output_ << message << "\n"; - if (!capture_text_only_) - *error_ << message << "\n"; - PrintTextFooter(); - PrintImageFooter(); - MessageLoop::current()->PostTask(FROM_HERE, MessageLoop::QuitClosure()); -} - -// WebKitTestController ------------------------------------------------------- - -WebKitTestController* WebKitTestController::instance_ = NULL; - -// static -WebKitTestController* WebKitTestController::Get() { - DCHECK(!instance_ || instance_->CalledOnValidThread()); - return instance_; -} - -WebKitTestController::WebKitTestController() { - CHECK(!instance_); - instance_ = this; - printer_.reset(new WebKitTestResultPrinter(&std::cout, &std::cerr)); - ResetAfterLayoutTest(); -} - -WebKitTestController::~WebKitTestController() { - DCHECK(CalledOnValidThread()); - CHECK(instance_ == this); - if (main_window_) - main_window_->Close(); - instance_ = NULL; -} - -bool WebKitTestController::PrepareForLayoutTest( - const GURL& test_url, - const FilePath& current_working_directory, - bool enable_pixel_dumping, - const std::string& expected_pixel_hash) { - DCHECK(CalledOnValidThread()); - current_working_directory_ = current_working_directory; - enable_pixel_dumping_ = enable_pixel_dumping; - expected_pixel_hash_ = expected_pixel_hash; - if (test_url.spec().find("/dumpAsText/") != std::string::npos || - test_url.spec().find("\\dumpAsText\\") != std::string::npos) { - dump_as_text_ = true; - enable_pixel_dumping_ = false; - } - printer_->reset(); - printer_->PrintTextHeader(); - content::ShellBrowserContext* browser_context = - static_cast( - content::GetContentClient()->browser())->browser_context(); - main_window_ = content::Shell::CreateNewWindow( - browser_context, - test_url, - NULL, - MSG_ROUTING_NONE, - NULL); - Observe(main_window_->web_contents()); - return true; -} - -bool WebKitTestController::ResetAfterLayoutTest() { - DCHECK(CalledOnValidThread()); - printer_->PrintTextFooter(); - printer_->PrintImageFooter(); - enable_pixel_dumping_ = false; - expected_pixel_hash_.clear(); - captured_dump_ = false; - dump_as_text_ = false; - dump_child_frames_ = false; - is_printing_ = false; - should_stay_on_page_after_handling_before_unload_ = false; - wait_until_done_ = false; - prefs_ = ShellWebPreferences(); - watchdog_.Cancel(); - if (main_window_) { - Observe(NULL); - main_window_ = NULL; - } - Shell::CloseAllWindows(); - Send(new ShellViewMsg_ResetAll); - return true; -} - -void WebKitTestController::RendererUnresponsive() { - if (!CommandLine::ForCurrentProcess()->HasSwitch(switches::kNoTimeout)) - printer_->AddErrorMessage("#PROCESS UNRESPONSIVE - renderer"); -} - -void WebKitTestController::NotifyDone() { - if (!wait_until_done_) - return; - watchdog_.Cancel(); - CaptureDump(); -} - -void WebKitTestController::WaitUntilDone() { - if (wait_until_done_) - return; - if (!CommandLine::ForCurrentProcess()->HasSwitch(switches::kNoTimeout)) { - watchdog_.Reset(base::Bind(&WebKitTestController::TimeoutHandler, - base::Unretained(this))); - MessageLoop::current()->PostDelayedTask( - FROM_HERE, - watchdog_.callback(), - base::TimeDelta::FromMilliseconds(kTestTimeoutMilliseconds)); - } - wait_until_done_ = true; -} - -void WebKitTestController::NotImplemented( - const std::string& object_name, - const std::string& property_name) { - printer_->AddErrorMessage( - std::string("FAIL: NOT IMPLEMENTED: ") + - object_name + "." + property_name); -} - -bool WebKitTestController::OnMessageReceived(const IPC::Message& message) { - bool handled = true; - IPC_BEGIN_MESSAGE_MAP(WebKitTestController, message) - IPC_MESSAGE_HANDLER(ShellViewHostMsg_DidFinishLoad, OnDidFinishLoad) - IPC_MESSAGE_HANDLER(ShellViewHostMsg_PrintMessage, OnPrintMessage) - IPC_MESSAGE_HANDLER(ShellViewHostMsg_TextDump, OnTextDump) - IPC_MESSAGE_HANDLER(ShellViewHostMsg_ImageDump, OnImageDump) - IPC_MESSAGE_HANDLER(ShellViewHostMsg_OverridePreferences, - OnOverridePreferences) - IPC_MESSAGE_UNHANDLED(handled = false) - IPC_END_MESSAGE_MAP() - - return handled; -} - -void WebKitTestController::PluginCrashed(const FilePath& plugin_path) { - printer_->AddErrorMessage("#CRASHED - plugin"); -} - -void WebKitTestController::RenderViewCreated(RenderViewHost* render_view_host) { - render_view_host->Send(new ShellViewMsg_SetCurrentWorkingDirectory( - render_view_host->GetRoutingID(), current_working_directory_)); -} - -void WebKitTestController::RenderViewGone(base::TerminationStatus status) { - if (status == base::TERMINATION_STATUS_PROCESS_CRASHED || - status == base::TERMINATION_STATUS_ABNORMAL_TERMINATION) { - printer_->AddErrorMessage("#CRASHED - renderer"); - } -} - -void WebKitTestController::WebContentsDestroyed(WebContents* web_contents) { - main_window_ = NULL; - printer_->AddErrorMessage("FAIL: main window was destroyed"); -} - -void WebKitTestController::CaptureDump() { - if (captured_dump_ || !main_window_ || !printer_->in_text_block()) - return; - captured_dump_ = true; - - RenderViewHost* render_view_host = - main_window_->web_contents()->GetRenderViewHost(); - - render_view_host->Send(new ShellViewMsg_CaptureTextDump( - render_view_host->GetRoutingID(), - dump_as_text_, - is_printing_, - dump_child_frames_)); - if (!dump_as_text_ && enable_pixel_dumping_) { - render_view_host->Send(new ShellViewMsg_CaptureImageDump( - render_view_host->GetRoutingID(), - expected_pixel_hash_)); - } -} - -void WebKitTestController::TimeoutHandler() { - printer_->AddErrorMessage( - "FAIL: Timed out waiting for notifyDone to be called"); -} - -void WebKitTestController::OnDidFinishLoad() { - if (wait_until_done_) - return; - CaptureDump(); -} - -void WebKitTestController::OnImageDump( - const std::string& actual_pixel_hash, - const SkBitmap& image) { - SkAutoLockPixels image_lock(image); - - printer_->PrintImageHeader(actual_pixel_hash, expected_pixel_hash_); - - // Only encode and dump the png if the hashes don't match. Encoding the - // image is really expensive. - if (actual_pixel_hash != expected_pixel_hash_) { - std::vector png; - - // Only the expected PNGs for Mac have a valid alpha channel. -#if defined(OS_MACOSX) - bool discard_transparency = false; -#else - bool discard_transparency = true; -#endif - - bool success = false; -#if defined(OS_ANDROID) - success = webkit_support::EncodeRGBAPNGWithChecksum( - reinterpret_cast(image.getPixels()), - image.width(), - image.height(), - static_cast(image.rowBytes()), - discard_transparency, - actual_pixel_hash, - &png); -#else - success = webkit_support::EncodeBGRAPNGWithChecksum( - reinterpret_cast(image.getPixels()), - image.width(), - image.height(), - static_cast(image.rowBytes()), - discard_transparency, - actual_pixel_hash, - &png); -#endif - if (success) - printer_->PrintImageBlock(png); - } - printer_->PrintImageFooter(); - MessageLoop::current()->PostTask(FROM_HERE, MessageLoop::QuitClosure()); -} - -void WebKitTestController::OnTextDump(const std::string& dump) { - printer_->PrintTextBlock(dump); - printer_->PrintTextFooter(); - if (dump_as_text_ || !enable_pixel_dumping_) { - printer_->PrintImageFooter(); - MessageLoop::current()->PostTask(FROM_HERE, MessageLoop::QuitClosure()); - } -} - -void WebKitTestController::OnPrintMessage(const std::string& message) { - printer_->AddMessageRaw(message); -} - -void WebKitTestController::OnOverridePreferences( - const ShellWebPreferences& prefs) { - prefs_ = prefs; -} - -// WebKitTestRunnerHost ------------------------------------------------------- - -WebKitTestRunnerHost::WebKitTestRunnerHost( - RenderViewHost* render_view_host) - : RenderViewHostObserver(render_view_host) { -} - -WebKitTestRunnerHost::~WebKitTestRunnerHost() { -} - -bool WebKitTestRunnerHost::OnMessageReceived( - const IPC::Message& message) { - bool handled = true; - IPC_BEGIN_MESSAGE_MAP(WebKitTestRunnerHost, message) - IPC_MESSAGE_HANDLER(ShellViewHostMsg_NotifyDone, OnNotifyDone) - IPC_MESSAGE_HANDLER(ShellViewHostMsg_DumpAsText, OnDumpAsText) - IPC_MESSAGE_HANDLER(ShellViewHostMsg_DumpChildFramesAsText, - OnDumpChildFramesAsText) - IPC_MESSAGE_HANDLER(ShellViewHostMsg_SetPrinting, OnSetPrinting) - IPC_MESSAGE_HANDLER( - ShellViewHostMsg_SetShouldStayOnPageAfterHandlingBeforeUnload, - OnSetShouldStayOnPageAfterHandlingBeforeUnload) - IPC_MESSAGE_HANDLER(ShellViewHostMsg_WaitUntilDone, OnWaitUntilDone) - IPC_MESSAGE_HANDLER(ShellViewHostMsg_NotImplemented, OnNotImplemented) - IPC_MESSAGE_UNHANDLED(handled = false) - IPC_END_MESSAGE_MAP() - - return handled; -} - -void WebKitTestRunnerHost::OnNotifyDone() { - WebKitTestController::Get()->NotifyDone(); -} - -void WebKitTestRunnerHost::OnDumpAsText() { - WebKitTestController::Get()->set_dump_as_text(true); -} - -void WebKitTestRunnerHost::OnSetPrinting() { - WebKitTestController::Get()->set_is_printing(true); -} - -void WebKitTestRunnerHost::OnSetShouldStayOnPageAfterHandlingBeforeUnload( - bool should_stay_on_page) { - WebKitTestController* controller = WebKitTestController::Get(); - controller->set_should_stay_on_page_after_handling_before_unload( - should_stay_on_page); -} - -void WebKitTestRunnerHost::OnDumpChildFramesAsText() { - WebKitTestController::Get()->set_dump_child_frames(true); -} - -void WebKitTestRunnerHost::OnWaitUntilDone() { - WebKitTestController::Get()->WaitUntilDone(); -} - -void WebKitTestRunnerHost::OnNotImplemented( - const std::string& object_name, - const std::string& property_name) { - WebKitTestController::Get()->NotImplemented(object_name, property_name); -} - -} // namespace content diff --git a/content/shell/webkit_test_runner_host.h b/content/shell/webkit_test_runner_host.h deleted file mode 100644 index 596a910..0000000 --- a/content/shell/webkit_test_runner_host.h +++ /dev/null @@ -1,181 +0,0 @@ -// Copyright (c) 2012 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 CONTENT_SHELL_WEBKIT_TEST_RUNNER_HOST_H_ -#define CONTENT_SHELL_WEBKIT_TEST_RUNNER_HOST_H_ - -#include -#include - -#include "base/cancelable_callback.h" -#include "base/file_path.h" -#include "base/threading/non_thread_safe.h" -#include "content/public/browser/render_view_host_observer.h" -#include "content/public/browser/web_contents_observer.h" -#include "content/shell/shell_webpreferences.h" - -class SkBitmap; - -namespace content { - -class Shell; - -class WebKitTestResultPrinter { - public: - WebKitTestResultPrinter(std::ostream* output, std::ostream* error); - ~WebKitTestResultPrinter(); - - void reset() { - state_ = BEFORE_TEST; - } - bool in_text_block() const { return state_ == IN_TEXT_BLOCK; } - void set_capture_text_only(bool capture_text_only) { - capture_text_only_ = capture_text_only; - } - - void PrintTextHeader(); - void PrintTextBlock(const std::string& block); - void PrintTextFooter(); - - void PrintImageHeader(const std::string& actual_hash, - const std::string& expected_hash); - void PrintImageBlock(const std::vector& png_image); - void PrintImageFooter(); - - void AddMessage(const std::string& message); - void AddMessageRaw(const std::string& message); - void AddErrorMessage(const std::string& message); - - private: - enum State { - BEFORE_TEST, - IN_TEXT_BLOCK, - IN_IMAGE_BLOCK, - AFTER_TEST - }; - State state_; - bool capture_text_only_; - - std::ostream* output_; - std::ostream* error_; - - DISALLOW_COPY_AND_ASSIGN(WebKitTestResultPrinter); -}; - -class WebKitTestController : public base::NonThreadSafe, - public WebContentsObserver { - public: - static WebKitTestController* Get(); - - WebKitTestController(); - virtual ~WebKitTestController(); - - // True if the controller is ready for testing. - bool PrepareForLayoutTest(const GURL& test_url, - const FilePath& current_working_directory, - bool enable_pixel_dumping, - const std::string& expected_pixel_hash); - // True if the controller was reset successfully. - bool ResetAfterLayoutTest(); - - void RendererUnresponsive(); - - WebKitTestResultPrinter* printer() { return printer_.get(); } - void set_printer(WebKitTestResultPrinter* printer) { - printer_.reset(printer); - } - const ShellWebPreferences& web_preferences() const { return prefs_; } - - // Interface for WebKitTestRunnerHost. - void NotifyDone(); - void WaitUntilDone(); - void NotImplemented(const std::string& object_name, - const std::string& method_name); - - bool should_stay_on_page_after_handling_before_unload() const { - return should_stay_on_page_after_handling_before_unload_; - } - void set_should_stay_on_page_after_handling_before_unload( - bool should_stay_on_page_after_handling_before_unload) { - should_stay_on_page_after_handling_before_unload_ = - should_stay_on_page_after_handling_before_unload; - } - bool dump_as_text() const { return dump_as_text_; } - void set_dump_as_text(bool dump_as_text) { dump_as_text_ = dump_as_text; } - bool dump_child_frames() const { return dump_child_frames_; } - void set_dump_child_frames(bool dump_child_frames) { - dump_child_frames_ = dump_child_frames; - } - bool is_printing() const { return is_printing_; } - void set_is_printing(bool is_printing) { is_printing_ = is_printing; } - - // WebContentsObserver implementation. - virtual bool OnMessageReceived(const IPC::Message& message) OVERRIDE; - virtual void PluginCrashed(const FilePath& plugin_path) OVERRIDE; - virtual void RenderViewCreated(RenderViewHost* render_view_host) OVERRIDE; - virtual void RenderViewGone(base::TerminationStatus status) OVERRIDE; - virtual void WebContentsDestroyed(WebContents* web_contents) OVERRIDE; - - private: - static WebKitTestController* instance_; - - void CaptureDump(); - void TimeoutHandler(); - - // Message handlers. - void OnDidFinishLoad(); - void OnImageDump(const std::string& actual_pixel_hash, const SkBitmap& image); - void OnTextDump(const std::string& dump); - void OnPrintMessage(const std::string& message); - void OnOverridePreferences(const ShellWebPreferences& prefs); - - scoped_ptr printer_; - - FilePath current_working_directory_; - - Shell* main_window_; - - bool enable_pixel_dumping_; - std::string expected_pixel_hash_; - - bool captured_dump_; - - bool dump_as_text_; - bool dump_child_frames_; - bool is_printing_; - bool should_stay_on_page_after_handling_before_unload_; - bool wait_until_done_; - ShellWebPreferences prefs_; - - base::CancelableClosure watchdog_; - - DISALLOW_COPY_AND_ASSIGN(WebKitTestController); -}; - -class WebKitTestRunnerHost : public RenderViewHostObserver { - public: - explicit WebKitTestRunnerHost(RenderViewHost* render_view_host); - virtual ~WebKitTestRunnerHost(); - - // RenderViewHostObserver implementation. - virtual bool OnMessageReceived(const IPC::Message& message) OVERRIDE; - - private: - // testRunner handlers. - void OnNotifyDone(); - void OnDumpAsText(); - void OnDumpChildFramesAsText(); - void OnSetPrinting(); - void OnSetShouldStayOnPageAfterHandlingBeforeUnload(bool should_stay_on_page); - void OnWaitUntilDone(); - - void OnNotImplemented(const std::string& object_name, - const std::string& method_name); - - DISALLOW_COPY_AND_ASSIGN(WebKitTestRunnerHost); -}; - -} // namespace content - -#endif // CONTENT_SHELL_WEBKIT_TEST_RUNNER_HOST_H_ -- cgit v1.1