Skip to content

Instantly share code, notes, and snippets.

@mordilion
Created November 15, 2019 09:38
Show Gist options
  • Save mordilion/dfd8856e289f07dfcc3949a64cf0a7c9 to your computer and use it in GitHub Desktop.
Save mordilion/dfd8856e289f07dfcc3949a64cf0a7c9 to your computer and use it in GitHub Desktop.
Doctrine Validator - Validator to use with zendframework/zend-validator to validate against a Doctrine-Emtity
<?php
declare(strict_types=1);
namespace Database\Validator;
use Doctrine\Common\Collections\Criteria;
use Doctrine\ORM\EntityRepository;
use Zend\Validator\AbstractValidator;
use Zend\Validator\Exception;
/**
* @author Henning Huncke <mordilion@gmx.de>
*/
class DoctrineEntity extends AbstractValidator
{
public const NOT_EXISTS = 'doctrineEntityNotExists';
public const ALREADY_EXISTS = 'doctrineEntityAlreadyExists';
public const CHECK_EXISTS = 'exists';
public const CHECK_NOT_EXISTS = 'not_exists';
/**
* Validation failure message template definitions
*
* @var string[]
*/
protected $messageTemplates = [
self::NOT_EXISTS => 'The Entity not exists',
self::ALREADY_EXISTS => 'The Entity already exists',
];
/**
* @var string
*/
private $check = self::CHECK_EXISTS;
/**
* @var Criteria|null
*/
private $criteria;
/**
* @var string
*/
private $field = 'id';
/**
* @var EntityRepository|null
*/
private $repository;
/**
* PhoneNumber constructor.
*
* @param array|null $options
*/
public function __construct(?array $options = null)
{
parent::__construct($options);
if ($options !== null) {
$this->setCriteria($options['criteria'] ?? null);
$this->setField($options['field'] ?? $this->field);
$this->setRepository($options['repository'] ?? null);
}
}
/**
* @return string
*/
public function getCheck(): string
{
return $this->check;
}
/**
* @param string $check
*/
public function setCheck(string $check): void
{
$this->check = $check;
}
/**
* @return Criteria
*/
public function getCriteria(): Criteria
{
if ($this->criteria === null) {
$this->criteria = new Criteria();
}
return $this->criteria;
}
/**
* @param Criteria $criteria
*/
public function setCriteria(?Criteria $criteria): void
{
$this->criteria = $criteria;
}
/**
* @return string
*/
public function getField(): string
{
return $this->field;
}
/**
* @param string $field
*/
public function setField(string $field): void
{
$this->field = $field;
}
/**
* @return EntityRepository|null
*/
public function getRepository(): ?EntityRepository
{
return $this->repository;
}
/**
* @param EntityRepository|null $repository
*/
public function setRepository(?EntityRepository $repository): void
{
$this->repository = $repository;
}
/**
* Returns true if and only if $value meets the validation requirements
* If $value fails validation, then this method returns false, and
* getMessages() will return an array of messages that explain why the
* validation failed.
*
* @param mixed $value
*
* @return bool
* @throws Exception\RuntimeException If validation of $value is impossible
*/
public function isValid($value): bool
{
$repository = $this->getRepository();
if ($repository === null) {
throw new Exception\RuntimeException('Please configure a repository first.');
}
$match = null;
$criteria = $this->getCriteria();
$criteria->andWhere($criteria::expr()->eq($this->getField(), $value));
$match = $repository->matching($criteria);
if ($match->count() === 0 && $this->getCheck() === self::CHECK_EXISTS) {
$this->error(self::NOT_EXISTS);
return false;
}
if ($match->count() > 0 && $this->getCheck() === self::CHECK_NOT_EXISTS) {
$this->error(self::ALREADY_EXISTS);
return false;
}
return true;
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment