Ejemplo n.º 1
0
 /**
  * @Remote
  */
 public function suggestAction(array $params)
 {
     Toolkit::validateRequiredRequestParams($params, ['queryType', 'query']);
     /* @var FilterAutoSuggestService $service */
     $service = $this->get('modera_backend_tools_activity_log.auto_suggest.filter_auto_suggest_service');
     return $service->suggest($params['queryType'], $params['query']);
 }
Ejemplo n.º 2
0
 /**
  * {@inheritdoc}
  */
 public function create(array $params, array $config)
 {
     $entityClass = $config['entity'];
     // if __construct method doesn't have any mandatory parameters the we will use it
     $useConstructor = false;
     foreach (Toolkit::getReflectionMethods($entityClass) as $reflMethod) {
         /* @var \ReflectionMethod $reflMethod */
         if ($reflMethod->getName() == '__construct' && $reflMethod->isPublic()) {
             if (count($reflMethod->getParameters()) == 0) {
                 $useConstructor = true;
             } else {
                 // if all parameters are optional we still can use constructor
                 $allParametersOptional = true;
                 foreach ($reflMethod->getParameters() as $reflParam) {
                     /* @var \ReflectionParameter $reflParam */
                     if (!$reflParam->isOptional()) {
                         $allParametersOptional = false;
                     }
                 }
                 $useConstructor = $allParametersOptional;
             }
         }
     }
     if ($useConstructor) {
         return new $entityClass();
     } else {
         $serialized = sprintf('O:%u:"%s":0:{}', strlen($entityClass), $entityClass);
         return unserialize($serialized);
     }
 }
 public function testHowWellContainerIsInjected()
 {
     $repository = new Repository('test repo', array('filesystem' => '', 'storage_key_generator' => ''));
     self::$em->persist($repository);
     self::$em->flush();
     self::$em->clear();
     /* @var Repository $repository */
     $repository = self::$em->getRepository(Repository::clazz())->find($repository->getId());
     $this->assertInstanceOf('Symfony\\Component\\DependencyInjection\\ContainerInterface', Toolkit::getPropertyValue($repository, 'container'));
 }
 public function resolve($entityFqcn, $fieldName)
 {
     $metadata = $this->em->getClassMetadata($entityFqcn);
     if (!$metadata) {
         throw new \RuntimeException("Unable to load metadata for class '{$entityFqcn}'.");
     }
     $fieldMapping = $metadata->getAssociationMapping($fieldName);
     /* @var QueryOrder $ann */
     $ann = $this->ar->getPropertyAnnotation(Tk::getReflectionProperty($entityFqcn, $fieldName), QueryOrder::clazz());
     if (!$ann) {
         // no property annotation found
         $ann = $this->ar->getClassAnnotation(new \ReflectionClass($fieldMapping['targetEntity']), QueryOrder::clazz());
         if (!$ann) {
             // no class annotation found
             return $this->getDefaultPropertyName($fieldMapping['targetEntity']);
         } else {
             return $ann->value;
         }
     } else {
         return $ann->value;
     }
 }
Ejemplo n.º 5
0
 public function testHowWellItWorks()
 {
     /* @var FileRepository $fr */
     $fr = self::$container->get('modera_file_repository.repository.file_repository');
     $this->assertNull($fr->getRepository('dummy_repository'));
     $repositoryConfig = array('storage_key_generator' => 'modera_file_repository.repository.uniqid_key_generator', 'filesystem' => 'dummy_tmp_fs');
     $this->assertFalse($fr->repositoryExists('dummy_repository'));
     $repository = $fr->createRepository('dummy_repository', $repositoryConfig, 'My dummy repository');
     $this->assertTrue($fr->repositoryExists('dummy_repository'));
     $this->assertInstanceOf(Repository::clazz(), $repository);
     $this->assertNotNull($repository->getId());
     $this->assertEquals('dummy_repository', $repository->getName());
     $this->assertEquals('My dummy repository', $repository->getLabel());
     $this->assertSame($repositoryConfig, $repository->getConfig());
     $this->assertInstanceOf('Symfony\\Component\\DependencyInjection\\ContainerInterface', Toolkit::getPropertyValue($repository, 'container'));
     // ---
     $fileContents = 'foo contents';
     $filePath = sys_get_temp_dir() . DIRECTORY_SEPARATOR . 'our-dummy-file.txt';
     file_put_contents($filePath, $fileContents);
     $file = new File($filePath);
     $storedFile = $fr->put($repository->getName(), $file, array());
     self::$em->clear();
     // this way we will make sure that data is actually persisted in database
     /* @var StoredFile $storedFile */
     $storedFile = self::$em->find(StoredFile::clazz(), $storedFile->getId());
     $this->assertInstanceOf(StoredFile::clazz(), $storedFile);
     $this->assertNotNull($storedFile->getId());
     $this->assertNotNull($storedFile->getStorageKey());
     $this->assertEquals('our-dummy-file.txt', $storedFile->getFilename());
     $this->assertNotNull($storedFile->getCreatedAt());
     $this->assertEquals('txt', $storedFile->getExtension());
     $this->assertEquals('text/plain', $storedFile->getMimeType());
     $this->assertSame($repository->getId(), $storedFile->getRepository()->getId());
     $this->assertEquals($fileContents, $storedFile->getContents());
     $this->assertTrue('' != $storedFile->getChecksum());
     $this->assertEquals($file->getSize(), $storedFile->getSize());
     // ---
     $storedFileData = array('id' => $storedFile->getId(), 'storageKey' => $storedFile->getStorageKey(), 'filename' => $storedFile->getFilename());
     $fileContents = 'bar contents';
     $filePath = sys_get_temp_dir() . DIRECTORY_SEPARATOR . 'bar-dummy-file.txt';
     file_put_contents($filePath, $fileContents);
     $file = new File($filePath);
     $storedFile = $fr->put($repository->getName(), $file, array());
     self::$em->clear();
     // this way we will make sure that data is actually persisted in database
     /* @var StoredFile $storedFile */
     $storedFile = self::$em->find(StoredFile::clazz(), $storedFile->getId());
     $this->assertNotEquals($storedFileData['id'], $storedFile->getId());
     $this->assertNotEquals($storedFileData['storageKey'], $storedFile->getStorageKey());
     $this->assertNotEquals($storedFileData['filename'], $storedFile->getFilename());
     // ---
     $repositoryConfig['overwrite_files'] = true;
     $repository = $storedFile->getRepository();
     $repository->setConfig($repositoryConfig);
     self::$em->persist($repository);
     self::$em->flush();
     $storedFileData = array('id' => $storedFile->getId(), 'storageKey' => $storedFile->getStorageKey(), 'filename' => $storedFile->getFilename());
     $storedFile = $fr->put($repository->getName(), $file, array());
     self::$em->clear();
     // this way we will make sure that data is actually persisted in database
     /* @var StoredFile $storedFile */
     $storedFile = self::$em->find(StoredFile::clazz(), $storedFile->getId());
     $this->assertEquals($storedFileData['id'], $storedFile->getId());
     $this->assertEquals($storedFileData['storageKey'], $storedFile->getStorageKey());
     $this->assertEquals($storedFileData['filename'], $storedFile->getFilename());
     // ---
     $fs = $storedFile->getRepository()->getFilesystem();
     $this->assertTrue($fs->has($storedFile->getStorageKey()));
     self::$em->remove($storedFile);
     self::$em->flush();
     $this->assertFalse($fs->has($storedFile->getStorageKey()));
 }
Ejemplo n.º 6
0
 /**
  * @Remote
  */
 public function batchUpdateAction(array $params)
 {
     $config = $this->getPreparedConfig();
     try {
         $persistenceHandler = $config['batch_update_entities_handler'];
         $dataMapper = $config['map_data_on_update'];
         $validator = $config['updated_entity_validator'];
         $this->interceptAction('batchUpdate', $params);
         if (isset($params['queries']) && is_array($params['queries']) && isset($params['record']) && is_array($params['record'])) {
             if (!isset($params['record'])) {
                 $e = new BadRequestException("'/record' hasn't been provided");
                 $e->setParams($params);
                 $e->setPath('/record');
                 throw $e;
             }
             $entities = array();
             foreach ($params['queries'] as $query) {
                 $entities = array_merge($entities, $this->getPersistenceHandler()->query($config['entity'], $query));
             }
             $errors = array();
             $operationResult = null;
             foreach ($entities as $entity) {
                 $dataMapper($params['record'], $entity, $this->getDataMapper(), $this->container);
                 if ($validator) {
                     /* @var ValidationResult $validationResult */
                     $validationResult = $validator($params, $entity, $this->getEntityValidator(), $config, $this->container);
                     if ($validationResult->hasErrors()) {
                         $pkFields = $this->getPersistenceHandler()->resolveEntityPrimaryKeyFields($config['entity']);
                         $ids = array();
                         foreach ($pkFields as $fieldName) {
                             $ids[$fieldName] = Toolkit::getPropertyValue($entity, $fieldName);
                         }
                         $errors[] = array('id' => $ids, 'errors' => $validationResult->toArray());
                     }
                 }
             }
             if (count($errors) == 0) {
                 $operationResult = $persistenceHandler($entities, $params, $this->getPersistenceHandler(), $this->container);
                 return array_merge($operationResult->toArray($this->getModelManager()), array('success' => true));
             } else {
                 return array('success' => false, 'errors' => $errors);
             }
         } elseif (isset($params['records']) && is_array($params['records'])) {
             $entities = array();
             $errors = array();
             foreach ($params['records'] as $recordParams) {
                 $missingPkFields = array();
                 $query = array();
                 foreach ($this->getPersistenceHandler()->resolveEntityPrimaryKeyFields($config['entity']) as $fieldName) {
                     if (isset($recordParams[$fieldName])) {
                         $query[] = array('property' => $fieldName, 'value' => 'eq:' . $recordParams[$fieldName]);
                     } else {
                         $missingPkFields[] = $fieldName;
                     }
                 }
                 if (count($missingPkFields) == 0) {
                     $entity = $this->getPersistenceHandler()->query($config['entity'], array('filter' => $query));
                     $this->validateResultHasExactlyOneEntity($entity, $params);
                     $entity = $entity[0];
                     $entities[] = $entity;
                     $dataMapper($recordParams, $entity, $this->getDataMapper(), $this->container);
                     if ($validator) {
                         /* @var ValidationResult $validationResult */
                         $validationResult = $validator($params, $entity, $this->getEntityValidator(), $config, $this->container);
                         if ($validationResult->hasErrors()) {
                             $pkFields = $this->getPersistenceHandler()->resolveEntityPrimaryKeyFields($config['entity']);
                             $ids = array();
                             foreach ($pkFields as $fieldName) {
                                 $ids[$fieldName] = Toolkit::getPropertyValue($entity, $fieldName);
                             }
                             $errors[] = array('id' => $ids, 'errors' => $validationResult->toArray());
                         }
                     }
                 }
             }
             if (count($errors) == 0) {
                 $operationResult = $persistenceHandler($entities, $params, $this->getPersistenceHandler(), $this->container);
                 return array_merge($operationResult->toArray($this->getModelManager()), array('success' => true));
             } else {
                 return array('success' => false, 'errors' => $errors);
             }
         } else {
             $e = new BadRequestException("Invalid request structure. Valid request would either contain 'queries' and 'record' or 'records' keys.");
             $e->setPath($params);
             $e->setPath('/');
             throw $e;
         }
     } catch (\Exception $e) {
         return $this->createExceptionResponse($e, ExceptionHandlerInterface::OPERATION_UPDATE);
     }
 }
Ejemplo n.º 7
0
 public static function doSetUpBeforeClass()
 {
     $driver = new AnnotationDriver(self::$kernel->getContainer()->get('annotation_reader'), array(__DIR__));
     Toolkit::addMetadataDriverForEntityManager(self::$em, $driver, __NAMESPACE__);
 }
 public static function doTearDownAfterClass()
 {
     Toolkit::dropTableForEntity(self::$em, DummyArticle::clazz());
 }
 /**
  * Be aware, that "id" property will never be mapped to you entities even if it is provided
  * in $params, we presume that it always be generated automatically.
  *
  * @param Object $entity
  * @param array $params  Data usually received from client-side
  * @param array $allowedFields  Fields names you want to allow have mapped
  * @throws \RuntimeException
  */
 public function mapEntity($entity, array $params, array $allowedFields)
 {
     $entityMethods = get_class_methods($entity);
     $metadata = $this->em->getClassMetadata(get_class($entity));
     foreach ($metadata->getFieldNames() as $fieldName) {
         if (!in_array($fieldName, $allowedFields) || 'id' == $fieldName) {
             // ID is always generated dynamically
             continue;
         }
         if (isset($params[$fieldName])) {
             $value = $params[$fieldName];
             $mapping = $metadata->getFieldMapping($fieldName);
             // if a field is number and at the same time its value was not provided,
             // then we are not touching it at all, if the model has specified
             // a default value for it - fine, everything's gonna be fine, otherwise
             // Doctrine will look if this field isNullable etc ... and throw
             // an exception if needed
             if (!(in_array($mapping['type'], array('integer', 'smallint', 'bigint', 'decimal', 'float')) && '' === $value)) {
                 try {
                     $methodParams = $this->paramsProvider->getParameters(get_class($entity), $this->fm->formatSetterName($fieldName));
                     $convertedValue = null;
                     if (is_object($value) || is_array($value)) {
                         foreach ($this->complexFiledValueConvertersProvider->getItems() as $converter) {
                             /* @var ComplexFieldValueConverterInterface $converter */
                             if ($converter->isResponsible($value, $fieldName, $metadata)) {
                                 $convertedValue = $converter->convert($value, $fieldName, $metadata);
                             }
                         }
                     } else {
                         $convertedValue = $this->convertValue($value, $mapping['type']);
                     }
                     $methodParams = array_merge(array($convertedValue), $methodParams);
                     $this->fm->set($entity, $fieldName, $methodParams);
                 } catch (\Exception $e) {
                     throw new \RuntimeException("Something went wrong during mapping of a scalar field '{$fieldName}' - " . $e->getMessage(), null, $e);
                 }
             }
         }
     }
     foreach ($metadata->getAssociationMappings() as $mapping) {
         $fieldName = $mapping['fieldName'];
         if (!in_array($fieldName, $allowedFields)) {
             continue;
         }
         if (isset($params[$fieldName]) && null !== $params[$fieldName]) {
             if (in_array($mapping['type'], array(CMI::ONE_TO_ONE, CMI::MANY_TO_ONE))) {
                 $rawValue = $params[$fieldName];
                 $methodParams = $this->paramsProvider->getParameters(get_class($entity), $this->fm->formatSetterName($fieldName));
                 if ('-' == $rawValue) {
                     $this->fm->set($entity, $fieldName, array_merge(array(null), $methodParams));
                 } else {
                     $value = $this->em->getRepository($mapping['targetEntity'])->find($rawValue);
                     if ($value) {
                         $this->fm->set($entity, $fieldName, array_merge(array($value), $methodParams));
                     }
                 }
             } else {
                 // one_to_many, many_to_many
                 $rawValue = $params[$fieldName];
                 $col = $metadata->getFieldValue($entity, $fieldName);
                 // if it is a new entity ( you should remember, the entity's constructor is not invoked )
                 // it will have no collection initialized, because this usually happens in the constructor
                 if (!$col) {
                     $col = new ArrayCollection();
                     $this->fm->set($entity, $fieldName, array($col));
                 }
                 $oldIds = Toolkit::extractIds($col);
                 $newIds = is_array($rawValue) ? $rawValue : explode(', ', $rawValue);
                 $idsToDelete = array_diff($oldIds, $newIds);
                 $idsToAdd = array_diff($newIds, $oldIds);
                 $entitiesToDelete = $this->getEntitiesByIds($idsToDelete, $mapping['targetEntity']);
                 $entitiesToAdd = $this->getEntitiesByIds($idsToAdd, $mapping['targetEntity']);
                 /*
                  * At first it will be checked if removeXXX/addXXX methods exist, if they
                  * do, then they will be used, otherwise we will try to manage
                  * relation manually
                  */
                 $removeMethod = 'remove' . ucfirst(Toolkit::singlifyWord($fieldName));
                 if (in_array($removeMethod, $entityMethods) && count($idsToDelete) > 0) {
                     foreach ($entitiesToDelete as $refEntity) {
                         $methodParams = array_merge(array($refEntity), $this->paramsProvider->getParameters(get_class($entity), $removeMethod));
                         call_user_func_array(array($entity, $removeMethod), $methodParams);
                     }
                 } else {
                     foreach ($entitiesToDelete as $refEntity) {
                         if ($col->contains($refEntity)) {
                             $col->removeElement($refEntity);
                             if (CMI::MANY_TO_MANY == $mapping['type']) {
                                 $refMetadata = $this->em->getClassMetadata(get_class($refEntity));
                                 // bidirectional
                                 if ($refMetadata->hasAssociation($mapping['mappedBy'])) {
                                     $inversedCol = $refMetadata->getFieldValue($refEntity, $mapping['mappedBy']);
                                     if ($inversedCol instanceof Collection) {
                                         $inversedCol->removeElement($entity);
                                     }
                                 }
                             } else {
                                 // nulling the other side of relation
                                 $this->fm->set($refEntity, $mapping['mappedBy'], array(null));
                             }
                         }
                     }
                 }
                 $addMethod = 'add' . ucfirst(Toolkit::singlifyWord($fieldName));
                 if (in_array($addMethod, $entityMethods) && count($idsToAdd) > 0) {
                     foreach ($entitiesToAdd as $refEntity) {
                         $methodParams = array_merge(array($refEntity), $this->paramsProvider->getParameters(get_class($entity), $addMethod));
                         call_user_func_array(array($entity, $addMethod), $methodParams);
                     }
                 } else {
                     foreach ($entitiesToAdd as $refEntity) {
                         if (!$col->contains($refEntity)) {
                             $col->add($refEntity);
                             if (CMI::MANY_TO_MANY == $mapping['type']) {
                                 $refMetadata = $this->em->getClassMetadata(get_class($refEntity));
                                 // bidirectional
                                 if ($refMetadata->hasAssociation($mapping['mappedBy'])) {
                                     $inversedCol = $refMetadata->getFieldValue($refEntity, $mapping['mappedBy']);
                                     if ($inversedCol instanceof Collection) {
                                         $inversedCol->add($entity);
                                     }
                                 }
                             } else {
                                 $this->fm->set($refEntity, $mapping['mappedBy'], array($entity));
                             }
                         }
                     }
                 }
             }
         }
     }
 }