3 * This file is part of PHPUnit.
5 * (c) Sebastian Bergmann <sebastian@phpunit.de>
7 * For the full copyright and license information, please view the LICENSE
8 * file that was distributed with this source code.
11 use SebastianBergmann\GlobalState\Snapshot;
12 use SebastianBergmann\GlobalState\Restorer;
13 use SebastianBergmann\GlobalState\Blacklist;
14 use SebastianBergmann\Diff\Differ;
15 use SebastianBergmann\Exporter\Exporter;
16 use Prophecy\Exception\Prediction\PredictionException;
20 * A TestCase defines the fixture to run multiple tests.
22 * To define a TestCase
24 * 1) Implement a subclass of PHPUnit_Framework_TestCase.
25 * 2) Define instance variables that store the state of the fixture.
26 * 3) Initialize the fixture state by overriding setUp().
27 * 4) Clean-up after a test by overriding tearDown().
29 * Each test runs in its own fixture so there can be no side effects
36 * class MathTest extends PHPUnit_Framework_TestCase
41 * protected function setUp()
50 * For each test implement a method which interacts with the fixture.
51 * Verify the expected results with assertions specified by calling
52 * assert with a boolean.
56 * public function testPass()
58 * $this->assertTrue($this->value1 + $this->value2 == 5);
63 * @since Class available since Release 2.0.0
65 abstract class PHPUnit_Framework_TestCase extends PHPUnit_Framework_Assert implements PHPUnit_Framework_Test, PHPUnit_Framework_SelfDescribing
68 * Enable or disable the backup and restoration of the $GLOBALS array.
69 * Overwrite this attribute in a child class of TestCase.
70 * Setting this attribute in setUp() has no effect!
74 protected $backupGlobals = null;
79 protected $backupGlobalsBlacklist = array();
82 * Enable or disable the backup and restoration of static attributes.
83 * Overwrite this attribute in a child class of TestCase.
84 * Setting this attribute in setUp() has no effect!
88 protected $backupStaticAttributes = null;
93 protected $backupStaticAttributesBlacklist = array();
96 * Whether or not this test is to be run in a separate PHP process.
100 protected $runTestInSeparateProcess = null;
103 * Whether or not this test should preserve the global state when
104 * running in a separate PHP process.
108 protected $preserveGlobalState = true;
111 * Whether or not this test is running in a separate PHP process.
115 private $inIsolation = false;
120 private $data = array();
125 private $dataName = '';
130 private $useErrorHandler = null;
133 * The name of the expected Exception.
137 private $expectedException = null;
140 * The message of the expected Exception.
144 private $expectedExceptionMessage = '';
147 * The regex pattern to validate the expected Exception message.
151 private $expectedExceptionMessageRegExp = '';
154 * The code of the expected Exception.
158 private $expectedExceptionCode;
161 * The name of the test case.
165 private $name = null;
170 private $dependencies = array();
175 private $dependencyInput = array();
180 private $iniSettings = array();
185 private $locale = array();
190 private $mockObjects = array();
195 private $mockObjectGenerator = null;
205 private $statusMessage = '';
210 private $numAssertions = 0;
213 * @var PHPUnit_Framework_TestResult
225 private $output = '';
230 private $outputExpectedRegex = null;
235 private $outputExpectedString = null;
240 private $outputCallback = false;
245 private $outputBufferingActive = false;
250 private $outputBufferingLevel;
253 * @var SebastianBergmann\GlobalState\Snapshot
258 * @var Prophecy\Prophet
265 private $disallowChangesToGlobalState = false;
268 * Constructs a test case with the given name.
270 * @param string $name
272 * @param string $dataName
274 public function __construct($name = null, array $data = array(), $dataName = '')
276 if ($name !== null) {
277 $this->setName($name);
281 $this->dataName = $dataName;
285 * Returns a string representation of the test case.
289 public function toString()
291 $class = new ReflectionClass($this);
296 $this->getName(false)
299 return $buffer . $this->getDataSetAsString();
303 * Counts the number of test cases executed by run(TestResult result).
307 public function count()
313 * Returns the annotations for this test.
317 * @since Method available since Release 3.4.0
319 public function getAnnotations()
321 return PHPUnit_Util_Test::parseTestMethodAnnotations(
328 * Gets the name of a TestCase.
330 * @param bool $withDataSet
334 public function getName($withDataSet = true)
337 return $this->name . $this->getDataSetAsString(false);
344 * Returns the size of the test.
348 * @since Method available since Release 3.6.0
350 public function getSize()
352 return PHPUnit_Util_Test::getSize(
354 $this->getName(false)
361 * @since Method available since Release 3.6.0
363 public function getActualOutput()
365 if (!$this->outputBufferingActive) {
366 return $this->output;
368 return ob_get_contents();
375 * @since Method available since Release 3.6.0
377 public function hasOutput()
379 if (strlen($this->output) === 0) {
383 if ($this->hasExpectationOnOutput()) {
391 * @param string $expectedRegex
393 * @since Method available since Release 3.6.0
395 * @throws PHPUnit_Framework_Exception
397 public function expectOutputRegex($expectedRegex)
399 if ($this->outputExpectedString !== null) {
400 throw new PHPUnit_Framework_Exception;
403 if (is_string($expectedRegex) || is_null($expectedRegex)) {
404 $this->outputExpectedRegex = $expectedRegex;
409 * @param string $expectedString
411 * @since Method available since Release 3.6.0
413 public function expectOutputString($expectedString)
415 if ($this->outputExpectedRegex !== null) {
416 throw new PHPUnit_Framework_Exception;
419 if (is_string($expectedString) || is_null($expectedString)) {
420 $this->outputExpectedString = $expectedString;
427 * @since Method available since Release 3.6.5
430 public function hasPerformedExpectationsOnOutput()
432 return $this->hasExpectationOnOutput();
438 * @since Method available since Release 4.3.3
440 public function hasExpectationOnOutput()
442 return is_string($this->outputExpectedString) || is_string($this->outputExpectedRegex);
448 * @since Method available since Release 3.2.0
450 public function getExpectedException()
452 return $this->expectedException;
456 * @param mixed $exceptionName
457 * @param string $exceptionMessage
458 * @param int $exceptionCode
460 * @since Method available since Release 3.2.0
462 public function setExpectedException($exceptionName, $exceptionMessage = '', $exceptionCode = null)
464 $this->expectedException = $exceptionName;
465 $this->expectedExceptionMessage = $exceptionMessage;
466 $this->expectedExceptionCode = $exceptionCode;
470 * @param mixed $exceptionName
471 * @param string $exceptionMessageRegExp
472 * @param int $exceptionCode
474 * @since Method available since Release 4.3.0
476 public function setExpectedExceptionRegExp($exceptionName, $exceptionMessageRegExp = '', $exceptionCode = null)
478 $this->expectedException = $exceptionName;
479 $this->expectedExceptionMessageRegExp = $exceptionMessageRegExp;
480 $this->expectedExceptionCode = $exceptionCode;
484 * @since Method available since Release 3.4.0
486 protected function setExpectedExceptionFromAnnotation()
489 $expectedException = PHPUnit_Util_Test::getExpectedException(
494 if ($expectedException !== false) {
495 $this->setExpectedException(
496 $expectedException['class'],
497 $expectedException['message'],
498 $expectedException['code']
501 if (!empty($expectedException['message_regex'])) {
502 $this->setExpectedExceptionRegExp(
503 $expectedException['class'],
504 $expectedException['message_regex'],
505 $expectedException['code']
509 } catch (ReflectionException $e) {
514 * @param bool $useErrorHandler
516 * @since Method available since Release 3.4.0
518 public function setUseErrorHandler($useErrorHandler)
520 $this->useErrorHandler = $useErrorHandler;
524 * @since Method available since Release 3.4.0
526 protected function setUseErrorHandlerFromAnnotation()
529 $useErrorHandler = PHPUnit_Util_Test::getErrorHandlerSettings(
534 if ($useErrorHandler !== null) {
535 $this->setUseErrorHandler($useErrorHandler);
537 } catch (ReflectionException $e) {
542 * @since Method available since Release 3.6.0
544 protected function checkRequirements()
546 if (!$this->name || !method_exists($this, $this->name)) {
550 $missingRequirements = PHPUnit_Util_Test::getMissingRequirements(
555 if (!empty($missingRequirements)) {
556 $this->markTestSkipped(implode(PHP_EOL, $missingRequirements));
561 * Returns the status of this test.
565 * @since Method available since Release 3.1.0
567 public function getStatus()
569 return $this->status;
573 * Returns the status message of this test.
577 * @since Method available since Release 3.3.0
579 public function getStatusMessage()
581 return $this->statusMessage;
585 * Returns whether or not this test has failed.
589 * @since Method available since Release 3.0.0
591 public function hasFailed()
593 $status = $this->getStatus();
595 return $status == PHPUnit_Runner_BaseTestRunner::STATUS_FAILURE ||
596 $status == PHPUnit_Runner_BaseTestRunner::STATUS_ERROR;
600 * Runs the test case and collects the results in a TestResult object.
601 * If no TestResult object is passed a new one will be created.
603 * @param PHPUnit_Framework_TestResult $result
605 * @return PHPUnit_Framework_TestResult
607 * @throws PHPUnit_Framework_Exception
609 public function run(PHPUnit_Framework_TestResult $result = null)
611 if ($result === null) {
612 $result = $this->createResult();
615 if (!$this instanceof PHPUnit_Framework_Warning) {
616 $this->setTestResultObject($result);
617 $this->setUseErrorHandlerFromAnnotation();
620 if ($this->useErrorHandler !== null) {
621 $oldErrorHandlerSetting = $result->getConvertErrorsToExceptions();
622 $result->convertErrorsToExceptions($this->useErrorHandler);
625 if (!$this instanceof PHPUnit_Framework_Warning && !$this->handleDependencies()) {
629 if ($this->runTestInSeparateProcess === true &&
630 $this->inIsolation !== true &&
631 !$this instanceof PHPUnit_Extensions_SeleniumTestCase &&
632 !$this instanceof PHPUnit_Extensions_PhptTestCase) {
633 $class = new ReflectionClass($this);
635 $template = new Text_Template(
636 __DIR__ . '/../Util/PHP/Template/TestCaseMethod.tpl'
639 if ($this->preserveGlobalState) {
640 $constants = PHPUnit_Util_GlobalState::getConstantsAsString();
641 $globals = PHPUnit_Util_GlobalState::getGlobalsAsString();
642 $includedFiles = PHPUnit_Util_GlobalState::getIncludedFilesAsString();
643 $iniSettings = PHPUnit_Util_GlobalState::getIniSettingsAsString();
646 if (!empty($GLOBALS['__PHPUNIT_BOOTSTRAP'])) {
647 $globals = '$GLOBALS[\'__PHPUNIT_BOOTSTRAP\'] = ' . var_export($GLOBALS['__PHPUNIT_BOOTSTRAP'], true) . ";\n";
655 $coverage = $result->getCollectCodeCoverageInformation() ? 'true' : 'false';
656 $isStrictAboutTestsThatDoNotTestAnything = $result->isStrictAboutTestsThatDoNotTestAnything() ? 'true' : 'false';
657 $isStrictAboutOutputDuringTests = $result->isStrictAboutOutputDuringTests() ? 'true' : 'false';
658 $isStrictAboutTestSize = $result->isStrictAboutTestSize() ? 'true' : 'false';
659 $isStrictAboutTodoAnnotatedTests = $result->isStrictAboutTodoAnnotatedTests() ? 'true' : 'false';
661 if (defined('PHPUNIT_COMPOSER_INSTALL')) {
662 $composerAutoload = var_export(PHPUNIT_COMPOSER_INSTALL, true);
664 $composerAutoload = '\'\'';
667 if (defined('__PHPUNIT_PHAR__')) {
668 $phar = var_export(__PHPUNIT_PHAR__, true);
673 if ($result->getCodeCoverage()) {
674 $codeCoverageFilter = $result->getCodeCoverage()->filter();
676 $codeCoverageFilter = null;
679 $data = var_export(serialize($this->data), true);
680 $dataName = var_export($this->dataName, true);
681 $dependencyInput = var_export(serialize($this->dependencyInput), true);
682 $includePath = var_export(get_include_path(), true);
683 $codeCoverageFilter = var_export(serialize($codeCoverageFilter), true);
684 // must do these fixes because TestCaseMethod.tpl has unserialize('{data}') in it, and we can't break BC
685 // the lines above used to use addcslashes() rather than var_export(), which breaks null byte escape sequences
686 $data = "'." . $data . ".'";
687 $dataName = "'.(" . $dataName . ").'";
688 $dependencyInput = "'." . $dependencyInput . ".'";
689 $includePath = "'." . $includePath . ".'";
690 $codeCoverageFilter = "'." . $codeCoverageFilter . ".'";
692 $configurationFilePath = (isset($GLOBALS['__PHPUNIT_CONFIGURATION_FILE']) ? $GLOBALS['__PHPUNIT_CONFIGURATION_FILE'] : '');
696 'composerAutoload' => $composerAutoload,
698 'filename' => $class->getFileName(),
699 'className' => $class->getName(),
700 'methodName' => $this->name,
701 'collectCodeCoverageInformation' => $coverage,
703 'dataName' => $dataName,
704 'dependencyInput' => $dependencyInput,
705 'constants' => $constants,
706 'globals' => $globals,
707 'include_path' => $includePath,
708 'included_files' => $includedFiles,
709 'iniSettings' => $iniSettings,
710 'isStrictAboutTestsThatDoNotTestAnything' => $isStrictAboutTestsThatDoNotTestAnything,
711 'isStrictAboutOutputDuringTests' => $isStrictAboutOutputDuringTests,
712 'isStrictAboutTestSize' => $isStrictAboutTestSize,
713 'isStrictAboutTodoAnnotatedTests' => $isStrictAboutTodoAnnotatedTests,
714 'codeCoverageFilter' => $codeCoverageFilter,
715 'configurationFilePath' => $configurationFilePath
719 $this->prepareTemplate($template);
721 $php = PHPUnit_Util_PHP::factory();
722 $php->runTestJob($template->render(), $this, $result);
727 if ($this->useErrorHandler !== null) {
728 $result->convertErrorsToExceptions($oldErrorHandlerSetting);
731 $this->result = null;
737 * Runs the bare test sequence.
739 public function runBare()
741 $this->numAssertions = 0;
743 $this->snapshotGlobalState();
744 $this->startOutputBuffering();
746 $currentWorkingDirectory = getcwd();
748 $hookMethods = PHPUnit_Util_Test::getHookMethods(get_class($this));
751 $hasMetRequirements = false;
752 $this->checkRequirements();
753 $hasMetRequirements = true;
755 if ($this->inIsolation) {
756 foreach ($hookMethods['beforeClass'] as $method) {
761 $this->setExpectedExceptionFromAnnotation();
763 foreach ($hookMethods['before'] as $method) {
767 $this->assertPreConditions();
768 $this->testResult = $this->runTest();
769 $this->verifyMockObjects();
770 $this->assertPostConditions();
772 $this->status = PHPUnit_Runner_BaseTestRunner::STATUS_PASSED;
773 } catch (PHPUnit_Framework_IncompleteTest $e) {
774 $this->status = PHPUnit_Runner_BaseTestRunner::STATUS_INCOMPLETE;
775 $this->statusMessage = $e->getMessage();
776 } catch (PHPUnit_Framework_SkippedTest $e) {
777 $this->status = PHPUnit_Runner_BaseTestRunner::STATUS_SKIPPED;
778 $this->statusMessage = $e->getMessage();
779 } catch (PHPUnit_Framework_AssertionFailedError $e) {
780 $this->status = PHPUnit_Runner_BaseTestRunner::STATUS_FAILURE;
781 $this->statusMessage = $e->getMessage();
782 } catch (PredictionException $e) {
783 $this->status = PHPUnit_Runner_BaseTestRunner::STATUS_FAILURE;
784 $this->statusMessage = $e->getMessage();
785 } catch (Throwable $_e) {
787 } catch (Exception $_e) {
792 $this->status = PHPUnit_Runner_BaseTestRunner::STATUS_ERROR;
793 $this->statusMessage = $_e->getMessage();
796 // Clean up the mock objects.
797 $this->mockObjects = array();
798 $this->prophet = null;
800 // Tear down the fixture. An exception raised in tearDown() will be
801 // caught and passed on when no exception was raised before.
803 if ($hasMetRequirements) {
804 foreach ($hookMethods['after'] as $method) {
808 if ($this->inIsolation) {
809 foreach ($hookMethods['afterClass'] as $method) {
814 } catch (Throwable $_e) {
818 } catch (Exception $_e) {
825 $this->stopOutputBuffering();
826 } catch (PHPUnit_Framework_RiskyTestError $_e) {
834 if ($currentWorkingDirectory != getcwd()) {
835 chdir($currentWorkingDirectory);
838 $this->restoreGlobalState();
840 // Clean up INI settings.
841 foreach ($this->iniSettings as $varName => $oldValue) {
842 ini_set($varName, $oldValue);
845 $this->iniSettings = array();
847 // Clean up locale settings.
848 foreach ($this->locale as $category => $locale) {
849 setlocale($category, $locale);
852 // Perform assertion on output.
855 if ($this->outputExpectedRegex !== null) {
856 $this->assertRegExp($this->outputExpectedRegex, $this->output);
857 } elseif ($this->outputExpectedString !== null) {
858 $this->assertEquals($this->outputExpectedString, $this->output);
860 } catch (Throwable $_e) {
862 } catch (Exception $_e) {
867 // Workaround for missing "finally".
869 if ($e instanceof PredictionException) {
870 $e = new PHPUnit_Framework_AssertionFailedError($e->getMessage());
873 if (!$e instanceof Exception) {
874 // Rethrow Error directly on PHP 7 as onNotSuccessfulTest does not support it
878 $this->onNotSuccessfulTest($e);
883 * Override to run the test and assert its state.
887 * @throws Exception|PHPUnit_Framework_Exception
888 * @throws PHPUnit_Framework_Exception
890 protected function runTest()
892 if ($this->name === null) {
893 throw new PHPUnit_Framework_Exception(
894 'PHPUnit_Framework_TestCase::$name must not be null.'
899 $class = new ReflectionClass($this);
900 $method = $class->getMethod($this->name);
901 } catch (ReflectionException $e) {
902 $this->fail($e->getMessage());
906 $testResult = $method->invokeArgs(
908 array_merge($this->data, $this->dependencyInput)
910 } catch (Throwable $_e) {
912 } catch (Exception $_e) {
917 $checkException = false;
919 if (!($e instanceof PHPUnit_Framework_SkippedTestError) && is_string($this->expectedException)) {
920 $checkException = true;
922 if ($e instanceof PHPUnit_Framework_Exception) {
923 $checkException = false;
926 $reflector = new ReflectionClass($this->expectedException);
928 if ($this->expectedException === 'PHPUnit_Framework_Exception' ||
929 $this->expectedException === '\PHPUnit_Framework_Exception' ||
930 $reflector->isSubclassOf('PHPUnit_Framework_Exception')) {
931 $checkException = true;
935 if ($checkException) {
938 new PHPUnit_Framework_Constraint_Exception(
939 $this->expectedException
943 if (is_string($this->expectedExceptionMessage) &&
944 !empty($this->expectedExceptionMessage)) {
947 new PHPUnit_Framework_Constraint_ExceptionMessage(
948 $this->expectedExceptionMessage
953 if (is_string($this->expectedExceptionMessageRegExp) &&
954 !empty($this->expectedExceptionMessageRegExp)) {
957 new PHPUnit_Framework_Constraint_ExceptionMessageRegExp(
958 $this->expectedExceptionMessageRegExp
963 if ($this->expectedExceptionCode !== null) {
966 new PHPUnit_Framework_Constraint_ExceptionCode(
967 $this->expectedExceptionCode
978 if ($this->expectedException !== null) {
981 new PHPUnit_Framework_Constraint_Exception(
982 $this->expectedException
991 * Verifies the mock object expectations.
993 * @since Method available since Release 3.5.0
995 protected function verifyMockObjects()
997 foreach ($this->mockObjects as $mockObject) {
998 if ($mockObject->__phpunit_hasMatchers()) {
999 $this->numAssertions++;
1002 $mockObject->__phpunit_verify();
1005 if ($this->prophet !== null) {
1007 $this->prophet->checkPredictions();
1008 } catch (Throwable $e) {
1009 /* Intentionally left empty */
1010 } catch (Exception $e) {
1011 /* Intentionally left empty */
1014 foreach ($this->prophet->getProphecies() as $objectProphecy) {
1015 foreach ($objectProphecy->getMethodProphecies() as $methodProphecies) {
1016 foreach ($methodProphecies as $methodProphecy) {
1017 $this->numAssertions += count($methodProphecy->getCheckedPredictions());
1029 * Sets the name of a TestCase.
1033 public function setName($name)
1035 $this->name = $name;
1039 * Sets the dependencies of a TestCase.
1041 * @param array $dependencies
1043 * @since Method available since Release 3.4.0
1045 public function setDependencies(array $dependencies)
1047 $this->dependencies = $dependencies;
1051 * Returns true if the tests has dependencies
1055 * @since Method available since Release 4.0.0
1057 public function hasDependencies()
1059 return count($this->dependencies) > 0;
1065 * @param array $dependencyInput
1067 * @since Method available since Release 3.4.0
1069 public function setDependencyInput(array $dependencyInput)
1071 $this->dependencyInput = $dependencyInput;
1075 * @param bool $disallowChangesToGlobalState
1077 * @since Method available since Release 4.6.0
1079 public function setDisallowChangesToGlobalState($disallowChangesToGlobalState)
1081 $this->disallowChangesToGlobalState = $disallowChangesToGlobalState;
1085 * Calling this method in setUp() has no effect!
1087 * @param bool $backupGlobals
1089 * @since Method available since Release 3.3.0
1091 public function setBackupGlobals($backupGlobals)
1093 if (is_null($this->backupGlobals) && is_bool($backupGlobals)) {
1094 $this->backupGlobals = $backupGlobals;
1099 * Calling this method in setUp() has no effect!
1101 * @param bool $backupStaticAttributes
1103 * @since Method available since Release 3.4.0
1105 public function setBackupStaticAttributes($backupStaticAttributes)
1107 if (is_null($this->backupStaticAttributes) &&
1108 is_bool($backupStaticAttributes)) {
1109 $this->backupStaticAttributes = $backupStaticAttributes;
1114 * @param bool $runTestInSeparateProcess
1116 * @throws PHPUnit_Framework_Exception
1118 * @since Method available since Release 3.4.0
1120 public function setRunTestInSeparateProcess($runTestInSeparateProcess)
1122 if (is_bool($runTestInSeparateProcess)) {
1123 if ($this->runTestInSeparateProcess === null) {
1124 $this->runTestInSeparateProcess = $runTestInSeparateProcess;
1127 throw PHPUnit_Util_InvalidArgumentHelper::factory(1, 'boolean');
1132 * @param bool $preserveGlobalState
1134 * @throws PHPUnit_Framework_Exception
1136 * @since Method available since Release 3.4.0
1138 public function setPreserveGlobalState($preserveGlobalState)
1140 if (is_bool($preserveGlobalState)) {
1141 $this->preserveGlobalState = $preserveGlobalState;
1143 throw PHPUnit_Util_InvalidArgumentHelper::factory(1, 'boolean');
1148 * @param bool $inIsolation
1150 * @throws PHPUnit_Framework_Exception
1152 * @since Method available since Release 3.4.0
1154 public function setInIsolation($inIsolation)
1156 if (is_bool($inIsolation)) {
1157 $this->inIsolation = $inIsolation;
1159 throw PHPUnit_Util_InvalidArgumentHelper::factory(1, 'boolean');
1166 * @since Method available since Release 4.3.0
1168 public function isInIsolation()
1170 return $this->inIsolation;
1176 * @since Method available since Release 3.4.0
1178 public function getResult()
1180 return $this->testResult;
1184 * @param mixed $result
1186 * @since Method available since Release 3.4.0
1188 public function setResult($result)
1190 $this->testResult = $result;
1194 * @param callable $callback
1196 * @throws PHPUnit_Framework_Exception
1198 * @since Method available since Release 3.6.0
1200 public function setOutputCallback($callback)
1202 if (!is_callable($callback)) {
1203 throw PHPUnit_Util_InvalidArgumentHelper::factory(1, 'callback');
1206 $this->outputCallback = $callback;
1210 * @return PHPUnit_Framework_TestResult
1212 * @since Method available since Release 3.5.7
1214 public function getTestResultObject()
1216 return $this->result;
1220 * @param PHPUnit_Framework_TestResult $result
1222 * @since Method available since Release 3.6.0
1224 public function setTestResultObject(PHPUnit_Framework_TestResult $result)
1226 $this->result = $result;
1230 * This method is a wrapper for the ini_set() function that automatically
1231 * resets the modified php.ini setting to its original value after the
1234 * @param string $varName
1235 * @param string $newValue
1237 * @throws PHPUnit_Framework_Exception
1239 * @since Method available since Release 3.0.0
1241 protected function iniSet($varName, $newValue)
1243 if (!is_string($varName)) {
1244 throw PHPUnit_Util_InvalidArgumentHelper::factory(1, 'string');
1247 $currentValue = ini_set($varName, $newValue);
1249 if ($currentValue !== false) {
1250 $this->iniSettings[$varName] = $currentValue;
1252 throw new PHPUnit_Framework_Exception(
1254 'INI setting "%s" could not be set to "%s".',
1263 * This method is a wrapper for the setlocale() function that automatically
1264 * resets the locale to its original value after the test is run.
1266 * @param int $category
1267 * @param string $locale
1269 * @throws PHPUnit_Framework_Exception
1271 * @since Method available since Release 3.1.0
1273 protected function setLocale()
1275 $args = func_get_args();
1277 if (count($args) < 2) {
1278 throw new PHPUnit_Framework_Exception;
1281 $category = $args[0];
1284 $categories = array(
1285 LC_ALL, LC_COLLATE, LC_CTYPE, LC_MONETARY, LC_NUMERIC, LC_TIME
1288 if (defined('LC_MESSAGES')) {
1289 $categories[] = LC_MESSAGES;
1292 if (!in_array($category, $categories)) {
1293 throw new PHPUnit_Framework_Exception;
1296 if (!is_array($locale) && !is_string($locale)) {
1297 throw new PHPUnit_Framework_Exception;
1300 $this->locale[$category] = setlocale($category, null);
1302 $result = call_user_func_array('setlocale', $args);
1304 if ($result === false) {
1305 throw new PHPUnit_Framework_Exception(
1306 'The locale functionality is not implemented on your platform, ' .
1307 'the specified locale does not exist or the category name is ' .
1314 * Returns a mock object for the specified class.
1316 * @param string $originalClassName Name of the class to mock.
1317 * @param array|null $methods When provided, only methods whose names are in the array
1318 * are replaced with a configurable test double. The behavior
1319 * of the other methods is not changed.
1320 * Providing null means that no methods will be replaced.
1321 * @param array $arguments Parameters to pass to the original class' constructor.
1322 * @param string $mockClassName Class name for the generated test double class.
1323 * @param bool $callOriginalConstructor Can be used to disable the call to the original class' constructor.
1324 * @param bool $callOriginalClone Can be used to disable the call to the original class' clone constructor.
1325 * @param bool $callAutoload Can be used to disable __autoload() during the generation of the test double class.
1326 * @param bool $cloneArguments
1327 * @param bool $callOriginalMethods
1328 * @param object $proxyTarget
1330 * @return PHPUnit_Framework_MockObject_MockObject
1332 * @throws PHPUnit_Framework_Exception
1334 * @since Method available since Release 3.0.0
1336 public function getMock($originalClassName, $methods = array(), array $arguments = array(), $mockClassName = '', $callOriginalConstructor = true, $callOriginalClone = true, $callAutoload = true, $cloneArguments = false, $callOriginalMethods = false, $proxyTarget = null)
1338 $mockObject = $this->getMockObjectGenerator()->getMock(
1343 $callOriginalConstructor,
1347 $callOriginalMethods,
1351 $this->mockObjects[] = $mockObject;
1357 * Returns a builder object to create mock objects using a fluent interface.
1359 * @param string $className
1361 * @return PHPUnit_Framework_MockObject_MockBuilder
1363 * @since Method available since Release 3.5.0
1365 public function getMockBuilder($className)
1367 return new PHPUnit_Framework_MockObject_MockBuilder($this, $className);
1371 * Mocks the specified class and returns the name of the mocked class.
1373 * @param string $originalClassName
1374 * @param array $methods
1375 * @param array $arguments
1376 * @param string $mockClassName
1377 * @param bool $callOriginalConstructor
1378 * @param bool $callOriginalClone
1379 * @param bool $callAutoload
1380 * @param bool $cloneArguments
1384 * @throws PHPUnit_Framework_Exception
1386 * @since Method available since Release 3.5.0
1388 protected function getMockClass($originalClassName, $methods = array(), array $arguments = array(), $mockClassName = '', $callOriginalConstructor = false, $callOriginalClone = true, $callAutoload = true, $cloneArguments = false)
1390 $mock = $this->getMock(
1395 $callOriginalConstructor,
1401 return get_class($mock);
1405 * Returns a mock object for the specified abstract class with all abstract
1406 * methods of the class mocked. Concrete methods are not mocked by default.
1407 * To mock concrete methods, use the 7th parameter ($mockedMethods).
1409 * @param string $originalClassName
1410 * @param array $arguments
1411 * @param string $mockClassName
1412 * @param bool $callOriginalConstructor
1413 * @param bool $callOriginalClone
1414 * @param bool $callAutoload
1415 * @param array $mockedMethods
1416 * @param bool $cloneArguments
1418 * @return PHPUnit_Framework_MockObject_MockObject
1420 * @since Method available since Release 3.4.0
1422 * @throws PHPUnit_Framework_Exception
1424 public function getMockForAbstractClass($originalClassName, array $arguments = array(), $mockClassName = '', $callOriginalConstructor = true, $callOriginalClone = true, $callAutoload = true, $mockedMethods = array(), $cloneArguments = false)
1426 $mockObject = $this->getMockObjectGenerator()->getMockForAbstractClass(
1430 $callOriginalConstructor,
1437 $this->mockObjects[] = $mockObject;
1443 * Returns a mock object based on the given WSDL file.
1445 * @param string $wsdlFile
1446 * @param string $originalClassName
1447 * @param string $mockClassName
1448 * @param array $methods
1449 * @param bool $callOriginalConstructor
1450 * @param array $options An array of options passed to SOAPClient::_construct
1452 * @return PHPUnit_Framework_MockObject_MockObject
1454 * @since Method available since Release 3.4.0
1456 protected function getMockFromWsdl($wsdlFile, $originalClassName = '', $mockClassName = '', array $methods = array(), $callOriginalConstructor = true, array $options = array())
1458 if ($originalClassName === '') {
1459 $originalClassName = str_replace('.wsdl', '', basename($wsdlFile));
1462 if (!class_exists($originalClassName)) {
1464 $this->getMockObjectGenerator()->generateClassFromWsdl(
1473 return $this->getMock(
1476 array('', $options),
1478 $callOriginalConstructor,
1485 * Returns a mock object for the specified trait with all abstract methods
1486 * of the trait mocked. Concrete methods to mock can be specified with the
1487 * `$mockedMethods` parameter.
1489 * @param string $traitName
1490 * @param array $arguments
1491 * @param string $mockClassName
1492 * @param bool $callOriginalConstructor
1493 * @param bool $callOriginalClone
1494 * @param bool $callAutoload
1495 * @param array $mockedMethods
1496 * @param bool $cloneArguments
1498 * @return PHPUnit_Framework_MockObject_MockObject
1500 * @since Method available since Release 4.0.0
1502 * @throws PHPUnit_Framework_Exception
1504 public function getMockForTrait($traitName, array $arguments = array(), $mockClassName = '', $callOriginalConstructor = true, $callOriginalClone = true, $callAutoload = true, $mockedMethods = array(), $cloneArguments = false)
1506 $mockObject = $this->getMockObjectGenerator()->getMockForTrait(
1510 $callOriginalConstructor,
1517 $this->mockObjects[] = $mockObject;
1523 * Returns an object for the specified trait.
1525 * @param string $traitName
1526 * @param array $arguments
1527 * @param string $traitClassName
1528 * @param bool $callOriginalConstructor
1529 * @param bool $callOriginalClone
1530 * @param bool $callAutoload
1531 * @param bool $cloneArguments
1535 * @since Method available since Release 3.6.0
1537 * @throws PHPUnit_Framework_Exception
1539 protected function getObjectForTrait($traitName, array $arguments = array(), $traitClassName = '', $callOriginalConstructor = true, $callOriginalClone = true, $callAutoload = true, $cloneArguments = false)
1541 return $this->getMockObjectGenerator()->getObjectForTrait(
1545 $callOriginalConstructor,
1553 * @param string|null $classOrInterface
1555 * @return \Prophecy\Prophecy\ObjectProphecy
1557 * @throws \LogicException
1559 * @since Method available since Release 4.5.0
1561 protected function prophesize($classOrInterface = null)
1563 return $this->getProphet()->prophesize($classOrInterface);
1567 * Adds a value to the assertion counter.
1571 * @since Method available since Release 3.3.3
1573 public function addToAssertionCount($count)
1575 $this->numAssertions += $count;
1579 * Returns the number of assertions performed by this test.
1583 * @since Method available since Release 3.3.0
1585 public function getNumAssertions()
1587 return $this->numAssertions;
1591 * Returns a matcher that matches when the method is executed
1592 * zero or more times.
1594 * @return PHPUnit_Framework_MockObject_Matcher_AnyInvokedCount
1596 * @since Method available since Release 3.0.0
1598 public static function any()
1600 return new PHPUnit_Framework_MockObject_Matcher_AnyInvokedCount;
1604 * Returns a matcher that matches when the method is never executed.
1606 * @return PHPUnit_Framework_MockObject_Matcher_InvokedCount
1608 * @since Method available since Release 3.0.0
1610 public static function never()
1612 return new PHPUnit_Framework_MockObject_Matcher_InvokedCount(0);
1616 * Returns a matcher that matches when the method is executed
1619 * @param int $requiredInvocations
1621 * @return PHPUnit_Framework_MockObject_Matcher_InvokedAtLeastCount
1623 * @since Method available since Release 4.2.0
1625 public static function atLeast($requiredInvocations)
1627 return new PHPUnit_Framework_MockObject_Matcher_InvokedAtLeastCount(
1628 $requiredInvocations
1633 * Returns a matcher that matches when the method is executed at least once.
1635 * @return PHPUnit_Framework_MockObject_Matcher_InvokedAtLeastOnce
1637 * @since Method available since Release 3.0.0
1639 public static function atLeastOnce()
1641 return new PHPUnit_Framework_MockObject_Matcher_InvokedAtLeastOnce;
1645 * Returns a matcher that matches when the method is executed exactly once.
1647 * @return PHPUnit_Framework_MockObject_Matcher_InvokedCount
1649 * @since Method available since Release 3.0.0
1651 public static function once()
1653 return new PHPUnit_Framework_MockObject_Matcher_InvokedCount(1);
1657 * Returns a matcher that matches when the method is executed
1658 * exactly $count times.
1662 * @return PHPUnit_Framework_MockObject_Matcher_InvokedCount
1664 * @since Method available since Release 3.0.0
1666 public static function exactly($count)
1668 return new PHPUnit_Framework_MockObject_Matcher_InvokedCount($count);
1672 * Returns a matcher that matches when the method is executed
1675 * @param int $allowedInvocations
1677 * @return PHPUnit_Framework_MockObject_Matcher_InvokedAtMostCount
1679 * @since Method available since Release 4.2.0
1681 public static function atMost($allowedInvocations)
1683 return new PHPUnit_Framework_MockObject_Matcher_InvokedAtMostCount(
1689 * Returns a matcher that matches when the method is executed
1690 * at the given index.
1694 * @return PHPUnit_Framework_MockObject_Matcher_InvokedAtIndex
1696 * @since Method available since Release 3.0.0
1698 public static function at($index)
1700 return new PHPUnit_Framework_MockObject_Matcher_InvokedAtIndex($index);
1704 * @param mixed $value
1706 * @return PHPUnit_Framework_MockObject_Stub_Return
1708 * @since Method available since Release 3.0.0
1710 public static function returnValue($value)
1712 return new PHPUnit_Framework_MockObject_Stub_Return($value);
1716 * @param array $valueMap
1718 * @return PHPUnit_Framework_MockObject_Stub_ReturnValueMap
1720 * @since Method available since Release 3.6.0
1722 public static function returnValueMap(array $valueMap)
1724 return new PHPUnit_Framework_MockObject_Stub_ReturnValueMap($valueMap);
1728 * @param int $argumentIndex
1730 * @return PHPUnit_Framework_MockObject_Stub_ReturnArgument
1732 * @since Method available since Release 3.3.0
1734 public static function returnArgument($argumentIndex)
1736 return new PHPUnit_Framework_MockObject_Stub_ReturnArgument(
1742 * @param mixed $callback
1744 * @return PHPUnit_Framework_MockObject_Stub_ReturnCallback
1746 * @since Method available since Release 3.3.0
1748 public static function returnCallback($callback)
1750 return new PHPUnit_Framework_MockObject_Stub_ReturnCallback($callback);
1754 * Returns the current object.
1756 * This method is useful when mocking a fluent interface.
1758 * @return PHPUnit_Framework_MockObject_Stub_ReturnSelf
1760 * @since Method available since Release 3.6.0
1762 public static function returnSelf()
1764 return new PHPUnit_Framework_MockObject_Stub_ReturnSelf();
1768 * @param Exception $exception
1770 * @return PHPUnit_Framework_MockObject_Stub_Exception
1772 * @since Method available since Release 3.1.0
1774 public static function throwException(Exception $exception)
1776 return new PHPUnit_Framework_MockObject_Stub_Exception($exception);
1780 * @param mixed $value, ...
1782 * @return PHPUnit_Framework_MockObject_Stub_ConsecutiveCalls
1784 * @since Method available since Release 3.0.0
1786 public static function onConsecutiveCalls()
1788 $args = func_get_args();
1790 return new PHPUnit_Framework_MockObject_Stub_ConsecutiveCalls($args);
1794 * Gets the data set description of a TestCase.
1796 * @param bool $includeData
1800 * @since Method available since Release 3.3.0
1802 protected function getDataSetAsString($includeData = true)
1806 if (!empty($this->data)) {
1807 if (is_int($this->dataName)) {
1808 $buffer .= sprintf(' with data set #%d', $this->dataName);
1810 $buffer .= sprintf(' with data set "%s"', $this->dataName);
1813 $exporter = new Exporter;
1816 $buffer .= sprintf(' (%s)', $exporter->shortenedRecursiveExport($this->data));
1824 * Creates a default TestResult object.
1826 * @return PHPUnit_Framework_TestResult
1828 protected function createResult()
1830 return new PHPUnit_Framework_TestResult;
1834 * @since Method available since Release 3.5.4
1836 protected function handleDependencies()
1838 if (!empty($this->dependencies) && !$this->inIsolation) {
1839 $className = get_class($this);
1840 $passed = $this->result->passed();
1841 $passedKeys = array_keys($passed);
1842 $numKeys = count($passedKeys);
1844 for ($i = 0; $i < $numKeys; $i++) {
1845 $pos = strpos($passedKeys[$i], ' with data set');
1847 if ($pos !== false) {
1848 $passedKeys[$i] = substr($passedKeys[$i], 0, $pos);
1852 $passedKeys = array_flip(array_unique($passedKeys));
1854 foreach ($this->dependencies as $dependency) {
1855 if (strpos($dependency, '::') === false) {
1856 $dependency = $className . '::' . $dependency;
1859 if (!isset($passedKeys[$dependency])) {
1860 $this->result->addError(
1862 new PHPUnit_Framework_SkippedTestError(
1864 'This test depends on "%s" to pass.',
1874 if (isset($passed[$dependency])) {
1875 if ($passed[$dependency]['size'] != PHPUnit_Util_Test::UNKNOWN &&
1876 $this->getSize() != PHPUnit_Util_Test::UNKNOWN &&
1877 $passed[$dependency]['size'] > $this->getSize()) {
1878 $this->result->addError(
1880 new PHPUnit_Framework_SkippedTestError(
1881 'This test depends on a test that is larger than itself.'
1889 $this->dependencyInput[$dependency] = $passed[$dependency]['result'];
1891 $this->dependencyInput[$dependency] = null;
1900 * This method is called before the first test of this test class is run.
1902 * @since Method available since Release 3.4.0
1904 public static function setUpBeforeClass()
1909 * Sets up the fixture, for example, open a network connection.
1910 * This method is called before a test is executed.
1912 protected function setUp()
1917 * Performs assertions shared by all tests of a test case.
1919 * This method is called before the execution of a test starts
1920 * and after setUp() is called.
1922 * @since Method available since Release 3.2.8
1924 protected function assertPreConditions()
1929 * Performs assertions shared by all tests of a test case.
1931 * This method is called before the execution of a test ends
1932 * and before tearDown() is called.
1934 * @since Method available since Release 3.2.8
1936 protected function assertPostConditions()
1941 * Tears down the fixture, for example, close a network connection.
1942 * This method is called after a test is executed.
1944 protected function tearDown()
1949 * This method is called after the last test of this test class is run.
1951 * @since Method available since Release 3.4.0
1953 public static function tearDownAfterClass()
1958 * This method is called when a test method did not execute successfully.
1960 * @param Exception $e
1962 * @since Method available since Release 3.4.0
1966 protected function onNotSuccessfulTest(Exception $e)
1972 * Performs custom preparations on the process isolation template.
1974 * @param Text_Template $template
1976 * @since Method available since Release 3.4.0
1978 protected function prepareTemplate(Text_Template $template)
1983 * Get the mock object generator, creating it if it doesn't exist.
1985 * @return PHPUnit_Framework_MockObject_Generator
1987 protected function getMockObjectGenerator()
1989 if (null === $this->mockObjectGenerator) {
1990 $this->mockObjectGenerator = new PHPUnit_Framework_MockObject_Generator;
1993 return $this->mockObjectGenerator;
1997 * @since Method available since Release 4.2.0
1999 private function startOutputBuffering()
2001 while (!defined('PHPUNIT_TESTSUITE') && ob_get_level() > 0) {
2007 $this->outputBufferingActive = true;
2008 $this->outputBufferingLevel = ob_get_level();
2012 * @since Method available since Release 4.2.0
2014 private function stopOutputBuffering()
2016 if (ob_get_level() != $this->outputBufferingLevel) {
2017 while (ob_get_level() > 0) {
2021 throw new PHPUnit_Framework_RiskyTestError(
2022 'Test code or tested code did not (only) close its own output buffers'
2026 $output = ob_get_contents();
2028 if ($this->outputCallback === false) {
2029 $this->output = $output;
2031 $this->output = call_user_func_array(
2032 $this->outputCallback,
2039 $this->outputBufferingActive = false;
2040 $this->outputBufferingLevel = ob_get_level();
2043 private function snapshotGlobalState()
2045 $backupGlobals = $this->backupGlobals === null || $this->backupGlobals === true;
2047 if ($this->runTestInSeparateProcess || $this->inIsolation ||
2048 (!$backupGlobals && !$this->backupStaticAttributes)) {
2052 $this->snapshot = $this->createGlobalStateSnapshot($backupGlobals);
2055 private function restoreGlobalState()
2057 if (!$this->snapshot instanceof Snapshot) {
2061 $backupGlobals = $this->backupGlobals === null || $this->backupGlobals === true;
2063 if ($this->disallowChangesToGlobalState) {
2065 $this->compareGlobalStateSnapshots(
2067 $this->createGlobalStateSnapshot($backupGlobals)
2069 } catch (PHPUnit_Framework_RiskyTestError $rte) {
2070 // Intentionally left empty
2074 $restorer = new Restorer;
2076 if ($backupGlobals) {
2077 $restorer->restoreGlobalVariables($this->snapshot);
2080 if ($this->backupStaticAttributes) {
2081 $restorer->restoreStaticAttributes($this->snapshot);
2084 $this->snapshot = null;
2092 * @param bool $backupGlobals
2096 private function createGlobalStateSnapshot($backupGlobals)
2098 $blacklist = new Blacklist;
2100 foreach ($this->backupGlobalsBlacklist as $globalVariable) {
2101 $blacklist->addGlobalVariable($globalVariable);
2104 if (!defined('PHPUNIT_TESTSUITE')) {
2105 $blacklist->addClassNamePrefix('PHPUnit');
2106 $blacklist->addClassNamePrefix('File_Iterator');
2107 $blacklist->addClassNamePrefix('PHP_CodeCoverage');
2108 $blacklist->addClassNamePrefix('PHP_Invoker');
2109 $blacklist->addClassNamePrefix('PHP_Timer');
2110 $blacklist->addClassNamePrefix('PHP_Token');
2111 $blacklist->addClassNamePrefix('Symfony');
2112 $blacklist->addClassNamePrefix('Text_Template');
2113 $blacklist->addClassNamePrefix('Doctrine\Instantiator');
2115 foreach ($this->backupStaticAttributesBlacklist as $class => $attributes) {
2116 foreach ($attributes as $attribute) {
2117 $blacklist->addStaticAttribute($class, $attribute);
2122 return new Snapshot(
2125 $this->backupStaticAttributes,
2137 * @param Snapshot $before
2138 * @param Snapshot $after
2140 * @throws PHPUnit_Framework_RiskyTestError
2142 private function compareGlobalStateSnapshots(Snapshot $before, Snapshot $after)
2144 $backupGlobals = $this->backupGlobals === null || $this->backupGlobals === true;
2146 if ($backupGlobals) {
2147 $this->compareGlobalStateSnapshotPart(
2148 $before->globalVariables(),
2149 $after->globalVariables(),
2150 "--- Global variables before the test\n+++ Global variables after the test\n"
2153 $this->compareGlobalStateSnapshotPart(
2154 $before->superGlobalVariables(),
2155 $after->superGlobalVariables(),
2156 "--- Super-global variables before the test\n+++ Super-global variables after the test\n"
2160 if ($this->backupStaticAttributes) {
2161 $this->compareGlobalStateSnapshotPart(
2162 $before->staticAttributes(),
2163 $after->staticAttributes(),
2164 "--- Static attributes before the test\n+++ Static attributes after the test\n"
2170 * @param array $before
2171 * @param array $after
2172 * @param string $header
2174 * @throws PHPUnit_Framework_RiskyTestError
2176 private function compareGlobalStateSnapshotPart(array $before, array $after, $header)
2178 if ($before != $after) {
2179 $differ = new Differ($header);
2180 $exporter = new Exporter;
2182 $diff = $differ->diff(
2183 $exporter->export($before),
2184 $exporter->export($after)
2187 throw new PHPUnit_Framework_RiskyTestError(
2194 * @return Prophecy\Prophet
2196 * @since Method available since Release 4.5.0
2198 private function getProphet()
2200 if ($this->prophet === null) {
2201 $this->prophet = new Prophet;
2204 return $this->prophet;