Esempio n. 1
0
 private function getCompositeKey($record)
 {
     $composite = array();
     foreach ((array) $this->_table->getIdentifier() as $keyPart) {
         if (!isset($record[$keyPart])) {
             return false;
         }
         $composite[] = $record[$keyPart];
     }
     return join('-', $composite);
 }
Esempio n. 2
0
    /**
     * Populate the relationship $name for all records in the passed collection
     *
     * @param string $name
     * @param Doctrine_Collection $coll
     * @return void
     */
    public function populateRelated($name, Doctrine_Collection $coll)
    {
        $rel     = $this->_table->getRelation($name);
        $table   = $rel->getTable();
        $foreign = $rel->getForeign();
        $local   = $rel->getLocal();

        if ($rel instanceof Doctrine_Relation_LocalKey) {
            foreach ($this->data as $key => $record) {
                foreach ($coll as $k => $related) {
                    if ($related[$foreign] == $record[$local]) {
                        $this->data[$key]->setRelated($name, $related);
                    }
                }
            }
        } elseif ($rel instanceof Doctrine_Relation_ForeignKey) {
            foreach ($this->data as $key => $record) {
                if ( ! $record->exists()) {
                    continue;
                }
                $sub = Doctrine_Collection::create($table);

                foreach ($coll as $k => $related) {
                    if ($related[$foreign] == $record[$local]) {
                        $sub->add($related);
                        $coll->remove($k);
                    }
                }

                $this->data[$key]->setRelated($name, $sub);
            }
        } elseif ($rel instanceof Doctrine_Relation_Association) {
            $identifier = $this->_table->getIdentifier();
            $asf        = $rel->getAssociationFactory();
            $name       = $table->getComponentName();

            foreach ($this->data as $key => $record) {
                if ( ! $record->exists()) {
                    continue;
                }
                $sub = Doctrine_Collection::create($table);
                foreach ($coll as $k => $related) {
                    if ($related->get($local) == $record[$identifier]) {
                        $sub->add($related->get($name));
                    }
                }
                $this->data[$key]->setRelated($name, $sub);

            }
        }
    }
Esempio n. 3
0
 /**
  * isIdentifiable
  * returns whether or not a given data row is identifiable (it contains
  * all primary key fields specified in the second argument)
  *
  * @param array $row
  * @param Doctrine_Table $table
  * @return boolean
  */
 public function isIdentifiable(array $row, Doctrine_Table $table)
 {
     $primaryKeys = $table->getIdentifier();
     if (is_array($primaryKeys)) {
         foreach ($primaryKeys as $id) {
             if (!isset($row[$id])) {
                 return false;
             }
         }
     } else {
         if (!isset($row[$primaryKeys])) {
             return false;
         }
     }
     return true;
 }
Esempio n. 4
0
 /**
  * Execute a SQL REPLACE query. A REPLACE query is identical to a INSERT
  * query, except that if there is already a row in the table with the same
  * key field values, the REPLACE query just updates its values instead of
  * inserting a new row.
  *
  * The REPLACE type of query does not make part of the SQL standards. Since
  * practically only MySQL and SQLIte implement it natively, this type of
  * query isemulated through this method for other DBMS using standard types
  * of queries inside a transaction to assure the atomicity of the operation.
  *
  * @param                   string  name of the table on which the REPLACE query will
  *                          be executed.
  *
  * @param   array           an associative array that describes the fields and the
  *                          values that will be inserted or updated in the specified table. The
  *                          indexes of the array are the names of all the fields of the table.
  *
  *                          The values of the array are values to be assigned to the specified field.
  *
  * @param array $keys       an array containing all key fields (primary key fields
  *                          or unique index fields) for this table
  *
  *                          the uniqueness of a row will be determined according to
  *                          the provided key fields
  *
  *                          this method will fail if no key fields are specified
  *
  * @throws Doctrine_Connection_Exception        if this driver doesn't support replace
  * @throws Doctrine_Connection_Exception        if some of the key values was null
  * @throws Doctrine_Connection_Exception        if there were no key fields
  * @throws PDOException                         if something fails at PDO level
  * @ return integer                              number of rows affected
  */
 public function replace(Doctrine_Table $table, array $fields, array $keys)
 {
     if (empty($keys)) {
         throw new Doctrine_Connection_Exception('Not specified which fields are keys');
     }
     $identifier = (array) $table->getIdentifier();
     $condition = array();
     foreach ($fields as $fieldName => $value) {
         if (in_array($fieldName, $keys)) {
             if ($value !== null) {
                 $condition[] = $table->getColumnName($fieldName) . ' = ?';
                 $conditionValues[] = $value;
             }
         }
     }
     $affectedRows = 0;
     if (!empty($condition) && !empty($conditionValues)) {
         $query = 'DELETE FROM ' . $this->quoteIdentifier($table->getTableName()) . ' WHERE ' . implode(' AND ', $condition);
         $affectedRows = $this->exec($query, $conditionValues);
     }
     $this->insert($table, $fields);
     $affectedRows++;
     return $affectedRows;
 }
Esempio n. 5
0
 /**
  * Generates foreign keys for the plugin table based on the owner table.
  * These columns are automatically added to the generated model so we can
  * create foreign keys back to the table object that owns the plugin.
  *
  * @param Doctrine_Table $table     the table object that owns the plugin
  * @return array                    an array of foreign key definitions
  */
 public function buildForeignKeys(Doctrine_Table $table)
 {
     $fk = array();
     foreach ((array) $table->getIdentifier() as $column) {
         $def = $table->getDefinitionOf($column);
         unset($def['autoincrement']);
         unset($def['sequence']);
         unset($def['primary']);
         $col = $column;
         $def['primary'] = true;
         $fk[$col] = $def;
     }
     return $fk;
 }
Esempio n. 6
0
 /**
  * getIdentifiers
  * gives a list of identifiers from given table
  *
  * the identifiers are in format:
  * [componentName].[identifier]
  *
  * @param Doctrine_Table $table     table object to retrieve identifiers from
  */
 public function getIdentifiers(Doctrine_Table $table)
 {
     $componentNameToLower = strtolower($table->getComponentName());
     if (is_array($table->getIdentifier())) {
         $columns = array();
         foreach ((array) $table->getIdentifierColumnNames() as $identColName) {
             $columns[] = $componentNameToLower . '_' . $identColName;
         }
     } else {
         $columns = $componentNameToLower . '_' . $table->getColumnName($table->getIdentifier());
     }
     return $columns;
 }
Esempio n. 7
0
 /**
  * Completes the given definition
  *
  * @param array $def    definition array to be completed
  * @return array        completed definition array
  */
 public function completeDefinition($def)
 {
     $conn = $this->_table->getConnection();
     $def['table'] = $conn->getTable($def['class']);
     $foreignClasses = array_merge($def['table']->getOption('parents'), array($def['class']));
     $localClasses = array_merge($this->_table->getOption('parents'), array($this->_table->getComponentName()));
     if (isset($def['local'])) {
         if (!isset($def['foreign'])) {
             // local key is set, but foreign key is not
             // try to guess the foreign key
             if ($def['local'] === $this->_table->getIdentifier()) {
                 $def['foreign'] = $this->guessColumns($localClasses, $def['table']);
             } else {
                 // the foreign field is likely to be the
                 // identifier of the foreign class
                 $def['foreign'] = $def['table']->getIdentifier();
                 $def['localKey'] = true;
             }
         } else {
             if ($def['local'] !== $this->_table->getIdentifier()) {
                 $def['localKey'] = true;
             }
         }
     } else {
         if (isset($def['foreign'])) {
             // local key not set, but foreign key is set
             // try to guess the local key
             if ($def['foreign'] === $def['table']->getIdentifier()) {
                 $def['localKey'] = true;
                 try {
                     $def['local'] = $this->guessColumns($foreignClasses, $this->_table);
                 } catch (Doctrine_Relation_Exception $e) {
                     $def['local'] = $this->_table->getIdentifier();
                 }
             } else {
                 $def['local'] = $this->_table->getIdentifier();
             }
         } else {
             // neither local or foreign key is being set
             // try to guess both keys
             $conn = $this->_table->getConnection();
             // the following loops are needed for covering inheritance
             foreach ($localClasses as $class) {
                 $table = $conn->getTable($class);
                 $column = strtolower($table->getComponentName()) . '_' . $table->getIdentifier();
                 foreach ($foreignClasses as $class2) {
                     $table2 = $conn->getTable($class2);
                     if ($table2->hasColumn($column)) {
                         $def['foreign'] = $column;
                         $def['local'] = $table->getIdentifier();
                         return $def;
                     }
                 }
             }
             foreach ($foreignClasses as $class) {
                 $table = $conn->getTable($class);
                 $column = strtolower($table->getComponentName()) . '_' . $table->getIdentifier();
                 foreach ($localClasses as $class2) {
                     $table2 = $conn->getTable($class2);
                     if ($table2->hasColumn($column)) {
                         $def['foreign'] = $table->getIdentifier();
                         $def['local'] = $column;
                         $def['localKey'] = true;
                         return $def;
                     }
                 }
             }
             // auto-add columns and auto-build relation
             $columns = array();
             foreach ((array) $this->_table->getIdentifier() as $id) {
                 $column = strtolower($table->getComponentName()) . '_' . $id;
                 $col = $this->_table->getDefinitionOf($id);
                 $type = $col['type'];
                 $length = $col['length'];
                 unset($col['type']);
                 unset($col['length']);
                 unset($col['autoincrement']);
                 unset($col['sequence']);
                 unset($col['primary']);
                 $def['table']->setColumn($column, $type, $length, $col);
                 $columns[] = $column;
             }
             if (count($columns) > 1) {
                 $def['foreign'] = $columns;
             } else {
                 $def['foreign'] = $columns[0];
             }
             $def['local'] = $this->_table->getIdentifier();
         }
     }
     return $def;
 }