Chris@12
|
1 <?php
|
Chris@12
|
2
|
Chris@12
|
3 namespace Drupal\Tests;
|
Chris@12
|
4
|
Chris@12
|
5 /**
|
Chris@12
|
6 * Makes Drupal's test API forward compatible with multiple versions of PHPUnit.
|
Chris@12
|
7 */
|
Chris@12
|
8 trait PhpunitCompatibilityTrait {
|
Chris@12
|
9
|
Chris@12
|
10 /**
|
Chris@12
|
11 * Returns a mock object for the specified class using the available method.
|
Chris@12
|
12 *
|
Chris@12
|
13 * The getMock method does not exist in PHPUnit 6. To provide backward
|
Chris@12
|
14 * compatibility this trait provides the getMock method and uses createMock if
|
Chris@12
|
15 * this method is available on the parent class.
|
Chris@12
|
16 *
|
Chris@12
|
17 * @param string $originalClassName
|
Chris@12
|
18 * Name of the class to mock.
|
Chris@12
|
19 * @param array|null $methods
|
Chris@12
|
20 * When provided, only methods whose names are in the array are replaced
|
Chris@12
|
21 * with a configurable test double. The behavior of the other methods is not
|
Chris@12
|
22 * changed. Providing null means that no methods will be replaced.
|
Chris@12
|
23 * @param array $arguments
|
Chris@12
|
24 * Parameters to pass to the original class' constructor.
|
Chris@12
|
25 * @param string $mockClassName
|
Chris@12
|
26 * Class name for the generated test double class.
|
Chris@12
|
27 * @param bool $callOriginalConstructor
|
Chris@12
|
28 * Can be used to disable the call to the original class' constructor.
|
Chris@12
|
29 * @param bool $callOriginalClone
|
Chris@12
|
30 * Can be used to disable the call to the original class' clone constructor.
|
Chris@12
|
31 * @param bool $callAutoload
|
Chris@12
|
32 * Can be used to disable __autoload() during the generation of the test
|
Chris@12
|
33 * double class.
|
Chris@12
|
34 * @param bool $cloneArguments
|
Chris@12
|
35 * Enables the cloning of arguments passed to mocked methods.
|
Chris@12
|
36 * @param bool $callOriginalMethods
|
Chris@12
|
37 * Enables the invocation of the original methods.
|
Chris@12
|
38 * @param object $proxyTarget
|
Chris@12
|
39 * Sets the proxy target.
|
Chris@12
|
40 *
|
Chris@12
|
41 * @see \PHPUnit_Framework_TestCase::getMock
|
Chris@12
|
42 * @see https://github.com/sebastianbergmann/phpunit/wiki/Release-Announcement-for-PHPUnit-5.4.0
|
Chris@12
|
43 *
|
Chris@12
|
44 * @return \PHPUnit_Framework_MockObject_MockObject
|
Chris@12
|
45 *
|
Chris@12
|
46 * @deprecated in Drupal 8.5.0 and will be removed before Drupal 9.0.0.
|
Chris@12
|
47 * Use \Drupal\Tests\PhpunitCompatibilityTrait::createMock() instead.
|
Chris@12
|
48 *
|
Chris@12
|
49 * @see https://www.drupal.org/node/2907725
|
Chris@12
|
50 */
|
Chris@14
|
51 public function getMock($originalClassName, $methods = [], array $arguments = [], $mockClassName = '', $callOriginalConstructor = TRUE, $callOriginalClone = TRUE, $callAutoload = TRUE, $cloneArguments = FALSE, $callOriginalMethods = FALSE, $proxyTarget = NULL) {
|
Chris@12
|
52 if (!$this->supports('getMock')) {
|
Chris@12
|
53 $mock = $this->getMockBuilder($originalClassName)
|
Chris@12
|
54 ->setMethods($methods)
|
Chris@12
|
55 ->setConstructorArgs($arguments)
|
Chris@12
|
56 ->setMockClassName($mockClassName)
|
Chris@12
|
57 ->setProxyTarget($proxyTarget);
|
Chris@12
|
58 if ($callOriginalConstructor) {
|
Chris@12
|
59 $mock->enableOriginalConstructor();
|
Chris@12
|
60 }
|
Chris@12
|
61 else {
|
Chris@12
|
62 $mock->disableOriginalConstructor();
|
Chris@12
|
63 }
|
Chris@12
|
64 if ($callOriginalClone) {
|
Chris@12
|
65 $mock->enableOriginalClone();
|
Chris@12
|
66 }
|
Chris@12
|
67 else {
|
Chris@12
|
68 $mock->disableOriginalClone();
|
Chris@12
|
69 }
|
Chris@12
|
70 if ($callAutoload) {
|
Chris@12
|
71 $mock->enableAutoload();
|
Chris@12
|
72 }
|
Chris@12
|
73 else {
|
Chris@12
|
74 $mock->disableAutoload();
|
Chris@12
|
75 }
|
Chris@12
|
76 if ($cloneArguments) {
|
Chris@12
|
77 $mock->enableArgumentCloning();
|
Chris@12
|
78 }
|
Chris@12
|
79 else {
|
Chris@12
|
80 $mock->disableArgumentCloning();
|
Chris@12
|
81 }
|
Chris@12
|
82 if ($callOriginalMethods) {
|
Chris@12
|
83 $mock->enableProxyingToOriginalMethods();
|
Chris@12
|
84 }
|
Chris@12
|
85 else {
|
Chris@12
|
86 $mock->disableProxyingToOriginalMethods();
|
Chris@12
|
87 }
|
Chris@12
|
88 return $mock->getMock();
|
Chris@12
|
89 }
|
Chris@12
|
90 else {
|
Chris@12
|
91 return parent::getMock($originalClassName, $methods, $arguments, $mockClassName, $callOriginalConstructor, $callOriginalClone, $callAutoload, $cloneArguments, $callOriginalMethods, $proxyTarget);
|
Chris@12
|
92 }
|
Chris@12
|
93 }
|
Chris@12
|
94
|
Chris@12
|
95 /**
|
Chris@12
|
96 * Returns a mock object for the specified class using the available method.
|
Chris@12
|
97 *
|
Chris@12
|
98 * The createMock method does not exist in PHPUnit 4. To provide forward
|
Chris@12
|
99 * compatibility this trait provides the createMock method and uses createMock
|
Chris@12
|
100 * if this method is available on the parent class or falls back to getMock if
|
Chris@12
|
101 * it isn't.
|
Chris@12
|
102 *
|
Chris@12
|
103 * @param string $originalClassName
|
Chris@12
|
104 * Name of the class to mock.
|
Chris@12
|
105 *
|
Chris@12
|
106 * @see \PHPUnit_Framework_TestCase::getMock
|
Chris@12
|
107 *
|
Chris@12
|
108 * @return \PHPUnit_Framework_MockObject_MockObject
|
Chris@12
|
109 */
|
Chris@12
|
110 public function createMock($originalClassName) {
|
Chris@12
|
111 if ($this->supports('createMock')) {
|
Chris@12
|
112 return parent::createMock($originalClassName);
|
Chris@12
|
113 }
|
Chris@12
|
114 else {
|
Chris@12
|
115 return $this->getMock($originalClassName, [], [], '', FALSE, FALSE);
|
Chris@12
|
116 }
|
Chris@12
|
117 }
|
Chris@12
|
118
|
Chris@12
|
119 /**
|
Chris@14
|
120 * Compatibility layer for PHPUnit 6 to support PHPUnit 4 code.
|
Chris@14
|
121 *
|
Chris@14
|
122 * @param mixed $class
|
Chris@14
|
123 * The expected exception class.
|
Chris@14
|
124 * @param string $message
|
Chris@14
|
125 * The expected exception message.
|
Chris@14
|
126 * @param int $exception_code
|
Chris@14
|
127 * The expected exception code.
|
Chris@14
|
128 */
|
Chris@14
|
129 public function setExpectedException($class, $message = '', $exception_code = NULL) {
|
Chris@14
|
130 if (method_exists($this, 'expectException')) {
|
Chris@14
|
131 $this->expectException($class);
|
Chris@14
|
132 if (!empty($message)) {
|
Chris@14
|
133 $this->expectExceptionMessage($message);
|
Chris@14
|
134 }
|
Chris@14
|
135 if ($exception_code !== NULL) {
|
Chris@14
|
136 $this->expectExceptionCode($exception_code);
|
Chris@14
|
137 }
|
Chris@14
|
138 }
|
Chris@14
|
139 else {
|
Chris@14
|
140 parent::setExpectedException($class, $message, $exception_code);
|
Chris@14
|
141 }
|
Chris@14
|
142 }
|
Chris@14
|
143
|
Chris@14
|
144 /**
|
Chris@12
|
145 * Checks if the trait is used in a class that has a method.
|
Chris@12
|
146 *
|
Chris@12
|
147 * @param string $method
|
Chris@12
|
148 * Method to check.
|
Chris@12
|
149 *
|
Chris@12
|
150 * @return bool
|
Chris@12
|
151 * TRUE if the method is supported, FALSE if not.
|
Chris@12
|
152 */
|
Chris@12
|
153 private function supports($method) {
|
Chris@12
|
154 // Get the parent class of the currently running test class.
|
Chris@12
|
155 $parent = get_parent_class($this);
|
Chris@12
|
156 // Ensure that the method_exists() check on the createMock method is carried
|
Chris@12
|
157 // out on the first parent of $this that does not have access to this
|
Chris@12
|
158 // trait's methods. This is because the trait also has a method called
|
Chris@12
|
159 // createMock(). Most often the check will be made on
|
Chris@12
|
160 // \PHPUnit\Framework\TestCase.
|
Chris@12
|
161 while (method_exists($parent, 'supports')) {
|
Chris@12
|
162 $parent = get_parent_class($parent);
|
Chris@12
|
163 }
|
Chris@12
|
164 return method_exists($parent, $method);
|
Chris@12
|
165 }
|
Chris@12
|
166
|
Chris@12
|
167 }
|