Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(678)

Unified Diff: base/test/nslog_test_event_listener.mm

Issue 12047058: Add NSLogTestEventListener to support running tests on iOS 6 devices. (Closed) Base URL: http://git.chromium.org/chromium/src.git@master
Patch Set: one arg per line in declaration or definitions Created 7 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « base/test/nslog_test_event_listener.h ('k') | base/test/test_listener_ios.h » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: base/test/nslog_test_event_listener.mm
diff --git a/base/test/nslog_test_event_listener.mm b/base/test/nslog_test_event_listener.mm
new file mode 100644
index 0000000000000000000000000000000000000000..b55554e9565f60d961ad12c53d710367cb9ba43d
--- /dev/null
+++ b/base/test/nslog_test_event_listener.mm
@@ -0,0 +1,262 @@
+// Copyright 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 "base/test/nslog_test_event_listener.h"
+
+#import <Foundation/Foundation.h>
+
+#include "base/stringprintf.h"
+#include "base/sys_info.h"
+#include "testing/gtest/include/gtest/gtest.h"
+
+using testing::internal::StreamableToString;
+
+// The following static methods and TestEventListener implementation are largely
+// copied from gtest.cc, but have been refactored such that output goes to NSLog
+// instead of stdout (via printf).
+
+NSString* PrintTestName(const char* test_case, const char* test) {
+ return [NSString stringWithFormat:@"%s.%s", test_case, test];
+}
+
+// Formats a countable noun. Depending on its quantity, either the
+// singular form or the plural form is used. e.g.
+//
+// FormatCountableNoun(1, "formula", "formuli") returns "1 formula".
+// FormatCountableNoun(5, "book", "books") returns "5 books".
+static NSString* FormatCountableNoun(int count,
+ NSString* singular_form,
+ NSString* plural_form) {
+ return [NSString stringWithFormat:@"%d %@",
+ count, count == 1 ? singular_form : plural_form];
+}
+
+static NSString* FormatTestCount(int test_count) {
+ return FormatCountableNoun(test_count, @"test", @"tests");
+}
+
+static NSString* FormatTestCaseCount(int test_case_count) {
+ return FormatCountableNoun(test_case_count, @"test case", @"test cases");
+}
+
+// Converts a TestPartResult::Type enum to human-friendly string
+// representation. Both kNonFatalFailure and kFatalFailure are translated
+// to "Failure", as the user usually doesn't care about the difference
+// between the two when viewing the test result.
+static const char* TestPartResultTypeToString(
+ testing::TestPartResult::Type type) {
+ switch (type) {
+ case testing::TestPartResult::kSuccess:
+ return "Success";
+
+ case testing::TestPartResult::kNonFatalFailure:
+ case testing::TestPartResult::kFatalFailure:
+ return "Failure\n";
+ default:
+ return "Unknown result type";
+ }
+}
+
+// Prints a TestPartResult to an NSString*.
+static NSString* PrintTestPartResultToString(
+ const testing::TestPartResult& test_part_result) {
+ std::string message = (testing::Message()
+ << testing::internal::FormatFileLocation(test_part_result.file_name(),
+ test_part_result.line_number())
+ << " " << TestPartResultTypeToString(test_part_result.type())
+ << test_part_result.message()).GetString();
+ return [NSString stringWithFormat:@"%s", message.c_str()];
+}
+
+NSLogTestEventListener::NSLogTestEventListener() {
+}
+
+void NSLogTestEventListener::OnTestProgramStart(
+ const testing::UnitTest& /*unit_test*/) {
+}
+
+// Fired before each iteration of tests starts.
+void NSLogTestEventListener::OnTestIterationStart(
+ const testing::UnitTest& unit_test, int iteration) {
+ if (testing::GTEST_FLAG(repeat) != 1) {
+ NSLog(@"");
+ NSLog(@"Repeating all tests (iteration %d) . . .", iteration + 1);
+ NSLog(@"");
+ }
+
+ if (testing::GTEST_FLAG(shuffle)) {
+ NSLog(@"Note: Randomizing tests' orders with a seed of %d .",
+ unit_test.random_seed());
+ }
+
+ NSLog(@"[==========] Running %@ from %@.",
+ FormatTestCount(unit_test.test_to_run_count()),
+ FormatTestCaseCount(unit_test.test_case_to_run_count()));
+}
+
+void NSLogTestEventListener::OnEnvironmentsSetUpStart(
+ const testing::UnitTest& /*unit_test*/) {
+ NSLog(@"[----------] Global test environment set-up.");
+}
+
+void NSLogTestEventListener::OnEnvironmentsSetUpEnd(
+ const testing::UnitTest& /*unit_test*/) {
+}
+
+void NSLogTestEventListener::OnTestCaseStart(
+ const testing::TestCase& test_case) {
+ NSString* counts = FormatTestCount(test_case.test_to_run_count());
+ NSString* output = [NSString stringWithFormat:@"[----------] %@ from %s",
+ counts, test_case.name()];
+ if (test_case.type_param() != NULL) {
+ output = [output stringByAppendingFormat:@", where TypeParam = %s",
+ test_case.type_param()];
+ }
+ NSLog(@"%@", output);
+}
+
+void NSLogTestEventListener::OnTestStart(
+ const testing::TestInfo& test_info) {
+ NSLog(@"[ RUN ] %@",
+ PrintTestName(test_info.test_case_name(), test_info.name()));
+}
+
+// Called after an assertion failure.
+void NSLogTestEventListener::OnTestPartResult(
+ const testing::TestPartResult& result) {
+ // If the test part succeeded, we don't need to do anything.
+ if (result.type() == testing::TestPartResult::kSuccess)
+ return;
+
+ // Print failure message from the assertion (e.g. expected this and got that).
+ NSLog(@"%@", PrintTestPartResultToString(result));
+}
+
+void NSLogTestEventListener::OnTestEnd(
+ const testing::TestInfo& test_info) {
+ NSString* output = @"";
+ if (test_info.result()->Passed()) {
+ output = [output stringByAppendingString:@"[ OK ] "];
+ } else {
+ output = [output stringByAppendingString:@"[ FAILED ] "];
+ }
+ output = [output stringByAppendingString:
+ PrintTestName(test_info.test_case_name(), test_info.name())];
+ if (test_info.result()->Failed())
+ output = [output stringByAppendingString:
+ PrintFullTestCommentIfPresent(test_info)];
+
+ if (testing::GTEST_FLAG(print_time)) {
+ output = [output stringByAppendingFormat:@" (%s ms)",
+ StreamableToString(test_info.result()->elapsed_time()).c_str()];
+ }
+ NSLog(@"%@", output);
+}
+
+void NSLogTestEventListener::OnTestCaseEnd(
+ const testing::TestCase& test_case) {
+ if (!testing::GTEST_FLAG(print_time)) return;
+
+ NSString* counts = FormatTestCount(test_case.test_to_run_count());
+ NSLog(@"[----------] %@ from %s (%s ms total)",
+ counts, test_case.name(),
+ StreamableToString(test_case.elapsed_time()).c_str());
+ NSLog(@"");
+}
+
+void NSLogTestEventListener::OnEnvironmentsTearDownStart(
+ const testing::UnitTest& /*unit_test*/) {
+ NSLog(@"[----------] Global test environment tear-down");
+}
+
+// Internal helper for printing the list of failed tests.
+NSString* NSLogTestEventListener::PrintFailedTests(
+ const testing::UnitTest& unit_test) {
+ const int failed_test_count = unit_test.failed_test_count();
+ if (failed_test_count == 0) {
+ return @"";
+ }
+
+ NSString* output = @"";
+ for (int i = 0; i < unit_test.total_test_case_count(); ++i) {
+ const testing::TestCase& test_case = *unit_test.GetTestCase(i);
+ if (!test_case.should_run() || (test_case.failed_test_count() == 0)) {
+ continue;
+ }
+ for (int j = 0; j < test_case.total_test_count(); ++j) {
+ const testing::TestInfo& test_info = *test_case.GetTestInfo(j);
+ if (!test_info.should_run() || test_info.result()->Passed()) {
+ continue;
+ }
+ output = [output stringByAppendingFormat:@"[ FAILED ] %s.%s%@",
+ test_case.name(),
+ test_info.name(),
+ PrintFullTestCommentIfPresent(test_info)];
+ }
+ }
+ return output;
+}
+
+void NSLogTestEventListener::OnEnvironmentsTearDownEnd(
+ const testing::UnitTest& /*unit_test*/) {
+}
+
+NSString* NSLogTestEventListener::PrintFullTestCommentIfPresent(
+ const testing::TestInfo& test_info) {
+ const char* const type_param = test_info.type_param();
+ const char* const value_param = test_info.value_param();
+
+ NSString* comment = @"";
+ if (type_param != NULL || value_param != NULL) {
+ comment = [comment stringByAppendingString:@", where "];
+ if (type_param != NULL) {
+ comment = [comment stringByAppendingFormat:@"TypeParam = %s", type_param];
+ if (value_param != NULL)
+ comment = [comment stringByAppendingString:@" and "];
+ }
+ if (value_param != NULL) {
+ comment = [comment stringByAppendingFormat:
+ @"GetParam() = %s", value_param];
+ }
+ }
+ return comment;
+}
+
+void NSLogTestEventListener::OnTestIterationEnd(
+ const testing::UnitTest& unit_test, int /*iteration*/) {
+ NSString* output = [NSString stringWithFormat:@"[==========] %@ from %@ ran.",
+ FormatTestCount(unit_test.test_to_run_count()),
+ FormatTestCaseCount(unit_test.test_case_to_run_count())];
+ if (testing::GTEST_FLAG(print_time)) {
+ output = [output stringByAppendingFormat:@" (%s ms total)",
+ StreamableToString(unit_test.elapsed_time()).c_str()];
+ }
+ NSLog(@"%@", output);
+ NSLog(@"[ PASSED ] %@.",
+ FormatTestCount(unit_test.successful_test_count()));
+
+ int num_failures = unit_test.failed_test_count();
+ if (!unit_test.Passed()) {
+ const int failed_test_count = unit_test.failed_test_count();
+ NSLog(@"[ FAILED ] %@, listed below:",
+ FormatTestCount(failed_test_count));
+ NSLog(@"%@", PrintFailedTests(unit_test));
+ NSLog(@"");
+ NSLog(@"%2d FAILED %s", num_failures, num_failures == 1 ? "TEST" : "TESTS");
+ }
+
+ int num_disabled = unit_test.disabled_test_count();
+ if (num_disabled && !testing::GTEST_FLAG(also_run_disabled_tests)) {
+ if (!num_failures) {
+ NSLog(@""); // Add a spacer if no FAILURE banner is displayed.
+ }
+ NSLog(@" YOU HAVE %d DISABLED %s",
+ num_disabled, num_disabled == 1 ? "TEST" : "TESTS");
+ NSLog(@"");
+ }
+}
+
+void NSLogTestEventListener::OnTestProgramEnd(
+ const testing::UnitTest& /*unit_test*/) {
+}
« no previous file with comments | « base/test/nslog_test_event_listener.h ('k') | base/test/test_listener_ios.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698