@param FamilyInterface|null    $family
@param AttributeInterface|null $attribute
@param array|null              $context

@throws ContextException

@return Collection|ValueInterface[]
977751
public function getRefererValues(
        FamilyInterface $family = null,
        AttributeInterface $attribute = null,
        array $context = null
    ) {
        if (null === $family && null === $attribute && null === $context) {
            return $this->refererValues;
        }
        $values = new ArrayCollection();
        if ($context) {
            $context = array_merge($this->getCurrentContext(), $context);
        }

        foreach ($this->refererValues as $refererValue) {
            if ($attribute && $attribute->getCode() !== $refererValue->getAttributeCode()) {
                continue;
            }
            if ($family && $family->getCode() !== $refererValue->getData()->getFamilyCode()) {
                continue;
            }
            if ($context && !$refererValue->getAttribute()->isContextMatching($refererValue, $context)) {
                continue;
            }
            $values[] = $refererValue;
        }

        return $values;
    }
189341
protected function getQueryBuilderByAttribute(Request $request, AttributeInterface $attribute)
    {
        $term = '%'.trim($request->get('term'), '%').'%';

        if (!$attribute->getType()->isRelation() && !$attribute->getType()->isEmbedded()) {
            $family = $attribute->getFamily();
            $repository = $this->entityManager->getRepository($family->getDataClass());
            if (!$repository instanceof DataRepository) {
                throw new \UnexpectedValueException(
                    "Repository for class {$family->getDataClass()} must be a DataRepository"
                );
            }
            $eavQb = $repository->createFamilyQueryBuilder($family);
            $attributeQb = $eavQb->attribute($attribute);
            $qb = $eavQb->apply($attributeQb->like($term));
            $qb
                ->select($attributeQb->getColumn())
                ->groupBy($attributeQb->getColumn())
                ->orderBy($attributeQb->getColumn());

            return $qb;
        }

        /** @var array $familyCodes */
        $familyCodes = $attribute->getOption('allowed_families', []);
        $families = [];
        foreach ($familyCodes as $familyCode) {
            $families[] = $this->familyRegistry->getFamily($familyCode);
        }

        return $this->dataManager->getQbForFamiliesAndLabel($families, $term);
    }
482730
protected function getAttributeContext(
        DataInterface $object,
        $attribute,
        /** @noinspection PhpUnusedParameterInspection */
        $rawValue,
        array $context
    ) {
        return array_merge(
            $context,
            [
                'parent' => $object,
                'attribute' => $attribute,
            ]
        );
    }
763891
public function getFamilies(string $resourceClass): array
    {
        $matchingFamilies = [];
        foreach ($this->familyRegistry->getFamilies() as $family) {
            if (ltrim($family->getDataClass(), '\\') === ltrim($resourceClass, '\\')) {
                $matchingFamilies[] = $family;
            }
        }

        return $matchingFamilies;
    }
49871
protected function getValuesByAttribute(AttributeInterface $attribute)
    {
        if (null === $this->valuesByAttributes) {
            $this->valuesByAttributes = [];
        }

        if (!array_key_exists($attribute->getCode(), $this->valuesByAttributes)) {
            $this->valuesByAttributes[$attribute->getCode()] = [];
            foreach ($this->values as $value) {
                if ($value->getAttributeCode() === $attribute->getCode()) {
                    $this->addValueByAttribute($value);
                }
            }
        }

        return $this->valuesByAttributes[$attribute->getCode()];
    }
388840
protected function getAttributeMethods(FamilyInterface $family, AttributeInterface $attribute)
    {
        if ($this->isAttributeInherited($family, $attribute)) {
            return '';
        }
        $content = '';
        $dataClass = new \ReflectionClass($family->getDataClass());

        $getter = 'get'.ucfirst($attribute->getCode());
        if (!$dataClass->hasMethod($getter)) {
            $content .= $this->generateGetAnnotation($family, $attribute);
            $content .= "abstract public function {$getter}(array \$context = null);\n\n";
        }

        $setter = 'set'.ucfirst($attribute->getCode());
        if (!$dataClass->hasMethod($setter)) {
            $content .= $this->generateSetAnnotation($family, $attribute);
            $content .= 'abstract public function set'.ucfirst($attribute->getCode());
            $content .= '($value, array $context = null);'."\n\n";
        }

        if ($attribute->isCollection()) {
            // Adder and remover
            $setter = 'add'.ucfirst($attribute->getCode());
            if (!$dataClass->hasMethod($setter)) {
                $content .= $this->generateSetAnnotation($family, $attribute, true);
                $content .= 'abstract public function add'.ucfirst($attribute->getCode());
                $content .= '($value, array $context = null);'."\n\n";
            }

            $setter = 'remove'.ucfirst($attribute->getCode());
            if (!$dataClass->hasMethod($setter)) {
                $content .= $this->generateSetAnnotation($family, $attribute, true);
                $content .= 'abstract public function remove'.ucfirst($attribute->getCode());
                $content .= '($value, array $context = null);'."\n\n";
            }
        }

        return $content;
    }
747108
public static function _parseOneToMany($query, $relationship, $attribute = null)
    {
        $child = $relationship->getChildRepository();
        $child_query = $child->getQuery();
        $child_belongs_to_property = $child->getDescription()->getProperty($relationship->getChildkey());

        $columns = $child_belongs_to_property->getColumns();
        //if the relationship parent is not set then throw an error
        //if polymorphic with a base parent just use the id
        if (!$child_belongs_to_property->getParent()) {
            throw new AnDomainQueryException('Query Building Failed. Unkown Parent');
        } elseif ($child_belongs_to_property->isPolymorphic()) {
            $columnsKeys = array_keys($columns);
            $columnsValues = array_values($columns);
            $columns = array(array_shift($columnsKeys) => array_shift($columnsValues));
        }

        $condition = array();

        foreach ($columns as $parent_property => $child_column) {
            $result = self::parseColumn($query, $parent_property);
            $col = $result['columns'];
            $condition[(string) $col] = $child_column;
        }

        $query->link($child_query, $condition, array('as' => $relationship->getName()));

        if ($attribute) {
            return self::parseColumn($child_query, $attribute);
        }
    }
107232
protected function setFamily(FamilyInterface $family)
    {
        $this->family = $family;
        $this->container->get('router')->getContext()->setParameter('familyCode', $family->getCode());
    }
1146964
private function mapAttributeValues(array $attributes, Attribute $attribute)
    {
        $key = $attribute->getName();
        $value = $attribute->getAllAttributeValues();

        if (!array_key_exists($key, $attributes) && 1 === count($value)) {
            $value = array_shift($value);
        }

        if (array_key_exists($key, $attributes)) {
            $currentValue = (is_array($attributes[$key]) ? $attributes[$key] : [$attributes[$key]]);

            $value = array_merge($currentValue, $value);
        }

        $attributes[$key] = $value;

        return $attributes;
    }
544971
public static function execute($value, ContextInterface $context): array
    {
        // parser guarantees that input will be an array of [$type => $id] where type and id are scalars

        // we will check the type of every pair and send further identities only
        $indexes          = [];
        $foundInvalidType = null;
        $expectedType     = $context->getProperties()->getProperty(static::PROPERTY_RESOURCE_TYPE);
        foreach ($value as $typeAndId) {
            assert(is_array($typeAndId) === true && count($typeAndId) === 1);
            $index = reset($typeAndId);
            $type  = key($typeAndId);
            assert(is_scalar($index) === true && is_scalar($type) === true);
            if ($type === $expectedType) {
                $indexes[] = $index;
            } else {
                $foundInvalidType = $type;
                break;
            }
        }

        $reply = $foundInvalidType === null ?
            static::createSuccessReply($indexes) :
            static::createErrorReply(
                $context,
                $foundInvalidType,
                ErrorCodes::INVALID_RELATIONSHIP_TYPE,
                Messages::INVALID_RELATIONSHIP_TYPE,
                []
            );

        return $reply;
    }
1062267
public function virtuals($attribute = null)
    {
        $fields = [];
        foreach ($this->_columns as $name => $field) {
            if (empty($field['virtual'])) {
                continue;
            }
            $fields[] = $name;
        }
        return $fields;
    }
689189
public function getEAVAttributes(FamilyInterface $family, array $attributePaths): array
    {
        $attributes = [];
        foreach ($attributePaths as $attributePath) {
            $attribute = null;
            /** @var AttributeInterface $attribute */
            foreach (explode('.', $attributePath) as $attributeCode) {
                if (null !== $attribute) { // This means we're in a nested attribute
                    $families = $attribute->getOption('allowed_families', []);
                    if (1 !== \count($families)) {
                        throw new \UnexpectedValueException(
                            "Bad 'allowed_families' configuration for attribute {$attribute->getCode()}"
                        );
                    }
                    $family = $this->familyRegistry->getFamily(reset($families));
                    $attribute = $family->getAttribute($attributeCode); // No check on attribute existence: crash
                } else { // else we're at root level
                    $attribute = $family->getAttribute($attributeCode);
                }
            }

            if ($attribute) {
                $attributes[] = $attribute;
            }
        }

        return $attributes;
    }
753830
protected function getTargetClass(
        FamilyInterface $parentFamily,
        AttributeInterface $attribute,
        $forceSingle = false
    ) {
        $classMetadata = $this->manager->getClassMetadata($parentFamily->getValueClass());
        try {
            $mapping = $classMetadata->getAssociationMapping($attribute->getType()->getDatabaseType());
        } catch (MappingException $e) {
            return null;
        }
        if (empty($mapping['targetEntity'])) {
            return null;
        }

        $type = $mapping['targetEntity'];
        if (!$forceSingle && $attribute->isCollection()) {
            $type .= '[]|Collection';
        }

        return '\\'.$type;
    }
133424
public function attr($attribute = null)
    {
        if ($this->isNull($attribute)) {
            return $this->attribute;
        }

        return $this->parent->attr($attribute);
    }
1033091
protected function createChildContext(array $parentContext, $attribute/*, string $format = null */)
    {
        if (\func_num_args() >= 3) {
            $format = \func_get_arg(2);
        } else {
            // will be deprecated in version 4
            $format = null;
        }

        $context = parent::createChildContext($parentContext, $attribute, $format);
        // format is already included in the cache_key of the parent.
        $context['cache_key'] = $this->getCacheKey($format, $context);

        return $context;
    }
1171852
public function getFamily(): FamilyInterface
    {
        $familyCode = $this->getConfiguration()->getOption('family');
        if (null === $familyCode) {
            throw new UnexpectedValueException(
                "Missing 'family' configuration option for {$this->getConfiguration()->getCode()}"
            );
        }

        return $this->familyRegistry->getFamily($familyCode);
    }
1296492
public static function execute($value, ContextInterface $context): array
    {
        $reply = null;

        $result = [];
        if (is_array($value) === true) {
            foreach ($value as $key => $mightBeString) {
                if (is_string($mightBeString) === true || is_numeric($mightBeString) === true) {
                    $result[$key] = (int)$mightBeString;
                } else {
                    $reply = static::createErrorReply(
                        $context,
                        $mightBeString,
                        ErrorCodes::IS_STRING,
                        Messages::IS_STRING,
                        []
                    );
                    break;
                }
            }
        } else {
            $reply = static::createErrorReply($context, $value, ErrorCodes::IS_ARRAY, Messages::IS_ARRAY, []);
        }

        return $reply !== null ? $reply : static::createSuccessReply($result);
    }