Code Coverage |
||||||||||
Classes and Traits |
Functions and Methods |
Lines |
||||||||
Total | |
0.00% |
0 / 1 |
|
8.33% |
1 / 12 |
CRAP | |
20.59% |
14 / 68 |
EntityConstraintViolationList | |
0.00% |
0 / 1 |
|
8.33% |
1 / 12 |
364.53 | |
20.59% |
14 / 68 |
__construct | |
0.00% |
0 / 1 |
2 | |
0.00% |
0 / 3 |
|||
groupViolationOffsets | |
0.00% |
0 / 1 |
30 | |
0.00% |
0 / 10 |
|||
getEntityViolations | |
0.00% |
0 / 1 |
6 | |
0.00% |
0 / 5 |
|||
getByField | |
0.00% |
0 / 1 |
2 | |
0.00% |
0 / 1 |
|||
getByFields | |
0.00% |
0 / 1 |
12 | |
0.00% |
0 / 6 |
|||
filterByFields | |
0.00% |
0 / 1 |
14.12 | |
39.13% |
9 / 23 |
|||
filterByFieldAccess | |
100.00% |
1 / 1 |
3 | |
100.00% |
5 / 5 |
|||
getFieldNames | |
0.00% |
0 / 1 |
2 | |
0.00% |
0 / 2 |
|||
getEntity | |
0.00% |
0 / 1 |
2 | |
0.00% |
0 / 1 |
|||
add | |
0.00% |
0 / 1 |
2 | |
0.00% |
0 / 4 |
|||
remove | |
0.00% |
0 / 1 |
2 | |
0.00% |
0 / 4 |
|||
set | |
0.00% |
0 / 1 |
2 | |
0.00% |
0 / 4 |
<?php | |
/** | |
* @file | |
* Contains \Drupal\Core\Entity\EntityConstraintViolationList. | |
*/ | |
namespace Drupal\Core\Entity; | |
use Drupal\Core\Entity\Plugin\Validation\Constraint\CompositeConstraintBase; | |
use Drupal\Core\Session\AccountInterface; | |
use Drupal\Core\StringTranslation\StringTranslationTrait; | |
use Symfony\Component\Validator\ConstraintViolation; | |
use Symfony\Component\Validator\ConstraintViolationInterface; | |
use Symfony\Component\Validator\ConstraintViolationList; | |
/** | |
* Implements an entity constraint violation list. | |
*/ | |
class EntityConstraintViolationList extends ConstraintViolationList implements EntityConstraintViolationListInterface { | |
use StringTranslationTrait; | |
/** | |
* The entity that has been validated. | |
* | |
* @var \Drupal\Core\Entity\FieldableEntityInterface | |
*/ | |
protected $entity; | |
/** | |
* Violations offsets of entity level violations. | |
* | |
* @var int[]|null | |
*/ | |
protected $entityViolationOffsets; | |
/** | |
* Violation offsets grouped by field. | |
* | |
* Keys are field names, values are arrays of violation offsets. | |
* | |
* @var array[]|null | |
*/ | |
protected $violationOffsetsByField; | |
/** | |
* {@inheritdoc} | |
* | |
* @param \Drupal\Core\Entity\FieldableEntityInterface $entity | |
* The entity that has been validated. | |
* @param array $violations | |
* The array of violations. | |
*/ | |
public function __construct(FieldableEntityInterface $entity, array $violations = array()) { | |
parent::__construct($violations); | |
$this->entity = $entity; | |
} | |
/** | |
* Groups violation offsets by field and entity level. | |
* | |
* Sets the $violationOffsetsByField and $entityViolationOffsets properties. | |
*/ | |
protected function groupViolationOffsets() { | |
if (!isset($this->violationOffsetsByField)) { | |
$this->violationOffsetsByField = []; | |
$this->entityViolationOffsets = []; | |
foreach ($this as $offset => $violation) { | |
if ($path = $violation->getPropertyPath()) { | |
// An example of $path might be 'title.0.value'. | |
list($field_name) = explode('.', $path, 2); | |
if ($this->entity->hasField($field_name)) { | |
$this->violationOffsetsByField[$field_name][$offset] = $offset; | |
} | |
} | |
else { | |
$this->entityViolationOffsets[$offset] = $offset; | |
} | |
} | |
} | |
} | |
/** | |
* {@inheritdoc} | |
*/ | |
public function getEntityViolations() { | |
$this->groupViolationOffsets(); | |
$violations = []; | |
foreach ($this->entityViolationOffsets as $offset) { | |
$violations[] = $this->get($offset); | |
} | |
return new static($this->entity, $violations); | |
} | |
/** | |
* {@inheritdoc} | |
*/ | |
public function getByField($field_name) { | |
return $this->getByFields([$field_name]); | |
} | |
/** | |
* {@inheritdoc} | |
*/ | |
public function getByFields(array $field_names) { | |
$this->groupViolationOffsets(); | |
$violations = []; | |
foreach (array_intersect_key($this->violationOffsetsByField, array_flip($field_names)) as $field_name => $offsets) { | |
foreach ($offsets as $offset) { | |
$violations[] = $this->get($offset); | |
} | |
} | |
return new static($this->entity, $violations); | |
} | |
/** | |
* {@inheritdoc} | |
*/ | |
public function filterByFields(array $field_names) { | |
$this->groupViolationOffsets(); | |
$new_violations = []; | |
foreach (array_intersect_key($this->violationOffsetsByField, array_flip($field_names)) as $field_name => $offsets) { | |
foreach ($offsets as $offset) { | |
$violation = $this->get($offset); | |
// Take care of composite field violations and re-map them to some | |
// covered field if necessary. | |
if ($violation->getConstraint() instanceof CompositeConstraintBase) { | |
$covered_fields = $violation->getConstraint()->coversFields(); | |
// Keep the composite field if it covers some remaining field and put | |
// a violation on some other covered field instead. | |
if ($remaining_fields = array_diff($covered_fields, $field_names)) { | |
$message_params = ['%field_name' => $field_name]; | |
$violation = new ConstraintViolation( | |
$this->t('The validation failed because the value conflicts with the value in %field_name, which you cannot access.', $message_params), | |
'The validation failed because the value conflicts with the value in %field_name, which you cannot access.', | |
$message_params, | |
$violation->getRoot(), | |
reset($remaining_fields), | |
$violation->getInvalidValue(), | |
$violation->getPlural(), | |
$violation->getCode(), | |
$violation->getConstraint(), | |
$violation->getCause() | |
); | |
$new_violations[] = $violation; | |
} | |
} | |
$this->remove($offset); | |
} | |
} | |
foreach ($new_violations as $violation) { | |
$this->add($violation); | |
} | |
return $this; | |
} | |
/** | |
* {@inheritdoc} | |
*/ | |
public function filterByFieldAccess(AccountInterface $account = NULL) { | |
$filtered_fields = array(); | |
foreach ($this->getFieldNames() as $field_name) { | |
if (!$this->entity->get($field_name)->access('edit', $account)) { | |
$filtered_fields[] = $field_name; | |
} | |
} | |
return $this->filterByFields($filtered_fields); | |
} | |
/** | |
* {@inheritdoc} | |
*/ | |
public function getFieldNames() { | |
$this->groupViolationOffsets(); | |
return array_keys($this->violationOffsetsByField); | |
} | |
/** | |
* {@inheritdoc} | |
*/ | |
public function getEntity() { | |
return $this->entity; | |
} | |
/** | |
* {@inheritdoc} | |
*/ | |
public function add(ConstraintViolationInterface $violation) { | |
parent::add($violation); | |
$this->violationOffsetsByField = NULL; | |
$this->entityViolationOffsets = NULL; | |
} | |
/** | |
* {@inheritdoc} | |
*/ | |
public function remove($offset) { | |
parent::remove($offset); | |
$this->violationOffsetsByField = NULL; | |
$this->entityViolationOffsets = NULL; | |
} | |
/** | |
* {@inheritdoc} | |
*/ | |
public function set($offset, ConstraintViolationInterface $violation) { | |
parent::set($offset, $violation); | |
$this->violationOffsetsByField = NULL; | |
$this->entityViolationOffsets = NULL; | |
} | |
} |