/**
  * Gets an association proxy instance.
  */
 public function getAssociationProxy($owner, \Doctrine\ORM\Mapping\AssociationMapping $assoc)
 {
     $proxyClassName = str_replace('\\', '_', $assoc->getTargetEntityName()) . 'AProxy';
     if (!class_exists($proxyClassName, false)) {
         $this->_em->getMetadataFactory()->setMetadataFor(self::$_ns . $proxyClassName, $this->_em->getClassMetadata($assoc->getTargetEntityName()));
         $fileName = $this->_cacheDir . $proxyClassName . '.g.php';
         if (!file_exists($fileName)) {
             $this->_generateAssociationProxyClass($assoc->getTargetEntityName(), $proxyClassName, $fileName);
         }
         require $fileName;
     }
     $proxyClassName = '\\' . self::$_ns . $proxyClassName;
     return new $proxyClassName($this->_em, $assoc, $owner);
 }
 /**
  * {@inheritdoc}
  */
 public function remove($key)
 {
     // TODO: If the keys are persistent as well (not yet implemented)
     //       and the collection is not initialized and orphanRemoval is
     //       not used we can issue a straight SQL delete/update on the
     //       association (table). Without initializing the collection.
     $this->_initialize();
     $removed = $this->_coll->remove($key);
     if ($removed) {
         $this->_changed();
         if ($this->_association !== null && $this->_association->isOneToMany() && $this->_association->orphanRemoval) {
             $this->_em->getUnitOfWork()->scheduleOrphanRemoval($removed);
         }
     }
     return $removed;
 }
 /**
  * {@inheritdoc}
  */
 public function clear()
 {
     if ($this->initialized && $this->isEmpty()) {
         return;
     }
     if ($this->association->isOneToMany() && $this->association->orphanRemoval) {
         foreach ($this->coll as $element) {
             $this->em->getUnitOfWork()->scheduleOrphanRemoval($element);
         }
     }
     $this->coll->clear();
     if ($this->association->isOwningSide) {
         $this->changed();
         $this->em->getUnitOfWork()->scheduleCollectionDeletion($this);
         $this->takeSnapshot();
     }
 }
 /**
  * Adds an element to the collection.
  * 
  * @param mixed $value
  * @param string $key 
  * @return boolean Always TRUE.
  * @override
  */
 public function add($value)
 {
     parent::add($value);
     if ($this->_hydrationFlag) {
         if ($this->_backRefFieldName) {
             // Set back reference to owner
             if ($this->_association->isOneToMany()) {
                 $this->_typeClass->getReflectionProperty($this->_backRefFieldName)->setValue($value, $this->_owner);
             } else {
                 // ManyToMany
                 $this->_typeClass->getReflectionProperty($this->_backRefFieldName)->getValue($value)->add($this->_owner);
             }
         }
     } else {
         $this->_changed();
     }
     return true;
 }
Example #5
0
 /**
  * Gather columns and fk constraints that are required for one part of relationship.
  * 
  * @param array $joinColumns
  * @param \Doctrine\DBAL\Schema\Table $theJoinTable
  * @param ClassMetadata $class
  * @param \Doctrine\ORM\Mapping\AssociationMapping $mapping
  * @param array $primaryKeyColumns
  * @param array $uniqueConstraints
  */
 private function _gatherRelationJoinColumns($joinColumns, $theJoinTable, $class, $mapping, &$primaryKeyColumns, &$uniqueConstraints)
 {
     $localColumns = array();
     $foreignColumns = array();
     $fkOptions = array();
     foreach ($joinColumns as $joinColumn) {
         // Note that this thing might be quoted, i.e. `foo`, [foo], ...
         $columnName = $mapping->getQuotedJoinColumnName($joinColumn['name'], $this->_platform);
         $referencedFieldName = $class->getFieldName($joinColumn['referencedColumnName']);
         if (!$class->hasField($referencedFieldName)) {
             throw new \Doctrine\Common\DoctrineException("Column name `" . $joinColumn['referencedColumnName'] . "` referenced for relation from " . "{$mapping->sourceEntityName} towards {$mapping->targetEntityName} does not exist.");
         }
         $primaryKeyColumns[] = $columnName;
         $localColumns[] = $columnName;
         $foreignColumns[] = $joinColumn['referencedColumnName'];
         if (!$theJoinTable->hasColumn($joinColumn['name'])) {
             // Only add the column to the table if it does not exist already.
             // It might exist already if the foreign key is mapped into a regular
             // property as well.
             $fieldMapping = $class->getFieldMapping($referencedFieldName);
             $columnDef = null;
             if (isset($joinColumn['columnDefinition'])) {
                 $columnDef = $joinColumn['columnDefinition'];
             } else {
                 if (isset($fieldMapping['columnDefinition'])) {
                     $columnDef = $fieldMapping['columnDefinition'];
                 }
             }
             $columnOptions = array('notnull' => false, 'columnDefinition' => $columnDef);
             if (isset($joinColumn['nullable'])) {
                 $columnOptions['notnull'] = !$joinColumn['nullable'];
             }
             $theJoinTable->createColumn($columnName, $class->getTypeOfColumn($joinColumn['referencedColumnName']), $columnOptions);
         }
         if (isset($joinColumn['unique']) && $joinColumn['unique'] == true) {
             $uniqueConstraints[] = array('columns' => array($columnName));
         }
         if (isset($joinColumn['onUpdate'])) {
             $fkOptions['onUpdate'] = $joinColumn['onUpdate'];
         }
         if (isset($joinColumn['onDelete'])) {
             $fkOptions['onDelete'] = $joinColumn['onDelete'];
         }
     }
     $theJoinTable->addUnnamedForeignKeyConstraint($class->getQuotedTableName($this->_platform), $localColumns, $foreignColumns, $fkOptions);
 }
Example #6
0
 /**
  * Stores the association mapping.
  *
  * @param AssociationMapping $assocMapping
  */
 private function _storeAssociationMapping(AssociationMapping $assocMapping)
 {
     $sourceFieldName = $assocMapping->getSourceFieldName();
     if (isset($this->associationMappings[$sourceFieldName])) {
         throw MappingException::duplicateFieldMapping();
     }
     $this->associationMappings[$sourceFieldName] = $assocMapping;
     $this->_registerMappingIfInverse($assocMapping);
     // Store ReflectionProperty of mapped field
     $refProp = $this->reflClass->getProperty($sourceFieldName);
     $refProp->setAccessible(true);
     $this->reflFields[$sourceFieldName] = $refProp;
 }
 /**
  * INTERNAL:
  * Sets the collection owner. Used (only?) during hydration.
  *
  * @param object $entity
  * @param AssociationMapping $assoc
  */
 public function setOwner($entity, AssociationMapping $assoc)
 {
     $this->_owner = $entity;
     $this->_association = $assoc;
     if ($assoc->isInverseSide()) {
         // For sure bi-directional
         $this->_backRefFieldName = $assoc->mappedByFieldName;
     } else {
         $targetClass = $this->_em->getClassMetadata($assoc->targetEntityName);
         if (isset($targetClass->inverseMappings[$assoc->sourceFieldName])) {
             // Bi-directional
             $this->_backRefFieldName = $targetClass->inverseMappings[$assoc->sourceFieldName]->sourceFieldName;
         }
     }
 }