/**
* Finds an object from the repository by searching for its identity properties.
*
* @param array $identityProperties Property names and values to search for
* @param string $type The object type to look for
* @return object Either the object matching the identity or NULL if no object was found
* @throws DuplicateObjectException if more than one object was found
*/
protected function findObjectByIdentityProperties(array $identityProperties, $type)
{
$query = $this->persistenceManager->createQueryForType($type);
$classSchema = $this->reflectionService->getClassSchema($type);
$equals = [];
foreach ($classSchema->getIdentityProperties() as $propertyName => $propertyType) {
if (isset($identityProperties[$propertyName])) {
if ($propertyType === 'string') {
$equals[] = $query->equals($propertyName, $identityProperties[$propertyName], false);
} else {
$equals[] = $query->equals($propertyName, $identityProperties[$propertyName]);
}
}
}
if (count($equals) === 1) {
$constraint = current($equals);
} else {
$constraint = $query->logicalAnd(current($equals), next($equals));
while (($equal = next($equals)) !== false) {
$constraint = $query->logicalAnd($constraint, $equal);
}
}
$objects = $query->matching($constraint)->execute();
$numberOfResults = $objects->count();
if ($numberOfResults === 1) {
return $objects->getFirst();
} elseif ($numberOfResults === 0) {
return null;
} else {
throw new DuplicateObjectException('More than one object was returned for the given identity, this is a constraint violation.', 1259612399);
}
}