From 184175e62de2e389225f725b3c673e9eba533b9e Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Fri, 30 Nov 2018 14:54:17 +0100 Subject: [PATCH 01/51] Added ANSI dim colors --- phpunit.xml | 1 + src/TextUI/ResultPrinter.php | 35 +++++++++++++------------- src/Util/TestDox/CliTestDoxPrinter.php | 2 +- 3 files changed, 20 insertions(+), 18 deletions(-) diff --git a/phpunit.xml b/phpunit.xml index eb95d4c51fc..c17c90dea7e 100644 --- a/phpunit.xml +++ b/phpunit.xml @@ -3,6 +3,7 @@ xsi:noNamespaceSchemaLocation="phpunit.xsd" bootstrap="tests/bootstrap.php" executionOrder="depends" + colors="true" verbose="true"> diff --git a/src/TextUI/ResultPrinter.php b/src/TextUI/ResultPrinter.php index 2782f07cc1a..da7b6d6cd9f 100644 --- a/src/TextUI/ResultPrinter.php +++ b/src/TextUI/ResultPrinter.php @@ -51,23 +51,24 @@ class ResultPrinter extends Printer implements TestListener * @var array */ private static $ansiCodes = [ - 'bold' => 1, - 'fg-black' => 30, - 'fg-red' => 31, - 'fg-green' => 32, - 'fg-yellow' => 33, - 'fg-blue' => 34, - 'fg-magenta' => 35, - 'fg-cyan' => 36, - 'fg-white' => 37, - 'bg-black' => 40, - 'bg-red' => 41, - 'bg-green' => 42, - 'bg-yellow' => 43, - 'bg-blue' => 44, - 'bg-magenta' => 45, - 'bg-cyan' => 46, - 'bg-white' => 47, + 'bold' => '1', + 'dim' => '2', + 'fg-black' => '30', + 'fg-red' => '31', + 'fg-green' => '32', + 'fg-yellow' => '33', + 'fg-blue' => '34', + 'fg-magenta' => '35', + 'fg-cyan' => '36', + 'fg-white' => '37', + 'bg-black' => '40', + 'bg-red' => '41', + 'bg-green' => '42', + 'bg-yellow' => '43', + 'bg-blue' => '44', + 'bg-magenta' => '45', + 'bg-cyan' => '46', + 'bg-white' => '47', ]; /** diff --git a/src/Util/TestDox/CliTestDoxPrinter.php b/src/Util/TestDox/CliTestDoxPrinter.php index 217377e72cd..50753e17810 100644 --- a/src/Util/TestDox/CliTestDoxPrinter.php +++ b/src/Util/TestDox/CliTestDoxPrinter.php @@ -368,7 +368,7 @@ private function getFormattedRuntime(float $time): string return $this->formatWithColor('fg-yellow', \sprintf('[%.2f ms]', $time * 1000)); } - return \sprintf('[%.2f ms]', $time * 1000); + return $this->formatWithColor('dim', \sprintf('[%.2f ms]', $time * 1000)); } private function getFormattedAdditionalInformation(string $resultMessage, bool $verbose): string From 9c551e1c597bb7598dc9f9cd5e549528abf05755 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Mon, 3 Dec 2018 13:20:26 +0100 Subject: [PATCH 02/51] Use result success colors also to render test duration Switched to ANSI 8-color magenta for 'slow tests' for now. Will redesign this part of the result report later on --- src/TextUI/ResultPrinter.php | 2 +- src/Util/TestDox/CliTestDoxPrinter.php | 36 ++++++++++++++------------ 2 files changed, 21 insertions(+), 17 deletions(-) diff --git a/src/TextUI/ResultPrinter.php b/src/TextUI/ResultPrinter.php index da7b6d6cd9f..507609d703d 100644 --- a/src/TextUI/ResultPrinter.php +++ b/src/TextUI/ResultPrinter.php @@ -540,7 +540,7 @@ protected function formatWithColor(string $color, string $buffer): string $styles = []; foreach ($codes as $code) { - $styles[] = self::$ansiCodes[$code]; + $styles[] = self::$ansiCodes[$code] ?? ''; } $style = \sprintf("\x1b[%sm", \implode(';', $styles)); diff --git a/src/Util/TestDox/CliTestDoxPrinter.php b/src/Util/TestDox/CliTestDoxPrinter.php index 50753e17810..612772531a1 100644 --- a/src/Util/TestDox/CliTestDoxPrinter.php +++ b/src/Util/TestDox/CliTestDoxPrinter.php @@ -144,7 +144,8 @@ public function endTest(Test $test, float $time): void $this->nonSuccessfulTestResults[] = $this->testIndex; } else { $resultMessage = $this->formatTestResultMessage( - $this->formatWithColor('fg-green', '✔'), + 'fg-green', + '✔', '', $time, $this->verbose @@ -169,7 +170,8 @@ public function addError(Test $test, \Throwable $t, float $time): void { $this->lastTestFailed = true; $this->testResultMessage = $this->formatTestResultMessage( - $this->formatWithColor('fg-yellow', '✘'), + 'fg-yellow', + '✘', (string) $t, $time, true @@ -180,7 +182,8 @@ public function addWarning(Test $test, Warning $e, float $time): void { $this->lastTestFailed = true; $this->testResultMessage = $this->formatTestResultMessage( - $this->formatWithColor('fg-yellow', '✘'), + 'fg-yellow', + '✘', (string) $e, $time, true @@ -191,7 +194,8 @@ public function addFailure(Test $test, AssertionFailedError $e, float $time): vo { $this->lastTestFailed = true; $this->testResultMessage = $this->formatTestResultMessage( - $this->formatWithColor('fg-red', '✘'), + 'fg-red', + '✘', (string) $e, $time, true @@ -202,7 +206,8 @@ public function addIncompleteTest(Test $test, \Throwable $t, float $time): void { $this->lastTestFailed = true; $this->testResultMessage = $this->formatTestResultMessage( - $this->formatWithColor('fg-yellow', '∅'), + 'fg-yellow', + '∅', (string) $t, $time, false @@ -213,7 +218,8 @@ public function addRiskyTest(Test $test, \Throwable $t, float $time): void { $this->lastTestFailed = true; $this->testResultMessage = $this->formatTestResultMessage( - $this->formatWithColor('fg-yellow', '☢'), + 'fg-yellow', + '☢', (string) $t, $time, false @@ -224,7 +230,8 @@ public function addSkippedTest(Test $test, \Throwable $t, float $time): void { $this->lastTestFailed = true; $this->testResultMessage = $this->formatTestResultMessage( - $this->formatWithColor('fg-yellow', '→'), + 'fg-yellow', + '→', (string) $t, $time, false @@ -339,6 +346,7 @@ private function formatTestSuiteHeader(?string $lastClassName, string $className } private function formatTestResultMessage( + string $color, string $symbol, string $resultMessage, float $time, @@ -347,9 +355,9 @@ private function formatTestResultMessage( $additionalInformation = $this->getFormattedAdditionalInformation($resultMessage, $alwaysVerbose); $msg = \sprintf( " %s %s%s\n%s", - $symbol, + $this->formatWithColor($color, $symbol), $this->testMethod, - $this->verbose ? ' ' . $this->getFormattedRuntime($time) : '', + $this->verbose ? ' ' . $this->getFormattedRuntime($time, $color) : '', $additionalInformation ); @@ -358,17 +366,13 @@ private function formatTestResultMessage( return $msg; } - private function getFormattedRuntime(float $time): string + private function getFormattedRuntime(float $time, string $color = ''): string { - if ($time > 5) { - return $this->formatWithColor('fg-red', \sprintf('[%.2f ms]', $time * 1000)); - } - if ($time > 1) { - return $this->formatWithColor('fg-yellow', \sprintf('[%.2f ms]', $time * 1000)); + return $this->formatWithColor('fg-magenta', \sprintf('[%.2f ms]', $time * 1000)); } - return $this->formatWithColor('dim', \sprintf('[%.2f ms]', $time * 1000)); + return $this->formatWithColor($color, \sprintf('[%.2f ms]', $time * 1000)); } private function getFormattedAdditionalInformation(string $resultMessage, bool $verbose): string From 432c7c883264ba484ced04d357d61f890daf1f59 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Mon, 3 Dec 2018 21:48:36 +0100 Subject: [PATCH 03/51] Mirror test result color in verbose duration. Colorize stacktraces. --- src/Util/TestDox/CliTestDoxPrinter.php | 66 +++++++++++++++++++++++--- 1 file changed, 60 insertions(+), 6 deletions(-) diff --git a/src/Util/TestDox/CliTestDoxPrinter.php b/src/Util/TestDox/CliTestDoxPrinter.php index 612772531a1..04d4d8784c0 100644 --- a/src/Util/TestDox/CliTestDoxPrinter.php +++ b/src/Util/TestDox/CliTestDoxPrinter.php @@ -172,7 +172,7 @@ public function addError(Test $test, \Throwable $t, float $time): void $this->testResultMessage = $this->formatTestResultMessage( 'fg-yellow', '✘', - (string) $t, + $this->formatThrowable($t), $time, true ); @@ -184,7 +184,7 @@ public function addWarning(Test $test, Warning $e, float $time): void $this->testResultMessage = $this->formatTestResultMessage( 'fg-yellow', '✘', - (string) $e, + $this->formatThrowable($e), $time, true ); @@ -196,7 +196,7 @@ public function addFailure(Test $test, AssertionFailedError $e, float $time): vo $this->testResultMessage = $this->formatTestResultMessage( 'fg-red', '✘', - (string) $e, + $this->formatThrowable($e), $time, true ); @@ -208,7 +208,7 @@ public function addIncompleteTest(Test $test, \Throwable $t, float $time): void $this->testResultMessage = $this->formatTestResultMessage( 'fg-yellow', '∅', - (string) $t, + $this->formatThrowable($t), $time, false ); @@ -220,7 +220,7 @@ public function addRiskyTest(Test $test, \Throwable $t, float $time): void $this->testResultMessage = $this->formatTestResultMessage( 'fg-yellow', '☢', - (string) $t, + $this->formatThrowable($t), $time, false ); @@ -232,7 +232,7 @@ public function addSkippedTest(Test $test, \Throwable $t, float $time): void $this->testResultMessage = $this->formatTestResultMessage( 'fg-yellow', '→', - (string) $t, + $this->formatThrowable($t), $time, false ); @@ -430,4 +430,58 @@ private function getEmptyTestResult(): array 'verbose' => '', ]; } + + private function formatThrowable(\Throwable $t): string + { + return \sprintf( + "%s\n\n%s", + $t->getMessage(), + $this->colorizeStacktrace($t) + ); + } + + private function colorizeStacktrace(\Throwable $t): string + { + $trace = \PHPUnit\Util\Filter::getFilteredStacktrace($t); + + if (!$this->colors) { + return $trace; + } + + $lines = []; + $prevPath = ''; + + foreach (\explode("\n", $trace) as $line) { + if (\preg_match('/^(.*):(\d+)$/', $line, $matches)) { + $lines[] = $this->colorizePath($matches[1], $prevPath) . + $this->formatWithColor('dim', ':') . + $this->formatWithColor('fg-blue', $matches[2]) . + "\n"; + $prevPath = $matches[1]; + } else { + $lines[] = $line; + $prevPath = ''; + } + } + + return \implode('', $lines); + } + + private function colorizePath(string $path, ?string $prevPath): string + { + if ($prevPath === null) { + $prevPath = ''; + } + + $path = \explode(\DIRECTORY_SEPARATOR, $path); + $prevPath = \explode(\DIRECTORY_SEPARATOR, $prevPath); + + for ($i = 0; $i < \min(\count($path), \count($prevPath)); $i++) { + if ($path[$i] == $prevPath[$i]) { + $path[$i] = $this->formatWithColor('dim', $path[$i]); + } + } + + return \implode($this->formatWithColor('dim', \DIRECTORY_SEPARATOR), $path); + } } From d56e3148a844f843af00dc39fa1791b47c8535a0 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Mon, 3 Dec 2018 22:03:03 +0100 Subject: [PATCH 04/51] Use built-in pretty print for error messages --- src/Util/TestDox/CliTestDoxPrinter.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/Util/TestDox/CliTestDoxPrinter.php b/src/Util/TestDox/CliTestDoxPrinter.php index 04d4d8784c0..a1efd62619a 100644 --- a/src/Util/TestDox/CliTestDoxPrinter.php +++ b/src/Util/TestDox/CliTestDoxPrinter.php @@ -434,8 +434,8 @@ private function getEmptyTestResult(): array private function formatThrowable(\Throwable $t): string { return \sprintf( - "%s\n\n%s", - $t->getMessage(), + "%s\n%s", + \PHPUnit\Framework\TestFailure::exceptionToString($t), $this->colorizeStacktrace($t) ); } From 9ebba27cd0fddd1ffc6cb9d2bba3d0916ca4764e Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Tue, 4 Dec 2018 00:52:45 +0100 Subject: [PATCH 05/51] Underline test suite names --- src/TextUI/ResultPrinter.php | 1 + src/Util/TestDox/CliTestDoxPrinter.php | 4 ++-- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/src/TextUI/ResultPrinter.php b/src/TextUI/ResultPrinter.php index 507609d703d..08683eb52cb 100644 --- a/src/TextUI/ResultPrinter.php +++ b/src/TextUI/ResultPrinter.php @@ -53,6 +53,7 @@ class ResultPrinter extends Printer implements TestListener private static $ansiCodes = [ 'bold' => '1', 'dim' => '2', + 'underlined' => '4', 'fg-black' => '30', 'fg-red' => '31', 'fg-green' => '32', diff --git a/src/Util/TestDox/CliTestDoxPrinter.php b/src/Util/TestDox/CliTestDoxPrinter.php index a1efd62619a..e9c8e3dcb53 100644 --- a/src/Util/TestDox/CliTestDoxPrinter.php +++ b/src/Util/TestDox/CliTestDoxPrinter.php @@ -313,7 +313,7 @@ private function writeBufferTestResult(array $prevResult, array $result): void // Write suite header if ($prevResult['className'] !== $result['className']) { - $this->write($result['className'] . "\n"); + $this->write($this->formatWithColor('underlined', $result['className']) . "\n"); } // Write the test result itself @@ -337,7 +337,7 @@ private function formatTestSuiteHeader(?string $lastClassName, string $className return \sprintf( "%s%s\n%s", ($this->lastClassName !== '') ? "\n" : '', - $className, + $this->formatWithColor('underlined', $className), $msg ); } From 363a3cbbb17ab431f587450c2bc895f8c8d43cb4 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Thu, 6 Dec 2018 00:11:38 +0100 Subject: [PATCH 06/51] WIP refactoring TestDox CLI printer --- phpunit.xml | 1 + src/Util/TestDox/CliTestDoxPrinter.php | 238 +++++++++++++------------ 2 files changed, 125 insertions(+), 114 deletions(-) diff --git a/phpunit.xml b/phpunit.xml index c17c90dea7e..82bfb122799 100644 --- a/phpunit.xml +++ b/phpunit.xml @@ -2,6 +2,7 @@ diff --git a/src/Util/TestDox/CliTestDoxPrinter.php b/src/Util/TestDox/CliTestDoxPrinter.php index e9c8e3dcb53..9be9ca6c5b5 100644 --- a/src/Util/TestDox/CliTestDoxPrinter.php +++ b/src/Util/TestDox/CliTestDoxPrinter.php @@ -15,6 +15,7 @@ use PHPUnit\Framework\TestResult; use PHPUnit\Framework\TestSuite; use PHPUnit\Framework\Warning; +use PHPUnit\Runner\BaseTestRunner; use PHPUnit\Runner\PhptTestCase; use PHPUnit\Runner\TestSuiteSorter; use PHPUnit\TextUI\ResultPrinter; @@ -47,14 +48,19 @@ class CliTestDoxPrinter extends ResultPrinter private $testFlushIndex = 0; /** - * @var array Buffer for write() + * @var array Buffer for test results */ - private $outputBuffer = []; + private $testResults = []; + + /** + * @var array Lookup table for testname to testResults[index] + */ + private $testNameResultIndex = []; /** * @var bool */ - private $bufferExecutionOrder = false; + private $enableOutputBuffer = false; /** * @var array array @@ -76,10 +82,36 @@ class CliTestDoxPrinter extends ResultPrinter */ private $testMethod; - /** - * @var string Test result message of current test - */ - private $testResultMessage; + private $statusStyles = [ + BaseTestRunner::STATUS_PASSED => [ + 'symbol' => '✔', + 'color' => 'fg-green', + ], + BaseTestRunner::STATUS_ERROR => [ + 'symbol' => '✘', + 'color' => 'fg-yellow', + ], + BaseTestRunner::STATUS_FAILURE => [ + 'symbol' => '✘', + 'color' => 'fg-red', + ], + BaseTestRunner::STATUS_SKIPPED => [ + 'symbol' => '→', + 'color' => 'fg-yellow', + ], + BaseTestRunner::STATUS_RISKY => [ + 'symbol' => '☢', + 'color' => 'fg-yellow', + ], + BaseTestRunner::STATUS_INCOMPLETE => [ + 'symbol' => '∅', + 'color' => 'fg-yellow', + ], + BaseTestRunner::STATUS_WARNING => [ + 'symbol' => '✘', + 'color' => 'fg-yellow', + ], + ]; /** * @var bool Test result message of current test contains a verbose dump @@ -102,7 +134,7 @@ public function __construct( public function setOriginalExecutionOrder(array $order): void { $this->originalExecutionOrder = $order; - $this->bufferExecutionOrder = !empty($order); + $this->enableOutputBuffer = !empty($order); } public function startTest(Test $test): void @@ -111,9 +143,7 @@ public function startTest(Test $test): void return; } - $this->lastTestFailed = false; $this->lastClassName = $this->className; - $this->testResultMessage = ''; if ($test instanceof TestCase) { $className = $this->prettifier->prettifyTestClass(\get_class($test)); @@ -135,32 +165,18 @@ public function endTest(Test $test, float $time): void return; } - if ($test instanceof TestCase || $test instanceof PhptTestCase) { - $this->testIndex++; - } - - if ($this->lastTestFailed) { - $resultMessage = $this->testResultMessage; - $this->nonSuccessfulTestResults[] = $this->testIndex; - } else { + if ($this->testHasPassed()) { $resultMessage = $this->formatTestResultMessage( - 'fg-green', - '✔', '', - $time, $this->verbose ); + $this->registerTestResult($test, BaseTestRunner::STATUS_PASSED, $time, $resultMessage); } - if ($this->bufferExecutionOrder) { - $this->bufferTestResult($test, $resultMessage); - $this->flushOutputBuffer(); - } else { - $this->writeTestResult($resultMessage); + $this->flushOutputBuffer(); - if ($this->lastTestFailed) { - $this->bufferTestResult($test, $resultMessage); - } + if ($test instanceof TestCase || $test instanceof PhptTestCase) { + $this->testIndex++; } parent::endTest($test, $time); @@ -168,94 +184,84 @@ public function endTest(Test $test, float $time): void public function addError(Test $test, \Throwable $t, float $time): void { - $this->lastTestFailed = true; - $this->testResultMessage = $this->formatTestResultMessage( - 'fg-yellow', - '✘', + $resultMessage = $this->formatTestResultMessage( $this->formatThrowable($t), - $time, true ); + $this->registerTestResult($test, BaseTestRunner::STATUS_ERROR, $time, $resultMessage); } public function addWarning(Test $test, Warning $e, float $time): void { - $this->lastTestFailed = true; - $this->testResultMessage = $this->formatTestResultMessage( - 'fg-yellow', - '✘', + $resultMessage = $this->formatTestResultMessage( $this->formatThrowable($e), - $time, true ); + $this->registerTestResult($test, BaseTestRunner::STATUS_WARNING, $time, $resultMessage); } public function addFailure(Test $test, AssertionFailedError $e, float $time): void { - $this->lastTestFailed = true; - $this->testResultMessage = $this->formatTestResultMessage( - 'fg-red', - '✘', + $resultMessage = $this->formatTestResultMessage( $this->formatThrowable($e), - $time, true ); + $this->registerTestResult($test, BaseTestRunner::STATUS_FAILURE, $time, $resultMessage); } public function addIncompleteTest(Test $test, \Throwable $t, float $time): void { - $this->lastTestFailed = true; - $this->testResultMessage = $this->formatTestResultMessage( - 'fg-yellow', - '∅', + $resultMessage = $this->formatTestResultMessage( $this->formatThrowable($t), - $time, false ); + $this->registerTestResult($test, BaseTestRunner::STATUS_INCOMPLETE, $time, $resultMessage); } public function addRiskyTest(Test $test, \Throwable $t, float $time): void { - $this->lastTestFailed = true; - $this->testResultMessage = $this->formatTestResultMessage( - 'fg-yellow', - '☢', + $resultMessage = $this->formatTestResultMessage( $this->formatThrowable($t), - $time, false ); + $this->registerTestResult($test, BaseTestRunner::STATUS_RISKY, $time, $resultMessage); } public function addSkippedTest(Test $test, \Throwable $t, float $time): void { - $this->lastTestFailed = true; - $this->testResultMessage = $this->formatTestResultMessage( - 'fg-yellow', - '→', + $resultMessage = $this->formatTestResultMessage( $this->formatThrowable($t), - $time, false ); + $this->registerTestResult($test, BaseTestRunner::STATUS_SKIPPED, $time, $resultMessage); } - public function bufferTestResult(Test $test, string $msg): void + public function registerTestResult(Test $test, int $status, float $time, string $msg): void { - $this->outputBuffer[$this->testIndex] = [ + $testName = TestSuiteSorter::getTestSorterUID($test); + $this->testResults[$this->testIndex] = [ 'className' => $this->className, - 'testName' => TestSuiteSorter::getTestSorterUID($test), + 'testName' => $testName, 'testMethod' => $this->testMethod, 'message' => $msg, - 'failed' => $this->lastTestFailed, + 'status' => $status, 'verbose' => $this->lastFlushedTestWasVerbose, + 'time' => $time, ]; - } - public function writeTestResult(string $msg): void - { - $msg = $this->formatTestSuiteHeader($this->lastClassName, $this->className, $msg); - $this->write($msg); + $this->testNameResultIndex[$testName] = $this->testIndex; + + if ($status !== BaseTestRunner::STATUS_PASSED) { + $this->nonSuccessfulTestResults[] = $this->testIndex; + } } +// public function writeTestResult(string $msg): void +// { +// $msg = $this->formatTestSuiteHeader($this->lastClassName, $this->className, $msg); +// $this->write($msg); +// } +// public function writeProgress(string $progress): void { } @@ -278,32 +284,49 @@ protected function printHeader(): void $this->write("\n" . Timer::resourceUsage() . "\n\n"); } + private function testHasPassed(): bool + { + if (!isset($this->testResults[$this->testIndex]['status'])) { + return true; + } + + if ($this->testResults[$this->testIndex]['status'] === BaseTestRunner::STATUS_PASSED) { + return true; + } + + return false; + } + private function flushOutputBuffer(): void { - if ($this->testFlushIndex === $this->testIndex) { + if ($this->enableOutputBuffer && ($this->testFlushIndex === $this->testIndex)) { return; } if ($this->testFlushIndex > 0) { - $prevResult = $this->getTestResultByName($this->originalExecutionOrder[$this->testFlushIndex - 1]); + $prevResult = $this->testResults[$this->testFlushIndex - 1]; } else { $prevResult = $this->getEmptyTestResult(); } - do { - $flushed = false; - $result = $this->getTestResultByName($this->originalExecutionOrder[$this->testFlushIndex]); - - if (!empty($result)) { - $this->writeBufferTestResult($prevResult, $result); - $this->testFlushIndex++; - $prevResult = $result; - $flushed = true; - } - } while ($flushed && $this->testFlushIndex < $this->testIndex); + if (!$this->enableOutputBuffer) { + $this->writeTestResult($prevResult, $this->testResults[$this->testFlushIndex++]); + } else { + do { + $flushed = false; + $result = $this->getTestResultByName($this->originalExecutionOrder[$this->testFlushIndex]); + + if (!empty($result)) { + $this->writeTestResult($prevResult, $result); + $this->testFlushIndex++; + $prevResult = $result; + $flushed = true; + } + } while ($flushed && $this->testFlushIndex <= $this->testIndex); + } } - private function writeBufferTestResult(array $prevResult, array $result): void + private function writeTestResult(array $prevResult, array $result): void { // Write spacer line for new suite headers and after verbose messages if ($prevResult['testName'] !== '' && @@ -316,50 +339,37 @@ private function writeBufferTestResult(array $prevResult, array $result): void $this->write($this->formatWithColor('underlined', $result['className']) . "\n"); } - // Write the test result itself + // Write the test result line and additional information when verbose + if ($result['className'] == PhptTestCase::class) { + $testName = $this->colorizePath($result['testName'], $prevResult['testName']); + } else { + $testName = $result['testMethod']; + } + $style = $this->statusStyles[$result['status']]; + $line = \sprintf( + " %s %s%s\n", + $this->formatWithColor($style['color'], $style['symbol']), + $testName, + $this->verbose ? ' ' . $this->getFormattedRuntime($result['time'], $style['color']) : '' + ); + $this->write($line); $this->write($result['message']); } private function getTestResultByName(string $testName): array { - foreach ($this->outputBuffer as $result) { - if ($result['testName'] === $testName) { - return $result; - } + if (isset($this->testNameResultIndex[$testName])) { + return $this->testResults[$this->testNameResultIndex[$testName]]; } return []; } - private function formatTestSuiteHeader(?string $lastClassName, string $className, string $msg): string - { - if ($lastClassName === null || $className !== $lastClassName) { - return \sprintf( - "%s%s\n%s", - ($this->lastClassName !== '') ? "\n" : '', - $this->formatWithColor('underlined', $className), - $msg - ); - } - - return $msg; - } - private function formatTestResultMessage( - string $color, - string $symbol, string $resultMessage, - float $time, bool $alwaysVerbose = false ): string { - $additionalInformation = $this->getFormattedAdditionalInformation($resultMessage, $alwaysVerbose); - $msg = \sprintf( - " %s %s%s\n%s", - $this->formatWithColor($color, $symbol), - $this->testMethod, - $this->verbose ? ' ' . $this->getFormattedRuntime($time, $color) : '', - $additionalInformation - ); + $msg = $this->getFormattedAdditionalInformation($resultMessage, $alwaysVerbose); $this->lastFlushedTestWasVerbose = !empty($additionalInformation); @@ -414,8 +424,8 @@ private function printNonSuccessfulTestsSummary(int $numberOfExecutedTests): voi $prevResult = $this->getEmptyTestResult(); foreach ($this->nonSuccessfulTestResults as $testIndex) { - $result = $this->outputBuffer[$testIndex]; - $this->writeBufferTestResult($prevResult, $result); + $result = $this->testResults[$testIndex]; + $this->writeTestResult($prevResult, $result); $prevResult = $result; } } From ff663d1e6178f0bbdbd1eb950aafed0026685cdd Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Thu, 6 Dec 2018 11:07:53 +0100 Subject: [PATCH 07/51] Remove some dead code --- src/Util/TestDox/CliTestDoxPrinter.php | 13 ------------- 1 file changed, 13 deletions(-) diff --git a/src/Util/TestDox/CliTestDoxPrinter.php b/src/Util/TestDox/CliTestDoxPrinter.php index 9be9ca6c5b5..ff8ee236561 100644 --- a/src/Util/TestDox/CliTestDoxPrinter.php +++ b/src/Util/TestDox/CliTestDoxPrinter.php @@ -72,11 +72,6 @@ class CliTestDoxPrinter extends ResultPrinter */ private $className = ''; - /** - * @var string Classname of the previous test; empty for first test - */ - private $lastClassName = ''; - /** * @var string Prettified test name of current test */ @@ -143,8 +138,6 @@ public function startTest(Test $test): void return; } - $this->lastClassName = $this->className; - if ($test instanceof TestCase) { $className = $this->prettifier->prettifyTestClass(\get_class($test)); $testMethod = $this->prettifier->prettifyTestCase($test); @@ -256,12 +249,6 @@ public function registerTestResult(Test $test, int $status, float $time, string } } -// public function writeTestResult(string $msg): void -// { -// $msg = $this->formatTestSuiteHeader($this->lastClassName, $this->className, $msg); -// $this->write($msg); -// } -// public function writeProgress(string $progress): void { } From 50693bb9ffd767ee4ac3b0c979c5e32f92cb84bb Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Thu, 6 Dec 2018 15:18:38 +0100 Subject: [PATCH 08/51] Remove obsolete code for handling TestSuite setup failures --- src/Util/TestDox/CliTestDoxPrinter.php | 11 ++++------- 1 file changed, 4 insertions(+), 7 deletions(-) diff --git a/src/Util/TestDox/CliTestDoxPrinter.php b/src/Util/TestDox/CliTestDoxPrinter.php index ff8ee236561..9ac696e08ee 100644 --- a/src/Util/TestDox/CliTestDoxPrinter.php +++ b/src/Util/TestDox/CliTestDoxPrinter.php @@ -139,16 +139,13 @@ public function startTest(Test $test): void } if ($test instanceof TestCase) { - $className = $this->prettifier->prettifyTestClass(\get_class($test)); - $testMethod = $this->prettifier->prettifyTestCase($test); + $this->className = $this->prettifier->prettifyTestClass(\get_class($test)); + $this->testMethod = $this->prettifier->prettifyTestCase($test); } elseif ($test instanceof PhptTestCase) { - $className = \get_class($test); - $testMethod = $test->getName(); + $this->className = \get_class($test); + $this->testMethod = $test->getName(); } - $this->className = $className; - $this->testMethod = $testMethod; - parent::startTest($test); } From 4d0ec36f46f69fa5290430d9e7d9bb2673978b1b Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Fri, 7 Dec 2018 00:10:03 +0100 Subject: [PATCH 09/51] WIP refactor TestDox printer to allow for prettier output --- src/Util/TestDox/CliTestDoxPrinter.php | 92 ++++++++++---------------- src/Util/TestDox/NamePrettifier.php | 10 +++ 2 files changed, 44 insertions(+), 58 deletions(-) diff --git a/src/Util/TestDox/CliTestDoxPrinter.php b/src/Util/TestDox/CliTestDoxPrinter.php index 9ac696e08ee..0b2dd9b76bf 100644 --- a/src/Util/TestDox/CliTestDoxPrinter.php +++ b/src/Util/TestDox/CliTestDoxPrinter.php @@ -67,16 +67,6 @@ class CliTestDoxPrinter extends ResultPrinter */ private $originalExecutionOrder = []; - /** - * @var string Classname of the current test - */ - private $className = ''; - - /** - * @var string Prettified test name of current test - */ - private $testMethod; - private $statusStyles = [ BaseTestRunner::STATUS_PASSED => [ 'symbol' => '✔', @@ -108,11 +98,6 @@ class CliTestDoxPrinter extends ResultPrinter ], ]; - /** - * @var bool Test result message of current test contains a verbose dump - */ - private $lastFlushedTestWasVerbose = false; - public function __construct( $out = null, bool $verbose = false, @@ -123,7 +108,7 @@ public function __construct( ) { parent::__construct($out, $verbose, $colors, $debug, $numberOfColumns, $reverse); - $this->prettifier = new NamePrettifier; + $this->prettifier = new NamePrettifier($colors); } public function setOriginalExecutionOrder(array $order): void @@ -132,23 +117,6 @@ public function setOriginalExecutionOrder(array $order): void $this->enableOutputBuffer = !empty($order); } - public function startTest(Test $test): void - { - if (!$test instanceof TestCase && !$test instanceof PhptTestCase && !$test instanceof TestSuite) { - return; - } - - if ($test instanceof TestCase) { - $this->className = $this->prettifier->prettifyTestClass(\get_class($test)); - $this->testMethod = $this->prettifier->prettifyTestCase($test); - } elseif ($test instanceof PhptTestCase) { - $this->className = \get_class($test); - $this->testMethod = $test->getName(); - } - - parent::startTest($test); - } - public function endTest(Test $test, float $time): void { if (!$test instanceof TestCase && !$test instanceof PhptTestCase && !$test instanceof TestSuite) { @@ -156,11 +124,7 @@ public function endTest(Test $test, float $time): void } if ($this->testHasPassed()) { - $resultMessage = $this->formatTestResultMessage( - '', - $this->verbose - ); - $this->registerTestResult($test, BaseTestRunner::STATUS_PASSED, $time, $resultMessage); + $this->registerTestResult($test, BaseTestRunner::STATUS_PASSED, $time, ''); } $this->flushOutputBuffer(); @@ -230,12 +194,11 @@ public function registerTestResult(Test $test, int $status, float $time, string { $testName = TestSuiteSorter::getTestSorterUID($test); $this->testResults[$this->testIndex] = [ - 'className' => $this->className, + 'className' => $this->getPrettyClassName($test), 'testName' => $testName, - 'testMethod' => $this->testMethod, + 'testMethod' => $this->getPrettyTestName($test), 'message' => $msg, 'status' => $status, - 'verbose' => $this->lastFlushedTestWasVerbose, 'time' => $time, ]; @@ -268,6 +231,24 @@ protected function printHeader(): void $this->write("\n" . Timer::resourceUsage() . "\n\n"); } + private function getPrettyClassName(Test $test): string + { + if ($test instanceof TestCase) { + return $this->prettifier->prettifyTestClass(\get_class($test)); + } + + return \get_class($test); + } + + private function getPrettyTestName(Test $test): string + { + if ($test instanceof TestCase) { + return $this->prettifier->prettifyTestCase($test); + } + + return $test->getName(); + } + private function testHasPassed(): bool { if (!isset($this->testResults[$this->testIndex]['status'])) { @@ -288,7 +269,11 @@ private function flushOutputBuffer(): void } if ($this->testFlushIndex > 0) { - $prevResult = $this->testResults[$this->testFlushIndex - 1]; + if ($this->enableOutputBuffer) { + $prevResult = $this->getTestResultByName($this->originalExecutionOrder[$this->testFlushIndex - 1]); + } else { + $prevResult = $this->testResults[$this->testFlushIndex - 1]; + } } else { $prevResult = $this->getEmptyTestResult(); } @@ -312,18 +297,18 @@ private function flushOutputBuffer(): void private function writeTestResult(array $prevResult, array $result): void { - // Write spacer line for new suite headers and after verbose messages + // spacer line for new suite headers and after verbose messages if ($prevResult['testName'] !== '' && - ($prevResult['verbose'] === true || $prevResult['className'] !== $result['className'])) { + (!empty($prevResult['message']) || $prevResult['className'] !== $result['className'])) { $this->write("\n"); } - // Write suite header + // suite header if ($prevResult['className'] !== $result['className']) { $this->write($this->formatWithColor('underlined', $result['className']) . "\n"); } - // Write the test result line and additional information when verbose + // test result line if ($result['className'] == PhptTestCase::class) { $testName = $this->colorizePath($result['testName'], $prevResult['testName']); } else { @@ -337,6 +322,8 @@ private function writeTestResult(array $prevResult, array $result): void $this->verbose ? ' ' . $this->getFormattedRuntime($result['time'], $style['color']) : '' ); $this->write($line); + + // additional information when verbose $this->write($result['message']); } @@ -349,17 +336,6 @@ private function getTestResultByName(string $testName): array return []; } - private function formatTestResultMessage( - string $resultMessage, - bool $alwaysVerbose = false - ): string { - $msg = $this->getFormattedAdditionalInformation($resultMessage, $alwaysVerbose); - - $this->lastFlushedTestWasVerbose = !empty($additionalInformation); - - return $msg; - } - private function getFormattedRuntime(float $time, string $color = ''): string { if ($time > 1) { @@ -369,7 +345,7 @@ private function getFormattedRuntime(float $time, string $color = ''): string return $this->formatWithColor($color, \sprintf('[%.2f ms]', $time * 1000)); } - private function getFormattedAdditionalInformation(string $resultMessage, bool $verbose): string + private function formatTestResultMessage(string $resultMessage, bool $verbose): string { if ($resultMessage === '') { return ''; diff --git a/src/Util/TestDox/NamePrettifier.php b/src/Util/TestDox/NamePrettifier.php index fc5a1fe4a53..cc3d11ef6c4 100644 --- a/src/Util/TestDox/NamePrettifier.php +++ b/src/Util/TestDox/NamePrettifier.php @@ -22,6 +22,16 @@ final class NamePrettifier */ private $strings = []; + /** + * @var bool + */ + private $useColor; + + public function __construct($useColor = false) + { + $this->useColor = $useColor; + } + /** * Prettifies the name of a test class. */ From 1a46f392faa326eae9e529a65ac8b4b625c05eb1 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Fri, 7 Dec 2018 00:50:32 +0100 Subject: [PATCH 10/51] Make basic ANSI colors available in NamePrettifier. Colorize data sets. --- src/TextUI/ResultPrinter.php | 35 +---------------- src/Util/TestDox/CliTestDoxPrinter.php | 2 +- src/Util/TestDox/Color.php | 52 ++++++++++++++++++++++++++ src/Util/TestDox/NamePrettifier.php | 19 +++++++++- 4 files changed, 73 insertions(+), 35 deletions(-) create mode 100644 src/Util/TestDox/Color.php diff --git a/src/TextUI/ResultPrinter.php b/src/TextUI/ResultPrinter.php index 08683eb52cb..97ada83b0c3 100644 --- a/src/TextUI/ResultPrinter.php +++ b/src/TextUI/ResultPrinter.php @@ -21,6 +21,7 @@ use PHPUnit\Runner\PhptTestCase; use PHPUnit\Util\InvalidArgumentHelper; use PHPUnit\Util\Printer; +use PHPUnit\Util\TestDox\Color; use SebastianBergmann\Environment\Console; use SebastianBergmann\Timer\Timer; @@ -47,31 +48,6 @@ class ResultPrinter extends Printer implements TestListener private const AVAILABLE_COLORS = [self::COLOR_NEVER, self::COLOR_AUTO, self::COLOR_ALWAYS]; - /** - * @var array - */ - private static $ansiCodes = [ - 'bold' => '1', - 'dim' => '2', - 'underlined' => '4', - 'fg-black' => '30', - 'fg-red' => '31', - 'fg-green' => '32', - 'fg-yellow' => '33', - 'fg-blue' => '34', - 'fg-magenta' => '35', - 'fg-cyan' => '36', - 'fg-white' => '37', - 'bg-black' => '40', - 'bg-red' => '41', - 'bg-green' => '42', - 'bg-yellow' => '43', - 'bg-blue' => '44', - 'bg-magenta' => '45', - 'bg-cyan' => '46', - 'bg-white' => '47', - ]; - /** * @var int */ @@ -535,21 +511,14 @@ protected function formatWithColor(string $color, string $buffer): string return $buffer; } - $codes = \array_map('\trim', \explode(',', $color)); $lines = \explode("\n", $buffer); $padding = \max(\array_map('\strlen', $lines)); $styles = []; - foreach ($codes as $code) { - $styles[] = self::$ansiCodes[$code] ?? ''; - } - - $style = \sprintf("\x1b[%sm", \implode(';', $styles)); - $styledLines = []; foreach ($lines as $line) { - $styledLines[] = $style . \str_pad($line, $padding) . "\x1b[0m"; + $styledLines[] = Color::colorize($color, \str_pad($line, $padding)); } return \implode("\n", $styledLines); diff --git a/src/Util/TestDox/CliTestDoxPrinter.php b/src/Util/TestDox/CliTestDoxPrinter.php index 0b2dd9b76bf..7f52509658b 100644 --- a/src/Util/TestDox/CliTestDoxPrinter.php +++ b/src/Util/TestDox/CliTestDoxPrinter.php @@ -108,7 +108,7 @@ public function __construct( ) { parent::__construct($out, $verbose, $colors, $debug, $numberOfColumns, $reverse); - $this->prettifier = new NamePrettifier($colors); + $this->prettifier = new NamePrettifier($this->colors); } public function setOriginalExecutionOrder(array $order): void diff --git a/src/Util/TestDox/Color.php b/src/Util/TestDox/Color.php new file mode 100644 index 00000000000..7d90565196e --- /dev/null +++ b/src/Util/TestDox/Color.php @@ -0,0 +1,52 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ +namespace PHPUnit\Util\TestDox; + +class Color +{ + /** + * @var array + */ + private static $ansiCodes = [ + 'reset' => '0', + 'bold' => '1', + 'dim' => '2', + 'underlined' => '4', + 'fg-black' => '30', + 'fg-red' => '31', + 'fg-green' => '32', + 'fg-yellow' => '33', + 'fg-blue' => '34', + 'fg-magenta' => '35', + 'fg-cyan' => '36', + 'fg-white' => '37', + 'bg-black' => '40', + 'bg-red' => '41', + 'bg-green' => '42', + 'bg-yellow' => '43', + 'bg-blue' => '44', + 'bg-magenta' => '45', + 'bg-cyan' => '46', + 'bg-white' => '47', + ]; + + public static function colorize(string $color, string $buffer): string + { + $codes = \array_map('\trim', \explode(',', $color)); + + foreach ($codes as $code) { + $styles[] = self::$ansiCodes[$code] ?? ''; + } + + $style = \sprintf("\x1b[%sm", \implode(';', $styles)); + + return $style . $buffer . "\x1b[0m"; + } +} diff --git a/src/Util/TestDox/NamePrettifier.php b/src/Util/TestDox/NamePrettifier.php index cc3d11ef6c4..24dd1ea88d6 100644 --- a/src/Util/TestDox/NamePrettifier.php +++ b/src/Util/TestDox/NamePrettifier.php @@ -94,12 +94,29 @@ public function prettifyTestCase(TestCase $test): string } if ($test->usesDataProvider() && !$annotationWithPlaceholders) { - $result .= $test->getDataSetAsString(false); + $result .= $this->prettifyDataSet($test); } return $result; } + public function prettifyDataSet(TestCase $test): string + { + $data = $test->getDataSetAsString(false); + + if (!$this->useColor) { + return $data; + } + + return \preg_replace_callback( + '/(with data set )(.*)/', + function ($matches) { + return Color::colorize('dim', $matches[1] . Color::colorize('fg-cyan', $matches[2])); + }, + $data + ); + } + /** * Prettifies the name of a test method. */ From bd59324a996c8b282f72809cc0a2407332e1d3e3 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Fri, 7 Dec 2018 01:12:57 +0100 Subject: [PATCH 11/51] Refactor colorization --- src/Util/TestDox/CliTestDoxPrinter.php | 26 ++++---------------------- src/Util/TestDox/Color.php | 19 +++++++++++++++++++ src/Util/TestDox/NamePrettifier.php | 23 +++++++++++++---------- 3 files changed, 36 insertions(+), 32 deletions(-) diff --git a/src/Util/TestDox/CliTestDoxPrinter.php b/src/Util/TestDox/CliTestDoxPrinter.php index 7f52509658b..657dcda572e 100644 --- a/src/Util/TestDox/CliTestDoxPrinter.php +++ b/src/Util/TestDox/CliTestDoxPrinter.php @@ -310,7 +310,7 @@ private function writeTestResult(array $prevResult, array $result): void // test result line if ($result['className'] == PhptTestCase::class) { - $testName = $this->colorizePath($result['testName'], $prevResult['testName']); + $testName = Color::colorizePath($result['testName'], $prevResult['testName']); } else { $testName = $result['testMethod']; } @@ -423,9 +423,9 @@ private function colorizeStacktrace(\Throwable $t): string foreach (\explode("\n", $trace) as $line) { if (\preg_match('/^(.*):(\d+)$/', $line, $matches)) { - $lines[] = $this->colorizePath($matches[1], $prevPath) . - $this->formatWithColor('dim', ':') . - $this->formatWithColor('fg-blue', $matches[2]) . + $lines[] = Color::colorizePath($matches[1], $prevPath) . + Color::colorize('dim', ':') . + Color::colorize('fg-blue', $matches[2]) . "\n"; $prevPath = $matches[1]; } else { @@ -436,22 +436,4 @@ private function colorizeStacktrace(\Throwable $t): string return \implode('', $lines); } - - private function colorizePath(string $path, ?string $prevPath): string - { - if ($prevPath === null) { - $prevPath = ''; - } - - $path = \explode(\DIRECTORY_SEPARATOR, $path); - $prevPath = \explode(\DIRECTORY_SEPARATOR, $prevPath); - - for ($i = 0; $i < \min(\count($path), \count($prevPath)); $i++) { - if ($path[$i] == $prevPath[$i]) { - $path[$i] = $this->formatWithColor('dim', $path[$i]); - } - } - - return \implode($this->formatWithColor('dim', \DIRECTORY_SEPARATOR), $path); - } } diff --git a/src/Util/TestDox/Color.php b/src/Util/TestDox/Color.php index 7d90565196e..01742c401bd 100644 --- a/src/Util/TestDox/Color.php +++ b/src/Util/TestDox/Color.php @@ -49,4 +49,23 @@ public static function colorize(string $color, string $buffer): string return $style . $buffer . "\x1b[0m"; } + + public static function colorizePath(string $path, ?string $prevPath): string + { + if ($prevPath === null) { + $prevPath = ''; + } + + $path = \explode(\DIRECTORY_SEPARATOR, $path); + $prevPath = \explode(\DIRECTORY_SEPARATOR, $prevPath); + + for ($i = 0; $i < \min(\count($path), \count($prevPath)); $i++) { + if ($path[$i] == $prevPath[$i]) { + $path[$i] = Color::colorize('dim', $path[$i]); + } + } + + return \implode(Color::colorize('dim', \DIRECTORY_SEPARATOR), $path); + } + } diff --git a/src/Util/TestDox/NamePrettifier.php b/src/Util/TestDox/NamePrettifier.php index 24dd1ea88d6..7389bdc701c 100644 --- a/src/Util/TestDox/NamePrettifier.php +++ b/src/Util/TestDox/NamePrettifier.php @@ -102,19 +102,18 @@ public function prettifyTestCase(TestCase $test): string public function prettifyDataSet(TestCase $test): string { - $data = $test->getDataSetAsString(false); - if (!$this->useColor) { - return $data; + return $test->getDataSetAsString(false); + } + + $data = Color::colorize('dim', ' with data set '); + if (\is_int($test->dataName())) { + $data .= Color::colorize('fg-cyan', '#' . $test->dataName()); + } else { + $data .= Color::colorize('fg-cyan', $test->dataName()); } - return \preg_replace_callback( - '/(with data set )(.*)/', - function ($matches) { - return Color::colorize('dim', $matches[1] . Color::colorize('fg-cyan', $matches[2])); - }, - $data - ); + return $data; } /** @@ -212,6 +211,10 @@ private function mapTestMethodParameterNamesToProvidedDataValues(TestCase $test) $value = $exporter->export($value); } + if ($this->useColor) { + $value = Color::colorize('bg-yellow', $value); + } + $providedData['$' . $parameter->getName()] = $value; } From 1db838729bc76ed00d54d1b3abe8d8c64a019f8c Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Fri, 7 Dec 2018 01:31:53 +0100 Subject: [PATCH 12/51] Colorize @testdox annotation parameter values --- src/Util/TestDox/Color.php | 5 ++--- src/Util/TestDox/NamePrettifier.php | 3 ++- tests/unit/Runner/TestSuiteSorterTest.php | 1 + tests/unit/Util/RegularExpressionTest.php | 2 ++ 4 files changed, 7 insertions(+), 4 deletions(-) diff --git a/src/Util/TestDox/Color.php b/src/Util/TestDox/Color.php index 01742c401bd..1d283bd175c 100644 --- a/src/Util/TestDox/Color.php +++ b/src/Util/TestDox/Color.php @@ -61,11 +61,10 @@ public static function colorizePath(string $path, ?string $prevPath): string for ($i = 0; $i < \min(\count($path), \count($prevPath)); $i++) { if ($path[$i] == $prevPath[$i]) { - $path[$i] = Color::colorize('dim', $path[$i]); + $path[$i] = self::colorize('dim', $path[$i]); } } - return \implode(Color::colorize('dim', \DIRECTORY_SEPARATOR), $path); + return \implode(self::colorize('dim', \DIRECTORY_SEPARATOR), $path); } - } diff --git a/src/Util/TestDox/NamePrettifier.php b/src/Util/TestDox/NamePrettifier.php index 7389bdc701c..2d9ae46c4fc 100644 --- a/src/Util/TestDox/NamePrettifier.php +++ b/src/Util/TestDox/NamePrettifier.php @@ -107,6 +107,7 @@ public function prettifyDataSet(TestCase $test): string } $data = Color::colorize('dim', ' with data set '); + if (\is_int($test->dataName())) { $data .= Color::colorize('fg-cyan', '#' . $test->dataName()); } else { @@ -212,7 +213,7 @@ private function mapTestMethodParameterNamesToProvidedDataValues(TestCase $test) } if ($this->useColor) { - $value = Color::colorize('bg-yellow', $value); + $value = Color::colorize('fg-cyan', $value); } $providedData['$' . $parameter->getName()] = $value; diff --git a/tests/unit/Runner/TestSuiteSorterTest.php b/tests/unit/Runner/TestSuiteSorterTest.php index 165af2117d3..9f2114477b2 100644 --- a/tests/unit/Runner/TestSuiteSorterTest.php +++ b/tests/unit/Runner/TestSuiteSorterTest.php @@ -13,6 +13,7 @@ use PHPUnit\Framework\TestSuite; /** + * @testdox Reordering test execution * @group test-reorder */ class TestSuiteSorterTest extends TestCase diff --git a/tests/unit/Util/RegularExpressionTest.php b/tests/unit/Util/RegularExpressionTest.php index 07bfe539b1e..1fcb524f226 100644 --- a/tests/unit/Util/RegularExpressionTest.php +++ b/tests/unit/Util/RegularExpressionTest.php @@ -33,6 +33,7 @@ public function invalidRegexpProvider(): array } /** + * @testdox Valid regex $pattern on $subject returns $return * @dataProvider validRegexpProvider * * @throws \Exception @@ -44,6 +45,7 @@ public function testValidRegex($pattern, $subject, $return): void } /** + * @testdox Invalid regex $pattern on $subject * @dataProvider invalidRegexpProvider * * @throws \Exception From 8ba1b437c8c90967188985a86953b4a97a9eaaa9 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Fri, 7 Dec 2018 01:56:26 +0100 Subject: [PATCH 13/51] Remove clutter from runtime when using color --- phpunit.xml | 2 -- src/Util/TestDox/CliTestDoxPrinter.php | 8 ++++++-- tests/unit/Util/JsonTest.php | 1 + 3 files changed, 7 insertions(+), 4 deletions(-) diff --git a/phpunit.xml b/phpunit.xml index 82bfb122799..aa3e47fa7b0 100644 --- a/phpunit.xml +++ b/phpunit.xml @@ -2,8 +2,6 @@ diff --git a/src/Util/TestDox/CliTestDoxPrinter.php b/src/Util/TestDox/CliTestDoxPrinter.php index 657dcda572e..b43746cb239 100644 --- a/src/Util/TestDox/CliTestDoxPrinter.php +++ b/src/Util/TestDox/CliTestDoxPrinter.php @@ -338,11 +338,15 @@ private function getTestResultByName(string $testName): array private function getFormattedRuntime(float $time, string $color = ''): string { + if (!$this->colors) { + return \sprintf('[%.2f ms]', $time * 1000); + } + if ($time > 1) { - return $this->formatWithColor('fg-magenta', \sprintf('[%.2f ms]', $time * 1000)); + $color = 'fg-magenta'; } - return $this->formatWithColor($color, \sprintf('[%.2f ms]', $time * 1000)); + return Color::colorize($color, \sprintf(' %.2f ms', $time * 1000)); } private function formatTestResultMessage(string $resultMessage, bool $verbose): string diff --git a/tests/unit/Util/JsonTest.php b/tests/unit/Util/JsonTest.php index 3a437e6395a..429fe569656 100644 --- a/tests/unit/Util/JsonTest.php +++ b/tests/unit/Util/JsonTest.php @@ -15,6 +15,7 @@ class JsonTest extends TestCase { /** + * @testdox Canonicalize $actual * @dataProvider canonicalizeProvider * * @throws \PHPUnit\Framework\ExpectationFailedException From 9082a291d9a1d834926fb722564ccd1e6c284c53 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Fri, 7 Dec 2018 11:52:48 +0100 Subject: [PATCH 14/51] Restore cacheResult configuration --- phpunit.xml | 1 + 1 file changed, 1 insertion(+) diff --git a/phpunit.xml b/phpunit.xml index aa3e47fa7b0..92b3e855560 100644 --- a/phpunit.xml +++ b/phpunit.xml @@ -2,6 +2,7 @@ From a0e2e9d2d1cfd5b6e8f35c970ac1126019f1775b Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Fri, 7 Dec 2018 20:53:05 +0100 Subject: [PATCH 15/51] Add $_dataName parameter for @testdox with a dataprovider --- src/Util/TestDox/NamePrettifier.php | 12 ++++++++---- tests/unit/Runner/ResultCacheExtensionTest.php | 1 + 2 files changed, 9 insertions(+), 4 deletions(-) diff --git a/src/Util/TestDox/NamePrettifier.php b/src/Util/TestDox/NamePrettifier.php index 2d9ae46c4fc..44d7741d722 100644 --- a/src/Util/TestDox/NamePrettifier.php +++ b/src/Util/TestDox/NamePrettifier.php @@ -187,6 +187,8 @@ private function mapTestMethodParameterNamesToProvidedDataValues(TestCase $test) $providedDataValues = \array_values($test->getProvidedData()); $i = 0; + $providedData['$_dataName'] = $test->dataName(); + foreach ($reflector->getParameters() as $parameter) { if (!\array_key_exists($i, $providedDataValues) && $parameter->isDefaultValueAvailable()) { $providedDataValues[$i] = $parameter->getDefaultValue(); @@ -212,13 +214,15 @@ private function mapTestMethodParameterNamesToProvidedDataValues(TestCase $test) $value = $exporter->export($value); } - if ($this->useColor) { - $value = Color::colorize('fg-cyan', $value); - } - $providedData['$' . $parameter->getName()] = $value; } + if ($this->useColor) { + $providedData = \array_map(function ($value) { + return Color::colorize('fg-cyan', $value); + }, $providedData); + } + return $providedData; } } diff --git a/tests/unit/Runner/ResultCacheExtensionTest.php b/tests/unit/Runner/ResultCacheExtensionTest.php index 4a1edc3e6f2..f2bce541c01 100644 --- a/tests/unit/Runner/ResultCacheExtensionTest.php +++ b/tests/unit/Runner/ResultCacheExtensionTest.php @@ -47,6 +47,7 @@ protected function setUp(): void } /** + * @testdox Clean up test name $_dataName * @dataProvider longTestNamesDataprovider */ public function testStripsDataproviderParametersFromTestName(string $testName, string $expectedTestName): void From d51ad7a57d85da9c627d4b84f1276d1ad6815d00 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Fri, 7 Dec 2018 20:55:29 +0100 Subject: [PATCH 16/51] Improve colorizer and add tests --- src/Util/TestDox/Color.php | 16 +++++-- tests/unit/Util/ConfigurationTest.php | 39 ++++++++-------- tests/unit/Util/TestDox/ColorTest.php | 64 +++++++++++++++++++++++++++ 3 files changed, 97 insertions(+), 22 deletions(-) create mode 100644 tests/unit/Util/TestDox/ColorTest.php diff --git a/src/Util/TestDox/Color.php b/src/Util/TestDox/Color.php index 1d283bd175c..7e724ca1f42 100644 --- a/src/Util/TestDox/Color.php +++ b/src/Util/TestDox/Color.php @@ -39,15 +39,25 @@ class Color public static function colorize(string $color, string $buffer): string { + if (\trim($buffer) === '') { + return $buffer; + } + $codes = \array_map('\trim', \explode(',', $color)); + $styles = []; + foreach ($codes as $code) { - $styles[] = self::$ansiCodes[$code] ?? ''; + if (isset(self::$ansiCodes[$code])) { + $styles[] = self::$ansiCodes[$code] ?? ''; + } } - $style = \sprintf("\x1b[%sm", \implode(';', $styles)); + if (empty($styles)) { + return $buffer; + } - return $style . $buffer . "\x1b[0m"; + return \sprintf("\x1b[%sm", \implode(';', $styles)) . $buffer . "\x1b[0m"; } public static function colorizePath(string $path, ?string $prevPath): string diff --git a/tests/unit/Util/ConfigurationTest.php b/tests/unit/Util/ConfigurationTest.php index 8e34e85ee55..845068cd98d 100644 --- a/tests/unit/Util/ConfigurationTest.php +++ b/tests/unit/Util/ConfigurationTest.php @@ -93,6 +93,7 @@ public function testShouldUseDefaultValuesForInvalidIntegers(): void } /** + * @testdox Parse XML configuration root attribute $optionName = $optionValue * @dataProvider configurationRootOptionsProvider * * @group test-reorder @@ -117,25 +118,25 @@ public function testShouldParseXmlConfigurationRootAttributes(string $optionName public function configurationRootOptionsProvider(): array { return [ - 'executionOrder default' => ['executionOrder', 'default', TestSuiteSorter::ORDER_DEFAULT], - 'executionOrder random' => ['executionOrder', 'random', TestSuiteSorter::ORDER_RANDOMIZED], - 'executionOrder reverse' => ['executionOrder', 'reverse', TestSuiteSorter::ORDER_REVERSED], - 'cacheResult false' => ['cacheResult', 'false', false], - 'cacheResult true' => ['cacheResult', 'true', true], - 'cacheResultFile absolute path' => ['cacheResultFile', '/path/to/result/cache', '/path/to/result/cache'], - 'columns' => ['columns', 'max', 'max'], - 'stopOnFailure' => ['stopOnFailure', 'true', true], - 'stopOnWarning' => ['stopOnWarning', 'true', true], - 'stopOnIncomplete' => ['stopOnIncomplete', 'true', true], - 'stopOnRisky' => ['stopOnRisky', 'true', true], - 'stopOnSkipped' => ['stopOnSkipped', 'true', true], - 'failOnWarning' => ['failOnWarning', 'true', true], - 'failOnRisky' => ['failOnRisky', 'true', true], - 'disableCodeCoverageIgnore' => ['disableCodeCoverageIgnore', 'true', true], - 'processIsolation' => ['processIsolation', 'true', true], - 'testSuiteLoaderFile absolute path' => ['testSuiteLoaderFile', '/path/to/file', '/path/to/file'], - 'reverseDefectList' => ['reverseDefectList', 'true', true], - 'registerMockObjectsFromTestArgumentsRecursively' => ['registerMockObjectsFromTestArgumentsRecursively', 'true', true], + 'executionOrder default' => ['executionOrder', 'default', TestSuiteSorter::ORDER_DEFAULT], + 'executionOrder random' => ['executionOrder', 'random', TestSuiteSorter::ORDER_RANDOMIZED], + 'executionOrder reverse' => ['executionOrder', 'reverse', TestSuiteSorter::ORDER_REVERSED], + 'cacheResult=false' => ['cacheResult', 'false', false], + 'cacheResult=true' => ['cacheResult', 'true', true], + 'cacheResultFile absolute path' => ['cacheResultFile', '/path/to/result/cache', '/path/to/result/cache'], + 'columns' => ['columns', 'max', 'max'], + 'stopOnFailure' => ['stopOnFailure', 'true', true], + 'stopOnWarning' => ['stopOnWarning', 'true', true], + 'stopOnIncomplete' => ['stopOnIncomplete', 'true', true], + 'stopOnRisky' => ['stopOnRisky', 'true', true], + 'stopOnSkipped' => ['stopOnSkipped', 'true', true], + 'failOnWarning' => ['failOnWarning', 'true', true], + 'failOnRisky' => ['failOnRisky', 'true', true], + 'disableCodeCoverageIgnore' => ['disableCodeCoverageIgnore', 'true', true], + 'processIsolation' => ['processIsolation', 'true', true], + 'testSuiteLoaderFile absolute path' => ['testSuiteLoaderFile', '/path/to/file', '/path/to/file'], + 'reverseDefectList' => ['reverseDefectList', 'true', true], + 'registerMockObjectsFromTestArgumentsRecursively'=> ['registerMockObjectsFromTestArgumentsRecursively', 'true', true], ]; } diff --git a/tests/unit/Util/TestDox/ColorTest.php b/tests/unit/Util/TestDox/ColorTest.php new file mode 100644 index 00000000000..3d4ade39436 --- /dev/null +++ b/tests/unit/Util/TestDox/ColorTest.php @@ -0,0 +1,64 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ +namespace PHPUnit\Util\TestDox; + +use PHPUnit\Framework\TestCase; + +/** + * @testdox Basic ANSI color support + */ +class ColorTest extends TestCase +{ + /** + * @testdox Colorize with $_dataName + * @dataProvider colorizeProvider + */ + public function testColorize(string $color, string $buffer, string $expected): void + { + $this->assertSame($expected, Color::colorize($color, $buffer)); + } + + /** + * @testdox Colorize path $path after $prevPath + * @dataProvider colorizePathProvider + */ + public function testColorizePath(string $prevPath, string $path, string $expected): void + { + $this->assertSame($expected, Color::colorizePath($path, $prevPath)); + } + + public function colorizeProvider(): array + { + return [ + 'no color' => ['', 'string', 'string'], + 'one color' => ['fg-blue', 'string', "\x1b[34mstring\x1b[0m"], + 'multiple colors' => ['bold,dim,fg-blue,bg-yellow', 'string', "\x1b[1;2;34;43mstring\x1b[0m"], + ]; + } + + public function colorizePathProvider(): array + { + $sep = \DIRECTORY_SEPARATOR; + $sepDim = Color::colorize('dim', $sep); + + return [ + 'no previous path' => [ + $sep, + $sep . 'php' . $sep . 'unit' . $sep . 'test.phpt', + $sepDim . 'php' . $sepDim . 'unit' . $sepDim . 'test.phpt', + ], + 'partial part' => [ + $sep . 'php' . $sep, + $sep . 'php' . $sep . 'unit' . $sep . 'test.phpt', + $sepDim . Color::colorize('dim', 'php') . $sepDim . 'unit' . $sepDim . 'test.phpt', + ], + ]; + } +} From 07f4816ea1ea8fe89438bd74a1b07ca3047f0e31 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Mon, 10 Dec 2018 14:15:53 +0100 Subject: [PATCH 17/51] Visiualize whitespace characters with dimmed interpuncts --- src/Util/TestDox/Color.php | 27 ++++++++++++++++++++-- src/Util/TestDox/NamePrettifier.php | 4 ++-- tests/unit/Framework/AssertTest.php | 17 ++++++++++++-- tests/unit/Util/TestDox/ColorTest.php | 33 ++++++++++++++++++++++++--- 4 files changed, 72 insertions(+), 9 deletions(-) diff --git a/src/Util/TestDox/Color.php b/src/Util/TestDox/Color.php index 7e724ca1f42..cc31b04d632 100644 --- a/src/Util/TestDox/Color.php +++ b/src/Util/TestDox/Color.php @@ -18,6 +18,7 @@ class Color 'reset' => '0', 'bold' => '1', 'dim' => '2', + 'dim-reset' => '22', 'underlined' => '4', 'fg-black' => '30', 'fg-red' => '31', @@ -37,6 +38,12 @@ class Color 'bg-white' => '47', ]; + private const WHITESPACE_MAP = [ + " " => "·", + "\t" => "⇥", + "\n" => "↵", + ]; + public static function colorize(string $color, string $buffer): string { if (\trim($buffer) === '') { @@ -71,10 +78,26 @@ public static function colorizePath(string $path, ?string $prevPath): string for ($i = 0; $i < \min(\count($path), \count($prevPath)); $i++) { if ($path[$i] == $prevPath[$i]) { - $path[$i] = self::colorize('dim', $path[$i]); + $path[$i] = self::dim($path[$i]); } } - return \implode(self::colorize('dim', \DIRECTORY_SEPARATOR), $path); + return \implode(self::dim(\DIRECTORY_SEPARATOR), $path); + } + + public static function dim(string $buffer): string + { + if (\trim($buffer) === '') { + return $buffer; + } + + return "\x1b[2m$buffer\x1b[22m"; + } + + public static function visiualizeWhitespace(string $buffer): string + { + return \preg_replace_callback('/\s+/', function ($matches) { + return self::dim(\strtr($matches[0], self::WHITESPACE_MAP)); + }, $buffer); } } diff --git a/src/Util/TestDox/NamePrettifier.php b/src/Util/TestDox/NamePrettifier.php index 44d7741d722..d4ac286c4df 100644 --- a/src/Util/TestDox/NamePrettifier.php +++ b/src/Util/TestDox/NamePrettifier.php @@ -111,7 +111,7 @@ public function prettifyDataSet(TestCase $test): string if (\is_int($test->dataName())) { $data .= Color::colorize('fg-cyan', '#' . $test->dataName()); } else { - $data .= Color::colorize('fg-cyan', $test->dataName()); + $data .= Color::colorize('fg-cyan', Color::visiualizeWhitespace($test->dataName())); } return $data; @@ -219,7 +219,7 @@ private function mapTestMethodParameterNamesToProvidedDataValues(TestCase $test) if ($this->useColor) { $providedData = \array_map(function ($value) { - return Color::colorize('fg-cyan', $value); + return Color::colorize('fg-cyan', Color::visiualizeWhitespace($value)); }, $providedData); } diff --git a/tests/unit/Framework/AssertTest.php b/tests/unit/Framework/AssertTest.php index 5542b0d95fd..242471d99f1 100644 --- a/tests/unit/Framework/AssertTest.php +++ b/tests/unit/Framework/AssertTest.php @@ -146,6 +146,7 @@ public function testAssertArraySubsetWithStrictCheckAndObjects(): void } /** + * @testdox assertArraySubset($_dataName) raises exception * @dataProvider assertArraySubsetInvalidArgumentProvider * * @throws Exception @@ -162,8 +163,8 @@ public function testAssertArraySubsetRaisesExceptionForInvalidArguments($partial public function assertArraySubsetInvalidArgumentProvider(): array { return [ - [false, []], - [[], false], + 'false, []' => [false, []], + '[], false' => [[], false], ]; } @@ -357,6 +358,7 @@ public function testAssertNotEqualsSucceeds($a, $b): void } /** + * @testdox assertNotEquals($a, $b) with delta $delta, canoicalize $canonicalize, ignoreCase $ignoreCase * @dataProvider equalProvider * * @throws ExpectationFailedException @@ -370,6 +372,7 @@ public function testAssertNotEqualsFails($a, $b): void } /** + * @testdox assertNotSame($a, $b) fails * @dataProvider sameProvider * * @throws ExpectationFailedException @@ -381,6 +384,7 @@ public function testAssertSameSucceeds($a, $b): void } /** + * @testdox assertNotSame($a, $b) * @dataProvider notSameProvider * * @throws ExpectationFailedException @@ -394,6 +398,7 @@ public function testAssertSameFails($a, $b): void } /** + * @testdox assertSame($a, $b) fails * @dataProvider notSameProvider * * @throws ExpectationFailedException @@ -405,6 +410,7 @@ public function testAssertNotSameSucceeds($a, $b): void } /** + * @testdox assertSame($a, $b) * @dataProvider sameProvider * * @throws ExpectationFailedException @@ -1640,11 +1646,17 @@ public function testAssertNotSameSizeThrowsExceptionIfActualIsNotCountable(): vo $this->assertNotSameSize([], ''); } + /** + * @testdox Assert JSON + */ public function testAssertJson(): void { $this->assertJson('{}'); } + /** + * @testdox Assert JSON string equals JSON string + */ public function testAssertJsonStringEqualsJsonString(): void { $expected = '{"Mascott" : "Tux"}'; @@ -1677,6 +1689,7 @@ public function testAssertJsonStringNotEqualsJsonString(): void } /** + * @testdox Assert JSON string equals equals JSON string raised $_dataName * @dataProvider validInvalidJsonDataprovider * * @throws ExpectationFailedException diff --git a/tests/unit/Util/TestDox/ColorTest.php b/tests/unit/Util/TestDox/ColorTest.php index 3d4ade39436..45fedb95ccf 100644 --- a/tests/unit/Util/TestDox/ColorTest.php +++ b/tests/unit/Util/TestDox/ColorTest.php @@ -12,7 +12,7 @@ use PHPUnit\Framework\TestCase; /** - * @testdox Basic ANSI color support + * @testdox Basic ANSI color highlighting support */ class ColorTest extends TestCase { @@ -34,6 +34,24 @@ public function testColorizePath(string $prevPath, string $path, string $expecte $this->assertSame($expected, Color::colorizePath($path, $prevPath)); } + /** + * @testdox dim($m) and colorize('dim',$m) return different ANSI codes + */ + public function testDimAndColorizeDimAreDifferent(): void + { + $buffer = 'some string'; + $this->assertNotSame(Color::dim($buffer), Color::colorize('dim', $buffer)); + } + + /** + * @testdox Visiualize whitespace characters in $actual + * @dataProvider whitespacedStringProvider + */ + public function testVisibleWhitespace(string $actual, string $expected): void + { + $this->assertSame($expected, Color::visiualizeWhitespace($actual)); + } + public function colorizeProvider(): array { return [ @@ -46,7 +64,7 @@ public function colorizeProvider(): array public function colorizePathProvider(): array { $sep = \DIRECTORY_SEPARATOR; - $sepDim = Color::colorize('dim', $sep); + $sepDim = Color::dim($sep); return [ 'no previous path' => [ @@ -57,8 +75,17 @@ public function colorizePathProvider(): array 'partial part' => [ $sep . 'php' . $sep, $sep . 'php' . $sep . 'unit' . $sep . 'test.phpt', - $sepDim . Color::colorize('dim', 'php') . $sepDim . 'unit' . $sepDim . 'test.phpt', + $sepDim . Color::dim('php') . $sepDim . 'unit' . $sepDim . 'test.phpt', ], ]; } + + public function whitespacedStringProvider(): array + { + return [ + ["no-spaces", "no-spaces"], + [" space invaders ", "\x1b[2m·\x1b[22mspace\e[2m···\e[22minvaders\e[2m·\e[22m"], + ["\tindent, space and LF\n", "\e[2m⇥\e[22mindent,\e[2m·\e[22mspace\e[2m·\e[22mand\e[2m·\e[22mLF\e[2m↵\e[22m"] + ]; + } } From 355f20ba4504d6b495452638e890f3bec1c159c1 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Mon, 10 Dec 2018 14:26:50 +0100 Subject: [PATCH 18/51] Improve readability of @testdox and @dataprovider parameters --- src/Util/TestDox/NamePrettifier.php | 4 +++- tests/end-to-end/dataprovider-testdox.phpt | 2 +- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/src/Util/TestDox/NamePrettifier.php b/src/Util/TestDox/NamePrettifier.php index d4ac286c4df..58dbc874636 100644 --- a/src/Util/TestDox/NamePrettifier.php +++ b/src/Util/TestDox/NamePrettifier.php @@ -106,7 +106,7 @@ public function prettifyDataSet(TestCase $test): string return $test->getDataSetAsString(false); } - $data = Color::colorize('dim', ' with data set '); + $data = Color::dim( ' with '); if (\is_int($test->dataName())) { $data .= Color::colorize('fg-cyan', '#' . $test->dataName()); @@ -201,6 +201,8 @@ private function mapTestMethodParameterNamesToProvidedDataValues(TestCase $test) if ($reflector->hasMethod('__toString')) { $value = (string) $value; + } else { + $value = \get_class($value); } } diff --git a/tests/end-to-end/dataprovider-testdox.phpt b/tests/end-to-end/dataprovider-testdox.phpt index 3eeefc56501..5c74389bf5b 100644 --- a/tests/end-to-end/dataprovider-testdox.phpt +++ b/tests/end-to-end/dataprovider-testdox.phpt @@ -24,7 +24,7 @@ DataProviderTestDox ✔ ... 1.0 ... ✔ ... string ... ✔ ... array ... - ✔ ... object ... + ✔ ... stdClass ... ✔ ... string ... ✔ ... resource ... ✔ ... NULL ... From ff9f1d7130b89a711359e1d9eab934d0d43bdd88 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Mon, 10 Dec 2018 14:27:52 +0100 Subject: [PATCH 19/51] CS/WS fixes and better @testdox annotations --- src/Util/TestDox/Color.php | 12 ++++++------ src/Util/TestDox/NamePrettifier.php | 2 +- .../unit/Framework/Constraint/IsJsonTest.php | 1 + .../JsonMatchesErrorMessageProviderTest.php | 1 + .../Framework/MockObject/MockObjectTest.php | 19 +++++++++++++------ tests/unit/Util/ConfigurationTest.php | 15 +++++++++++++-- tests/unit/Util/JsonTest.php | 1 + tests/unit/Util/TestDox/ColorTest.php | 6 +++--- tests/unit/Util/XmlTest.php | 9 +++++++++ 9 files changed, 48 insertions(+), 18 deletions(-) diff --git a/src/Util/TestDox/Color.php b/src/Util/TestDox/Color.php index cc31b04d632..f792b6ec22f 100644 --- a/src/Util/TestDox/Color.php +++ b/src/Util/TestDox/Color.php @@ -11,6 +11,12 @@ class Color { + private const WHITESPACE_MAP = [ + ' ' => '·', + "\t" => '⇥', + "\n" => '↵', + ]; + /** * @var array */ @@ -38,12 +44,6 @@ class Color 'bg-white' => '47', ]; - private const WHITESPACE_MAP = [ - " " => "·", - "\t" => "⇥", - "\n" => "↵", - ]; - public static function colorize(string $color, string $buffer): string { if (\trim($buffer) === '') { diff --git a/src/Util/TestDox/NamePrettifier.php b/src/Util/TestDox/NamePrettifier.php index 58dbc874636..52d3c345f24 100644 --- a/src/Util/TestDox/NamePrettifier.php +++ b/src/Util/TestDox/NamePrettifier.php @@ -106,7 +106,7 @@ public function prettifyDataSet(TestCase $test): string return $test->getDataSetAsString(false); } - $data = Color::dim( ' with '); + $data = Color::dim(' with '); if (\is_int($test->dataName())) { $data .= Color::colorize('fg-cyan', '#' . $test->dataName()); diff --git a/tests/unit/Framework/Constraint/IsJsonTest.php b/tests/unit/Framework/Constraint/IsJsonTest.php index e9e2d1a7fdb..c8b7336f21d 100644 --- a/tests/unit/Framework/Constraint/IsJsonTest.php +++ b/tests/unit/Framework/Constraint/IsJsonTest.php @@ -20,6 +20,7 @@ public static function evaluateDataprovider(): array } /** + * @testdox Evaluate $_dataName * @dataProvider evaluateDataprovider * * @throws \PHPUnit\Framework\ExpectationFailedException diff --git a/tests/unit/Framework/Constraint/JsonMatchesErrorMessageProviderTest.php b/tests/unit/Framework/Constraint/JsonMatchesErrorMessageProviderTest.php index 48a76d4964b..4cfd1b872b8 100644 --- a/tests/unit/Framework/Constraint/JsonMatchesErrorMessageProviderTest.php +++ b/tests/unit/Framework/Constraint/JsonMatchesErrorMessageProviderTest.php @@ -69,6 +69,7 @@ public function testTranslateTypeToPrefix($expected, $type): void } /** + * @testdox Determine JSON error $_dataName * @dataProvider determineJsonErrorDataprovider * * @throws \PHPUnit\Framework\ExpectationFailedException diff --git a/tests/unit/Framework/MockObject/MockObjectTest.php b/tests/unit/Framework/MockObject/MockObjectTest.php index cad33c56895..18862afc1ff 100644 --- a/tests/unit/Framework/MockObject/MockObjectTest.php +++ b/tests/unit/Framework/MockObject/MockObjectTest.php @@ -464,6 +464,9 @@ public function testOriginalCloneSettingConsidered(): void $this->assertNotEquals(\get_class($mock1), \get_class($mock2)); } + /** + * @testdox getMock() for abstract class + */ public function testGetMockForAbstractClass(): void { $mock = $this->getMockBuilder(AbstractMockTestClass::class) @@ -474,6 +477,7 @@ public function testGetMockForAbstractClass(): void } /** + * @testdox getMock() for Traversable $_dataName * @dataProvider traversableProvider */ public function testGetMockForTraversable($type): void @@ -493,6 +497,9 @@ public function testMultipleInterfacesCanBeMockedInSingleObject(): void $this->assertInstanceOf(AnotherInterface::class, $mock); } + /** + * @testdox getMockForTrait() + */ public function testGetMockForTrait(): void { $mock = $this->getMockForTrait(AbstractTrait::class); @@ -1016,12 +1023,12 @@ public function testStringableClassCanBeMocked(): void public function traversableProvider(): array { return [ - ['Traversable'], - ['\Traversable'], - ['TraversableMockTestInterface'], - [['Traversable']], - [['Iterator', 'Traversable']], - [['\Iterator', '\Traversable']], + 'Traversable' => ['Traversable'], + '\Traversable' => ['\Traversable'], + 'TraversableMockTestInterface' => ['TraversableMockTestInterface'], + "['Traversable']" => [['Traversable']], + "['Iterator', 'Traversable']" => [['Iterator', 'Traversable']], + "['\Iterator', '\Traversable']" => [['\Iterator', '\Traversable']], ]; } diff --git a/tests/unit/Util/ConfigurationTest.php b/tests/unit/Util/ConfigurationTest.php index 845068cd98d..2a575ff231f 100644 --- a/tests/unit/Util/ConfigurationTest.php +++ b/tests/unit/Util/ConfigurationTest.php @@ -341,6 +341,9 @@ public function testLoggingConfigurationIsReadCorrectly(): void ); } + /** + * @testdox PHP configuration is read correctly + */ public function testPHPConfigurationIsReadCorrectly(): void { $this->assertEquals( @@ -365,6 +368,7 @@ public function testPHPConfigurationIsReadCorrectly(): void } /** + * @testdox PHP configuration is handled correctly * @backupGlobals enabled */ public function testPHPConfigurationIsHandledCorrectly(): void @@ -395,11 +399,12 @@ public function testPHPConfigurationIsHandledCorrectly(): void } /** + * @testdox handlePHPConfiguration() does not overwrite existing $ENV[] variables * @backupGlobals enabled * * @see https://github.com/sebastianbergmann/phpunit/issues/1181 */ - public function testHandlePHPConfigurationDoesNotOverwrittenExistingEnvArrayVariables(): void + public function testHandlePHPConfigurationDoesNotOverwriteExistingEnvArrayVariables(): void { $_ENV['foo'] = false; $this->configuration->handlePHPConfiguration(); @@ -409,6 +414,7 @@ public function testHandlePHPConfigurationDoesNotOverwrittenExistingEnvArrayVari } /** + * @testdox handlePHPConfiguration() does force overwritten existing $ENV[] variables * @backupGlobals enabled * * @see https://github.com/sebastianbergmann/phpunit/issues/2353 @@ -423,11 +429,12 @@ public function testHandlePHPConfigurationDoesForceOverwrittenExistingEnvArrayVa } /** + * @testdox handlePHPConfiguration() does not overwrite variables from putenv() * @backupGlobals enabled * * @see https://github.com/sebastianbergmann/phpunit/issues/1181 */ - public function testHandlePHPConfigurationDoesNotOverriteVariablesFromPutEnv(): void + public function testHandlePHPConfigurationDoesNotOverwriteVariablesFromPutEnv(): void { $backupFoo = \getenv('foo'); @@ -445,6 +452,7 @@ public function testHandlePHPConfigurationDoesNotOverriteVariablesFromPutEnv(): } /** + * @testdox handlePHPConfiguration() does overwrite variables from putenv() when forced * @backupGlobals enabled * * @see https://github.com/sebastianbergmann/phpunit/issues/1181 @@ -458,6 +466,9 @@ public function testHandlePHPConfigurationDoesOverwriteVariablesFromPutEnvWhenFo $this->assertEquals('forced', \getenv('foo_force')); } + /** + * @testdox PHPUnit configuration is read correctly + */ public function testPHPUnitConfigurationIsReadCorrectly(): void { $this->assertEquals( diff --git a/tests/unit/Util/JsonTest.php b/tests/unit/Util/JsonTest.php index 429fe569656..947c4b12310 100644 --- a/tests/unit/Util/JsonTest.php +++ b/tests/unit/Util/JsonTest.php @@ -41,6 +41,7 @@ public function canonicalizeProvider(): array } /** + * @testdox Prettify $actual * @dataProvider prettifyProvider * * @throws \PHPUnit\Framework\Exception diff --git a/tests/unit/Util/TestDox/ColorTest.php b/tests/unit/Util/TestDox/ColorTest.php index 45fedb95ccf..baef9958e30 100644 --- a/tests/unit/Util/TestDox/ColorTest.php +++ b/tests/unit/Util/TestDox/ColorTest.php @@ -83,9 +83,9 @@ public function colorizePathProvider(): array public function whitespacedStringProvider(): array { return [ - ["no-spaces", "no-spaces"], - [" space invaders ", "\x1b[2m·\x1b[22mspace\e[2m···\e[22minvaders\e[2m·\e[22m"], - ["\tindent, space and LF\n", "\e[2m⇥\e[22mindent,\e[2m·\e[22mspace\e[2m·\e[22mand\e[2m·\e[22mLF\e[2m↵\e[22m"] + ['no-spaces', 'no-spaces'], + [' space invaders ', "\x1b[2m·\x1b[22mspace\e[2m···\e[22minvaders\e[2m·\e[22m"], + ["\tindent, space and LF\n", "\e[2m⇥\e[22mindent,\e[2m·\e[22mspace\e[2m·\e[22mand\e[2m·\e[22mLF\e[2m↵\e[22m"], ]; } } diff --git a/tests/unit/Util/XmlTest.php b/tests/unit/Util/XmlTest.php index 216348355c8..363b453c867 100644 --- a/tests/unit/Util/XmlTest.php +++ b/tests/unit/Util/XmlTest.php @@ -74,6 +74,9 @@ public function testLoadBoolean(): void Xml::load(false); } + /** + * @testdox Nested xmlToVariable() + */ public function testNestedXmlToVariable(): void { $xml = 'foobar'; @@ -92,6 +95,9 @@ public function testNestedXmlToVariable(): void $this->assertSame($expected, $actual); } + /** + * @testdox xmlToVariable() can handle multiple of the same argument type + */ public function testXmlToVariableCanHandleMultipleOfTheSameArgumentType(): void { $xml = 'abc'; @@ -105,6 +111,9 @@ public function testXmlToVariableCanHandleMultipleOfTheSameArgumentType(): void $this->assertSame($expected, (array) $actual); } + /** + * @testdox xmlToVariable() can construct objects with constructor arguments recursively + */ public function testXmlToVariableCanConstructObjectsWithConstructorArgumentsRecursively(): void { $xml = 'one0two'; From 0abdb877b93e19a96d218c7cdd64d7f284012529 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Mon, 10 Dec 2018 14:58:51 +0100 Subject: [PATCH 20/51] Do not highlight PHPT paths when colors are off --- src/Util/TestDox/CliTestDoxPrinter.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Util/TestDox/CliTestDoxPrinter.php b/src/Util/TestDox/CliTestDoxPrinter.php index b43746cb239..8d50f7b4185 100644 --- a/src/Util/TestDox/CliTestDoxPrinter.php +++ b/src/Util/TestDox/CliTestDoxPrinter.php @@ -309,7 +309,7 @@ private function writeTestResult(array $prevResult, array $result): void } // test result line - if ($result['className'] == PhptTestCase::class) { + if ($this->colors && $result['className'] == PhptTestCase::class) { $testName = Color::colorizePath($result['testName'], $prevResult['testName']); } else { $testName = $result['testMethod']; From 83f0388472de6cc57e58629b23758e7b075fb700 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Mon, 10 Dec 2018 16:18:42 +0100 Subject: [PATCH 21/51] Improve colorization of test result messages --- src/TextUI/ResultPrinter.php | 1 - src/Util/TestDox/CliTestDoxPrinter.php | 37 +++++++++++++++++++------- src/Util/TestDox/Color.php | 2 ++ 3 files changed, 30 insertions(+), 10 deletions(-) diff --git a/src/TextUI/ResultPrinter.php b/src/TextUI/ResultPrinter.php index 97ada83b0c3..b863f57d6f5 100644 --- a/src/TextUI/ResultPrinter.php +++ b/src/TextUI/ResultPrinter.php @@ -513,7 +513,6 @@ protected function formatWithColor(string $color, string $buffer): string $lines = \explode("\n", $buffer); $padding = \max(\array_map('\strlen', $lines)); - $styles = []; $styledLines = []; diff --git a/src/Util/TestDox/CliTestDoxPrinter.php b/src/Util/TestDox/CliTestDoxPrinter.php index 8d50f7b4185..a3f16c15bf8 100644 --- a/src/Util/TestDox/CliTestDoxPrinter.php +++ b/src/Util/TestDox/CliTestDoxPrinter.php @@ -75,27 +75,38 @@ class CliTestDoxPrinter extends ResultPrinter BaseTestRunner::STATUS_ERROR => [ 'symbol' => '✘', 'color' => 'fg-yellow', + 'message' => 'bg-yellow,fg-black' ], BaseTestRunner::STATUS_FAILURE => [ 'symbol' => '✘', 'color' => 'fg-red', + 'message' => 'bg-red,fg-white' ], BaseTestRunner::STATUS_SKIPPED => [ 'symbol' => '→', 'color' => 'fg-yellow', + 'message' => 'fg-yellow' ], BaseTestRunner::STATUS_RISKY => [ 'symbol' => '☢', 'color' => 'fg-yellow', + 'message' => 'fg-yellow' ], BaseTestRunner::STATUS_INCOMPLETE => [ 'symbol' => '∅', 'color' => 'fg-yellow', + 'message' => 'fg-yellow' ], BaseTestRunner::STATUS_WARNING => [ 'symbol' => '✘', 'color' => 'fg-yellow', + 'message' => 'fg-yellow' ], + BaseTestRunner::STATUS_UNKNOWN => [ + 'symbol' => '?', + 'color' => 'fg-blue', + 'message' => 'fg-white,bg-blue' + ] ]; public function __construct( @@ -139,7 +150,7 @@ public function endTest(Test $test, float $time): void public function addError(Test $test, \Throwable $t, float $time): void { $resultMessage = $this->formatTestResultMessage( - $this->formatThrowable($t), + $this->formatThrowable($t, BaseTestRunner::STATUS_ERROR), true ); $this->registerTestResult($test, BaseTestRunner::STATUS_ERROR, $time, $resultMessage); @@ -148,7 +159,7 @@ public function addError(Test $test, \Throwable $t, float $time): void public function addWarning(Test $test, Warning $e, float $time): void { $resultMessage = $this->formatTestResultMessage( - $this->formatThrowable($e), + $this->formatThrowable($e, BaseTestRunner::STATUS_WARNING), true ); $this->registerTestResult($test, BaseTestRunner::STATUS_WARNING, $time, $resultMessage); @@ -157,7 +168,7 @@ public function addWarning(Test $test, Warning $e, float $time): void public function addFailure(Test $test, AssertionFailedError $e, float $time): void { $resultMessage = $this->formatTestResultMessage( - $this->formatThrowable($e), + $this->formatThrowable($e, BaseTestRunner::STATUS_FAILURE), true ); $this->registerTestResult($test, BaseTestRunner::STATUS_FAILURE, $time, $resultMessage); @@ -166,7 +177,7 @@ public function addFailure(Test $test, AssertionFailedError $e, float $time): vo public function addIncompleteTest(Test $test, \Throwable $t, float $time): void { $resultMessage = $this->formatTestResultMessage( - $this->formatThrowable($t), + $this->formatThrowable($t, BaseTestRunner::STATUS_INCOMPLETE), false ); $this->registerTestResult($test, BaseTestRunner::STATUS_INCOMPLETE, $time, $resultMessage); @@ -175,7 +186,7 @@ public function addIncompleteTest(Test $test, \Throwable $t, float $time): void public function addRiskyTest(Test $test, \Throwable $t, float $time): void { $resultMessage = $this->formatTestResultMessage( - $this->formatThrowable($t), + $this->formatThrowable($t, BaseTestRunner::STATUS_RISKY), false ); $this->registerTestResult($test, BaseTestRunner::STATUS_RISKY, $time, $resultMessage); @@ -184,7 +195,7 @@ public function addRiskyTest(Test $test, \Throwable $t, float $time): void public function addSkippedTest(Test $test, \Throwable $t, float $time): void { $resultMessage = $this->formatTestResultMessage( - $this->formatThrowable($t), + $this->formatThrowable($t, BaseTestRunner::STATUS_SKIPPED), false ); $this->registerTestResult($test, BaseTestRunner::STATUS_SKIPPED, $time, $resultMessage); @@ -405,11 +416,19 @@ private function getEmptyTestResult(): array ]; } - private function formatThrowable(\Throwable $t): string + private function formatThrowable(\Throwable $t, ?int $status = null): string { + $message = \PHPUnit\Framework\TestFailure::exceptionToString($t); + + if ($this->colors) { + $status = $status ?? BaseTestRunner::STATUS_UNKNOWN; + $style = $this->statusStyles[$status]['message'] ?? ''; + $message = $this->formatWithColor($style, $message); + } + return \sprintf( "%s\n%s", - \PHPUnit\Framework\TestFailure::exceptionToString($t), + $message, $this->colorizeStacktrace($t) ); } @@ -428,7 +447,7 @@ private function colorizeStacktrace(\Throwable $t): string foreach (\explode("\n", $trace) as $line) { if (\preg_match('/^(.*):(\d+)$/', $line, $matches)) { $lines[] = Color::colorizePath($matches[1], $prevPath) . - Color::colorize('dim', ':') . + Color::dim(':') . Color::colorize('fg-blue', $matches[2]) . "\n"; $prevPath = $matches[1]; diff --git a/src/Util/TestDox/Color.php b/src/Util/TestDox/Color.php index f792b6ec22f..f3faef82b2f 100644 --- a/src/Util/TestDox/Color.php +++ b/src/Util/TestDox/Color.php @@ -26,6 +26,7 @@ class Color 'dim' => '2', 'dim-reset' => '22', 'underlined' => '4', + 'fg-default' => '39', 'fg-black' => '30', 'fg-red' => '31', 'fg-green' => '32', @@ -34,6 +35,7 @@ class Color 'fg-magenta' => '35', 'fg-cyan' => '36', 'fg-white' => '37', + 'bg-default' => '49', 'bg-black' => '40', 'bg-red' => '41', 'bg-green' => '42', From a976be8b26ce0f80ce090686f0ad42e53d940021 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Mon, 10 Dec 2018 16:27:50 +0100 Subject: [PATCH 22/51] CS/WS fixes --- src/Util/TestDox/CliTestDoxPrinter.php | 48 +++++++++++++------------- 1 file changed, 24 insertions(+), 24 deletions(-) diff --git a/src/Util/TestDox/CliTestDoxPrinter.php b/src/Util/TestDox/CliTestDoxPrinter.php index a3f16c15bf8..85a5c584d8b 100644 --- a/src/Util/TestDox/CliTestDoxPrinter.php +++ b/src/Util/TestDox/CliTestDoxPrinter.php @@ -73,40 +73,40 @@ class CliTestDoxPrinter extends ResultPrinter 'color' => 'fg-green', ], BaseTestRunner::STATUS_ERROR => [ - 'symbol' => '✘', - 'color' => 'fg-yellow', - 'message' => 'bg-yellow,fg-black' + 'symbol' => '✘', + 'color' => 'fg-yellow', + 'message' => 'bg-yellow,fg-black', ], BaseTestRunner::STATUS_FAILURE => [ - 'symbol' => '✘', - 'color' => 'fg-red', - 'message' => 'bg-red,fg-white' + 'symbol' => '✘', + 'color' => 'fg-red', + 'message' => 'bg-red,fg-white', ], BaseTestRunner::STATUS_SKIPPED => [ - 'symbol' => '→', - 'color' => 'fg-yellow', - 'message' => 'fg-yellow' + 'symbol' => '→', + 'color' => 'fg-yellow', + 'message' => 'fg-yellow', ], BaseTestRunner::STATUS_RISKY => [ - 'symbol' => '☢', - 'color' => 'fg-yellow', - 'message' => 'fg-yellow' + 'symbol' => '☢', + 'color' => 'fg-yellow', + 'message' => 'fg-yellow', ], BaseTestRunner::STATUS_INCOMPLETE => [ - 'symbol' => '∅', - 'color' => 'fg-yellow', - 'message' => 'fg-yellow' + 'symbol' => '∅', + 'color' => 'fg-yellow', + 'message' => 'fg-yellow', ], BaseTestRunner::STATUS_WARNING => [ - 'symbol' => '✘', - 'color' => 'fg-yellow', - 'message' => 'fg-yellow' + 'symbol' => '✘', + 'color' => 'fg-yellow', + 'message' => 'fg-yellow', ], BaseTestRunner::STATUS_UNKNOWN => [ - 'symbol' => '?', - 'color' => 'fg-blue', - 'message' => 'fg-white,bg-blue' - ] + 'symbol' => '?', + 'color' => 'fg-blue', + 'message' => 'fg-white,bg-blue', + ], ]; public function __construct( @@ -421,8 +421,8 @@ private function formatThrowable(\Throwable $t, ?int $status = null): string $message = \PHPUnit\Framework\TestFailure::exceptionToString($t); if ($this->colors) { - $status = $status ?? BaseTestRunner::STATUS_UNKNOWN; - $style = $this->statusStyles[$status]['message'] ?? ''; + $status = $status ?? BaseTestRunner::STATUS_UNKNOWN; + $style = $this->statusStyles[$status]['message'] ?? ''; $message = $this->formatWithColor($style, $message); } From f0cb17180d8b80d20cfa95b9e57527e7b5094606 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Mon, 10 Dec 2018 17:03:27 +0100 Subject: [PATCH 23/51] Fix missing testdox result. Add some more descriptive annotations. --- src/Util/TestDox/CliTestDoxPrinter.php | 2 +- tests/unit/Util/JsonTest.php | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/Util/TestDox/CliTestDoxPrinter.php b/src/Util/TestDox/CliTestDoxPrinter.php index 85a5c584d8b..199f1adc573 100644 --- a/src/Util/TestDox/CliTestDoxPrinter.php +++ b/src/Util/TestDox/CliTestDoxPrinter.php @@ -275,7 +275,7 @@ private function testHasPassed(): bool private function flushOutputBuffer(): void { - if ($this->enableOutputBuffer && ($this->testFlushIndex === $this->testIndex)) { + if ($this->enableOutputBuffer && ($this->testFlushIndex > $this->testIndex)) { return; } diff --git a/tests/unit/Util/JsonTest.php b/tests/unit/Util/JsonTest.php index 947c4b12310..bffa3eb1be9 100644 --- a/tests/unit/Util/JsonTest.php +++ b/tests/unit/Util/JsonTest.php @@ -41,7 +41,7 @@ public function canonicalizeProvider(): array } /** - * @testdox Prettify $actual + * @testdox Prettify $actual to $expected * @dataProvider prettifyProvider * * @throws \PHPUnit\Framework\Exception From 392fe39e7f24a84ffd5caff7d0513b9589821b03 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Mon, 10 Dec 2018 20:00:09 +0100 Subject: [PATCH 24/51] Show empty string parameters in @testdox annotations --- src/Util/TestDox/NamePrettifier.php | 4 ++++ tests/unit/Util/TestDox/ColorTest.php | 5 +++++ 2 files changed, 9 insertions(+) diff --git a/src/Util/TestDox/NamePrettifier.php b/src/Util/TestDox/NamePrettifier.php index 52d3c345f24..3730da1bbe5 100644 --- a/src/Util/TestDox/NamePrettifier.php +++ b/src/Util/TestDox/NamePrettifier.php @@ -216,6 +216,10 @@ private function mapTestMethodParameterNamesToProvidedDataValues(TestCase $test) $value = $exporter->export($value); } + if (\is_string($value) && $value === '') { + $value = Color::colorize('underlined', 'empty'); + } + $providedData['$' . $parameter->getName()] = $value; } diff --git a/tests/unit/Util/TestDox/ColorTest.php b/tests/unit/Util/TestDox/ColorTest.php index baef9958e30..77de0d95f57 100644 --- a/tests/unit/Util/TestDox/ColorTest.php +++ b/tests/unit/Util/TestDox/ColorTest.php @@ -68,6 +68,11 @@ public function colorizePathProvider(): array return [ 'no previous path' => [ + '', + $sep . 'php' . $sep . 'unit' . $sep . 'test.phpt', + $sepDim . 'php' . $sepDim . 'unit' . $sepDim . 'test.phpt', + ], + 'from root' => [ $sep, $sep . 'php' . $sep . 'unit' . $sep . 'test.phpt', $sepDim . 'php' . $sepDim . 'unit' . $sepDim . 'test.phpt', From 93bc853a316084aeb1aba56c60187a6909bca20b Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Mon, 10 Dec 2018 20:10:19 +0100 Subject: [PATCH 25/51] Improve description of named and unnamed dataprovider sets --- src/Util/TestDox/NamePrettifier.php | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/src/Util/TestDox/NamePrettifier.php b/src/Util/TestDox/NamePrettifier.php index 3730da1bbe5..74037b243b6 100644 --- a/src/Util/TestDox/NamePrettifier.php +++ b/src/Util/TestDox/NamePrettifier.php @@ -106,12 +106,10 @@ public function prettifyDataSet(TestCase $test): string return $test->getDataSetAsString(false); } - $data = Color::dim(' with '); - if (\is_int($test->dataName())) { - $data .= Color::colorize('fg-cyan', '#' . $test->dataName()); + $data = Color::dim(' with data set ') . Color::colorize('fg-cyan', $test->dataName()); } else { - $data .= Color::colorize('fg-cyan', Color::visiualizeWhitespace($test->dataName())); + $data = Color::dim(' with ') . Color::colorize('fg-cyan', Color::visiualizeWhitespace($test->dataName())); } return $data; From eb682c34c8afeca691944e5de0575759bf882d49 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Mon, 10 Dec 2018 21:32:53 +0100 Subject: [PATCH 26/51] Add test for testdox parameter colorization --- .../testdox-dataprovider-placeholder.phpt | 18 ++++++------------ 1 file changed, 6 insertions(+), 12 deletions(-) diff --git a/tests/end-to-end/testdox-dataprovider-placeholder.phpt b/tests/end-to-end/testdox-dataprovider-placeholder.phpt index 1081501020c..610dd5cddaf 100644 --- a/tests/end-to-end/testdox-dataprovider-placeholder.phpt +++ b/tests/end-to-end/testdox-dataprovider-placeholder.phpt @@ -1,20 +1,14 @@ --TEST-- -phpunit --testdox RouterTest ../_files/RouterTest.php +phpunit --testdox --colors=always --verbose RouterTest ../unit/Util/TestDox/ColorTest.php --FILE-- Date: Mon, 10 Dec 2018 21:36:43 +0100 Subject: [PATCH 27/51] Fiddle with path to get Windows CI working --- tests/end-to-end/testdox-dataprovider-placeholder.phpt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/end-to-end/testdox-dataprovider-placeholder.phpt b/tests/end-to-end/testdox-dataprovider-placeholder.phpt index 610dd5cddaf..b5d57ae0530 100644 --- a/tests/end-to-end/testdox-dataprovider-placeholder.phpt +++ b/tests/end-to-end/testdox-dataprovider-placeholder.phpt @@ -11,4 +11,4 @@ $_SERVER['argv'][5] = __DIR__ . '/../unit/Util/TestDox/ColorTest.php'; require __DIR__ . '/../bootstrap.php'; PHPUnit\TextUI\Command::main(); --EXPECTF_EXTERNAL-- -/../_files/raw_output_ColorTest.txt +../_files/raw_output_ColorTest.txt From 47dad52c1871e1b019fa5d33b3afcf57f8a24e1f Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Mon, 10 Dec 2018 21:38:31 +0100 Subject: [PATCH 28/51] Add raw example output for ANSI colors test --- tests/_files/raw_output_ColorTest.txt | 19 +++++++++++++++++++ 1 file changed, 19 insertions(+) create mode 100644 tests/_files/raw_output_ColorTest.txt diff --git a/tests/_files/raw_output_ColorTest.txt b/tests/_files/raw_output_ColorTest.txt new file mode 100644 index 00000000000..84334ef35c2 --- /dev/null +++ b/tests/_files/raw_output_ColorTest.txt @@ -0,0 +1,19 @@ +PHPUnit %s by Sebastian Bergmann and contributors. + +Runtime: %s + +Basic ANSI color highlighting support + ✔ Colorize with no·color  %f ms + ✔ Colorize with one·color  %f ms + ✔ Colorize with multiple·colors  %f ms + ✔ Colorize path /php/unit/test.phpt after empty  %f ms + ✔ Colorize path /php/unit/test.phpt after /  %f ms + ✔ Colorize path /php/unit/test.phpt after /php/  %f ms + ✔ dim($m) and colorize('dim',$m) return different ANSI codes  %f ms + ✔ Visiualize whitespace characters in no-spaces  %f ms + ✔ Visiualize whitespace characters in ·space···invaders·  %s ms + ✔ Visiualize whitespace characters in ⇥indent,·space·and·LF↵  %s ms + +Time: %s, Memory: %s + +OK (10 tests, 10 assertions) From aa5e1ddc91274f5ba532cbd2e5c86478e94feeb8 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Mon, 10 Dec 2018 21:44:38 +0100 Subject: [PATCH 29/51] Fix test to support generic directory separators --- tests/_files/raw_output_ColorTest.txt | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/tests/_files/raw_output_ColorTest.txt b/tests/_files/raw_output_ColorTest.txt index 84334ef35c2..0b50280b8c4 100644 --- a/tests/_files/raw_output_ColorTest.txt +++ b/tests/_files/raw_output_ColorTest.txt @@ -6,9 +6,9 @@ Runtime: %s ✔ Colorize with no·color  %f ms ✔ Colorize with one·color  %f ms ✔ Colorize with multiple·colors  %f ms - ✔ Colorize path /php/unit/test.phpt after empty  %f ms - ✔ Colorize path /php/unit/test.phpt after /  %f ms - ✔ Colorize path /php/unit/test.phpt after /php/  %f ms + ✔ Colorize path %ephp%eunit%etest.phpt after empty  %f ms + ✔ Colorize path %ephp%eunit%etest.phpt after %e  %f ms + ✔ Colorize path %ephp%eunit%etest.phpt after %ephp%e  %f ms ✔ dim($m) and colorize('dim',$m) return different ANSI codes  %f ms ✔ Visiualize whitespace characters in no-spaces  %f ms ✔ Visiualize whitespace characters in ·space···invaders·  %s ms From 4128cf6858625f92037785c874b7993e8b9cc06d Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Mon, 10 Dec 2018 22:14:57 +0100 Subject: [PATCH 30/51] Improve test coverage of testdox annotation with a dataprovider --- src/Util/TestDox/Color.php | 2 +- tests/_files/raw_output_ColorTest.txt | 9 ++++- tests/unit/Util/TestDox/ColorTest.php | 50 +++++++++++++++++++++++++-- 3 files changed, 57 insertions(+), 4 deletions(-) diff --git a/src/Util/TestDox/Color.php b/src/Util/TestDox/Color.php index f3faef82b2f..49bf37fd836 100644 --- a/src/Util/TestDox/Color.php +++ b/src/Util/TestDox/Color.php @@ -69,7 +69,7 @@ public static function colorize(string $color, string $buffer): string return \sprintf("\x1b[%sm", \implode(';', $styles)) . $buffer . "\x1b[0m"; } - public static function colorizePath(string $path, ?string $prevPath): string + public static function colorizePath(string $path, ?string $prevPath = null): string { if ($prevPath === null) { $prevPath = ''; diff --git a/tests/_files/raw_output_ColorTest.txt b/tests/_files/raw_output_ColorTest.txt index 0b50280b8c4..19dc04b65ac 100644 --- a/tests/_files/raw_output_ColorTest.txt +++ b/tests/_files/raw_output_ColorTest.txt @@ -6,6 +6,7 @@ Runtime: %s ✔ Colorize with no·color  %f ms ✔ Colorize with one·color  %f ms ✔ Colorize with multiple·colors  %f ms + ✔ Colorize path %ephp%eunit%etest.phpt after NULL  %f ms ✔ Colorize path %ephp%eunit%etest.phpt after empty  %f ms ✔ Colorize path %ephp%eunit%etest.phpt after %e  %f ms ✔ Colorize path %ephp%eunit%etest.phpt after %ephp%e  %f ms @@ -13,7 +14,13 @@ Runtime: %s ✔ Visiualize whitespace characters in no-spaces  %f ms ✔ Visiualize whitespace characters in ·space···invaders·  %s ms ✔ Visiualize whitespace characters in ⇥indent,·space·and·LF↵  %s ms + ✔ Prettify unnamed dataprovider with data set 0  %f ms + ✔ Prettify unnamed dataprovider with data set 1  %f ms + ✔ Prettify named dataprovider with one  %f ms + ✔ Prettify named dataprovider with two  %f ms + ✔ TestDox shows name of data set one with value 1  %f ms + ✔ TestDox shows name of data set two with value 2  %f ms Time: %s, Memory: %s -OK (10 tests, 10 assertions) +OK (17 tests, 17 assertions) diff --git a/tests/unit/Util/TestDox/ColorTest.php b/tests/unit/Util/TestDox/ColorTest.php index 77de0d95f57..0508fcfcc80 100644 --- a/tests/unit/Util/TestDox/ColorTest.php +++ b/tests/unit/Util/TestDox/ColorTest.php @@ -29,7 +29,7 @@ public function testColorize(string $color, string $buffer, string $expected): v * @testdox Colorize path $path after $prevPath * @dataProvider colorizePathProvider */ - public function testColorizePath(string $prevPath, string $path, string $expected): void + public function testColorizePath(?string $prevPath, string $path, string $expected): void { $this->assertSame($expected, Color::colorizePath($path, $prevPath)); } @@ -52,6 +52,31 @@ public function testVisibleWhitespace(string $actual, string $expected): void $this->assertSame($expected, Color::visiualizeWhitespace($actual)); } + /** + * @dataProvider unnamedDataSetProvider + */ + public function testPrettifyUnnamedDataprovider(int $value): void + { + $this->assertSame($value, $value); + } + + /** + * @dataProvider namedDataSetProvider + */ + public function testPrettifyNamedDataprovider(int $value): void + { + $this->assertSame($value, $value); + } + + /** + * @testdox TestDox shows name of data set $_dataName with value $value + * @dataProvider namedDataSetProvider + */ + public function testTestdoxDatanameAsParameter(int $value): void + { + $this->assertSame($value, $value); + } + public function colorizeProvider(): array { return [ @@ -67,7 +92,12 @@ public function colorizePathProvider(): array $sepDim = Color::dim($sep); return [ - 'no previous path' => [ + 'null previous path' => [ + null, + $sep . 'php' . $sep . 'unit' . $sep . 'test.phpt', + $sepDim . 'php' . $sepDim . 'unit' . $sepDim . 'test.phpt', + ], + 'empty previous path' => [ '', $sep . 'php' . $sep . 'unit' . $sep . 'test.phpt', $sepDim . 'php' . $sepDim . 'unit' . $sepDim . 'test.phpt', @@ -93,4 +123,20 @@ public function whitespacedStringProvider(): array ["\tindent, space and LF\n", "\e[2m⇥\e[22mindent,\e[2m·\e[22mspace\e[2m·\e[22mand\e[2m·\e[22mLF\e[2m↵\e[22m"], ]; } + + public function unnamedDataSetProvider(): array + { + return [ + [1], + [2], + ]; + } + + public function namedDataSetProvider(): array + { + return [ + 'one' => [1], + 'two' => [2], + ]; + } } From bd110df36a5bfdd980c1a3513cbfd705259cbf12 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Tue, 11 Dec 2018 00:39:47 +0100 Subject: [PATCH 31/51] Clean up --- src/Util/TestDox/Color.php | 2 +- src/Util/TestDox/NamePrettifier.php | 4 ++-- tests/_files/raw_output_ColorTest.txt | 6 +++--- tests/unit/Util/TestDox/ColorTest.php | 4 ++-- 4 files changed, 8 insertions(+), 8 deletions(-) diff --git a/src/Util/TestDox/Color.php b/src/Util/TestDox/Color.php index 49bf37fd836..22d9827a444 100644 --- a/src/Util/TestDox/Color.php +++ b/src/Util/TestDox/Color.php @@ -96,7 +96,7 @@ public static function dim(string $buffer): string return "\x1b[2m$buffer\x1b[22m"; } - public static function visiualizeWhitespace(string $buffer): string + public static function visualizeWhitespace(string $buffer): string { return \preg_replace_callback('/\s+/', function ($matches) { return self::dim(\strtr($matches[0], self::WHITESPACE_MAP)); diff --git a/src/Util/TestDox/NamePrettifier.php b/src/Util/TestDox/NamePrettifier.php index 74037b243b6..8700003cb22 100644 --- a/src/Util/TestDox/NamePrettifier.php +++ b/src/Util/TestDox/NamePrettifier.php @@ -109,7 +109,7 @@ public function prettifyDataSet(TestCase $test): string if (\is_int($test->dataName())) { $data = Color::dim(' with data set ') . Color::colorize('fg-cyan', $test->dataName()); } else { - $data = Color::dim(' with ') . Color::colorize('fg-cyan', Color::visiualizeWhitespace($test->dataName())); + $data = Color::dim(' with ') . Color::colorize('fg-cyan', Color::visualizeWhitespace($test->dataName())); } return $data; @@ -223,7 +223,7 @@ private function mapTestMethodParameterNamesToProvidedDataValues(TestCase $test) if ($this->useColor) { $providedData = \array_map(function ($value) { - return Color::colorize('fg-cyan', Color::visiualizeWhitespace($value)); + return Color::colorize('fg-cyan', Color::visualizeWhitespace($value)); }, $providedData); } diff --git a/tests/_files/raw_output_ColorTest.txt b/tests/_files/raw_output_ColorTest.txt index 19dc04b65ac..13ce5a89c05 100644 --- a/tests/_files/raw_output_ColorTest.txt +++ b/tests/_files/raw_output_ColorTest.txt @@ -11,9 +11,9 @@ Runtime: %s ✔ Colorize path %ephp%eunit%etest.phpt after %e  %f ms ✔ Colorize path %ephp%eunit%etest.phpt after %ephp%e  %f ms ✔ dim($m) and colorize('dim',$m) return different ANSI codes  %f ms - ✔ Visiualize whitespace characters in no-spaces  %f ms - ✔ Visiualize whitespace characters in ·space···invaders·  %s ms - ✔ Visiualize whitespace characters in ⇥indent,·space·and·LF↵  %s ms + ✔ Visualize whitespace characters in no-spaces  %f ms + ✔ Visualize whitespace characters in ·space···invaders·  %s ms + ✔ Visualize whitespace characters in ⇥indent,·space·and·LF↵  %s ms ✔ Prettify unnamed dataprovider with data set 0  %f ms ✔ Prettify unnamed dataprovider with data set 1  %f ms ✔ Prettify named dataprovider with one  %f ms diff --git a/tests/unit/Util/TestDox/ColorTest.php b/tests/unit/Util/TestDox/ColorTest.php index 0508fcfcc80..04616768360 100644 --- a/tests/unit/Util/TestDox/ColorTest.php +++ b/tests/unit/Util/TestDox/ColorTest.php @@ -44,12 +44,12 @@ public function testDimAndColorizeDimAreDifferent(): void } /** - * @testdox Visiualize whitespace characters in $actual + * @testdox Visualize whitespace characters in $actual * @dataProvider whitespacedStringProvider */ public function testVisibleWhitespace(string $actual, string $expected): void { - $this->assertSame($expected, Color::visiualizeWhitespace($actual)); + $this->assertSame($expected, Color::visualizeWhitespace($actual)); } /** From 52fcad0aeb6608e688ad14802d6dadc86f1a89e0 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Tue, 11 Dec 2018 14:13:39 +0100 Subject: [PATCH 32/51] Mirror test result colors for nicer verbose messages --- src/Util/TestDox/CliTestDoxPrinter.php | 72 ++++++++++++-------------- 1 file changed, 33 insertions(+), 39 deletions(-) diff --git a/src/Util/TestDox/CliTestDoxPrinter.php b/src/Util/TestDox/CliTestDoxPrinter.php index 199f1adc573..adde897d63a 100644 --- a/src/Util/TestDox/CliTestDoxPrinter.php +++ b/src/Util/TestDox/CliTestDoxPrinter.php @@ -135,7 +135,7 @@ public function endTest(Test $test, float $time): void } if ($this->testHasPassed()) { - $this->registerTestResult($test, BaseTestRunner::STATUS_PASSED, $time, ''); + $this->registerTestResult($test, null, BaseTestRunner::STATUS_PASSED, $time, false); } $this->flushOutputBuffer(); @@ -149,66 +149,54 @@ public function endTest(Test $test, float $time): void public function addError(Test $test, \Throwable $t, float $time): void { - $resultMessage = $this->formatTestResultMessage( - $this->formatThrowable($t, BaseTestRunner::STATUS_ERROR), - true - ); - $this->registerTestResult($test, BaseTestRunner::STATUS_ERROR, $time, $resultMessage); + $this->registerTestResult($test, $t, BaseTestRunner::STATUS_ERROR, $time, true); } public function addWarning(Test $test, Warning $e, float $time): void { - $resultMessage = $this->formatTestResultMessage( - $this->formatThrowable($e, BaseTestRunner::STATUS_WARNING), - true - ); - $this->registerTestResult($test, BaseTestRunner::STATUS_WARNING, $time, $resultMessage); + $this->registerTestResult($test, $e, BaseTestRunner::STATUS_WARNING, $time, true); } public function addFailure(Test $test, AssertionFailedError $e, float $time): void { - $resultMessage = $this->formatTestResultMessage( - $this->formatThrowable($e, BaseTestRunner::STATUS_FAILURE), - true - ); - $this->registerTestResult($test, BaseTestRunner::STATUS_FAILURE, $time, $resultMessage); + $this->registerTestResult($test, $e, BaseTestRunner::STATUS_FAILURE, $time, true); } public function addIncompleteTest(Test $test, \Throwable $t, float $time): void { - $resultMessage = $this->formatTestResultMessage( - $this->formatThrowable($t, BaseTestRunner::STATUS_INCOMPLETE), - false - ); - $this->registerTestResult($test, BaseTestRunner::STATUS_INCOMPLETE, $time, $resultMessage); + $this->registerTestResult($test, $t, BaseTestRunner::STATUS_INCOMPLETE, $time, false); } public function addRiskyTest(Test $test, \Throwable $t, float $time): void { - $resultMessage = $this->formatTestResultMessage( - $this->formatThrowable($t, BaseTestRunner::STATUS_RISKY), - false - ); - $this->registerTestResult($test, BaseTestRunner::STATUS_RISKY, $time, $resultMessage); + $this->registerTestResult($test, $t, BaseTestRunner::STATUS_RISKY, $time, false); } public function addSkippedTest(Test $test, \Throwable $t, float $time): void { - $resultMessage = $this->formatTestResultMessage( - $this->formatThrowable($t, BaseTestRunner::STATUS_SKIPPED), - false - ); - $this->registerTestResult($test, BaseTestRunner::STATUS_SKIPPED, $time, $resultMessage); + $this->registerTestResult($test, $t, BaseTestRunner::STATUS_SKIPPED, $time, false); } - public function registerTestResult(Test $test, int $status, float $time, string $msg): void + public function registerTestResult(Test $test, ?\Throwable $t, int $status, float $time, bool $verbose): void { - $testName = TestSuiteSorter::getTestSorterUID($test); + $testName = TestSuiteSorter::getTestSorterUID($test); + $status = $status ?? BaseTestRunner::STATUS_UNKNOWN; + + if ($t === null) { + $resultMessage = ''; + } else { + $resultMessage = $this->formatTestResultMessage( + $this->formatThrowable($t, $status), + $verbose, + $this->statusStyles[$status]['color'] + ); + } + $this->testResults[$this->testIndex] = [ 'className' => $this->getPrettyClassName($test), 'testName' => $testName, 'testMethod' => $this->getPrettyTestName($test), - 'message' => $msg, + 'message' => $resultMessage, 'status' => $status, 'time' => $time, ]; @@ -360,7 +348,7 @@ private function getFormattedRuntime(float $time, string $color = ''): string return Color::colorize($color, \sprintf(' %.2f ms', $time * 1000)); } - private function formatTestResultMessage(string $resultMessage, bool $verbose): string + private function formatTestResultMessage(string $resultMessage, bool $verbose, ?string $prefixColor = null): string { if ($resultMessage === '') { return ''; @@ -370,13 +358,20 @@ private function formatTestResultMessage(string $resultMessage, bool $verbose): return ''; } + $prefix = '│'; + + if ($this->colors && $prefixColor !== null) { + $prefix = Color::colorize($prefixColor, $prefix); + } + return \sprintf( - " │\n%s\n", + " %s\n%s\n", + $prefix, \implode( "\n", \array_map( - function (string $text) { - return \sprintf(' │ %s', $text); + function (string $text) use ($prefix) { + return \sprintf(' %s %s', $prefix, $text); }, \explode("\n", $resultMessage) ) @@ -421,7 +416,6 @@ private function formatThrowable(\Throwable $t, ?int $status = null): string $message = \PHPUnit\Framework\TestFailure::exceptionToString($t); if ($this->colors) { - $status = $status ?? BaseTestRunner::STATUS_UNKNOWN; $style = $this->statusStyles[$status]['message'] ?? ''; $message = $this->formatWithColor($style, $message); } From 9274c8248c793d3869aef671abac7e0b4bfacf67 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Thu, 13 Dec 2018 21:10:04 +0100 Subject: [PATCH 33/51] Remove dead code --- src/Util/TestDox/TestResult.php | 155 -------------------------------- 1 file changed, 155 deletions(-) delete mode 100644 src/Util/TestDox/TestResult.php diff --git a/src/Util/TestDox/TestResult.php b/src/Util/TestDox/TestResult.php deleted file mode 100644 index 6d8ae2fcf44..00000000000 --- a/src/Util/TestDox/TestResult.php +++ /dev/null @@ -1,155 +0,0 @@ - - * - * For the full copyright and license information, please view the LICENSE - * file that was distributed with this source code. - */ -namespace PHPUnit\Util\TestDox; - -final class TestResult -{ - /** - * @var callable - */ - private $colorize; - - /** - * @var string - */ - private $testClass; - - /** - * @var string - */ - private $testMethod; - - /** - * @var bool - */ - private $testSuccesful; - - /** - * @var string - */ - private $symbol; - - /** - * @var string - */ - private $additionalInformation; - - /** - * @var bool - */ - private $additionalInformationVerbose; - - /** - * @var float - */ - private $runtime; - - public function __construct(callable $colorize, string $testClass, string $testMethod) - { - $this->colorize = $colorize; - $this->testClass = $testClass; - $this->testMethod = $testMethod; - $this->testSuccesful = true; - $this->symbol = ($this->colorize)('fg-green', '✔'); - $this->additionalInformation = ''; - } - - public function isTestSuccessful(): bool - { - return $this->testSuccesful; - } - - public function fail(string $symbol, string $additionalInformation, bool $additionalInformationVerbose = false): void - { - $this->testSuccesful = false; - $this->symbol = $symbol; - $this->additionalInformation = $additionalInformation; - $this->additionalInformationVerbose = $additionalInformationVerbose; - } - - public function setRuntime(float $runtime): void - { - $this->runtime = $runtime; - } - - public function toString(?self $previousTestResult, $verbose = false): string - { - return \sprintf( - "%s%s %s %s%s\n%s", - $previousTestResult && $previousTestResult->additionalInformationPrintable($verbose) ? "\n" : '', - $this->getClassNameHeader($previousTestResult ? $previousTestResult->testClass : null), - $this->symbol, - $this->testMethod, - $verbose ? ' ' . $this->getFormattedRuntime() : '', - $this->getFormattedAdditionalInformation($verbose) - ); - } - - private function getClassNameHeader(?string $previousTestClass): string - { - $className = ''; - - if ($this->testClass !== $previousTestClass) { - if (null !== $previousTestClass) { - $className = "\n"; - } - - $className .= \sprintf("%s\n", $this->testClass); - } - - return $className; - } - - private function getFormattedRuntime(): string - { - if ($this->runtime > 5) { - return ($this->colorize)('fg-red', \sprintf('[%.2f ms]', $this->runtime * 1000)); - } - - if ($this->runtime > 1) { - return ($this->colorize)('fg-yellow', \sprintf('[%.2f ms]', $this->runtime * 1000)); - } - - return \sprintf('[%.2f ms]', $this->runtime * 1000); - } - - private function getFormattedAdditionalInformation($verbose): string - { - if (!$this->additionalInformationPrintable($verbose)) { - return ''; - } - - return \sprintf( - " │\n%s\n", - \implode( - "\n", - \array_map( - function (string $text) { - return \sprintf(' │ %s', $text); - }, - \explode("\n", $this->additionalInformation) - ) - ) - ); - } - - private function additionalInformationPrintable(bool $verbose): bool - { - if ($this->additionalInformation === '') { - return false; - } - - if ($this->additionalInformationVerbose && !$verbose) { - return false; - } - - return true; - } -} From 0e9f9e317d68fc720f6737f8d6b128b4cdbaa7a7 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Thu, 13 Dec 2018 22:27:19 +0100 Subject: [PATCH 34/51] Refactor generic parts of buffering TestDox printer --- src/Util/TestDox/CliTestDoxPrinter.php | 340 +++++-------------------- src/Util/TestDox/TestDoxPrinter.php | 287 +++++++++++++++++++++ 2 files changed, 350 insertions(+), 277 deletions(-) create mode 100644 src/Util/TestDox/TestDoxPrinter.php diff --git a/src/Util/TestDox/CliTestDoxPrinter.php b/src/Util/TestDox/CliTestDoxPrinter.php index adde897d63a..bdaf1c73e07 100644 --- a/src/Util/TestDox/CliTestDoxPrinter.php +++ b/src/Util/TestDox/CliTestDoxPrinter.php @@ -9,64 +9,24 @@ */ namespace PHPUnit\Util\TestDox; -use PHPUnit\Framework\AssertionFailedError; use PHPUnit\Framework\Test; use PHPUnit\Framework\TestCase; use PHPUnit\Framework\TestResult; -use PHPUnit\Framework\TestSuite; -use PHPUnit\Framework\Warning; use PHPUnit\Runner\BaseTestRunner; use PHPUnit\Runner\PhptTestCase; -use PHPUnit\Runner\TestSuiteSorter; -use PHPUnit\TextUI\ResultPrinter; use SebastianBergmann\Timer\Timer; /** * This printer is for CLI output only. For the classes that output to file, html and xml, * please refer to the PHPUnit\Util\TestDox namespace */ -class CliTestDoxPrinter extends ResultPrinter +class CliTestDoxPrinter extends TestDoxPrinter { /** * @var int[] */ private $nonSuccessfulTestResults = []; - /** - * @var NamePrettifier - */ - private $prettifier; - - /** - * @var int The number of test results received from the TestRunner - */ - private $testIndex = 0; - - /** - * @var int The number of test results already sent to the output - */ - private $testFlushIndex = 0; - - /** - * @var array Buffer for test results - */ - private $testResults = []; - - /** - * @var array Lookup table for testname to testResults[index] - */ - private $testNameResultIndex = []; - - /** - * @var bool - */ - private $enableOutputBuffer = false; - - /** - * @var array array - */ - private $originalExecutionOrder = []; - private $statusStyles = [ BaseTestRunner::STATUS_PASSED => [ 'symbol' => '✔', @@ -109,113 +69,6 @@ class CliTestDoxPrinter extends ResultPrinter ], ]; - public function __construct( - $out = null, - bool $verbose = false, - $colors = self::COLOR_DEFAULT, - bool $debug = false, - $numberOfColumns = 80, - bool $reverse = false - ) { - parent::__construct($out, $verbose, $colors, $debug, $numberOfColumns, $reverse); - - $this->prettifier = new NamePrettifier($this->colors); - } - - public function setOriginalExecutionOrder(array $order): void - { - $this->originalExecutionOrder = $order; - $this->enableOutputBuffer = !empty($order); - } - - public function endTest(Test $test, float $time): void - { - if (!$test instanceof TestCase && !$test instanceof PhptTestCase && !$test instanceof TestSuite) { - return; - } - - if ($this->testHasPassed()) { - $this->registerTestResult($test, null, BaseTestRunner::STATUS_PASSED, $time, false); - } - - $this->flushOutputBuffer(); - - if ($test instanceof TestCase || $test instanceof PhptTestCase) { - $this->testIndex++; - } - - parent::endTest($test, $time); - } - - public function addError(Test $test, \Throwable $t, float $time): void - { - $this->registerTestResult($test, $t, BaseTestRunner::STATUS_ERROR, $time, true); - } - - public function addWarning(Test $test, Warning $e, float $time): void - { - $this->registerTestResult($test, $e, BaseTestRunner::STATUS_WARNING, $time, true); - } - - public function addFailure(Test $test, AssertionFailedError $e, float $time): void - { - $this->registerTestResult($test, $e, BaseTestRunner::STATUS_FAILURE, $time, true); - } - - public function addIncompleteTest(Test $test, \Throwable $t, float $time): void - { - $this->registerTestResult($test, $t, BaseTestRunner::STATUS_INCOMPLETE, $time, false); - } - - public function addRiskyTest(Test $test, \Throwable $t, float $time): void - { - $this->registerTestResult($test, $t, BaseTestRunner::STATUS_RISKY, $time, false); - } - - public function addSkippedTest(Test $test, \Throwable $t, float $time): void - { - $this->registerTestResult($test, $t, BaseTestRunner::STATUS_SKIPPED, $time, false); - } - - public function registerTestResult(Test $test, ?\Throwable $t, int $status, float $time, bool $verbose): void - { - $testName = TestSuiteSorter::getTestSorterUID($test); - $status = $status ?? BaseTestRunner::STATUS_UNKNOWN; - - if ($t === null) { - $resultMessage = ''; - } else { - $resultMessage = $this->formatTestResultMessage( - $this->formatThrowable($t, $status), - $verbose, - $this->statusStyles[$status]['color'] - ); - } - - $this->testResults[$this->testIndex] = [ - 'className' => $this->getPrettyClassName($test), - 'testName' => $testName, - 'testMethod' => $this->getPrettyTestName($test), - 'message' => $resultMessage, - 'status' => $status, - 'time' => $time, - ]; - - $this->testNameResultIndex[$testName] = $this->testIndex; - - if ($status !== BaseTestRunner::STATUS_PASSED) { - $this->nonSuccessfulTestResults[] = $this->testIndex; - } - } - - public function writeProgress(string $progress): void - { - } - - public function flush(): void - { - } - public function printResult(TestResult $result): void { $this->printHeader(); @@ -230,7 +83,7 @@ protected function printHeader(): void $this->write("\n" . Timer::resourceUsage() . "\n\n"); } - private function getPrettyClassName(Test $test): string + protected function formatClassName(Test $test): string { if ($test instanceof TestCase) { return $this->prettifier->prettifyTestClass(\get_class($test)); @@ -239,62 +92,25 @@ private function getPrettyClassName(Test $test): string return \get_class($test); } - private function getPrettyTestName(Test $test): string - { - if ($test instanceof TestCase) { - return $this->prettifier->prettifyTestCase($test); - } - - return $test->getName(); - } - - private function testHasPassed(): bool + protected function registerTestResult(Test $test, ?\Throwable $t, int $status, float $time, bool $verbose): void { - if (!isset($this->testResults[$this->testIndex]['status'])) { - return true; - } - - if ($this->testResults[$this->testIndex]['status'] === BaseTestRunner::STATUS_PASSED) { - return true; + if ($status !== BaseTestRunner::STATUS_PASSED) { + $this->nonSuccessfulTestResults[] = $this->testIndex; } - return false; + parent::registerTestResult($test, $t, $status, $time, $verbose); } - private function flushOutputBuffer(): void + protected function formatTestName(Test $test): string { - if ($this->enableOutputBuffer && ($this->testFlushIndex > $this->testIndex)) { - return; - } - - if ($this->testFlushIndex > 0) { - if ($this->enableOutputBuffer) { - $prevResult = $this->getTestResultByName($this->originalExecutionOrder[$this->testFlushIndex - 1]); - } else { - $prevResult = $this->testResults[$this->testFlushIndex - 1]; - } - } else { - $prevResult = $this->getEmptyTestResult(); + if ($test instanceof TestCase) { + return $this->prettifier->prettifyTestCase($test); } - if (!$this->enableOutputBuffer) { - $this->writeTestResult($prevResult, $this->testResults[$this->testFlushIndex++]); - } else { - do { - $flushed = false; - $result = $this->getTestResultByName($this->originalExecutionOrder[$this->testFlushIndex]); - - if (!empty($result)) { - $this->writeTestResult($prevResult, $result); - $this->testFlushIndex++; - $prevResult = $result; - $flushed = true; - } - } while ($flushed && $this->testFlushIndex <= $this->testIndex); - } + return parent::formatTestName($test); } - private function writeTestResult(array $prevResult, array $result): void + protected function writeTestResult(array $prevResult, array $result): void { // spacer line for new suite headers and after verbose messages if ($prevResult['testName'] !== '' && @@ -318,7 +134,7 @@ private function writeTestResult(array $prevResult, array $result): void " %s %s%s\n", $this->formatWithColor($style['color'], $style['symbol']), $testName, - $this->verbose ? ' ' . $this->getFormattedRuntime($result['time'], $style['color']) : '' + $this->verbose ? ' ' . $this->formatRuntime($result['time'], $style['color']) : '' ); $this->write($line); @@ -326,31 +142,52 @@ private function writeTestResult(array $prevResult, array $result): void $this->write($result['message']); } - private function getTestResultByName(string $testName): array + protected function formatThrowable(\Throwable $t, ?int $status = null): string { - if (isset($this->testNameResultIndex[$testName])) { - return $this->testResults[$this->testNameResultIndex[$testName]]; + $message = \PHPUnit\Framework\TestFailure::exceptionToString($t); + + if ($this->colors) { + $style = $this->statusStyles[$status]['message'] ?? ''; + $message = $this->formatWithColor($style, $message); } - return []; + return \sprintf( + "%s\n%s", + $message, + $this->formatStacktrace($t) + ); } - private function getFormattedRuntime(float $time, string $color = ''): string + protected function formatStacktrace(\Throwable $t): string { + $trace = \PHPUnit\Util\Filter::getFilteredStacktrace($t); + if (!$this->colors) { - return \sprintf('[%.2f ms]', $time * 1000); + return $trace; } - if ($time > 1) { - $color = 'fg-magenta'; + $lines = []; + $prevPath = ''; + + foreach (\explode("\n", $trace) as $line) { + if (\preg_match('/^(.*):(\d+)$/', $line, $matches)) { + $lines[] = Color::colorizePath($matches[1], $prevPath) . + Color::dim(':') . + Color::colorize('fg-blue', $matches[2]) . + "\n"; + $prevPath = $matches[1]; + } else { + $lines[] = $line; + $prevPath = ''; + } } - return Color::colorize($color, \sprintf(' %.2f ms', $time * 1000)); + return \implode('', $lines); } - private function formatTestResultMessage(string $resultMessage, bool $verbose, ?string $prefixColor = null): string + protected function formatTestResultMessage(string $message, int $status, bool $verbose, ?string $prefix = null): string { - if ($resultMessage === '') { + if ($message === '') { return ''; } @@ -358,25 +195,28 @@ private function formatTestResultMessage(string $resultMessage, bool $verbose, ? return ''; } - $prefix = '│'; + if ($prefix === null) { + $prefix = '│'; + } - if ($this->colors && $prefixColor !== null) { - $prefix = Color::colorize($prefixColor, $prefix); + if ($this->colors) { + $prefix = Color::colorize($this->statusStyles[$status]['color'] ?? '', $prefix); } - return \sprintf( - " %s\n%s\n", - $prefix, - \implode( - "\n", - \array_map( - function (string $text) use ($prefix) { - return \sprintf(' %s %s', $prefix, $text); - }, - \explode("\n", $resultMessage) - ) - ) - ); + return parent::formatTestResultMessage($message, $status, $verbose, $prefix); + } + + private function formatRuntime(float $time, string $color = ''): string + { + if (!$this->colors) { + return \sprintf('[%.2f ms]', $time * 1000); + } + + if ($time > 1) { + $color = 'fg-magenta'; + } + + return Color::colorize($color, \sprintf(' %.2f ms', $time * 1000)); } private function printNonSuccessfulTestsSummary(int $numberOfExecutedTests): void @@ -399,58 +239,4 @@ private function printNonSuccessfulTestsSummary(int $numberOfExecutedTests): voi $prevResult = $result; } } - - private function getEmptyTestResult(): array - { - return [ - 'className' => '', - 'testName' => '', - 'message' => '', - 'failed' => '', - 'verbose' => '', - ]; - } - - private function formatThrowable(\Throwable $t, ?int $status = null): string - { - $message = \PHPUnit\Framework\TestFailure::exceptionToString($t); - - if ($this->colors) { - $style = $this->statusStyles[$status]['message'] ?? ''; - $message = $this->formatWithColor($style, $message); - } - - return \sprintf( - "%s\n%s", - $message, - $this->colorizeStacktrace($t) - ); - } - - private function colorizeStacktrace(\Throwable $t): string - { - $trace = \PHPUnit\Util\Filter::getFilteredStacktrace($t); - - if (!$this->colors) { - return $trace; - } - - $lines = []; - $prevPath = ''; - - foreach (\explode("\n", $trace) as $line) { - if (\preg_match('/^(.*):(\d+)$/', $line, $matches)) { - $lines[] = Color::colorizePath($matches[1], $prevPath) . - Color::dim(':') . - Color::colorize('fg-blue', $matches[2]) . - "\n"; - $prevPath = $matches[1]; - } else { - $lines[] = $line; - $prevPath = ''; - } - } - - return \implode('', $lines); - } } diff --git a/src/Util/TestDox/TestDoxPrinter.php b/src/Util/TestDox/TestDoxPrinter.php new file mode 100644 index 00000000000..3a30a5ba8f4 --- /dev/null +++ b/src/Util/TestDox/TestDoxPrinter.php @@ -0,0 +1,287 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ +namespace PHPUnit\Util\TestDox; + +use PHPUnit\Framework\AssertionFailedError; +use PHPUnit\Framework\Test; +use PHPUnit\Framework\TestCase; +use PHPUnit\Framework\TestResult; +use PHPUnit\Framework\TestSuite; +use PHPUnit\Framework\Warning; +use PHPUnit\Runner\BaseTestRunner; +use PHPUnit\Runner\PhptTestCase; +use PHPUnit\Runner\TestSuiteSorter; +use PHPUnit\TextUI\ResultPrinter; + +class TestDoxPrinter extends ResultPrinter +{ + /** + * @var NamePrettifier + */ + protected $prettifier; + + /** + * @var int The number of test results received from the TestRunner + */ + protected $testIndex = 0; + + /** + * @var int The number of test results already sent to the output + */ + protected $testFlushIndex = 0; + + /** + * @var array Buffer for test results + */ + protected $testResults = []; + + /** + * @var array Lookup table for testname to testResults[index] + */ + protected $testNameResultIndex = []; + + /** + * @var bool + */ + protected $enableOutputBuffer = false; + + /** + * @var array array + */ + protected $originalExecutionOrder = []; + + public function __construct( + $out = null, + bool $verbose = false, + $colors = self::COLOR_DEFAULT, + bool $debug = false, + $numberOfColumns = 80, + bool $reverse = false + ) { + parent::__construct($out, $verbose, $colors, $debug, $numberOfColumns, $reverse); + + $this->prettifier = new NamePrettifier($this->colors); + } + + public function setOriginalExecutionOrder(array $order): void + { + $this->originalExecutionOrder = $order; + $this->enableOutputBuffer = !empty($order); + } + + public function printResult(TestResult $result): void + { + } + + public function endTest(Test $test, float $time): void + { + if (!$test instanceof TestCase && !$test instanceof PhptTestCase && !$test instanceof TestSuite) { + return; + } + + if ($this->testHasPassed()) { + $this->registerTestResult($test, null, BaseTestRunner::STATUS_PASSED, $time, false); + } + + if ($test instanceof TestCase || $test instanceof PhptTestCase) { + $this->testIndex++; + } + + parent::endTest($test, $time); + } + + public function addError(Test $test, \Throwable $t, float $time): void + { + $this->registerTestResult($test, $t, BaseTestRunner::STATUS_ERROR, $time, true); + } + + public function addWarning(Test $test, Warning $e, float $time): void + { + $this->registerTestResult($test, $e, BaseTestRunner::STATUS_WARNING, $time, true); + } + + public function addFailure(Test $test, AssertionFailedError $e, float $time): void + { + $this->registerTestResult($test, $e, BaseTestRunner::STATUS_FAILURE, $time, true); + } + + public function addIncompleteTest(Test $test, \Throwable $t, float $time): void + { + $this->registerTestResult($test, $t, BaseTestRunner::STATUS_INCOMPLETE, $time, false); + } + + public function addRiskyTest(Test $test, \Throwable $t, float $time): void + { + $this->registerTestResult($test, $t, BaseTestRunner::STATUS_RISKY, $time, false); + } + + public function addSkippedTest(Test $test, \Throwable $t, float $time): void + { + $this->registerTestResult($test, $t, BaseTestRunner::STATUS_SKIPPED, $time, false); + } + + public function writeProgress(string $progress): void + { + $this->flushOutputBuffer(); + } + + public function flush(): void + { + $this->flushOutputBuffer(); + } + + protected function registerTestResult(Test $test, ?\Throwable $t, int $status, float $time, bool $verbose): void + { + $testName = TestSuiteSorter::getTestSorterUID($test); + $status = $status ?? BaseTestRunner::STATUS_UNKNOWN; + + if ($t === null) { + $resultMessage = ''; + } else { + $resultMessage = $this->formatTestResultMessage( + $this->formatThrowable($t, $status), + $status, + $verbose + ); + } + + $this->testResults[$this->testIndex] = [ + 'className' => $this->formatClassName($test), + 'testName' => $testName, + 'testMethod' => $this->formatTestName($test), + 'message' => $resultMessage, + 'status' => $status, + 'time' => $time, + ]; + + $this->testNameResultIndex[$testName] = $this->testIndex; + } + + protected function formatTestName(Test $test): string + { + return $test->getName(); + } + + protected function formatClassName(Test $test): string + { + return \get_class($test); + } + + protected function testHasPassed(): bool + { + if (!isset($this->testResults[$this->testIndex]['status'])) { + return true; + } + + if ($this->testResults[$this->testIndex]['status'] === BaseTestRunner::STATUS_PASSED) { + return true; + } + + return false; + } + + protected function flushOutputBuffer(): void + { + if ($this->testFlushIndex === $this->testIndex) { + return; + } + + if ($this->testFlushIndex > 0) { + if ($this->enableOutputBuffer) { + $prevResult = $this->getTestResultByName($this->originalExecutionOrder[$this->testFlushIndex - 1]); + } else { + $prevResult = $this->testResults[$this->testFlushIndex - 1]; + } + } else { + $prevResult = $this->getEmptyTestResult(); + } + + if (!$this->enableOutputBuffer) { + $this->writeTestResult($prevResult, $this->testResults[$this->testFlushIndex++]); + } else { + do { + $flushed = false; + $result = $this->getTestResultByName($this->originalExecutionOrder[$this->testFlushIndex]); + + if (!empty($result)) { + $this->writeTestResult($prevResult, $result); + $this->testFlushIndex++; + $prevResult = $result; + $flushed = true; + } + } while ($flushed && $this->testFlushIndex < $this->testIndex); + } + } + + protected function writeTestResult(array $prevResult, array $result): void + { + } + + protected function getEmptyTestResult(): array + { + return [ + 'className' => '', + 'testName' => '', + 'message' => '', + 'failed' => '', + 'verbose' => '', + ]; + } + + protected function getTestResultByName(?string $testName): array + { + if (isset($this->testNameResultIndex[$testName])) { + return $this->testResults[$this->testNameResultIndex[$testName]]; + } + + return []; + } + + protected function formatThrowable(\Throwable $t, ?int $status = null): string + { + $message = \PHPUnit\Framework\TestFailure::exceptionToString($t); + + return \sprintf( + "%s\n%s", + $message, + $this->formatStacktrace($t) + ); + } + + protected function formatStacktrace(\Throwable $t): string + { + return \PHPUnit\Util\Filter::getFilteredStacktrace($t); + } + + protected function formatTestResultMessage(string $message, int $status, bool $verbose, string $prefix = '│'): string + { + if ($message === '') { + return ''; + } + + if (!($this->verbose || $verbose)) { + return ''; + } + + return \sprintf( + " %s\n%s\n", + $prefix, + \implode( + "\n", + \array_map( + function (string $text) use ($prefix) { + return \sprintf(' %s %s', $prefix, $text); + }, + \explode("\n", $message) + ) + ) + ); + } +} From 4a43d862100a350e341187a95b2239f527829cec Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Fri, 14 Dec 2018 18:07:51 +0100 Subject: [PATCH 35/51] Improve coverage of TestDox colorization of unsuccessful test results --- tests/_files/raw_output_StatusTest.txt | 51 +++++++++++++++++++ .../testdox-dataprovider-placeholder.phpt | 2 +- .../testdox-status-colorization.phpt | 14 +++++ 3 files changed, 66 insertions(+), 1 deletion(-) create mode 100644 tests/_files/raw_output_StatusTest.txt create mode 100644 tests/end-to-end/testdox-status-colorization.phpt diff --git a/tests/_files/raw_output_StatusTest.txt b/tests/_files/raw_output_StatusTest.txt new file mode 100644 index 00000000000..f29f5ed3a50 --- /dev/null +++ b/tests/_files/raw_output_StatusTest.txt @@ -0,0 +1,51 @@ +PHPUnit %s by Sebastian Bergmann and contributors. + +Runtime: %s + +vendor\project\Status + ✔ Success  %f ms + ✘ Failure  %f ms + │ + │ Failed asserting that false is true. + │ + │ %stests%e_files%eStatusTest.php:24 + │ + + ✘ Error  %f ms + │ + │ RuntimeException:  + │ + │ %stests%e_files%eStatusTest.php:29 + │ + + ∅ Incomplete  %f ms + │ + │ + │ %stests%e_files%eStatusTest.php:34 + │ + + → Skipped  %f ms + │ + │ + │ %stests%e_files%eStatusTest.php:39 + │ + + ☢ Risky  %f ms + │ + │ This test did not perform any assertions  + │ + │ %stests%e_files%eStatusTest.php:42 + │ + │ + + ✘ Warning  %f ms + │ + │ + │ %stests%e_files%eStatusTest.php:48 + │ + +Time: %s, Memory: %s + + +ERRORS! +Tests: 7, Assertions: 2, Errors: 1, Failures: 1, Warnings: 1, Skipped: 1, Incomplete: 1, Risky: 1. diff --git a/tests/end-to-end/testdox-dataprovider-placeholder.phpt b/tests/end-to-end/testdox-dataprovider-placeholder.phpt index b5d57ae0530..0e790332cc7 100644 --- a/tests/end-to-end/testdox-dataprovider-placeholder.phpt +++ b/tests/end-to-end/testdox-dataprovider-placeholder.phpt @@ -6,7 +6,7 @@ $_SERVER['argv'][1] = '--no-configuration'; $_SERVER['argv'][2] = '--testdox'; $_SERVER['argv'][3] = '--colors=always'; $_SERVER['argv'][4] = '--verbose'; -$_SERVER['argv'][5] = __DIR__ . '/../unit/Util/TestDox/ColorTest.php'; +$_SERVER['argv'][5] = realpath(__DIR__ . '/../unit/Util/TestDox/ColorTest.php'); require __DIR__ . '/../bootstrap.php'; PHPUnit\TextUI\Command::main(); diff --git a/tests/end-to-end/testdox-status-colorization.phpt b/tests/end-to-end/testdox-status-colorization.phpt new file mode 100644 index 00000000000..72423798525 --- /dev/null +++ b/tests/end-to-end/testdox-status-colorization.phpt @@ -0,0 +1,14 @@ +--TEST-- +phpunit --testdox --colors=always --verbose RouterTest ../_files/StatusTest.php +--FILE-- + Date: Fri, 14 Dec 2018 18:59:32 +0100 Subject: [PATCH 36/51] Make visualizing EOL optional --- src/Util/TestDox/Color.php | 13 ++++++++++--- src/Util/TestDox/NamePrettifier.php | 2 +- tests/_files/raw_output_ColorTest.txt | 9 +++++---- tests/unit/Util/TestDox/ColorTest.php | 13 +++++++++++-- 4 files changed, 27 insertions(+), 10 deletions(-) diff --git a/src/Util/TestDox/Color.php b/src/Util/TestDox/Color.php index 22d9827a444..e5f06b70912 100644 --- a/src/Util/TestDox/Color.php +++ b/src/Util/TestDox/Color.php @@ -14,6 +14,11 @@ class Color private const WHITESPACE_MAP = [ ' ' => '·', "\t" => '⇥', + ]; + + private const WHITESPACE_EOL_MAP = [ + ' ' => '·', + "\t" => '⇥', "\n" => '↵', ]; @@ -96,10 +101,12 @@ public static function dim(string $buffer): string return "\x1b[2m$buffer\x1b[22m"; } - public static function visualizeWhitespace(string $buffer): string + public static function visualizeWhitespace(string $buffer, bool $visualizeEOL = false): string { - return \preg_replace_callback('/\s+/', function ($matches) { - return self::dim(\strtr($matches[0], self::WHITESPACE_MAP)); + $replaceMap = $visualizeEOL ? self::WHITESPACE_EOL_MAP : self::WHITESPACE_MAP; + + return \preg_replace_callback('/\s+/', function ($matches) use ($replaceMap) { + return self::dim(\strtr($matches[0], $replaceMap)); }, $buffer); } } diff --git a/src/Util/TestDox/NamePrettifier.php b/src/Util/TestDox/NamePrettifier.php index 8700003cb22..1ecb5e729e0 100644 --- a/src/Util/TestDox/NamePrettifier.php +++ b/src/Util/TestDox/NamePrettifier.php @@ -223,7 +223,7 @@ private function mapTestMethodParameterNamesToProvidedDataValues(TestCase $test) if ($this->useColor) { $providedData = \array_map(function ($value) { - return Color::colorize('fg-cyan', Color::visualizeWhitespace($value)); + return Color::colorize('fg-cyan', Color::visualizeWhitespace($value, true)); }, $providedData); } diff --git a/tests/_files/raw_output_ColorTest.txt b/tests/_files/raw_output_ColorTest.txt index 13ce5a89c05..d26df900849 100644 --- a/tests/_files/raw_output_ColorTest.txt +++ b/tests/_files/raw_output_ColorTest.txt @@ -11,9 +11,10 @@ Runtime: %s ✔ Colorize path %ephp%eunit%etest.phpt after %e  %f ms ✔ Colorize path %ephp%eunit%etest.phpt after %ephp%e  %f ms ✔ dim($m) and colorize('dim',$m) return different ANSI codes  %f ms - ✔ Visualize whitespace characters in no-spaces  %f ms - ✔ Visualize whitespace characters in ·space···invaders·  %s ms - ✔ Visualize whitespace characters in ⇥indent,·space·and·LF↵  %s ms + ✔ Visualize all whitespace characters in no-spaces  %f ms + ✔ Visualize all whitespace characters in ·space···invaders·  %s ms + ✔ Visualize all whitespace characters in ⇥indent,·space·and·LF↵  %s ms + ✔ Visualize whitespace but ignore EOL  %f ms ✔ Prettify unnamed dataprovider with data set 0  %f ms ✔ Prettify unnamed dataprovider with data set 1  %f ms ✔ Prettify named dataprovider with one  %f ms @@ -23,4 +24,4 @@ Runtime: %s Time: %s, Memory: %s -OK (17 tests, 17 assertions) +OK (18 tests, 18 assertions) diff --git a/tests/unit/Util/TestDox/ColorTest.php b/tests/unit/Util/TestDox/ColorTest.php index 04616768360..3d6cbc3c5e3 100644 --- a/tests/unit/Util/TestDox/ColorTest.php +++ b/tests/unit/Util/TestDox/ColorTest.php @@ -44,12 +44,21 @@ public function testDimAndColorizeDimAreDifferent(): void } /** - * @testdox Visualize whitespace characters in $actual + * @testdox Visualize all whitespace characters in $actual * @dataProvider whitespacedStringProvider */ public function testVisibleWhitespace(string $actual, string $expected): void { - $this->assertSame($expected, Color::visualizeWhitespace($actual)); + $this->assertSame($expected, Color::visualizeWhitespace($actual, true)); + } + + /** + * @testdox Visualize whitespace but ignore EOL + */ + public function testVisibleWhitespaceWithoutEOL(): void + { + $string = "line1\nline2\n"; + $this->assertSame($string, Color::visualizeWhitespace($string, false)); } /** From 5b04b9591539503b00e71766984ea7a2010a30d1 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Fri, 14 Dec 2018 20:03:28 +0100 Subject: [PATCH 37/51] Clean up colorized TestDox format of test result exception messages --- src/Util/TestDox/CliTestDoxPrinter.php | 20 +++++++++++--------- src/Util/TestDox/TestDoxPrinter.php | 14 ++++++++------ tests/_files/raw_output_StatusTest.txt | 13 +++++-------- 3 files changed, 24 insertions(+), 23 deletions(-) diff --git a/src/Util/TestDox/CliTestDoxPrinter.php b/src/Util/TestDox/CliTestDoxPrinter.php index bdaf1c73e07..30f8890a823 100644 --- a/src/Util/TestDox/CliTestDoxPrinter.php +++ b/src/Util/TestDox/CliTestDoxPrinter.php @@ -144,18 +144,20 @@ protected function writeTestResult(array $prevResult, array $result): void protected function formatThrowable(\Throwable $t, ?int $status = null): string { - $message = \PHPUnit\Framework\TestFailure::exceptionToString($t); + $message = trim(\PHPUnit\Framework\TestFailure::exceptionToString($t)); - if ($this->colors) { - $style = $this->statusStyles[$status]['message'] ?? ''; - $message = $this->formatWithColor($style, $message); + if ($message) { + if ($this->colors) { + $style = $this->statusStyles[$status]['message'] ?? ''; + $message = $this->formatWithColor($style, $message); + } + + $message .= "\n\n" . $this->formatStacktrace($t); + } else { + $message = $this->formatStacktrace($t); } - return \sprintf( - "%s\n%s", - $message, - $this->formatStacktrace($t) - ); + return $message; } protected function formatStacktrace(\Throwable $t): string diff --git a/src/Util/TestDox/TestDoxPrinter.php b/src/Util/TestDox/TestDoxPrinter.php index 3a30a5ba8f4..605bced52cb 100644 --- a/src/Util/TestDox/TestDoxPrinter.php +++ b/src/Util/TestDox/TestDoxPrinter.php @@ -246,13 +246,15 @@ protected function getTestResultByName(?string $testName): array protected function formatThrowable(\Throwable $t, ?int $status = null): string { - $message = \PHPUnit\Framework\TestFailure::exceptionToString($t); + $message = trim(\PHPUnit\Framework\TestFailure::exceptionToString($t)); - return \sprintf( - "%s\n%s", - $message, - $this->formatStacktrace($t) - ); + if ($message) { + $message .= "\n\n" . $this->formatStacktrace($t); + } else { + $message = $this->formatStacktrace($t); + } + + return $message; } protected function formatStacktrace(\Throwable $t): string diff --git a/tests/_files/raw_output_StatusTest.txt b/tests/_files/raw_output_StatusTest.txt index f29f5ed3a50..b3eaa576626 100644 --- a/tests/_files/raw_output_StatusTest.txt +++ b/tests/_files/raw_output_StatusTest.txt @@ -1,4 +1,4 @@ -PHPUnit %s by Sebastian Bergmann and contributors. +PHPUnit %s Sebastian Bergmann and contributors. Runtime: %s @@ -7,26 +7,24 @@ Runtime: %s ✘ Failure  %f ms │ │ Failed asserting that false is true. - │ + │ │ %stests%e_files%eStatusTest.php:24 │ ✘ Error  %f ms │ - │ RuntimeException:  - │ + │ RuntimeException: + │ │ %stests%e_files%eStatusTest.php:29 │ ∅ Incomplete  %f ms │ - │ │ %stests%e_files%eStatusTest.php:34 │ → Skipped  %f ms │ - │ │ %stests%e_files%eStatusTest.php:39 │ @@ -35,12 +33,11 @@ Runtime: %s │ This test did not perform any assertions  │ │ %stests%e_files%eStatusTest.php:42 - │ + │ │ ✘ Warning  %f ms │ - │ │ %stests%e_files%eStatusTest.php:48 │ From f350c9bfd1ac8cff18691a62602616c6bec6dde5 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Fri, 14 Dec 2018 20:11:02 +0100 Subject: [PATCH 38/51] Fix raw test data mangled by editor --- tests/_files/raw_output_StatusTest.txt | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/tests/_files/raw_output_StatusTest.txt b/tests/_files/raw_output_StatusTest.txt index b3eaa576626..ac70ebfdf48 100644 --- a/tests/_files/raw_output_StatusTest.txt +++ b/tests/_files/raw_output_StatusTest.txt @@ -30,8 +30,8 @@ Runtime: %s ☢ Risky  %f ms │ - │ This test did not perform any assertions  - │ + │ This test did not perform any assertions + │ │ %stests%e_files%eStatusTest.php:42 │ │ From adfde1f10d1ca94a5d20c5c542917acec18afc88 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Fri, 14 Dec 2018 20:45:26 +0100 Subject: [PATCH 39/51] CS/WS fixes. Work around edge case with Risky result messages. --- src/Util/TestDox/CliTestDoxPrinter.php | 3 ++- src/Util/TestDox/TestDoxPrinter.php | 2 +- tests/_files/raw_output_StatusTest.txt | 4 ++-- 3 files changed, 5 insertions(+), 4 deletions(-) diff --git a/src/Util/TestDox/CliTestDoxPrinter.php b/src/Util/TestDox/CliTestDoxPrinter.php index 30f8890a823..119fbdf6bf5 100644 --- a/src/Util/TestDox/CliTestDoxPrinter.php +++ b/src/Util/TestDox/CliTestDoxPrinter.php @@ -144,7 +144,8 @@ protected function writeTestResult(array $prevResult, array $result): void protected function formatThrowable(\Throwable $t, ?int $status = null): string { - $message = trim(\PHPUnit\Framework\TestFailure::exceptionToString($t)); + $message = \trim(\PHPUnit\Framework\TestFailure::exceptionToString($t)); + $message = \implode(\PHP_EOL, \array_map('\trim', \explode(\PHP_EOL, $message))); if ($message) { if ($this->colors) { diff --git a/src/Util/TestDox/TestDoxPrinter.php b/src/Util/TestDox/TestDoxPrinter.php index 605bced52cb..0df6887a324 100644 --- a/src/Util/TestDox/TestDoxPrinter.php +++ b/src/Util/TestDox/TestDoxPrinter.php @@ -246,7 +246,7 @@ protected function getTestResultByName(?string $testName): array protected function formatThrowable(\Throwable $t, ?int $status = null): string { - $message = trim(\PHPUnit\Framework\TestFailure::exceptionToString($t)); + $message = \trim(\PHPUnit\Framework\TestFailure::exceptionToString($t)); if ($message) { $message .= "\n\n" . $this->formatStacktrace($t); diff --git a/tests/_files/raw_output_StatusTest.txt b/tests/_files/raw_output_StatusTest.txt index ac70ebfdf48..4391c20e881 100644 --- a/tests/_files/raw_output_StatusTest.txt +++ b/tests/_files/raw_output_StatusTest.txt @@ -30,8 +30,8 @@ Runtime: %s ☢ Risky  %f ms │ - │ This test did not perform any assertions - │ + │ This test did not perform any assertions%w + │%w │ %stests%e_files%eStatusTest.php:42 │ │ From 8c73bdfff929c48899d349ae92736924cb8880ef Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Fri, 14 Dec 2018 21:49:18 +0100 Subject: [PATCH 40/51] Make PHPT filenames prettier --- src/Util/TestDox/CliTestDoxPrinter.php | 2 +- src/Util/TestDox/Color.php | 9 ++++++++- tests/_files/raw_output_ColorTest.txt | 3 ++- tests/unit/Util/TestDox/ColorTest.php | 14 ++++++++++++-- 4 files changed, 23 insertions(+), 5 deletions(-) diff --git a/src/Util/TestDox/CliTestDoxPrinter.php b/src/Util/TestDox/CliTestDoxPrinter.php index 119fbdf6bf5..9b1056e73fe 100644 --- a/src/Util/TestDox/CliTestDoxPrinter.php +++ b/src/Util/TestDox/CliTestDoxPrinter.php @@ -125,7 +125,7 @@ protected function writeTestResult(array $prevResult, array $result): void // test result line if ($this->colors && $result['className'] == PhptTestCase::class) { - $testName = Color::colorizePath($result['testName'], $prevResult['testName']); + $testName = Color::colorizePath($result['testName'], $prevResult['testName'], true); } else { $testName = $result['testMethod']; } diff --git a/src/Util/TestDox/Color.php b/src/Util/TestDox/Color.php index e5f06b70912..281132a1b67 100644 --- a/src/Util/TestDox/Color.php +++ b/src/Util/TestDox/Color.php @@ -74,7 +74,7 @@ public static function colorize(string $color, string $buffer): string return \sprintf("\x1b[%sm", \implode(';', $styles)) . $buffer . "\x1b[0m"; } - public static function colorizePath(string $path, ?string $prevPath = null): string + public static function colorizePath(string $path, ?string $prevPath = null, bool $colorizeFilename = false): string { if ($prevPath === null) { $prevPath = ''; @@ -89,6 +89,13 @@ public static function colorizePath(string $path, ?string $prevPath = null): str } } + if ($colorizeFilename) { + $last = \count($path) - 1; + $path[$last] = \preg_replace_callback('/([\-_\.]+|phpt$)/', function ($matches) { + return self::dim($matches[0]); + }, $path[$last]); + } + return \implode(self::dim(\DIRECTORY_SEPARATOR), $path); } diff --git a/tests/_files/raw_output_ColorTest.txt b/tests/_files/raw_output_ColorTest.txt index d26df900849..97179d07436 100644 --- a/tests/_files/raw_output_ColorTest.txt +++ b/tests/_files/raw_output_ColorTest.txt @@ -10,6 +10,7 @@ Runtime: %s ✔ Colorize path %ephp%eunit%etest.phpt after empty  %f ms ✔ Colorize path %ephp%eunit%etest.phpt after %e  %f ms ✔ Colorize path %ephp%eunit%etest.phpt after %ephp%e  %f ms + ✔ Colorize path %e_d-i.r%et-e_s.t.phpt after empty  %f ms ✔ dim($m) and colorize('dim',$m) return different ANSI codes  %f ms ✔ Visualize all whitespace characters in no-spaces  %f ms ✔ Visualize all whitespace characters in ·space···invaders·  %s ms @@ -24,4 +25,4 @@ Runtime: %s Time: %s, Memory: %s -OK (18 tests, 18 assertions) +OK (19 tests, 19 assertions) diff --git a/tests/unit/Util/TestDox/ColorTest.php b/tests/unit/Util/TestDox/ColorTest.php index 3d6cbc3c5e3..7bfbea18b81 100644 --- a/tests/unit/Util/TestDox/ColorTest.php +++ b/tests/unit/Util/TestDox/ColorTest.php @@ -29,9 +29,9 @@ public function testColorize(string $color, string $buffer, string $expected): v * @testdox Colorize path $path after $prevPath * @dataProvider colorizePathProvider */ - public function testColorizePath(?string $prevPath, string $path, string $expected): void + public function testColorizePath(?string $prevPath, string $path, bool $colorizeFilename, string $expected): void { - $this->assertSame($expected, Color::colorizePath($path, $prevPath)); + $this->assertSame($expected, Color::colorizePath($path, $prevPath, $colorizeFilename)); } /** @@ -104,23 +104,33 @@ public function colorizePathProvider(): array 'null previous path' => [ null, $sep . 'php' . $sep . 'unit' . $sep . 'test.phpt', + false, $sepDim . 'php' . $sepDim . 'unit' . $sepDim . 'test.phpt', ], 'empty previous path' => [ '', $sep . 'php' . $sep . 'unit' . $sep . 'test.phpt', + false, $sepDim . 'php' . $sepDim . 'unit' . $sepDim . 'test.phpt', ], 'from root' => [ $sep, $sep . 'php' . $sep . 'unit' . $sep . 'test.phpt', + false, $sepDim . 'php' . $sepDim . 'unit' . $sepDim . 'test.phpt', ], 'partial part' => [ $sep . 'php' . $sep, $sep . 'php' . $sep . 'unit' . $sep . 'test.phpt', + false, $sepDim . Color::dim('php') . $sepDim . 'unit' . $sepDim . 'test.phpt', ], + 'colorize filename' => [ + '', + $sep . '_d-i.r' . $sep . 't-e_s.t.phpt', + true, + $sepDim . '_d-i.r' . $sepDim . 't' . Color::dim('-') . 'e'. Color::dim('_') . 's' . Color::dim('.') . 't' . Color::dim('.') . Color::dim('phpt'), + ], ]; } From 4e871068e8f34d12cb0b563c7656cc616d721870 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Fri, 14 Dec 2018 21:57:04 +0100 Subject: [PATCH 41/51] Everybody needs some space --- tests/unit/Util/TestDox/ColorTest.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/unit/Util/TestDox/ColorTest.php b/tests/unit/Util/TestDox/ColorTest.php index 7bfbea18b81..7c67b45d5e2 100644 --- a/tests/unit/Util/TestDox/ColorTest.php +++ b/tests/unit/Util/TestDox/ColorTest.php @@ -129,7 +129,7 @@ public function colorizePathProvider(): array '', $sep . '_d-i.r' . $sep . 't-e_s.t.phpt', true, - $sepDim . '_d-i.r' . $sepDim . 't' . Color::dim('-') . 'e'. Color::dim('_') . 's' . Color::dim('.') . 't' . Color::dim('.') . Color::dim('phpt'), + $sepDim . '_d-i.r' . $sepDim . 't' . Color::dim('-') . 'e' . Color::dim('_') . 's' . Color::dim('.') . 't' . Color::dim('.') . Color::dim('phpt'), ], ]; } From f5c0e260e6d8d0c41f64d8c47ed7a629ba30be86 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Fri, 14 Dec 2018 22:22:05 +0100 Subject: [PATCH 42/51] Optimize ANSI code sequences --- src/Util/TestDox/Color.php | 9 +++++++-- tests/unit/Util/TestDox/ColorTest.php | 4 ++-- 2 files changed, 9 insertions(+), 4 deletions(-) diff --git a/src/Util/TestDox/Color.php b/src/Util/TestDox/Color.php index 281132a1b67..25e74249b11 100644 --- a/src/Util/TestDox/Color.php +++ b/src/Util/TestDox/Color.php @@ -96,7 +96,7 @@ public static function colorizePath(string $path, ?string $prevPath = null, bool }, $path[$last]); } - return \implode(self::dim(\DIRECTORY_SEPARATOR), $path); + return self::optimizeColor(\implode(self::dim(\DIRECTORY_SEPARATOR), $path)); } public static function dim(string $buffer): string @@ -105,7 +105,7 @@ public static function dim(string $buffer): string return $buffer; } - return "\x1b[2m$buffer\x1b[22m"; + return "\e[2m$buffer\e[22m"; } public static function visualizeWhitespace(string $buffer, bool $visualizeEOL = false): string @@ -116,4 +116,9 @@ public static function visualizeWhitespace(string $buffer, bool $visualizeEOL = return self::dim(\strtr($matches[0], $replaceMap)); }, $buffer); } + + private static function optimizeColor(string $buffer): string + { + return \str_replace("\e[22m\e[2m", '', $buffer); + } } diff --git a/tests/unit/Util/TestDox/ColorTest.php b/tests/unit/Util/TestDox/ColorTest.php index 7c67b45d5e2..3a3cf093e91 100644 --- a/tests/unit/Util/TestDox/ColorTest.php +++ b/tests/unit/Util/TestDox/ColorTest.php @@ -123,13 +123,13 @@ public function colorizePathProvider(): array $sep . 'php' . $sep, $sep . 'php' . $sep . 'unit' . $sep . 'test.phpt', false, - $sepDim . Color::dim('php') . $sepDim . 'unit' . $sepDim . 'test.phpt', + Color::dim($sep . 'php' . $sep) . 'unit' . $sepDim . 'test.phpt', ], 'colorize filename' => [ '', $sep . '_d-i.r' . $sep . 't-e_s.t.phpt', true, - $sepDim . '_d-i.r' . $sepDim . 't' . Color::dim('-') . 'e' . Color::dim('_') . 's' . Color::dim('.') . 't' . Color::dim('.') . Color::dim('phpt'), + $sepDim . '_d-i.r' . $sepDim . 't' . Color::dim('-') . 'e' . Color::dim('_') . 's' . Color::dim('.') . 't' . Color::dim('.phpt'), ], ]; } From 1364433539346771b134198a69a976162b79f472 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Fri, 14 Dec 2018 23:08:49 +0100 Subject: [PATCH 43/51] Improve line ending support --- src/Util/TestDox/Color.php | 1 + tests/_files/raw_output_ColorTest.txt | 2 +- tests/unit/Util/TestDox/ColorTest.php | 14 +++++++++++--- 3 files changed, 13 insertions(+), 4 deletions(-) diff --git a/src/Util/TestDox/Color.php b/src/Util/TestDox/Color.php index 25e74249b11..902a671a56d 100644 --- a/src/Util/TestDox/Color.php +++ b/src/Util/TestDox/Color.php @@ -20,6 +20,7 @@ class Color ' ' => '·', "\t" => '⇥', "\n" => '↵', + "\r" => '⟵', ]; /** diff --git a/tests/_files/raw_output_ColorTest.txt b/tests/_files/raw_output_ColorTest.txt index 97179d07436..5655c7a2973 100644 --- a/tests/_files/raw_output_ColorTest.txt +++ b/tests/_files/raw_output_ColorTest.txt @@ -14,7 +14,7 @@ Runtime: %s ✔ dim($m) and colorize('dim',$m) return different ANSI codes  %f ms ✔ Visualize all whitespace characters in no-spaces  %f ms ✔ Visualize all whitespace characters in ·space···invaders·  %s ms - ✔ Visualize all whitespace characters in ⇥indent,·space·and·LF↵  %s ms + ✔ Visualize all whitespace characters in ⇥indent,·space·and·\n↵\r⟵  %s ms ✔ Visualize whitespace but ignore EOL  %f ms ✔ Prettify unnamed dataprovider with data set 0  %f ms ✔ Prettify unnamed dataprovider with data set 1  %f ms diff --git a/tests/unit/Util/TestDox/ColorTest.php b/tests/unit/Util/TestDox/ColorTest.php index 3a3cf093e91..485a97d14a7 100644 --- a/tests/unit/Util/TestDox/ColorTest.php +++ b/tests/unit/Util/TestDox/ColorTest.php @@ -137,9 +137,17 @@ public function colorizePathProvider(): array public function whitespacedStringProvider(): array { return [ - ['no-spaces', 'no-spaces'], - [' space invaders ', "\x1b[2m·\x1b[22mspace\e[2m···\e[22minvaders\e[2m·\e[22m"], - ["\tindent, space and LF\n", "\e[2m⇥\e[22mindent,\e[2m·\e[22mspace\e[2m·\e[22mand\e[2m·\e[22mLF\e[2m↵\e[22m"], + [ 'no-spaces', + 'no-spaces' + ], + [ + ' space invaders ', + "\e[2m·\e[22mspace\e[2m···\e[22minvaders\e[2m·\e[22m" + ], + [ + "\tindent, space and \\n\n\\r\r", + "\e[2m⇥\e[22mindent,\e[2m·\e[22mspace\e[2m·\e[22mand\e[2m·\e[22m\\n\e[2m↵\e[22m\\r\e[2m⟵\e[22m" + ], ]; } From 186d2dffc5e8170b284c7e525d683ccead90bfb6 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Fri, 14 Dec 2018 23:12:43 +0100 Subject: [PATCH 44/51] CS fix --- tests/unit/Util/TestDox/ColorTest.php | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/tests/unit/Util/TestDox/ColorTest.php b/tests/unit/Util/TestDox/ColorTest.php index 485a97d14a7..978951379be 100644 --- a/tests/unit/Util/TestDox/ColorTest.php +++ b/tests/unit/Util/TestDox/ColorTest.php @@ -137,16 +137,16 @@ public function colorizePathProvider(): array public function whitespacedStringProvider(): array { return [ - [ 'no-spaces', - 'no-spaces' + ['no-spaces', + 'no-spaces', ], [ ' space invaders ', - "\e[2m·\e[22mspace\e[2m···\e[22minvaders\e[2m·\e[22m" + "\e[2m·\e[22mspace\e[2m···\e[22minvaders\e[2m·\e[22m", ], [ "\tindent, space and \\n\n\\r\r", - "\e[2m⇥\e[22mindent,\e[2m·\e[22mspace\e[2m·\e[22mand\e[2m·\e[22m\\n\e[2m↵\e[22m\\r\e[2m⟵\e[22m" + "\e[2m⇥\e[22mindent,\e[2m·\e[22mspace\e[2m·\e[22mand\e[2m·\e[22m\\n\e[2m↵\e[22m\\r\e[2m⟵\e[22m", ], ]; } From a3843dafef078bf9f556e97df61db99cfc03f4ad Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Fri, 14 Dec 2018 23:48:35 +0100 Subject: [PATCH 45/51] Show @testdox empty string parameters as '' when color is off --- src/Util/TestDox/NamePrettifier.php | 6 +++++- tests/_files/raw_output_ColorTest.txt | 4 ++-- 2 files changed, 7 insertions(+), 3 deletions(-) diff --git a/src/Util/TestDox/NamePrettifier.php b/src/Util/TestDox/NamePrettifier.php index 1ecb5e729e0..012d56c75fe 100644 --- a/src/Util/TestDox/NamePrettifier.php +++ b/src/Util/TestDox/NamePrettifier.php @@ -215,7 +215,11 @@ private function mapTestMethodParameterNamesToProvidedDataValues(TestCase $test) } if (\is_string($value) && $value === '') { - $value = Color::colorize('underlined', 'empty'); + if ($this->useColor) { + $value = Color::colorize('dim,underlined', 'empty'); + } else { + $value = "''"; + } } $providedData['$' . $parameter->getName()] = $value; diff --git a/tests/_files/raw_output_ColorTest.txt b/tests/_files/raw_output_ColorTest.txt index 5655c7a2973..1edb837aa18 100644 --- a/tests/_files/raw_output_ColorTest.txt +++ b/tests/_files/raw_output_ColorTest.txt @@ -7,10 +7,10 @@ Runtime: %s ✔ Colorize with one·color  %f ms ✔ Colorize with multiple·colors  %f ms ✔ Colorize path %ephp%eunit%etest.phpt after NULL  %f ms - ✔ Colorize path %ephp%eunit%etest.phpt after empty  %f ms + ✔ Colorize path %ephp%eunit%etest.phpt after empty  %f ms ✔ Colorize path %ephp%eunit%etest.phpt after %e  %f ms ✔ Colorize path %ephp%eunit%etest.phpt after %ephp%e  %f ms - ✔ Colorize path %e_d-i.r%et-e_s.t.phpt after empty  %f ms + ✔ Colorize path %e_d-i.r%et-e_s.t.phpt after empty  %f ms ✔ dim($m) and colorize('dim',$m) return different ANSI codes  %f ms ✔ Visualize all whitespace characters in no-spaces  %f ms ✔ Visualize all whitespace characters in ·space···invaders·  %s ms From a3aaef8e3f6ec3ae93e2cbe238a8aa7a1fae8b99 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Tue, 18 Dec 2018 19:12:43 +0100 Subject: [PATCH 46/51] Clean up a few obsolete tests for TestDox and test ordering --- tests/_files/DataProviderTestDoxTest.php | 83 ------------------- tests/end-to-end/colors-always.phpt | 18 ---- tests/end-to-end/dataprovider-debug.phpt | 33 -------- tests/end-to-end/dataprovider-testdox.phpt | 34 -------- tests/end-to-end/dependencies.phpt | 41 --------- ... depends-as-parameter-with-isolation.phpt} | 0 ...encies2.phpt => depends-as-parameter.phpt} | 0 ...ds-multiple-parameter-with-isolation.phpt} | 0 ....phpt => depends-multiple-parameters.phpt} | 0 tests/end-to-end/testdox-verbose.phpt | 25 ------ tests/end-to-end/testdox.phpt | 31 +++++-- 11 files changed, 24 insertions(+), 241 deletions(-) delete mode 100644 tests/_files/DataProviderTestDoxTest.php delete mode 100644 tests/end-to-end/colors-always.phpt delete mode 100644 tests/end-to-end/dataprovider-debug.phpt delete mode 100644 tests/end-to-end/dataprovider-testdox.phpt delete mode 100644 tests/end-to-end/dependencies.phpt rename tests/end-to-end/{dependencies2-isolation.phpt => depends-as-parameter-with-isolation.phpt} (100%) rename tests/end-to-end/{dependencies2.phpt => depends-as-parameter.phpt} (100%) rename tests/end-to-end/{dependencies3-isolation.phpt => depends-multiple-parameter-with-isolation.phpt} (100%) rename tests/end-to-end/{dependencies3.phpt => depends-multiple-parameters.phpt} (100%) delete mode 100644 tests/end-to-end/testdox-verbose.phpt diff --git a/tests/_files/DataProviderTestDoxTest.php b/tests/_files/DataProviderTestDoxTest.php deleted file mode 100644 index 72515b251ed..00000000000 --- a/tests/_files/DataProviderTestDoxTest.php +++ /dev/null @@ -1,83 +0,0 @@ - - * - * For the full copyright and license information, please view the LICENSE - * file that was distributed with this source code. - */ -use PHPUnit\Framework\TestCase; - -class DataProviderTestDoxTest extends TestCase -{ - /** - * @dataProvider provider - * @testdox Does something - */ - public function testOne(): void - { - $this->assertTrue(true); - } - - /** - * @dataProvider provider - */ - public function testDoesSomethingElse(): void - { - $this->assertTrue(true); - } - - /** - * @dataProvider providerWithIndexedArray - */ - public function testWithProviderWithIndexedArray($value): void - { - $this->assertTrue(true); - } - - /** - * @dataProvider placeHolderprovider - * @testdox ... $value ... - */ - public function testWithPlaceholders($value): void - { - $this->assertTrue(true); - } - - public function provider() - { - return [ - 'one' => [1], - 'two' => [2], - ]; - } - - public function providerWithIndexedArray() - { - return [ - ['first'], - ['second'], - ]; - } - - public function placeHolderprovider(): array - { - return [ - 'boolean' => [true], - 'integer' => [1], - 'float' => [1.0], - 'string' => ['string'], - 'array' => [[1, 2, 3]], - 'object' => [new \stdClass], - 'stringableObject' => [new class { - public function __toString() - { - return 'string'; - } - }], - 'resource' => [\fopen(__FILE__, 'rb')], - 'null' => [null], - ]; - } -} diff --git a/tests/end-to-end/colors-always.phpt b/tests/end-to-end/colors-always.phpt deleted file mode 100644 index ba8c74b8070..00000000000 --- a/tests/end-to-end/colors-always.phpt +++ /dev/null @@ -1,18 +0,0 @@ ---TEST-- -phpunit --colors=always BankAccountTest ../../_files/BankAccountTest.php ---FILE-- - Date: Thu, 20 Dec 2018 14:32:13 +0100 Subject: [PATCH 47/51] Improve test maintainability --- tests/end-to-end/cli/help.phpt | 13 ++ tests/end-to-end/cli/help2.phpt | 14 +++ .../{help.phpt => cli/output-cli-usage.txt} | 9 -- tests/end-to-end/help2.phpt | 114 ------------------ 4 files changed, 27 insertions(+), 123 deletions(-) create mode 100644 tests/end-to-end/cli/help.phpt create mode 100644 tests/end-to-end/cli/help2.phpt rename tests/end-to-end/{help.phpt => cli/output-cli-usage.txt} (97%) delete mode 100644 tests/end-to-end/help2.phpt diff --git a/tests/end-to-end/cli/help.phpt b/tests/end-to-end/cli/help.phpt new file mode 100644 index 00000000000..7f264aa21e1 --- /dev/null +++ b/tests/end-to-end/cli/help.phpt @@ -0,0 +1,13 @@ +--TEST-- +phpunit +--FILE-- + - -Code Coverage Options: - - --coverage-clover Generate code coverage report in Clover XML format - --coverage-crap4j Generate code coverage report in Crap4J XML format - --coverage-html Generate code coverage report in HTML format - --coverage-php Export PHP_CodeCoverage object to file - --coverage-text= Generate code coverage report in text format - Default: Standard output - --coverage-xml Generate code coverage report in PHPUnit XML format - --whitelist Whitelist for code coverage analysis - --disable-coverage-ignore Disable annotations for ignoring code coverage - --no-coverage Ignore code coverage configuration - --dump-xdebug-filter Generate script to set Xdebug code coverage filter - -Logging Options: - - --log-junit Log test execution in JUnit XML format to file - --log-teamcity Log test execution in TeamCity format to file - --testdox-html Write agile documentation in HTML format to file - --testdox-text Write agile documentation in Text format to file - --testdox-xml Write agile documentation in XML format to file - --reverse-list Print defects in reverse order - -Test Selection Options: - - --filter Filter which tests to run - --testsuite Filter which testsuite to run - --group ... Only runs tests from the specified group(s) - --exclude-group ... Exclude tests from the specified group(s) - --list-groups List available test groups - --list-suites List available test suites - --list-tests List available tests - --list-tests-xml List available tests in XML format - --test-suffix ... Only search for test in files with specified - suffix(es). Default: Test.php,.phpt - -Test Execution Options: - - --dont-report-useless-tests Do not report tests that do not test anything - --strict-coverage Be strict about @covers annotation usage - --strict-global-state Be strict about changes to global state - --disallow-test-output Be strict about output during tests - --disallow-resource-usage Be strict about resource usage during small tests - --enforce-time-limit Enforce time limit based on test size - --default-time-limit= Timeout in seconds for tests without @small, @medium or @large - --disallow-todo-tests Disallow @todo-annotated tests - - --process-isolation Run each test in a separate PHP process - --globals-backup Backup and restore $GLOBALS for each test - --static-backup Backup and restore static attributes for each test - - --colors= Use colors in output ("never", "auto" or "always") - --columns Number of columns to use for progress output - --columns max Use maximum number of columns for progress output - --stderr Write to STDERR instead of STDOUT - --stop-on-defect Stop execution upon first not-passed test - --stop-on-error Stop execution upon first error - --stop-on-failure Stop execution upon first error or failure - --stop-on-warning Stop execution upon first warning - --stop-on-risky Stop execution upon first risky test - --stop-on-skipped Stop execution upon first skipped test - --stop-on-incomplete Stop execution upon first incomplete test - --fail-on-warning Treat tests with warnings as failures - --fail-on-risky Treat risky tests as failures - -v|--verbose Output more verbose information - --debug Display debugging information - - --loader TestSuiteLoader implementation to use - --repeat Runs the test(s) repeatedly - --teamcity Report test execution progress in TeamCity format - --testdox Report test execution progress in TestDox format - --testdox-group Only include tests from the specified group(s) - --testdox-exclude-group Exclude tests from the specified group(s) - --printer TestListener implementation to use - - --order-by= Run tests in order: default|reverse|random|defects|no-depends - --random-order-seed= Use a specific random seed for random order - --cache-result Write test results to cache file - --do-not-cache-result Do not write test results to cache file - -Configuration Options: - - --prepend A PHP script that is included as early as possible - --bootstrap A PHP script that is included before the tests run - -c|--configuration Read configuration from XML file - --no-configuration Ignore default configuration file (phpunit.xml) - --no-logging Ignore logging configuration - --no-extensions Do not load PHPUnit extensions - --include-path Prepend PHP's include_path with given path(s) - -d key[=value] Sets a php.ini value - --generate-configuration Generate configuration file with suggested settings - --cache-result-file= Specify result cache path and filename - -Miscellaneous Options: - - -h|--help Prints this usage information - --version Prints the version and exits - --atleast-version Checks that version is greater than min and exits - --check-version Check whether PHPUnit is the latest version From aa9b8ed5bf12eb8cc6647af9bffb6941c9d4c441 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Thu, 20 Dec 2018 22:28:39 +0100 Subject: [PATCH 48/51] Move logger and printer tests together; nicer ARGV handling --- tests/end-to-end/cache-result.phpt | 17 +++++++------ tests/end-to-end/cli/help.phpt | 7 ++---- tests/end-to-end/cli/help2.phpt | 8 ++---- .../depends-as-parameter-with-isolation.phpt | 19 -------------- tests/end-to-end/depends-as-parameter.phpt | 18 ------------- ...nds-multiple-parameter-with-isolation.phpt | 19 -------------- .../depends-multiple-parameters.phpt | 19 -------------- .../execution-order-options-via-config.phpt | 2 +- .../loggers}/_files/ClonedDependencyTest.php | 0 .../loggers}/_files/DependencyTestSuite.php | 0 .../loggers}/_files/MultiDependencyTest.php | 0 .../MultiDependencyTest_result_cache.txt | 0 .../loggers}/_files/StackTest.php | 0 .../loggers}/_files/StatusTest.php | 0 .../loggers}/_files/TestDoxGroupTest.php | 0 .../loggers}/_files/raw_output_ColorTest.txt | 0 .../loggers}/_files/raw_output_StatusTest.txt | 14 +++++------ .../defects-first-order-via-cli.phpt | 25 +++++++++++-------- .../{ => loggers}/dependencies-clone.phpt | 13 ++++++---- .../{ => loggers}/dependencies-isolation.phpt | 17 +++++++------ .../depends-as-parameter-with-isolation.phpt | 22 ++++++++++++++++ .../loggers/depends-as-parameter.phpt | 21 ++++++++++++++++ ...nds-multiple-parameter-with-isolation.phpt | 22 ++++++++++++++++ .../loggers/depends-multiple-parameters.phpt | 22 ++++++++++++++++ .../{ => loggers}/log-junit-phpt.phpt | 13 ++++++---- tests/end-to-end/{ => loggers}/log-junit.phpt | 19 ++++++++------ .../{ => loggers}/log-teamcity-phpt.phpt | 13 ++++++---- .../{ => loggers}/log-teamcity.phpt | 17 +++++++------ .../teamcity-inner-exceptions.phpt | 15 ++++++----- tests/end-to-end/{ => loggers}/teamcity.phpt | 15 ++++++----- .../testdox-dataprovider-placeholder.phpt | 17 +++++++++++++ .../{ => loggers}/testdox-exclude-group.phpt | 19 ++++++++------ .../{ => loggers}/testdox-group.phpt | 19 ++++++++------ .../{ => loggers}/testdox-html.phpt | 15 ++++++----- .../loggers/testdox-status-colorization.phpt | 17 +++++++++++++ .../{ => loggers}/testdox-text.phpt | 15 ++++++----- .../end-to-end/{ => loggers}/testdox-xml.phpt | 17 +++++++------ tests/end-to-end/{ => loggers}/testdox.phpt | 13 ++++++---- .../order-by-default-invalid-via-cli.phpt | 14 +++++------ ...mized-seed-with-dependency-resolution.phpt | 2 +- ...randomized-with-dependency-resolution.phpt | 2 +- ...r-reversed-with-dependency-resolution.phpt | 2 +- ...eversed-without-dependency-resolution.phpt | 2 +- .../testdox-dataprovider-placeholder.phpt | 14 ----------- .../testdox-status-colorization.phpt | 14 ----------- tests/unit/Util/TestResultCacheTest.php | 4 +-- 46 files changed, 300 insertions(+), 243 deletions(-) delete mode 100644 tests/end-to-end/depends-as-parameter-with-isolation.phpt delete mode 100644 tests/end-to-end/depends-as-parameter.phpt delete mode 100644 tests/end-to-end/depends-multiple-parameter-with-isolation.phpt delete mode 100644 tests/end-to-end/depends-multiple-parameters.phpt rename tests/{ => end-to-end/loggers}/_files/ClonedDependencyTest.php (100%) rename tests/{ => end-to-end/loggers}/_files/DependencyTestSuite.php (100%) rename tests/{ => end-to-end/loggers}/_files/MultiDependencyTest.php (100%) rename tests/{ => end-to-end/loggers}/_files/MultiDependencyTest_result_cache.txt (100%) rename tests/{ => end-to-end/loggers}/_files/StackTest.php (100%) rename tests/{ => end-to-end/loggers}/_files/StatusTest.php (100%) rename tests/{ => end-to-end/loggers}/_files/TestDoxGroupTest.php (100%) rename tests/{ => end-to-end/loggers}/_files/raw_output_ColorTest.txt (100%) rename tests/{ => end-to-end/loggers}/_files/raw_output_StatusTest.txt (58%) rename tests/end-to-end/{ => loggers}/defects-first-order-via-cli.phpt (54%) rename tests/end-to-end/{ => loggers}/dependencies-clone.phpt (57%) rename tests/end-to-end/{ => loggers}/dependencies-isolation.phpt (73%) create mode 100644 tests/end-to-end/loggers/depends-as-parameter-with-isolation.phpt create mode 100644 tests/end-to-end/loggers/depends-as-parameter.phpt create mode 100644 tests/end-to-end/loggers/depends-multiple-parameter-with-isolation.phpt create mode 100644 tests/end-to-end/loggers/depends-multiple-parameters.phpt rename tests/end-to-end/{ => loggers}/log-junit-phpt.phpt (73%) rename tests/end-to-end/{ => loggers}/log-junit.phpt (89%) rename tests/end-to-end/{ => loggers}/log-teamcity-phpt.phpt (68%) rename tests/end-to-end/{ => loggers}/log-teamcity.phpt (83%) rename tests/end-to-end/{ => loggers}/teamcity-inner-exceptions.phpt (87%) rename tests/end-to-end/{ => loggers}/teamcity.phpt (83%) create mode 100644 tests/end-to-end/loggers/testdox-dataprovider-placeholder.phpt rename tests/end-to-end/{ => loggers}/testdox-exclude-group.phpt (52%) rename tests/end-to-end/{ => loggers}/testdox-group.phpt (52%) rename tests/end-to-end/{ => loggers}/testdox-html.phpt (83%) create mode 100644 tests/end-to-end/loggers/testdox-status-colorization.phpt rename tests/end-to-end/{ => loggers}/testdox-text.phpt (61%) rename tests/end-to-end/{ => loggers}/testdox-xml.phpt (90%) rename tests/end-to-end/{ => loggers}/testdox.phpt (82%) delete mode 100644 tests/end-to-end/testdox-dataprovider-placeholder.phpt delete mode 100644 tests/end-to-end/testdox-status-colorization.phpt diff --git a/tests/end-to-end/cache-result.phpt b/tests/end-to-end/cache-result.phpt index ffe5b609985..0f3e0846d8c 100644 --- a/tests/end-to-end/cache-result.phpt +++ b/tests/end-to-end/cache-result.phpt @@ -4,13 +4,16 @@ phpunit --order-by=no-depends,reverse --cache-result --cache-result-file MultiDe ---EXPECTF-- -PHPUnit %s by Sebastian Bergmann and contributors. - -..... 5 / 5 (100%) - -Time: %s, Memory: %s - -OK (5 tests, 6 assertions) diff --git a/tests/end-to-end/execution-order-options-via-config.phpt b/tests/end-to-end/execution-order-options-via-config.phpt index b5409faa986..b9b2d9afeec 100644 --- a/tests/end-to-end/execution-order-options-via-config.phpt +++ b/tests/end-to-end/execution-order-options-via-config.phpt @@ -6,7 +6,7 @@ $_SERVER['argv'][1] = '--debug'; $_SERVER['argv'][2] = '-c'; $_SERVER['argv'][3] = __DIR__ . '/../_files/configuration_execution_order_options.xml'; $_SERVER['argv'][4] = 'MultiDependencyTest'; -$_SERVER['argv'][5] = __DIR__ . '/../_files/MultiDependencyTest.php'; +$_SERVER['argv'][5] = __DIR__ . '/loggers/_files/MultiDependencyTest.php'; require __DIR__ . '/../bootstrap.php'; PHPUnit\TextUI\Command::main(); diff --git a/tests/_files/ClonedDependencyTest.php b/tests/end-to-end/loggers/_files/ClonedDependencyTest.php similarity index 100% rename from tests/_files/ClonedDependencyTest.php rename to tests/end-to-end/loggers/_files/ClonedDependencyTest.php diff --git a/tests/_files/DependencyTestSuite.php b/tests/end-to-end/loggers/_files/DependencyTestSuite.php similarity index 100% rename from tests/_files/DependencyTestSuite.php rename to tests/end-to-end/loggers/_files/DependencyTestSuite.php diff --git a/tests/_files/MultiDependencyTest.php b/tests/end-to-end/loggers/_files/MultiDependencyTest.php similarity index 100% rename from tests/_files/MultiDependencyTest.php rename to tests/end-to-end/loggers/_files/MultiDependencyTest.php diff --git a/tests/_files/MultiDependencyTest_result_cache.txt b/tests/end-to-end/loggers/_files/MultiDependencyTest_result_cache.txt similarity index 100% rename from tests/_files/MultiDependencyTest_result_cache.txt rename to tests/end-to-end/loggers/_files/MultiDependencyTest_result_cache.txt diff --git a/tests/_files/StackTest.php b/tests/end-to-end/loggers/_files/StackTest.php similarity index 100% rename from tests/_files/StackTest.php rename to tests/end-to-end/loggers/_files/StackTest.php diff --git a/tests/_files/StatusTest.php b/tests/end-to-end/loggers/_files/StatusTest.php similarity index 100% rename from tests/_files/StatusTest.php rename to tests/end-to-end/loggers/_files/StatusTest.php diff --git a/tests/_files/TestDoxGroupTest.php b/tests/end-to-end/loggers/_files/TestDoxGroupTest.php similarity index 100% rename from tests/_files/TestDoxGroupTest.php rename to tests/end-to-end/loggers/_files/TestDoxGroupTest.php diff --git a/tests/_files/raw_output_ColorTest.txt b/tests/end-to-end/loggers/_files/raw_output_ColorTest.txt similarity index 100% rename from tests/_files/raw_output_ColorTest.txt rename to tests/end-to-end/loggers/_files/raw_output_ColorTest.txt diff --git a/tests/_files/raw_output_StatusTest.txt b/tests/end-to-end/loggers/_files/raw_output_StatusTest.txt similarity index 58% rename from tests/_files/raw_output_StatusTest.txt rename to tests/end-to-end/loggers/_files/raw_output_StatusTest.txt index 4391c20e881..ad552f1e3e2 100644 --- a/tests/_files/raw_output_StatusTest.txt +++ b/tests/end-to-end/loggers/_files/raw_output_StatusTest.txt @@ -8,37 +8,37 @@ Runtime: %s │ │ Failed asserting that false is true. │ - │ %stests%e_files%eStatusTest.php:24 + │ %stests%eend-to-end%eloggers%e_files%eStatusTest.php:24 │ ✘ Error  %f ms │ │ RuntimeException: │ - │ %stests%e_files%eStatusTest.php:29 + │ %stests%eend-to-end%eloggers%e_files%eStatusTest.php:29 │ ∅ Incomplete  %f ms │ - │ %stests%e_files%eStatusTest.php:34 + │ %stests%eend-to-end%eloggers%e_files%eStatusTest.php:34 │ → Skipped  %f ms │ - │ %stests%e_files%eStatusTest.php:39 + │ %stests%eend-to-end%eloggers%e_files%eStatusTest.php:39 │ ☢ Risky  %f ms │ │ This test did not perform any assertions%w │%w - │ %stests%e_files%eStatusTest.php:42 - │ + │ %stests%eend-to-end%eloggers%e_files%eStatusTest.php:42%w + │%w │ ✘ Warning  %f ms │ - │ %stests%e_files%eStatusTest.php:48 + │ %stests%eend-to-end%eloggers%e_files%eStatusTest.php:48 │ Time: %s, Memory: %s diff --git a/tests/end-to-end/defects-first-order-via-cli.phpt b/tests/end-to-end/loggers/defects-first-order-via-cli.phpt similarity index 54% rename from tests/end-to-end/defects-first-order-via-cli.phpt rename to tests/end-to-end/loggers/defects-first-order-via-cli.phpt index 3d0ced55fe9..ec2a6d862cf 100644 --- a/tests/end-to-end/defects-first-order-via-cli.phpt +++ b/tests/end-to-end/loggers/defects-first-order-via-cli.phpt @@ -2,21 +2,24 @@ phpunit --order-by=defects MultiDependencyTest ./tests/_files/MultiDependencyTest.php --FILE-- +--EXPECTF-- +PHPUnit %s by Sebastian Bergmann and contributors. + +..... 5 / 5 (100%) + +Time: %s, Memory: %s + +OK (5 tests, 6 assertions) diff --git a/tests/end-to-end/log-junit-phpt.phpt b/tests/end-to-end/loggers/log-junit-phpt.phpt similarity index 73% rename from tests/end-to-end/log-junit-phpt.phpt rename to tests/end-to-end/loggers/log-junit-phpt.phpt index d3310dd547c..20e762c5a77 100644 --- a/tests/end-to-end/log-junit-phpt.phpt +++ b/tests/end-to-end/loggers/log-junit-phpt.phpt @@ -2,12 +2,15 @@ phpunit --log-junit php://stdout ../end-to-end/phpt-stderr.phpt --FILE-- --EXPECTF-- diff --git a/tests/end-to-end/log-junit.phpt b/tests/end-to-end/loggers/log-junit.phpt similarity index 89% rename from tests/end-to-end/log-junit.phpt rename to tests/end-to-end/loggers/log-junit.phpt index 42445c2f396..b0b90b4cdf4 100644 --- a/tests/end-to-end/log-junit.phpt +++ b/tests/end-to-end/loggers/log-junit.phpt @@ -1,14 +1,17 @@ --TEST-- -phpunit --log-junit php://stdout StatusTest ../../_files/StatusTest.php +phpunit --log-junit php://stdout StatusTest _files/StatusTest.php --FILE-- --EXPECTF-- diff --git a/tests/end-to-end/log-teamcity-phpt.phpt b/tests/end-to-end/loggers/log-teamcity-phpt.phpt similarity index 68% rename from tests/end-to-end/log-teamcity-phpt.phpt rename to tests/end-to-end/loggers/log-teamcity-phpt.phpt index 70fa1fa9779..b2271c276ef 100644 --- a/tests/end-to-end/log-teamcity-phpt.phpt +++ b/tests/end-to-end/loggers/log-teamcity-phpt.phpt @@ -2,12 +2,15 @@ phpunit --log-teamcity php://stdout ../end-to-end/phpt-stderr.phpt --FILE-- load(); @@ -28,7 +28,7 @@ public function testReadsCacheFromProvidedFilename(): void public function testDoesClearCacheBeforeLoad(): void { - $cacheFile = TEST_FILES_PATH . '/MultiDependencyTest_result_cache.txt'; + $cacheFile = TEST_FILES_PATH . '../end-to-end/loggers/_files/MultiDependencyTest_result_cache.txt'; $cache = new TestResultCache($cacheFile); $cache->setState('someTest', BaseTestRunner::STATUS_FAILURE); From 811da6f7a284e971370e6c81a5601cc95e3d6059 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Thu, 20 Dec 2018 23:29:43 +0100 Subject: [PATCH 49/51] Move execution ordering tests together --- .../_files/ClonedDependencyTest.php | 0 .../_files/DependencyTestSuite.php | 0 .../_files/MultiDependencyTest.php | 0 .../MultiDependencyTest_result_cache.txt | 0 .../_files/StackTest.php | 0 .../{ => execution-order}/cache-result.phpt | 4 +-- .../defects-first-order-via-cli.phpt | 0 .../dependencies-clone.phpt | 0 .../dependencies-isolation.phpt | 0 .../depends-as-parameter-with-isolation.phpt | 0 .../depends-as-parameter.phpt | 0 ...nds-multiple-parameter-with-isolation.phpt | 0 .../depends-multiple-parameters.phpt | 0 .../execution-order-options-via-config.phpt | 15 ++++++---- .../order-by-default-invalid-via-cli.phpt | 2 +- .../stop-on-defect-via-cli.phpt | 13 +++++---- .../stop-on-defect-via-config.phpt | 13 +++++---- .../stop-on-error-via-cli.phpt | 13 +++++---- .../stop-on-error-via-config.phpt | 13 +++++---- .../stop-on-incomplete-via-cli.phpt | 13 +++++---- .../stop-on-incomplete-via-config.phpt | 13 +++++---- .../stop-on-warning-via-cli.phpt | 15 ++++++---- .../stop-on-warning-via-config.phpt | 29 +++++++++++++++++++ ...mized-seed-with-dependency-resolution.phpt | 19 +++++++----- ...randomized-with-dependency-resolution.phpt | 28 ++++++++++++++++++ ...r-reversed-with-dependency-resolution.phpt | 17 ++++++----- ...eversed-without-dependency-resolution.phpt | 19 +++++++----- .../stop-on-warning-via-config.phpt | 26 ----------------- ...randomized-with-dependency-resolution.phpt | 25 ---------------- tests/unit/Util/TestResultCacheTest.php | 4 +-- 30 files changed, 160 insertions(+), 121 deletions(-) rename tests/end-to-end/{loggers => execution-order}/_files/ClonedDependencyTest.php (100%) rename tests/end-to-end/{loggers => execution-order}/_files/DependencyTestSuite.php (100%) rename tests/end-to-end/{loggers => execution-order}/_files/MultiDependencyTest.php (100%) rename tests/end-to-end/{loggers => execution-order}/_files/MultiDependencyTest_result_cache.txt (100%) rename tests/end-to-end/{loggers => execution-order}/_files/StackTest.php (100%) rename tests/end-to-end/{ => execution-order}/cache-result.phpt (91%) rename tests/end-to-end/{loggers => execution-order}/defects-first-order-via-cli.phpt (100%) rename tests/end-to-end/{loggers => execution-order}/dependencies-clone.phpt (100%) rename tests/end-to-end/{loggers => execution-order}/dependencies-isolation.phpt (100%) rename tests/end-to-end/{loggers => execution-order}/depends-as-parameter-with-isolation.phpt (100%) rename tests/end-to-end/{loggers => execution-order}/depends-as-parameter.phpt (100%) rename tests/end-to-end/{loggers => execution-order}/depends-multiple-parameter-with-isolation.phpt (100%) rename tests/end-to-end/{loggers => execution-order}/depends-multiple-parameters.phpt (100%) rename tests/end-to-end/{ => execution-order}/execution-order-options-via-config.phpt (70%) rename tests/end-to-end/{ => execution-order}/order-by-default-invalid-via-cli.phpt (89%) rename tests/end-to-end/{ => execution-order}/stop-on-defect-via-cli.phpt (56%) rename tests/end-to-end/{ => execution-order}/stop-on-defect-via-config.phpt (55%) rename tests/end-to-end/{ => execution-order}/stop-on-error-via-cli.phpt (61%) rename tests/end-to-end/{ => execution-order}/stop-on-error-via-config.phpt (60%) rename tests/end-to-end/{ => execution-order}/stop-on-incomplete-via-cli.phpt (53%) rename tests/end-to-end/{ => execution-order}/stop-on-incomplete-via-config.phpt (52%) rename tests/end-to-end/{ => execution-order}/stop-on-warning-via-cli.phpt (50%) create mode 100644 tests/end-to-end/execution-order/stop-on-warning-via-config.phpt rename tests/end-to-end/{ => execution-order}/test-order-randomized-seed-with-dependency-resolution.phpt (66%) create mode 100644 tests/end-to-end/execution-order/test-order-randomized-with-dependency-resolution.phpt rename tests/end-to-end/{ => execution-order}/test-order-reversed-with-dependency-resolution.phpt (68%) rename tests/end-to-end/{ => execution-order}/test-order-reversed-without-dependency-resolution.phpt (74%) delete mode 100644 tests/end-to-end/stop-on-warning-via-config.phpt delete mode 100644 tests/end-to-end/test-order-randomized-with-dependency-resolution.phpt diff --git a/tests/end-to-end/loggers/_files/ClonedDependencyTest.php b/tests/end-to-end/execution-order/_files/ClonedDependencyTest.php similarity index 100% rename from tests/end-to-end/loggers/_files/ClonedDependencyTest.php rename to tests/end-to-end/execution-order/_files/ClonedDependencyTest.php diff --git a/tests/end-to-end/loggers/_files/DependencyTestSuite.php b/tests/end-to-end/execution-order/_files/DependencyTestSuite.php similarity index 100% rename from tests/end-to-end/loggers/_files/DependencyTestSuite.php rename to tests/end-to-end/execution-order/_files/DependencyTestSuite.php diff --git a/tests/end-to-end/loggers/_files/MultiDependencyTest.php b/tests/end-to-end/execution-order/_files/MultiDependencyTest.php similarity index 100% rename from tests/end-to-end/loggers/_files/MultiDependencyTest.php rename to tests/end-to-end/execution-order/_files/MultiDependencyTest.php diff --git a/tests/end-to-end/loggers/_files/MultiDependencyTest_result_cache.txt b/tests/end-to-end/execution-order/_files/MultiDependencyTest_result_cache.txt similarity index 100% rename from tests/end-to-end/loggers/_files/MultiDependencyTest_result_cache.txt rename to tests/end-to-end/execution-order/_files/MultiDependencyTest_result_cache.txt diff --git a/tests/end-to-end/loggers/_files/StackTest.php b/tests/end-to-end/execution-order/_files/StackTest.php similarity index 100% rename from tests/end-to-end/loggers/_files/StackTest.php rename to tests/end-to-end/execution-order/_files/StackTest.php diff --git a/tests/end-to-end/cache-result.phpt b/tests/end-to-end/execution-order/cache-result.phpt similarity index 91% rename from tests/end-to-end/cache-result.phpt rename to tests/end-to-end/execution-order/cache-result.phpt index 0f3e0846d8c..11b04674c38 100644 --- a/tests/end-to-end/cache-result.phpt +++ b/tests/end-to-end/execution-order/cache-result.phpt @@ -11,11 +11,11 @@ $arguments = [ '--cache-result', '--cache-result-file=' . $target, 'MultiDependencyTest', - realpath(__DIR__ . '/loggers/_files/MultiDependencyTest.php'), + realpath(__DIR__ . '/../execution-order/_files/MultiDependencyTest.php'), ]; \array_splice($_SERVER['argv'], 1, count($arguments), $arguments); -require __DIR__ . '/../bootstrap.php'; +require __DIR__ . '/../../bootstrap.php'; PHPUnit\TextUI\Command::main(false); print file_get_contents($target); diff --git a/tests/end-to-end/loggers/defects-first-order-via-cli.phpt b/tests/end-to-end/execution-order/defects-first-order-via-cli.phpt similarity index 100% rename from tests/end-to-end/loggers/defects-first-order-via-cli.phpt rename to tests/end-to-end/execution-order/defects-first-order-via-cli.phpt diff --git a/tests/end-to-end/loggers/dependencies-clone.phpt b/tests/end-to-end/execution-order/dependencies-clone.phpt similarity index 100% rename from tests/end-to-end/loggers/dependencies-clone.phpt rename to tests/end-to-end/execution-order/dependencies-clone.phpt diff --git a/tests/end-to-end/loggers/dependencies-isolation.phpt b/tests/end-to-end/execution-order/dependencies-isolation.phpt similarity index 100% rename from tests/end-to-end/loggers/dependencies-isolation.phpt rename to tests/end-to-end/execution-order/dependencies-isolation.phpt diff --git a/tests/end-to-end/loggers/depends-as-parameter-with-isolation.phpt b/tests/end-to-end/execution-order/depends-as-parameter-with-isolation.phpt similarity index 100% rename from tests/end-to-end/loggers/depends-as-parameter-with-isolation.phpt rename to tests/end-to-end/execution-order/depends-as-parameter-with-isolation.phpt diff --git a/tests/end-to-end/loggers/depends-as-parameter.phpt b/tests/end-to-end/execution-order/depends-as-parameter.phpt similarity index 100% rename from tests/end-to-end/loggers/depends-as-parameter.phpt rename to tests/end-to-end/execution-order/depends-as-parameter.phpt diff --git a/tests/end-to-end/loggers/depends-multiple-parameter-with-isolation.phpt b/tests/end-to-end/execution-order/depends-multiple-parameter-with-isolation.phpt similarity index 100% rename from tests/end-to-end/loggers/depends-multiple-parameter-with-isolation.phpt rename to tests/end-to-end/execution-order/depends-multiple-parameter-with-isolation.phpt diff --git a/tests/end-to-end/loggers/depends-multiple-parameters.phpt b/tests/end-to-end/execution-order/depends-multiple-parameters.phpt similarity index 100% rename from tests/end-to-end/loggers/depends-multiple-parameters.phpt rename to tests/end-to-end/execution-order/depends-multiple-parameters.phpt diff --git a/tests/end-to-end/execution-order-options-via-config.phpt b/tests/end-to-end/execution-order/execution-order-options-via-config.phpt similarity index 70% rename from tests/end-to-end/execution-order-options-via-config.phpt rename to tests/end-to-end/execution-order/execution-order-options-via-config.phpt index b9b2d9afeec..c38119b0398 100644 --- a/tests/end-to-end/execution-order-options-via-config.phpt +++ b/tests/end-to-end/execution-order/execution-order-options-via-config.phpt @@ -2,13 +2,16 @@ phpunit -c ../_files/configuration_stop_on_defect.xml MultiDependencyTest ./tests/_files/MultiDependencyTest.php --FILE-- --EXPECTF-- diff --git a/tests/end-to-end/execution-order/test-order-randomized-with-dependency-resolution.phpt b/tests/end-to-end/execution-order/test-order-randomized-with-dependency-resolution.phpt new file mode 100644 index 00000000000..3b1b711bd16 --- /dev/null +++ b/tests/end-to-end/execution-order/test-order-randomized-with-dependency-resolution.phpt @@ -0,0 +1,28 @@ +--TEST-- +phpunit --order-by=depends,random ../_files/MultiDependencyTest.php +--FILE-- + +--EXPECTF-- +PHPUnit %s by Sebastian Bergmann and contributors. + +Runtime: %s +Random seed: %d + +..... 5 / 5 (100%) + +Time: %s, Memory: %s + +OK (5 tests, 6 assertions) diff --git a/tests/end-to-end/test-order-reversed-with-dependency-resolution.phpt b/tests/end-to-end/execution-order/test-order-reversed-with-dependency-resolution.phpt similarity index 68% rename from tests/end-to-end/test-order-reversed-with-dependency-resolution.phpt rename to tests/end-to-end/execution-order/test-order-reversed-with-dependency-resolution.phpt index cd5b29b075b..4b9b7c935b9 100644 --- a/tests/end-to-end/test-order-reversed-with-dependency-resolution.phpt +++ b/tests/end-to-end/execution-order/test-order-reversed-with-dependency-resolution.phpt @@ -2,14 +2,17 @@ phpunit --verbose --order-by=reverse ../_files/DependencySuccessTest.php --FILE-- --EXPECTF-- diff --git a/tests/end-to-end/test-order-reversed-without-dependency-resolution.phpt b/tests/end-to-end/execution-order/test-order-reversed-without-dependency-resolution.phpt similarity index 74% rename from tests/end-to-end/test-order-reversed-without-dependency-resolution.phpt rename to tests/end-to-end/execution-order/test-order-reversed-without-dependency-resolution.phpt index a67ae9d7ca8..ed2dd8f1a23 100644 --- a/tests/end-to-end/test-order-reversed-without-dependency-resolution.phpt +++ b/tests/end-to-end/execution-order/test-order-reversed-without-dependency-resolution.phpt @@ -2,14 +2,17 @@ phpunit --order-by=no-depends,reverse ../_files/MultiDependencyTest.php --FILE-- --EXPECTF-- diff --git a/tests/end-to-end/stop-on-warning-via-config.phpt b/tests/end-to-end/stop-on-warning-via-config.phpt deleted file mode 100644 index 84b5633933b..00000000000 --- a/tests/end-to-end/stop-on-warning-via-config.phpt +++ /dev/null @@ -1,26 +0,0 @@ ---TEST-- -phpunit -c ../../_files/configuration_stop_on_warning.xml --stop-on-warning StopOnWarningTestSuite ./tests/_files/StopOnWarningTestSuite.php ---FILE-- - ---EXPECTF-- -PHPUnit %s by Sebastian Bergmann and contributors. - -Runtime: %s -Random seed: %d - -..... 5 / 5 (100%) - -Time: %s, Memory: %s - -OK (5 tests, 6 assertions) diff --git a/tests/unit/Util/TestResultCacheTest.php b/tests/unit/Util/TestResultCacheTest.php index 369158e7fc3..ea7894bc6d7 100644 --- a/tests/unit/Util/TestResultCacheTest.php +++ b/tests/unit/Util/TestResultCacheTest.php @@ -18,7 +18,7 @@ class TestResultCacheTest extends TestCase { public function testReadsCacheFromProvidedFilename(): void { - $cacheFile = TEST_FILES_PATH . '../end-to-end/loggers/_files/MultiDependencyTest_result_cache.txt'; + $cacheFile = TEST_FILES_PATH . '../end-to-end/execution-order/_files/MultiDependencyTest_result_cache.txt'; $cache = new TestResultCache($cacheFile); $cache->load(); @@ -28,7 +28,7 @@ public function testReadsCacheFromProvidedFilename(): void public function testDoesClearCacheBeforeLoad(): void { - $cacheFile = TEST_FILES_PATH . '../end-to-end/loggers/_files/MultiDependencyTest_result_cache.txt'; + $cacheFile = TEST_FILES_PATH . '../end-to-end/execution-order/_files/MultiDependencyTest_result_cache.txt'; $cache = new TestResultCache($cacheFile); $cache->setState('someTest', BaseTestRunner::STATUS_FAILURE); From 0977a2ced4b89e6fb37bf56f424fefda175ddf46 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Fri, 21 Dec 2018 00:12:19 +0100 Subject: [PATCH 50/51] Move some more CLI tests together --- tests/_files/configuration.one-file-suite.xml | 2 +- .../{ => end-to-end/cli}/_files/MyCommand.php | 0 .../cli/{ => _files}/output-cli-usage.txt | 0 tests/end-to-end/cli/help.phpt | 2 +- tests/end-to-end/cli/help2.phpt | 2 +- tests/end-to-end/cli/mycommand.phpt | 27 +++++++++++++++++++ .../{ => cli}/options-after-arguments.phpt | 11 +++++--- .../{ => execution-order}/repeat.phpt | 15 ++++++----- .../{ => loggers}/_files/HookTest.php | 0 .../end-to-end/{ => loggers}/_files/hooks.xml | 0 tests/end-to-end/{ => loggers}/debug.phpt | 13 +++++---- tests/end-to-end/{ => loggers}/hooks.phpt | 13 +++++---- tests/end-to-end/mycommand.phpt | 24 ----------------- 13 files changed, 62 insertions(+), 47 deletions(-) rename tests/{ => end-to-end/cli}/_files/MyCommand.php (100%) rename tests/end-to-end/cli/{ => _files}/output-cli-usage.txt (100%) create mode 100644 tests/end-to-end/cli/mycommand.phpt rename tests/end-to-end/{ => cli}/options-after-arguments.phpt (58%) rename tests/end-to-end/{ => execution-order}/repeat.phpt (54%) rename tests/end-to-end/{ => loggers}/_files/HookTest.php (100%) rename tests/end-to-end/{ => loggers}/_files/hooks.xml (100%) rename tests/end-to-end/{ => loggers}/debug.phpt (70%) rename tests/end-to-end/{ => loggers}/hooks.phpt (88%) delete mode 100644 tests/end-to-end/mycommand.phpt diff --git a/tests/_files/configuration.one-file-suite.xml b/tests/_files/configuration.one-file-suite.xml index 4eddce62e92..71b2e27231d 100644 --- a/tests/_files/configuration.one-file-suite.xml +++ b/tests/_files/configuration.one-file-suite.xml @@ -1,7 +1,7 @@ - ../../tests/end-to-end/debug.phpt + ../../tests/end-to-end/loggers/debug.phpt diff --git a/tests/_files/MyCommand.php b/tests/end-to-end/cli/_files/MyCommand.php similarity index 100% rename from tests/_files/MyCommand.php rename to tests/end-to-end/cli/_files/MyCommand.php diff --git a/tests/end-to-end/cli/output-cli-usage.txt b/tests/end-to-end/cli/_files/output-cli-usage.txt similarity index 100% rename from tests/end-to-end/cli/output-cli-usage.txt rename to tests/end-to-end/cli/_files/output-cli-usage.txt diff --git a/tests/end-to-end/cli/help.phpt b/tests/end-to-end/cli/help.phpt index e9da9b7192f..7541b1dfecc 100644 --- a/tests/end-to-end/cli/help.phpt +++ b/tests/end-to-end/cli/help.phpt @@ -7,4 +7,4 @@ phpunit require __DIR__ . '/../../bootstrap.php'; PHPUnit\TextUI\Command::main(); --EXPECTF_EXTERNAL-- -output-cli-usage.txt +_files/output-cli-usage.txt diff --git a/tests/end-to-end/cli/help2.phpt b/tests/end-to-end/cli/help2.phpt index 581ee8eab12..48615c4cc38 100644 --- a/tests/end-to-end/cli/help2.phpt +++ b/tests/end-to-end/cli/help2.phpt @@ -7,4 +7,4 @@ phpunit --help require __DIR__ . '/../../bootstrap.php'; PHPUnit\TextUI\Command::main(); --EXPECTF_EXTERNAL-- -output-cli-usage.txt +_files/output-cli-usage.txt diff --git a/tests/end-to-end/cli/mycommand.phpt b/tests/end-to-end/cli/mycommand.phpt new file mode 100644 index 00000000000..028103950f5 --- /dev/null +++ b/tests/end-to-end/cli/mycommand.phpt @@ -0,0 +1,27 @@ +--TEST-- +phpunit BankAccountTest ../../_files/BankAccountTest.php +--FILE-- + +--EXPECTF-- +MyCommand::myHandler 123 +PHPUnit %s by Sebastian Bergmann and contributors. + +... 3 / 3 (100%) + +Time: %s, Memory: %s + +OK (3 tests, 3 assertions) diff --git a/tests/end-to-end/options-after-arguments.phpt b/tests/end-to-end/cli/options-after-arguments.phpt similarity index 58% rename from tests/end-to-end/options-after-arguments.phpt rename to tests/end-to-end/cli/options-after-arguments.phpt index 43fd5ecf58e..dee00a58ae5 100644 --- a/tests/end-to-end/options-after-arguments.phpt +++ b/tests/end-to-end/cli/options-after-arguments.phpt @@ -2,11 +2,14 @@ phpunit BankAccountTest ../../_files/BankAccountTest.php --colors --FILE-- ---EXPECTF-- -MyCommand::myHandler 123 -PHPUnit %s by Sebastian Bergmann and contributors. - -... 3 / 3 (100%) - -Time: %s, Memory: %s - -OK (3 tests, 3 assertions) From ae1cb175f4f507b6c05abcfeb553277c09dc2f27 Mon Sep 17 00:00:00 2001 From: Ewout Pieter den Ouden Date: Sat, 22 Dec 2018 20:16:08 +0100 Subject: [PATCH 51/51] Misc test housekeeping --- .../_files/configuration.custom-printer.xml | 0 .../{ => loggers}/custom-printer-debug.phpt | 15 +++++++++------ .../{ => loggers}/custom-printer-verbose.phpt | 19 +++++++++++-------- .../{ => loggers}/failure-reverse-list.phpt | 15 +++++++++------ tests/unit/Framework/ConstraintTest.php | 6 ++++++ 5 files changed, 35 insertions(+), 20 deletions(-) rename tests/{ => end-to-end/loggers}/_files/configuration.custom-printer.xml (100%) rename tests/end-to-end/{ => loggers}/custom-printer-debug.phpt (68%) rename tests/end-to-end/{ => loggers}/custom-printer-verbose.phpt (52%) rename tests/end-to-end/{ => loggers}/failure-reverse-list.phpt (89%) diff --git a/tests/_files/configuration.custom-printer.xml b/tests/end-to-end/loggers/_files/configuration.custom-printer.xml similarity index 100% rename from tests/_files/configuration.custom-printer.xml rename to tests/end-to-end/loggers/_files/configuration.custom-printer.xml diff --git a/tests/end-to-end/custom-printer-debug.phpt b/tests/end-to-end/loggers/custom-printer-debug.phpt similarity index 68% rename from tests/end-to-end/custom-printer-debug.phpt rename to tests/end-to-end/loggers/custom-printer-debug.phpt index e30227a5cd8..0ef0bd59807 100644 --- a/tests/end-to-end/custom-printer-debug.phpt +++ b/tests/end-to-end/loggers/custom-printer-debug.phpt @@ -2,13 +2,16 @@ phpunit -c ../../_files/configuration.custom-printer.xml --debug BankAccountTest ../../_files/BankAccountTest.php --FILE-- fail(); } + /** + * @testdox Constraint PCRE not match + */ public function testConstraintPCRENotMatch(): void { $constraint = Assert::logicalNot( @@ -1024,6 +1027,9 @@ public function testConstraintPCRENotMatch(): void $this->fail(); } + /** + * @testdox Constraint PCRE not match with custom message + */ public function testConstraintPCRENotMatch2(): void { $constraint = Assert::logicalNot(