comparison vendor/symfony/validator/Test/ConstraintValidatorTestCase.php @ 0:c75dbcec494b

Initial commit from drush-created site
author Chris Cannam
date Thu, 05 Jul 2018 14:24:15 +0000
parents
children a9cd425dd02b
comparison
equal deleted inserted replaced
-1:000000000000 0:c75dbcec494b
1 <?php
2
3 /*
4 * This file is part of the Symfony package.
5 *
6 * (c) Fabien Potencier <fabien@symfony.com>
7 *
8 * For the full copyright and license information, please view the LICENSE
9 * file that was distributed with this source code.
10 */
11
12 namespace Symfony\Component\Validator\Test;
13
14 use PHPUnit\Framework\Assert;
15 use PHPUnit\Framework\TestCase;
16 use Symfony\Component\Validator\Constraint;
17 use Symfony\Component\Validator\Constraints\NotNull;
18 use Symfony\Component\Validator\ConstraintValidatorInterface;
19 use Symfony\Component\Validator\ConstraintViolation;
20 use Symfony\Component\Validator\Context\ExecutionContext;
21 use Symfony\Component\Validator\Context\ExecutionContextInterface;
22 use Symfony\Component\Validator\Mapping\ClassMetadata;
23 use Symfony\Component\Validator\Mapping\PropertyMetadata;
24
25 /**
26 * A test case to ease testing Constraint Validators.
27 *
28 * @author Bernhard Schussek <bschussek@gmail.com>
29 */
30 abstract class ConstraintValidatorTestCase extends TestCase
31 {
32 /**
33 * @var ExecutionContextInterface
34 */
35 protected $context;
36
37 /**
38 * @var ConstraintValidatorInterface
39 */
40 protected $validator;
41
42 protected $group;
43 protected $metadata;
44 protected $object;
45 protected $value;
46 protected $root;
47 protected $propertyPath;
48 protected $constraint;
49 protected $defaultTimezone;
50
51 protected function setUp()
52 {
53 $this->group = 'MyGroup';
54 $this->metadata = null;
55 $this->object = null;
56 $this->value = 'InvalidValue';
57 $this->root = 'root';
58 $this->propertyPath = 'property.path';
59
60 // Initialize the context with some constraint so that we can
61 // successfully build a violation.
62 $this->constraint = new NotNull();
63
64 $this->context = $this->createContext();
65 $this->validator = $this->createValidator();
66 $this->validator->initialize($this->context);
67
68 \Locale::setDefault('en');
69
70 $this->setDefaultTimezone('UTC');
71 }
72
73 protected function tearDown()
74 {
75 $this->restoreDefaultTimezone();
76 }
77
78 protected function setDefaultTimezone($defaultTimezone)
79 {
80 // Make sure this method can not be called twice before calling
81 // also restoreDefaultTimezone()
82 if (null === $this->defaultTimezone) {
83 $this->defaultTimezone = date_default_timezone_get();
84 date_default_timezone_set($defaultTimezone);
85 }
86 }
87
88 protected function restoreDefaultTimezone()
89 {
90 if (null !== $this->defaultTimezone) {
91 date_default_timezone_set($this->defaultTimezone);
92 $this->defaultTimezone = null;
93 }
94 }
95
96 protected function createContext()
97 {
98 $translator = $this->getMockBuilder('Symfony\Component\Translation\TranslatorInterface')->getMock();
99 $validator = $this->getMockBuilder('Symfony\Component\Validator\Validator\ValidatorInterface')->getMock();
100 $contextualValidator = $this->getMockBuilder('Symfony\Component\Validator\Validator\ContextualValidatorInterface')->getMock();
101
102 $context = new ExecutionContext($validator, $this->root, $translator);
103 $context->setGroup($this->group);
104 $context->setNode($this->value, $this->object, $this->metadata, $this->propertyPath);
105 $context->setConstraint($this->constraint);
106
107 $validator->expects($this->any())
108 ->method('inContext')
109 ->with($context)
110 ->will($this->returnValue($contextualValidator));
111
112 return $context;
113 }
114
115 protected function setGroup($group)
116 {
117 $this->group = $group;
118 $this->context->setGroup($group);
119 }
120
121 protected function setObject($object)
122 {
123 $this->object = $object;
124 $this->metadata = is_object($object)
125 ? new ClassMetadata(get_class($object))
126 : null;
127
128 $this->context->setNode($this->value, $this->object, $this->metadata, $this->propertyPath);
129 }
130
131 protected function setProperty($object, $property)
132 {
133 $this->object = $object;
134 $this->metadata = is_object($object)
135 ? new PropertyMetadata(get_class($object), $property)
136 : null;
137
138 $this->context->setNode($this->value, $this->object, $this->metadata, $this->propertyPath);
139 }
140
141 protected function setValue($value)
142 {
143 $this->value = $value;
144 $this->context->setNode($this->value, $this->object, $this->metadata, $this->propertyPath);
145 }
146
147 protected function setRoot($root)
148 {
149 $this->root = $root;
150 $this->context = $this->createContext();
151 $this->validator->initialize($this->context);
152 }
153
154 protected function setPropertyPath($propertyPath)
155 {
156 $this->propertyPath = $propertyPath;
157 $this->context->setNode($this->value, $this->object, $this->metadata, $this->propertyPath);
158 }
159
160 protected function expectNoValidate()
161 {
162 $validator = $this->context->getValidator()->inContext($this->context);
163 $validator->expects($this->never())
164 ->method('atPath');
165 $validator->expects($this->never())
166 ->method('validate');
167 }
168
169 protected function expectValidateAt($i, $propertyPath, $value, $group)
170 {
171 $validator = $this->context->getValidator()->inContext($this->context);
172 $validator->expects($this->at(2 * $i))
173 ->method('atPath')
174 ->with($propertyPath)
175 ->will($this->returnValue($validator));
176 $validator->expects($this->at(2 * $i + 1))
177 ->method('validate')
178 ->with($value, $this->logicalOr(null, array(), $this->isInstanceOf('\Symfony\Component\Validator\Constraints\Valid')), $group);
179 }
180
181 protected function expectValidateValueAt($i, $propertyPath, $value, $constraints, $group = null)
182 {
183 $contextualValidator = $this->context->getValidator()->inContext($this->context);
184 $contextualValidator->expects($this->at(2 * $i))
185 ->method('atPath')
186 ->with($propertyPath)
187 ->will($this->returnValue($contextualValidator));
188 $contextualValidator->expects($this->at(2 * $i + 1))
189 ->method('validate')
190 ->with($value, $constraints, $group);
191 }
192
193 protected function assertNoViolation()
194 {
195 $this->assertSame(0, $violationsCount = count($this->context->getViolations()), sprintf('0 violation expected. Got %u.', $violationsCount));
196 }
197
198 /**
199 * @param $message
200 *
201 * @return ConstraintViolationAssertion
202 */
203 protected function buildViolation($message)
204 {
205 return new ConstraintViolationAssertion($this->context, $message, $this->constraint);
206 }
207
208 abstract protected function createValidator();
209 }
210
211 /**
212 * @internal
213 */
214 class ConstraintViolationAssertion
215 {
216 /**
217 * @var ExecutionContextInterface
218 */
219 private $context;
220
221 /**
222 * @var ConstraintViolationAssertion[]
223 */
224 private $assertions;
225
226 private $message;
227 private $parameters = array();
228 private $invalidValue = 'InvalidValue';
229 private $propertyPath = 'property.path';
230 private $plural;
231 private $code;
232 private $constraint;
233 private $cause;
234
235 public function __construct(ExecutionContextInterface $context, $message, Constraint $constraint = null, array $assertions = array())
236 {
237 $this->context = $context;
238 $this->message = $message;
239 $this->constraint = $constraint;
240 $this->assertions = $assertions;
241 }
242
243 public function atPath($path)
244 {
245 $this->propertyPath = $path;
246
247 return $this;
248 }
249
250 public function setParameter($key, $value)
251 {
252 $this->parameters[$key] = $value;
253
254 return $this;
255 }
256
257 public function setParameters(array $parameters)
258 {
259 $this->parameters = $parameters;
260
261 return $this;
262 }
263
264 public function setTranslationDomain($translationDomain)
265 {
266 // no-op for BC
267
268 return $this;
269 }
270
271 public function setInvalidValue($invalidValue)
272 {
273 $this->invalidValue = $invalidValue;
274
275 return $this;
276 }
277
278 public function setPlural($number)
279 {
280 $this->plural = $number;
281
282 return $this;
283 }
284
285 public function setCode($code)
286 {
287 $this->code = $code;
288
289 return $this;
290 }
291
292 public function setCause($cause)
293 {
294 $this->cause = $cause;
295
296 return $this;
297 }
298
299 public function buildNextViolation($message)
300 {
301 $assertions = $this->assertions;
302 $assertions[] = $this;
303
304 return new self($this->context, $message, $this->constraint, $assertions);
305 }
306
307 public function assertRaised()
308 {
309 $expected = array();
310 foreach ($this->assertions as $assertion) {
311 $expected[] = $assertion->getViolation();
312 }
313 $expected[] = $this->getViolation();
314
315 $violations = iterator_to_array($this->context->getViolations());
316
317 Assert::assertSame($expectedCount = count($expected), $violationsCount = count($violations), sprintf('%u violation(s) expected. Got %u.', $expectedCount, $violationsCount));
318
319 reset($violations);
320
321 foreach ($expected as $violation) {
322 Assert::assertEquals($violation, current($violations));
323 next($violations);
324 }
325 }
326
327 private function getViolation()
328 {
329 return new ConstraintViolation(
330 null,
331 $this->message,
332 $this->parameters,
333 $this->context->getRoot(),
334 $this->propertyPath,
335 $this->invalidValue,
336 $this->plural,
337 $this->code,
338 $this->constraint,
339 $this->cause
340 );
341 }
342 }