You are here

class ValidationVisitor in Plug 7

Default implementation of {@link ValidationVisitorInterface} and {@link GlobalExecutionContextInterface}.

@author Bernhard Schussek <bschussek@gmail.com>

Hierarchy

Expanded class hierarchy of ValidationVisitor

Deprecated

Deprecated since version 2.5, to be removed in Symfony 3.0.

1 file declares its use of ValidationVisitor
LegacyExecutionContextTest.php in lib/Symfony/validator/Symfony/Component/Validator/Tests/LegacyExecutionContextTest.php

File

lib/Symfony/validator/Symfony/Component/Validator/ValidationVisitor.php, line 26

Namespace

Symfony\Component\Validator
View source
class ValidationVisitor implements ValidationVisitorInterface, GlobalExecutionContextInterface {

  /**
   * @var mixed
   */
  private $root;

  /**
   * @var MetadataFactoryInterface
   */
  private $metadataFactory;

  /**
   * @var ConstraintValidatorFactoryInterface
   */
  private $validatorFactory;

  /**
   * @var TranslatorInterface
   */
  private $translator;

  /**
   * @var null|string
   */
  private $translationDomain;

  /**
   * @var array
   */
  private $objectInitializers;

  /**
   * @var ConstraintViolationList
   */
  private $violations;

  /**
   * @var array
   */
  private $validatedObjects = array();

  /**
   * Creates a new validation visitor.
   *
   * @param mixed                               $root               The value passed to the validator.
   * @param MetadataFactoryInterface            $metadataFactory    The factory for obtaining metadata instances.
   * @param ConstraintValidatorFactoryInterface $validatorFactory   The factory for creating constraint validators.
   * @param TranslatorInterface                 $translator         The translator for translating violation messages.
   * @param string|null                         $translationDomain  The domain of the translation messages.
   * @param ObjectInitializerInterface[]        $objectInitializers The initializers for preparing objects before validation.
   *
   * @throws UnexpectedTypeException If any of the object initializers is not an instance of ObjectInitializerInterface
   */
  public function __construct($root, MetadataFactoryInterface $metadataFactory, ConstraintValidatorFactoryInterface $validatorFactory, TranslatorInterface $translator, $translationDomain = null, array $objectInitializers = array()) {
    foreach ($objectInitializers as $initializer) {
      if (!$initializer instanceof ObjectInitializerInterface) {
        throw new UnexpectedTypeException($initializer, 'Symfony\\Component\\Validator\\ObjectInitializerInterface');
      }
    }
    $this->root = $root;
    $this->metadataFactory = $metadataFactory;
    $this->validatorFactory = $validatorFactory;
    $this->translator = $translator;
    $this->translationDomain = $translationDomain;
    $this->objectInitializers = $objectInitializers;
    $this->violations = new ConstraintViolationList();
  }

  /**
   * {@inheritdoc}
   */
  public function visit(MetadataInterface $metadata, $value, $group, $propertyPath) {
    $context = new ExecutionContext($this, $this->translator, $this->translationDomain, $metadata, $value, $group, $propertyPath);
    $context
      ->validateValue($value, $metadata
      ->findConstraints($group));
  }

  /**
   * {@inheritdoc}
   */
  public function validate($value, $group, $propertyPath, $traverse = false, $deep = false) {
    if (null === $value) {
      return;
    }
    if (is_object($value)) {
      $hash = spl_object_hash($value);

      // Exit, if the object is already validated for the current group
      if (isset($this->validatedObjects[$hash][$group])) {
        return;
      }

      // Initialize if the object wasn't initialized before
      if (!isset($this->validatedObjects[$hash])) {
        foreach ($this->objectInitializers as $initializer) {
          if (!$initializer instanceof ObjectInitializerInterface) {
            throw new \LogicException('Validator initializers must implement ObjectInitializerInterface.');
          }
          $initializer
            ->initialize($value);
        }
      }

      // Remember validating this object before starting and possibly
      // traversing the object graph
      $this->validatedObjects[$hash][$group] = true;
    }

    // Validate arrays recursively by default, otherwise every driver needs
    // to implement special handling for arrays.
    // https://github.com/symfony/symfony/issues/6246
    if (is_array($value) || $traverse && $value instanceof \Traversable) {
      foreach ($value as $key => $element) {

        // Ignore any scalar values in the collection
        if (is_object($element) || is_array($element)) {

          // Only repeat the traversal if $deep is set
          $this
            ->validate($element, $group, $propertyPath . '[' . $key . ']', $deep, $deep);
        }
      }
      try {
        $this->metadataFactory
          ->getMetadataFor($value)
          ->accept($this, $value, $group, $propertyPath);
      } catch (NoSuchMetadataException $e) {

        // Metadata doesn't necessarily have to exist for
        // traversable objects, because we know how to validate
        // them anyway. Optionally, additional metadata is supported.
      }
    }
    else {
      $this->metadataFactory
        ->getMetadataFor($value)
        ->accept($this, $value, $group, $propertyPath);
    }
  }

  /**
   * {@inheritdoc}
   */
  public function getViolations() {
    return $this->violations;
  }

  /**
   * {@inheritdoc}
   */
  public function getRoot() {
    return $this->root;
  }

  /**
   * {@inheritdoc}
   */
  public function getVisitor() {
    return $this;
  }

  /**
   * {@inheritdoc}
   */
  public function getValidatorFactory() {
    return $this->validatorFactory;
  }

  /**
   * {@inheritdoc}
   */
  public function getMetadataFactory() {
    return $this->metadataFactory;
  }

}

Members

Namesort descending Modifiers Type Description Overrides
ValidationVisitor::$metadataFactory private property
ValidationVisitor::$objectInitializers private property
ValidationVisitor::$root private property
ValidationVisitor::$translationDomain private property
ValidationVisitor::$translator private property
ValidationVisitor::$validatedObjects private property
ValidationVisitor::$validatorFactory private property
ValidationVisitor::$violations private property
ValidationVisitor::getMetadataFactory public function Returns the factory for validation metadata objects. Overrides GlobalExecutionContextInterface::getMetadataFactory
ValidationVisitor::getRoot public function Returns the value at which validation was started in the object graph. Overrides GlobalExecutionContextInterface::getRoot
ValidationVisitor::getValidatorFactory public function Returns the factory for constraint validators. Overrides GlobalExecutionContextInterface::getValidatorFactory
ValidationVisitor::getViolations public function Returns the violations generated by the validator so far. Overrides GlobalExecutionContextInterface::getViolations
ValidationVisitor::getVisitor public function Returns the visitor instance used to validate the object graph nodes. Overrides GlobalExecutionContextInterface::getVisitor
ValidationVisitor::validate public function Validates a value. Overrides ValidationVisitorInterface::validate
ValidationVisitor::visit public function Validates a value against the constraints defined in some metadata. Overrides ValidationVisitorInterface::visit
ValidationVisitor::__construct public function Creates a new validation visitor.