From 7bb9d0131ca5bfc7998922d05a15ec593c7f7f99 Mon Sep 17 00:00:00 2001 From: Timothy Flynn Date: Sun, 13 Oct 2024 09:23:27 -0400 Subject: [PATCH] headless-browser: Add a flag to log the slowest 10 LibWeb tests Useful for finding tests that take a long time to execute. As of this commit, on macOS, we have: Text/input/cookie.html: 1228ms Text/input/css/transition-basics.html: 1060ms Text/input/HTML/DedicatedWorkerGlobalScope-instanceof.html: 182ms Text/input/WebAnimations/misc/animation-events-basic.html: 148ms Text/input/Crypto/SubtleCrypto-deriveBits.html: 130ms Text/input/IntersectionObserver/observe-box-inside-container-with-scrollable-overflow.html: 117ms Text/input/navigation/attempt-navigating-object-without-a-document.html: 109ms Text/input/css/getComputedStyle-print-all.html: 71ms Text/input/WebAnimations/misc/animation-single-iteration-no-repeat.html: 61ms Text/input/WebAnimations/animation-methods/updatePlaybackRate.html: 55ms And on Linux: Text/input/cookie.html: 1326ms Text/input/css/transition-basics.html: 1155ms Screenshot/text-shadow.html: 772ms Screenshot/css-background-repeat.html: 622ms Screenshot/object-fit-position.html: 541ms Screenshot/css-background-position.html: 456ms Screenshot/css-gradients.html: 451ms Screenshot/border-radius.html: 400ms Screenshot/svg-radialGradient.html: 398ms Text/input/css/getComputedStyle-print-all.html: 325ms --- Ladybird/Headless/Application.cpp | 1 + Ladybird/Headless/Application.h | 1 + Ladybird/Headless/Test.cpp | 23 +++++++++++++++++++++++ Ladybird/Headless/Test.h | 4 ++++ 4 files changed, 29 insertions(+) diff --git a/Ladybird/Headless/Application.cpp b/Ladybird/Headless/Application.cpp index 58c4f60f723..ee209adbdf9 100644 --- a/Ladybird/Headless/Application.cpp +++ b/Ladybird/Headless/Application.cpp @@ -34,6 +34,7 @@ void Application::create_platform_arguments(Core::ArgsParser& args_parser) args_parser.add_option(resources_folder, "Path of the base resources folder (defaults to /res)", "resources", 'r', "resources-root-path"); args_parser.add_option(is_layout_test_mode, "Enable layout test mode", "layout-test-mode"); args_parser.add_option(rebaseline, "Rebaseline any executed layout or text tests", "rebaseline"); + args_parser.add_option(log_slowest_tests, "Log the tests with the slowest run times", "log-slowest-tests"); } void Application::create_platform_options(WebView::ChromeOptions& chrome_options, WebView::WebContentOptions& web_content_options) diff --git a/Ladybird/Headless/Application.h b/Ladybird/Headless/Application.h index 8b31185ec56..8027f122426 100644 --- a/Ladybird/Headless/Application.h +++ b/Ladybird/Headless/Application.h @@ -59,6 +59,7 @@ public: ByteString test_glob; bool test_dry_run { false }; bool rebaseline { false }; + bool log_slowest_tests { false }; private: RefPtr m_request_client; diff --git a/Ladybird/Headless/Test.cpp b/Ladybird/Headless/Test.cpp index 9fd1ee24137..e12b074ab76 100644 --- a/Ladybird/Headless/Test.cpp +++ b/Ladybird/Headless/Test.cpp @@ -8,6 +8,7 @@ #include #include #include +#include #include #include #include @@ -426,7 +427,9 @@ ErrorOr run_tests(Core::AnonymousBuffer const& theme, Gfx::IntSize window_ auto index = current_test++; if (index >= tests.size()) return; + auto& test = tests[index]; + test.start_time = UnixDateTime::now(); if (is_tty) { // Keep clearing and reusing the same line if stdout is a TTY. @@ -449,6 +452,8 @@ ErrorOr run_tests(Core::AnonymousBuffer const& theme, Gfx::IntSize window_ }; view.test_promise().when_resolved([&, run_next_test](auto result) { + result.test.end_time = UnixDateTime::now(); + switch (result.result) { case TestResult::Pass: ++pass_count; @@ -490,6 +495,24 @@ ErrorOr run_tests(Core::AnonymousBuffer const& theme, Gfx::IntSize window_ for (auto const& non_passing_test : non_passing_tests) outln("{}: {}", test_result_to_string(non_passing_test.result), non_passing_test.test.input_path); + if (app.log_slowest_tests) { + auto tests_to_print = min(10uz, tests.size()); + outln("\nSlowest {} tests:", tests_to_print); + + quick_sort(tests, [&](auto const& lhs, auto const& rhs) { + auto lhs_duration = lhs.end_time - lhs.start_time; + auto rhs_duration = rhs.end_time - rhs.start_time; + return lhs_duration > rhs_duration; + }); + + for (auto const& test : tests.span().trim(tests_to_print)) { + auto name = LexicalPath::relative_path(test.input_path, app.test_root_path); + auto duration = test.end_time - test.start_time; + + outln("{}: {}ms", name, duration.to_milliseconds()); + } + } + if (app.dump_gc_graph) { app.for_each_web_view([&](auto& view) { if (auto path = view.dump_gc_graph(); path.is_error()) diff --git a/Ladybird/Headless/Test.h b/Ladybird/Headless/Test.h index 709483515dd..3c629387ab7 100644 --- a/Ladybird/Headless/Test.h +++ b/Ladybird/Headless/Test.h @@ -12,6 +12,7 @@ #include #include #include +#include #include #include #include @@ -56,6 +57,9 @@ struct Test { ByteString input_path {}; ByteString expectation_path {}; + UnixDateTime start_time {}; + UnixDateTime end_time {}; + String text {}; bool did_finish_test { false }; bool did_finish_loading { false };