Skip to content

[Validator] Simplified testing of violations #12015

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Sep 25, 2014
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -159,7 +159,10 @@ public function testValidateUniqueness()

$this->validator->validate($entity2, $constraint);

$this->assertViolation('myMessage', array(), 'property.path.name', 'Foo');
$this->buildViolation('myMessage')
->atPath('property.path.name')
->setInvalidValue('Foo')
->assertRaised();
}

public function testValidateCustomErrorPath()
Expand All @@ -179,7 +182,10 @@ public function testValidateCustomErrorPath()

$this->validator->validate($entity2, $constraint);

$this->assertViolation('myMessage', array(), 'property.path.bar', 'Foo');
$this->buildViolation('myMessage')
->atPath('property.path.bar')
->setInvalidValue('Foo')
->assertRaised();
}

public function testValidateUniquenessWithNull()
Expand Down Expand Up @@ -227,7 +233,10 @@ public function testValidateUniquenessWithIgnoreNull()

$this->validator->validate($entity2, $constraint);

$this->assertViolation('myMessage', array(), 'property.path.name', 'Foo');
$this->buildViolation('myMessage')
->atPath('property.path.name')
->setInvalidValue('Foo')
->assertRaised();
}

public function testValidateUniquenessUsingCustomRepositoryMethod()
Expand Down Expand Up @@ -321,7 +330,10 @@ public function testAssociatedEntity()

$this->validator->validate($associated2, $constraint);

$this->assertViolation('myMessage', array(), 'property.path.single', 1);
$this->buildViolation('myMessage')
->atPath('property.path.single')
->setInvalidValue(1)
->assertRaised();
}

public function testAssociatedEntityWithNull()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -219,10 +219,12 @@ function () { throw new TransformationFailedException(); }

$this->validator->validate($form, new Form());

$this->assertViolation('invalid_message_key', array(
'{{ value }}' => 'foo',
'{{ foo }}' => 'bar',
), 'property.path', 'foo', null, Form::ERR_INVALID);
$this->buildViolation('invalid_message_key')
->setParameter('{{ value }}', 'foo')
->setParameter('{{ foo }}', 'bar')
->setInvalidValue('foo')
->setCode(Form::ERR_INVALID)
->assertRaised();
}

public function testAddInvalidErrorEvenIfNoValidationGroups()
Expand Down Expand Up @@ -251,10 +253,12 @@ function () { throw new TransformationFailedException(); }

$this->validator->validate($form, new Form());

$this->assertViolation('invalid_message_key', array(
'{{ value }}' => 'foo',
'{{ foo }}' => 'bar',
), 'property.path', 'foo', null, Form::ERR_INVALID);
$this->buildViolation('invalid_message_key')
->setParameter('{{ value }}', 'foo')
->setParameter('{{ foo }}', 'bar')
->setInvalidValue('foo')
->setCode(Form::ERR_INVALID)
->assertRaised();
}

public function testDontValidateConstraintsIfNotSynchronized()
Expand Down Expand Up @@ -283,9 +287,11 @@ function () { throw new TransformationFailedException(); }

$this->validator->validate($form, new Form());

$this->assertViolation('invalid_message_key', array(
'{{ value }}' => 'foo',
), 'property.path','foo', null, Form::ERR_INVALID);
$this->buildViolation('invalid_message_key')
->setParameter('{{ value }}', 'foo')
->setInvalidValue('foo')
->setCode(Form::ERR_INVALID)
->assertRaised();
}

// https://github.com/symfony/symfony/issues/4359
Expand Down Expand Up @@ -537,9 +543,10 @@ public function testViolationIfExtraData()

$this->validator->validate($form, new Form());

$this->assertViolation('Extra!', array(
'{{ extra_fields }}' => 'foo',
), 'property.path', array('foo' => 'bar'));
$this->buildViolation('Extra!')
->setParameter('{{ extra_fields }}', 'foo')
->setInvalidValue(array('foo' => 'bar'))
->assertRaised();
}

/**
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -84,11 +84,11 @@ public function testInvalidComparisonToValue($dirtyValue, $dirtyValueAsString, $

$this->validator->validate($dirtyValue, $constraint);

$this->assertViolation('Constraint Message', array(
'{{ value }}' => $dirtyValueAsString,
'{{ compared_value }}' => $comparedValueString,
'{{ compared_value_type }}' => $comparedValueType,
));
$this->buildViolation('Constraint Message')
->setParameter('{{ value }}', $dirtyValueAsString)
->setParameter('{{ compared_value }}', $comparedValueString)
->setParameter('{{ compared_value_type }}', $comparedValueType)
->assertRaised();
}

/**
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,8 +13,7 @@

use Symfony\Component\Validator\ConstraintValidatorInterface;
use Symfony\Component\Validator\ConstraintViolation;
use Symfony\Component\Validator\Context\ExecutionContext;
use Symfony\Component\Validator\Context\ExecutionContextInterface;
use Symfony\Component\Validator\ExecutionContextInterface;
use Symfony\Component\Validator\Mapping\ClassMetadata;
use Symfony\Component\Validator\Mapping\PropertyMetadata;
use Symfony\Component\Validator\Tests\Fixtures\StubGlobalExecutionContext;
Expand Down Expand Up @@ -80,6 +79,19 @@ protected function createContext()
->getMock();
}

/**
* @param $message
* @param array $parameters
* @param string $propertyPath
* @param string $invalidValue
* @param null $plural
* @param null $code
*
* @return ConstraintViolation
*
* @deprecated To be removed in Symfony 3.0. Use
* {@link buildViolation()} instead.
*/
protected function createViolation($message, array $parameters = array(), $propertyPath = 'property.path', $invalidValue = 'InvalidValue', $plural = null, $code = null)
{
return new ConstraintViolation(
Expand Down Expand Up @@ -169,14 +181,34 @@ protected function assertNoViolation()
$this->assertCount(0, $this->context->getViolations());
}

/**
* @param $message
* @param array $parameters
* @param string $propertyPath
* @param string $invalidValue
* @param null $plural
* @param null $code
*
* @deprecated To be removed in Symfony 3.0. Use
* {@link buildViolation()} instead.
*/
protected function assertViolation($message, array $parameters = array(), $propertyPath = 'property.path', $invalidValue = 'InvalidValue', $plural = null, $code = null)
{
$violations = $this->context->getViolations();

$this->assertCount(1, $violations);
$this->assertEquals($this->createViolation($message, $parameters, $propertyPath, $invalidValue, $plural, $code), $violations[0]);
$this->buildViolation($message)
->setParameters($parameters)
->atPath($propertyPath)
->setInvalidValue($invalidValue)
->setCode($code)
->setPlural($plural)
->assertRaised();
}

/**
* @param array $expected
*
* @deprecated To be removed in Symfony 3.0. Use
* {@link buildViolation()} instead.
*/
protected function assertViolations(array $expected)
{
$violations = $this->context->getViolations();
Expand All @@ -190,5 +222,137 @@ protected function assertViolations(array $expected)
}
}

/**
* @param $message
*
* @return ConstraintViolationAssertion
*/
protected function buildViolation($message)
{
return new ConstraintViolationAssertion($this->context, $message);
}

abstract protected function createValidator();
}

/**
* @internal
*/
class ConstraintViolationAssertion
{
/**
* @var ExecutionContextInterface
*/
private $context;

/**
* @var ConstraintViolationAssertion[]
*/
private $assertions;

private $message;
private $parameters = array();
private $invalidValue = 'InvalidValue';
private $propertyPath = 'property.path';
private $translationDomain;
private $plural;
private $code;

public function __construct(ExecutionContextInterface $context, $message, array $assertions = array())
{
$this->context = $context;
$this->message = $message;
$this->assertions = $assertions;
}

public function atPath($path)
{
$this->propertyPath = $path;

return $this;
}

public function setParameter($key, $value)
{
$this->parameters[$key] = $value;

return $this;
}

public function setParameters(array $parameters)
{
$this->parameters = $parameters;

return $this;
}

public function setTranslationDomain($translationDomain)
{
$this->translationDomain = $translationDomain;

return $this;
}

public function setInvalidValue($invalidValue)
{
$this->invalidValue = $invalidValue;

return $this;
}

public function setPlural($number)
{
$this->plural = $number;

return $this;
}

public function setCode($code)
{
$this->code = $code;

return $this;
}

public function buildNextViolation($message)
{
$assertions = $this->assertions;
$assertions[] = $this;

return new self($this->context, $message, $assertions);
}

public function assertRaised()
{
$expected = array();
foreach ($this->assertions as $assertion) {
$expected[] = $assertion->getViolation();
}
$expected[] = $this->getViolation();

$violations = iterator_to_array($this->context->getViolations());

\PHPUnit_Framework_Assert::assertCount(count($expected), $violations);

reset($violations);

foreach ($expected as $violation) {
\PHPUnit_Framework_Assert::assertEquals($violation, current($violations));
next($violations);
}
}

private function getViolation()
{
return new ConstraintViolation(
null,
$this->message,
$this->parameters,
$this->context->getRoot(),
$this->propertyPath,
$this->invalidValue,
$this->plural,
$this->code
);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -46,10 +46,9 @@ public function testInvalidValues($value, $valueAsString)

$this->validator->validate($value, $constraint);

$this->assertViolation(
'myMessage',
array('{{ value }}' => $valueAsString)
);
$this->buildViolation('myMessage')
->setParameter('{{ value }}', $valueAsString)
->assertRaised();
}

public function getInvalidValues()
Expand Down
Loading