Commit eb02b4d0 authored by romanb's avatar romanb

started refactoring to final mapper structure for 1.0. different mapping...

started refactoring to final mapper structure for 1.0. different mapping strategies are factored out as separate strategy classes instead of inheritance.
parent dcc2a54e
...@@ -77,22 +77,6 @@ class Doctrine_ClassMetadata extends Doctrine_Configurable implements Serializab ...@@ -77,22 +77,6 @@ class Doctrine_ClassMetadata extends Doctrine_Configurable implements Serializab
*/ */
protected $_inheritanceType = Doctrine::INHERITANCETYPE_TABLE_PER_CLASS; protected $_inheritanceType = Doctrine::INHERITANCETYPE_TABLE_PER_CLASS;
/**
* The name of the column that acts as a discriminator to identify the type of an
* object. Used in Single Table Inheritance and Class Table Inheritance.
*
* @var string
*/
protected $_discriminatorColumn;
/**
* The discriminator map contains the mapping of discriminator values (keys)
* to class names (values).
*
* @var array
*/
protected $_discriminatorMap;
/** /**
* An array containing all templates attached to the class. * An array containing all templates attached to the class.
* *
...@@ -120,10 +104,10 @@ class Doctrine_ClassMetadata extends Doctrine_Configurable implements Serializab ...@@ -120,10 +104,10 @@ class Doctrine_ClassMetadata extends Doctrine_Configurable implements Serializab
protected $_filters = array(); protected $_filters = array();
/** /**
* An array of column definitions, * The mapped columns and their mapping definitions.
* keys are column names and values are column definitions * Keys are column names and values are definitions.
* *
* the definition array has atleast the following values: * The definition array has atleast the following values:
* *
* -- type the column type, eg. 'integer' * -- type the column type, eg. 'integer'
* -- length the column length, eg. 11 * -- length the column length, eg. 11
...@@ -156,6 +140,12 @@ class Doctrine_ClassMetadata extends Doctrine_Configurable implements Serializab ...@@ -156,6 +140,12 @@ class Doctrine_ClassMetadata extends Doctrine_Configurable implements Serializab
*/ */
protected $_columnNames = array(); protected $_columnNames = array();
/**
* Caches enum value mappings. Keys are field names and values arrays with the
* mapping.
*/
protected $_enumValues = array();
/** /**
* @todo Implementation. * @todo Implementation.
*/ */
...@@ -164,7 +154,8 @@ class Doctrine_ClassMetadata extends Doctrine_Configurable implements Serializab ...@@ -164,7 +154,8 @@ class Doctrine_ClassMetadata extends Doctrine_Configurable implements Serializab
/** /**
* Tree object associated with the class. * Tree object associated with the class.
* *
* @var Doctrine_Tree * @var Doctrine_Tree
* @todo Belongs to the NestedSet Behavior plugin.
*/ */
protected $_tree; protected $_tree;
...@@ -692,18 +683,25 @@ class Doctrine_ClassMetadata extends Doctrine_Configurable implements Serializab ...@@ -692,18 +683,25 @@ class Doctrine_ClassMetadata extends Doctrine_Configurable implements Serializab
* @return mixed * @return mixed
*/ */
public function enumValue($fieldName, $index) public function enumValue($fieldName, $index)
{ {
if ($index instanceof Doctrine_Null) { if ($index instanceof Doctrine_Null) {
return $index; return $index;
} }
if (isset($this->_enumValues[$fieldName][$index])) {
return $this->_enumValues[$fieldName][$index];
}
$columnName = $this->getColumnName($fieldName); $columnName = $this->getColumnName($fieldName);
if ( ! $this->_conn->getAttribute(Doctrine::ATTR_USE_NATIVE_ENUM) && if ( ! $this->_conn->getAttribute(Doctrine::ATTR_USE_NATIVE_ENUM) &&
isset($this->_columns[$columnName]['values'][$index])) { isset($this->_columns[$columnName]['values'][$index])) {
return $this->_columns[$columnName]['values'][$index]; $enumValue = $this->_columns[$columnName]['values'][$index];
} else {
$enumValue = $index;
} }
$this->_enumValues[$fieldName][$index] = $enumValue;
return $index;
return $enumValue;
} }
/** /**
......
...@@ -13,6 +13,10 @@ class Doctrine_ClassMetadata_CodeDriver ...@@ -13,6 +13,10 @@ class Doctrine_ClassMetadata_CodeDriver
*/ */
public function loadMetadataForClass($className, Doctrine_ClassMetadata $metadata) public function loadMetadataForClass($className, Doctrine_ClassMetadata $metadata)
{ {
if ( ! method_exists($className, 'initMetadata')) {
throw new Doctrine_ClassMetadata_Exception("Unable to load metadata for class"
. " '$className'. Callback method 'initMetadata' not found.");
}
call_user_func_array(array($className, 'initMetadata'), array($metadata)); call_user_func_array(array($className, 'initMetadata'), array($metadata));
} }
} }
\ No newline at end of file
...@@ -165,6 +165,11 @@ class Doctrine_ClassMetadata_Factory ...@@ -165,6 +165,11 @@ class Doctrine_ClassMetadata_Factory
} while ($className = get_parent_class($className)); } while ($className = get_parent_class($className));
if ($className === false) { if ($className === false) {
try {
throw new Exception();
} catch (Exception $e) {
echo $e->getTraceAsString() . "<br />";
}
throw new Doctrine_ClassMetadata_Factory_Exception("Unknown component '$className'."); throw new Doctrine_ClassMetadata_Factory_Exception("Unknown component '$className'.");
} }
......
...@@ -109,7 +109,7 @@ class Doctrine_Collection extends Doctrine_Access implements Countable, Iterator ...@@ -109,7 +109,7 @@ class Doctrine_Collection extends Doctrine_Access implements Countable, Iterator
$this->_mapper = $mapper; $this->_mapper = $mapper;
if ($keyColumn === null) { if ($keyColumn === null) {
$keyColumn = $mapper->getBoundQueryPart('indexBy'); $keyColumn = $mapper->getClassMetadata()->getBoundQueryPart('indexBy');
} }
if ($keyColumn === null) { if ($keyColumn === null) {
...@@ -214,7 +214,7 @@ class Doctrine_Collection extends Doctrine_Access implements Countable, Iterator ...@@ -214,7 +214,7 @@ class Doctrine_Collection extends Doctrine_Access implements Countable, Iterator
$keyColumn = isset($array['keyColumn']) ? $array['keyColumn'] : null; $keyColumn = isset($array['keyColumn']) ? $array['keyColumn'] : null;
if ($keyColumn === null) { if ($keyColumn === null) {
$keyColumn = $this->_mapper->getBoundQueryPart('indexBy'); $keyColumn = $this->_mapper->getClassMetadata()->getBoundQueryPart('indexBy');
} }
if ($keyColumn !== null) { if ($keyColumn !== null) {
......
...@@ -1128,31 +1128,57 @@ abstract class Doctrine_Connection extends Doctrine_Configurable implements Coun ...@@ -1128,31 +1128,57 @@ abstract class Doctrine_Connection extends Doctrine_Configurable implements Coun
* @return Doctrine_Mapper The mapper object. * @return Doctrine_Mapper The mapper object.
* @todo package:orm * @todo package:orm
*/ */
public function getMapper($entityClassName) /*public function getMapper($entityName)
{ {
if (isset($this->_mappers[$entityClassName])) { if (isset($this->_mappers[$entityName])) {
return $this->_mappers[$entityClassName]; return $this->_mappers[$entityName];
} }
$metadata = $this->getClassMetadata($entityClassName); $metadata = $this->getClassMetadata($entityName);
$customMapperClassName = $metadata->getCustomMapperClass(); $customMapperClassName = $metadata->getCustomMapperClass();
if ($customMapperClassName !== null) { if ($customMapperClassName !== null) {
$mapper = new $customMapperClassName($entityClassName, $metadata); $mapper = new $customMapperClassName($entityName, $metadata);
} else { } else {
// instantiate correct mapper type // instantiate correct mapper type
$inheritanceType = $metadata->getInheritanceType(); $inheritanceType = $metadata->getInheritanceType();
if ($inheritanceType == Doctrine::INHERITANCETYPE_JOINED) { if ($inheritanceType == Doctrine::INHERITANCETYPE_JOINED) {
$mapper = new Doctrine_Mapper_Joined($entityClassName, $metadata); $mapper = new Doctrine_Mapper_Joined($entityName, $metadata);
} else if ($inheritanceType == Doctrine::INHERITANCETYPE_SINGLE_TABLE) { } else if ($inheritanceType == Doctrine::INHERITANCETYPE_SINGLE_TABLE) {
$mapper = new Doctrine_Mapper_SingleTable($entityClassName, $metadata); $mapper = new Doctrine_Mapper_SingleTable($entityName, $metadata);
} else if ($inheritanceType == Doctrine::INHERITANCETYPE_TABLE_PER_CLASS) { } else if ($inheritanceType == Doctrine::INHERITANCETYPE_TABLE_PER_CLASS) {
$mapper = new Doctrine_Mapper_TablePerClass($entityClassName, $metadata); $mapper = new Doctrine_Mapper_TablePerClass($entityName, $metadata);
} else { } else {
throw new Doctrine_Connection_Exception("Unknown inheritance type '$inheritanceType'. Can't create mapper."); throw new Doctrine_Connection_Exception("Unknown inheritance type '$inheritanceType'. Can't create mapper.");
} }
} }
$this->_mappers[$entityClassName] = $mapper; $this->_mappers[$entityName] = $mapper;
return $mapper;
}*/
/**
* Gets a mapper for the specified domain class that is used to map instances of
* the class between the relational database and their object representation.
*
* @param string $entityClassName The name of the entity class.
* @return Doctrine_Mapper The mapper object.
* @todo package:orm
*/
public function getMapper($entityName)
{
if (isset($this->_mappers[$entityName])) {
return $this->_mappers[$entityName];
}
$metadata = $this->getClassMetadata($entityName);
$customMapperClassName = $metadata->getCustomMapperClass();
if ($customMapperClassName !== null) {
$mapper = new $customMapperClassName($entityName, $metadata);
} else {
$mapper = new Doctrine_Mapper($entityName, $metadata);
}
$this->_mappers[$entityName] = $mapper;
return $mapper; return $mapper;
} }
......
...@@ -92,7 +92,7 @@ class Doctrine_Connection_UnitOfWork extends Doctrine_Connection_Module ...@@ -92,7 +92,7 @@ class Doctrine_Connection_UnitOfWork extends Doctrine_Connection_Module
{ {
$tree = array(); $tree = array();
foreach ($mappers as $k => $mapper) { foreach ($mappers as $k => $mapper) {
if ( ! ($mapper instanceof Doctrine_Mapper_Abstract)) { if ( ! ($mapper instanceof Doctrine_Mapper)) {
$mapper = $this->conn->getMapper($mapper); $mapper = $this->conn->getMapper($mapper);
} }
$nm = $mapper->getComponentName(); $nm = $mapper->getComponentName();
......
...@@ -1159,7 +1159,6 @@ class Doctrine_Export extends Doctrine_Connection_Module ...@@ -1159,7 +1159,6 @@ class Doctrine_Export extends Doctrine_Connection_Module
// as soon as ONE table is exported, because the data of one class is stored // as soon as ONE table is exported, because the data of one class is stored
// across many tables. // across many tables.
if ($classMetadata->getInheritanceType() == Doctrine::INHERITANCETYPE_JOINED) { if ($classMetadata->getInheritanceType() == Doctrine::INHERITANCETYPE_JOINED) {
//echo "joined.<br />";
$parents = $classMetadata->getOption('parents'); $parents = $classMetadata->getOption('parents');
foreach ($parents as $parent) { foreach ($parents as $parent) {
$data = $classMetadata->getConnection()->getClassMetadata($parent)->getExportableFormat(); $data = $classMetadata->getConnection()->getClassMetadata($parent)->getExportableFormat();
......
<?php <?php
/* /*
* $Id: Hydrate.php 3192 2007-11-19 17:55:23Z romanb $ * $Id$
* *
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
...@@ -20,9 +20,8 @@ ...@@ -20,9 +20,8 @@
*/ */
/** /**
* Doctrine_Hydrate is a base class for Doctrine_RawSql and Doctrine_Query. * The hydrator has the tedious task to construct object or array graphs out of
* Its purpose is to populate object graphs. * a database result set.
*
* *
* @package Doctrine * @package Doctrine
* @subpackage Hydrate * @subpackage Hydrate
...@@ -31,6 +30,7 @@ ...@@ -31,6 +30,7 @@
* @since 1.0 * @since 1.0
* @version $Revision: 3192 $ * @version $Revision: 3192 $
* @author Konsta Vesterinen <kvesteri@cc.hut.fi> * @author Konsta Vesterinen <kvesteri@cc.hut.fi>
* @author Roman Borschel <roman@code-factory.org>
*/ */
class Doctrine_Hydrator extends Doctrine_Hydrator_Abstract class Doctrine_Hydrator extends Doctrine_Hydrator_Abstract
{ {
...@@ -56,7 +56,7 @@ class Doctrine_Hydrator extends Doctrine_Hydrator_Abstract ...@@ -56,7 +56,7 @@ class Doctrine_Hydrator extends Doctrine_Hydrator_Abstract
* 'map' => Custom index to use as the key in the result (if any) * 'map' => Custom index to use as the key in the result (if any)
* ) * )
* ) * )
* @return array * @return mixed The created object/array graph.
*/ */
public function hydrateResultSet($stmt, $tableAliases, $hydrationMode = null) public function hydrateResultSet($stmt, $tableAliases, $hydrationMode = null)
{ {
...@@ -224,7 +224,7 @@ class Doctrine_Hydrator extends Doctrine_Hydrator_Abstract ...@@ -224,7 +224,7 @@ class Doctrine_Hydrator extends Doctrine_Hydrator_Abstract
} }
$id[$rootAlias] = ''; $id[$rootAlias] = '';
} }
$stmt->closeCursor(); $stmt->closeCursor();
$driver->flush(); $driver->flush();
...@@ -294,6 +294,7 @@ class Doctrine_Hydrator extends Doctrine_Hydrator_Abstract ...@@ -294,6 +294,7 @@ class Doctrine_Hydrator extends Doctrine_Hydrator_Abstract
foreach ($data as $key => $value) { foreach ($data as $key => $value) {
// Parse each column name only once. Cache the results. // Parse each column name only once. Cache the results.
if ( ! isset($cache[$key])) { if ( ! isset($cache[$key])) {
// cache general information like the column name <-> field name mapping
$e = explode('__', $key); $e = explode('__', $key);
$last = strtolower(array_pop($e)); $last = strtolower(array_pop($e));
$cache[$key]['dqlAlias'] = $this->_tableAliases[strtolower(implode('__', $e))]; $cache[$key]['dqlAlias'] = $this->_tableAliases[strtolower(implode('__', $e))];
...@@ -301,15 +302,20 @@ class Doctrine_Hydrator extends Doctrine_Hydrator_Abstract ...@@ -301,15 +302,20 @@ class Doctrine_Hydrator extends Doctrine_Hydrator_Abstract
$table = $mapper->getTable(); $table = $mapper->getTable();
$fieldName = $mapper->getFieldName($last); $fieldName = $mapper->getFieldName($last);
$cache[$key]['fieldName'] = $fieldName; $cache[$key]['fieldName'] = $fieldName;
// cache identifier information
if ($table->isIdentifier($fieldName)) { if ($table->isIdentifier($fieldName)) {
$cache[$key]['isIdentifier'] = true; $cache[$key]['isIdentifier'] = true;
} else { } else {
$cache[$key]['isIdentifier'] = false; $cache[$key]['isIdentifier'] = false;
} }
// cache type information
$type = $table->getTypeOfColumn($last); $type = $table->getTypeOfColumn($last);
if ($type == 'integer' || $type == 'string') { if ($type == 'integer' || $type == 'string') {
$cache[$key]['isSimpleType'] = true; $cache[$key]['isSimpleType'] = true;
} else { } else {
$cache[$key]['type'] = $type;
$cache[$key]['isSimpleType'] = false; $cache[$key]['isSimpleType'] = false;
} }
} }
...@@ -329,7 +335,8 @@ class Doctrine_Hydrator extends Doctrine_Hydrator_Abstract ...@@ -329,7 +335,8 @@ class Doctrine_Hydrator extends Doctrine_Hydrator_Abstract
if ($cache[$key]['isSimpleType']) { if ($cache[$key]['isSimpleType']) {
$rowData[$dqlAlias][$fieldName] = $value; $rowData[$dqlAlias][$fieldName] = $value;
} else { } else {
$rowData[$dqlAlias][$fieldName] = $mapper->prepareValue($fieldName, $value); $rowData[$dqlAlias][$fieldName] = $mapper->prepareValue(
$fieldName, $value, $cache[$key]['type']);
} }
if ( ! isset($nonemptyComponents[$dqlAlias]) && $value !== null) { if ( ! isset($nonemptyComponents[$dqlAlias]) && $value !== null) {
......
<?php
/**
* The default strategy maps a single instance to a single database table, as is
* the case in Single Table Inheritance & Concrete Table Inheritance.
*
* @since 1.0
*/
class Doctrine_Mapper_DefaultStrategy extends Doctrine_Mapper_Strategy
{
/**
* Deletes an entity.
*/
public function doDelete(Doctrine_Record $record)
{
$conn = $this->_mapper->getConnection();
$metadata = $this->_mapper->getClassMetadata();
try {
$conn->beginInternalTransaction();
$this->_deleteComposites($record);
$record->state(Doctrine_Record::STATE_TDIRTY);
$identifier = $this->_convertFieldToColumnNames($record->identifier(), $metadata);
$this->_deleteRow($metadata->getTableName(), $identifier);
$record->state(Doctrine_Record::STATE_TCLEAN);
$this->_mapper->removeRecord($record);
$conn->commit();
} catch (Exception $e) {
$conn->rollback();
throw $e;
}
}
/**
* deletes all related composites
* this method is always called internally when a record is deleted
*
* @throws PDOException if something went wrong at database level
* @return void
*/
protected function _deleteComposites(Doctrine_Record $record)
{
$classMetadata = $this->_mapper->getClassMetadata();
foreach ($classMetadata->getRelations() as $fk) {
if ($fk->isComposite()) {
$obj = $record->get($fk->getAlias());
if ($obj instanceof Doctrine_Record &&
$obj->state() != Doctrine_Record::STATE_LOCKED) {
$obj->delete($this->_mapper->getConnection());
}
}
}
}
/**
* Inserts a single entity into the database, without any related entities.
*
* @param Doctrine_Record $record The entity to insert.
*/
public function doInsert(Doctrine_Record $record)
{
$conn = $this->_mapper->getConnection();
$fields = $record->getPrepared();
if (empty($fields)) {
return false;
}
//$class = $record->getClassMetadata();
$class = $this->_mapper->getClassMetadata();
$identifier = (array) $class->getIdentifier();
$fields = $this->_convertFieldToColumnNames($fields, $class);
$seq = $class->getTableOption('sequenceName');
if ( ! empty($seq)) {
$id = $conn->sequence->nextId($seq);
$seqName = $class->getIdentifier();
$fields[$seqName] = $id;
$record->assignIdentifier($id);
}
$this->_insertRow($class->getTableName(), $fields);
if (empty($seq) && count($identifier) == 1 && $identifier[0] == $class->getIdentifier() &&
$class->getIdentifierType() != Doctrine::IDENTIFIER_NATURAL) {
if (strtolower($conn->getName()) == 'pgsql') {
$seq = $class->getTableName() . '_' . $identifier[0];
}
$id = $conn->sequence->lastInsertId($seq);
if ( ! $id) {
throw new Doctrine_Mapper_Exception("Couldn't get last insert identifier.");
}
$record->assignIdentifier($id);
} else {
$record->assignIdentifier(true);
}
}
/**
* Updates an entity.
*/
public function doUpdate(Doctrine_Record $record)
{
$conn = $this->_mapper->getConnection();
$classMetadata = $this->_mapper->getClassMetadata();
$identifier = $this->_convertFieldToColumnNames($record->identifier(), $classMetadata);
$data = $this->_convertFieldToColumnNames($record->getPrepared(), $classMetadata);
$this->_updateRow($classMetadata->getTableName(), $data, $identifier);
$record->assignIdentifier(true);
}
}
\ No newline at end of file
<?php
class Doctrine_Mapper_SingleTable extends Doctrine_Mapper_Abstract
{
/*public function addToWhere($componentAlias, array &$sqlWhereParts, Doctrine_Query $query)
{
$array = array();
$componentParts = $query->getQueryComponent($componentAlias);
$sqlTableAlias = $query->getSqlTableAlias($componentAlias);
$array[$sqlTableAlias][] = $this->getDiscriminatorColumn();
// apply inheritance maps
$str = '';
$c = array();
$index = 0;
foreach ($array as $tableAlias => $maps) {
$a = array();
// don't use table aliases if the query isn't a select query
if ($query->getType() !== Doctrine_Query::SELECT) {
$tableAlias = '';
} else {
$tableAlias .= '.';
}
foreach ($maps as $map) {
$b = array();
foreach ($map as $field => $value) {
$identifier = $this->_conn->quoteIdentifier($tableAlias . $field);
if ($index > 0) {
$b[] = '(' . $identifier . ' = ' . $this->_conn->quote($value)
. ' OR ' . $identifier . ' IS NULL)';
} else {
$b[] = $identifier . ' = ' . $this->_conn->quote($value);
}
}
if ( ! empty($b)) {
$a[] = implode(' AND ', $b);
}
}
if ( ! empty($a)) {
$c[] = implode(' AND ', $a);
}
$index++;
}
$str .= implode(' AND ', $c);
return $str;
}*/
}
<?php
abstract class Doctrine_Mapper_Strategy
{
protected $_mapper;
/**
* The names of all the fields that are available on entities created by this mapper.
*/
protected $_fieldNames = array();
public function __construct(Doctrine_Mapper $mapper)
{
$this->_mapper = $mapper;
}
/**
* Assumes that the keys of the given field array are field names and converts
* them to column names.
*
* @return array
*/
protected function _convertFieldToColumnNames(array $fields, Doctrine_ClassMetadata $class)
{
$converted = array();
foreach ($fields as $fieldName => $value) {
$converted[$class->getColumnName($fieldName)] = $value;
}
return $converted;
}
/**
* Callback that is invoked during the SQL construction process.
*/
public function getCustomJoins()
{
return array();
}
/**
* Callback that is invoked during the SQL construction process.
*/
public function getCustomFields()
{
return array();
}
public function getFieldName($columnName)
{
return $this->_mapper->getClassMetadata()->getFieldName($columnName);
}
public function getFieldNames()
{
if ($this->_fieldNames) {
return $this->_fieldNames;
}
$this->_fieldNames = $this->_mapper->getClassMetadata()->getFieldNames();
return $this->_fieldNames;
}
public function getOwningTable($fieldName)
{
return $this->_mapper->getClassMetadata();
}
abstract public function doDelete(Doctrine_Record $record);
abstract public function doInsert(Doctrine_Record $record);
abstract public function doUpdate(Doctrine_Record $record);
/**
* Inserts a row into a table.
*
* @todo This method could be used to allow mapping to secondary table(s).
* @see http://www.oracle.com/technology/products/ias/toplink/jpa/resources/toplink-jpa-annotations.html#SecondaryTable
*/
protected function _insertRow($tableName, array $data)
{
$this->_mapper->getConnection()->insert($tableName, $data);
}
/**
* Deletes rows of a table.
*
* @todo This method could be used to allow mapping to secondary table(s).
* @see http://www.oracle.com/technology/products/ias/toplink/jpa/resources/toplink-jpa-annotations.html#SecondaryTable
*/
protected function _deleteRow($tableName, array $identifierToMatch)
{
$this->_mapper->getConnection()->delete($tableName, $identifierToMatch);
}
/**
* Deletes rows of a table.
*
* @todo This method could be used to allow mapping to secondary table(s).
* @see http://www.oracle.com/technology/products/ias/toplink/jpa/resources/toplink-jpa-annotations.html#SecondaryTable
*/
protected function _updateRow($tableName, array $data, array $identifierToMatch)
{
$this->_mapper->getConnection()->update($tableName, $data, $identifierToMatch);
}
}
\ No newline at end of file
<?php
class Doctrine_Mapper_TablePerClass extends Doctrine_Mapper_Abstract
{
}
...@@ -562,7 +562,7 @@ abstract class Doctrine_Query_Abstract ...@@ -562,7 +562,7 @@ abstract class Doctrine_Query_Abstract
$array = array(); $array = array();
foreach ($this->_queryComponents as $componentAlias => $data) { foreach ($this->_queryComponents as $componentAlias => $data) {
$sqlTableAlias = $this->getSqlTableAlias($componentAlias); $sqlTableAlias = $this->getSqlTableAlias($componentAlias);
if ( ! $data['mapper'] instanceof Doctrine_Mapper_SingleTable) { if ($data['table']->getInheritanceType() != Doctrine::INHERITANCETYPE_SINGLE_TABLE) {
$array[$sqlTableAlias][] = array(); $array[$sqlTableAlias][] = array();
} else { } else {
$discCol = $data['table']->getInheritanceOption('discriminatorColumn'); $discCol = $data['table']->getInheritanceOption('discriminatorColumn');
......
...@@ -56,6 +56,11 @@ class Doctrine_Query_Registry ...@@ -56,6 +56,11 @@ class Doctrine_Query_Registry
$query = $this->_queries[$namespace][$key]; $query = $this->_queries[$namespace][$key];
} else { } else {
if ( ! isset($this->_queries[$key])) { if ( ! isset($this->_queries[$key])) {
try {
throw new Exception();
} catch (Exception $e) {
echo $e->getTraceAsString() ."<br /><br />";
}
throw new Doctrine_Query_Registry_Exception('A query with the name ' . $key . ' does not exist.'); throw new Doctrine_Query_Registry_Exception('A query with the name ' . $key . ' does not exist.');
} }
$query = $this->_queries[$key]; $query = $this->_queries[$key];
......
...@@ -31,6 +31,8 @@ Doctrine::autoload('Doctrine_Record_Abstract'); ...@@ -31,6 +31,8 @@ Doctrine::autoload('Doctrine_Record_Abstract');
* @link www.phpdoctrine.com * @link www.phpdoctrine.com
* @since 1.0 * @since 1.0
* @version $Revision$ * @version $Revision$
* @todo Remove the depdency on the ClassMetadata. All operations that involve the metadata
* should be left to the mapper.
*/ */
abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Countable, IteratorAggregate, Serializable abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Countable, IteratorAggregate, Serializable
{ {
...@@ -169,14 +171,14 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count ...@@ -169,14 +171,14 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count
*/ */
public function __construct($mapper = null, $isNewEntry = false, array $data = array()) public function __construct($mapper = null, $isNewEntry = false, array $data = array())
{ {
if (isset($mapper) && $mapper instanceof Doctrine_Mapper_Abstract) { if (isset($mapper) && $mapper instanceof Doctrine_Mapper) {
$class = get_class($this); $class = get_class($this);
$this->_mapper = Doctrine_Manager::getInstance()->getMapper($class); $this->_mapper = Doctrine_Manager::getInstance()->getMapper($class);
$this->_table = $this->_mapper->getTable(); $this->_table = $this->_mapper->getClassMetadata();
$exists = ! $isNewEntry; $exists = ! $isNewEntry;
} else { } else {
$this->_mapper = Doctrine_Manager::getInstance()->getMapper(get_class($this)); $this->_mapper = Doctrine_Manager::getInstance()->getMapper(get_class($this));
$this->_table = $this->_mapper->getTable(); $this->_table = $this->_mapper->getClassMetadata();
$exists = false; $exists = false;
} }
...@@ -193,7 +195,7 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count ...@@ -193,7 +195,7 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count
$this->_values = $this->cleanData($this->_data); $this->_values = $this->cleanData($this->_data);
$this->prepareIdentifiers($exists); $this->_extractIdentifier($exists);
if ( ! $exists) { if ( ! $exists) {
if ($count > count($this->_values)) { if ($count > count($this->_values)) {
...@@ -212,7 +214,6 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count ...@@ -212,7 +214,6 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count
} }
} }
$this->_errorStack = new Doctrine_Validator_ErrorStack(get_class($this));
$repository = $this->_mapper->getRepository(); $repository = $this->_mapper->getRepository();
$repository->add($this); $repository->add($this);
...@@ -270,8 +271,9 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count ...@@ -270,8 +271,9 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count
if ( ! $this->_mapper->getAttribute(Doctrine::ATTR_VALIDATE)) { if ( ! $this->_mapper->getAttribute(Doctrine::ATTR_VALIDATE)) {
return true; return true;
} }
// Clear the stack from any previous errors. // Clear the stack from any previous errors.
$this->_errorStack->clear(); $this->getErrorStack()->clear();
// Run validation process // Run validation process
$validator = new Doctrine_Validator(); $validator = new Doctrine_Validator();
...@@ -283,7 +285,7 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count ...@@ -283,7 +285,7 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count
$this->validateOnUpdate(); $this->validateOnUpdate();
} }
return $this->_errorStack->count() == 0 ? true : false; return $this->getErrorStack()->count() == 0 ? true : false;
} }
/** /**
...@@ -405,6 +407,9 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count ...@@ -405,6 +407,9 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count
*/ */
public function getErrorStack() public function getErrorStack()
{ {
if (is_null($this->_errorStack)) {
$this->_errorStack = new Doctrine_Validator_ErrorStack();
}
return $this->_errorStack; return $this->_errorStack;
} }
...@@ -423,7 +428,7 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count ...@@ -423,7 +428,7 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count
} }
$this->_errorStack = $stack; $this->_errorStack = $stack;
} else { } else {
return $this->_errorStack; return $this->getErrorStack();
} }
} }
...@@ -496,7 +501,7 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count ...@@ -496,7 +501,7 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count
{ {
$this->_values = array_merge($this->_values, $this->cleanData($data)); $this->_values = array_merge($this->_values, $this->cleanData($data));
$this->_data = array_merge($this->_data, $data); $this->_data = array_merge($this->_data, $data);
$this->prepareIdentifiers(true); $this->_extractIdentifier(true);
} }
/** /**
...@@ -507,7 +512,7 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count ...@@ -507,7 +512,7 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count
* @return void * @return void
* @todo Maybe better placed in the Mapper? * @todo Maybe better placed in the Mapper?
*/ */
private function prepareIdentifiers($exists = true) private function _extractIdentifier($exists = true)
{ {
switch ($this->_table->getIdentifierType()) { switch ($this->_table->getIdentifierType()) {
case Doctrine::IDENTIFIER_AUTOINC: case Doctrine::IDENTIFIER_AUTOINC:
...@@ -637,7 +642,7 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count ...@@ -637,7 +642,7 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count
$this->_mapper->getRepository()->add($this); $this->_mapper->getRepository()->add($this);
$this->cleanData($this->_data); $this->cleanData($this->_data);
$this->prepareIdentifiers($this->exists()); $this->_extractIdentifier($this->exists());
$this->postUnserialize($event); $this->postUnserialize($event);
} }
...@@ -730,7 +735,7 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count ...@@ -730,7 +735,7 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count
$this->_modified = array(); $this->_modified = array();
$this->prepareIdentifiers(); $this->_extractIdentifier();
$this->_state = Doctrine_Record::STATE_CLEAN; $this->_state = Doctrine_Record::STATE_CLEAN;
...@@ -1485,7 +1490,7 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count ...@@ -1485,7 +1490,7 @@ abstract class Doctrine_Record extends Doctrine_Record_Abstract implements Count
$this->_state = Doctrine_Record::STATE_TCLEAN; $this->_state = Doctrine_Record::STATE_TCLEAN;
$this->_modified = array(); $this->_modified = array();
} else if ($id === true) { } else if ($id === true) {
$this->prepareIdentifiers(true); $this->_extractIdentifier(true);
$this->_state = Doctrine_Record::STATE_CLEAN; $this->_state = Doctrine_Record::STATE_CLEAN;
$this->_modified = array(); $this->_modified = array();
} else { } else {
......
...@@ -5,6 +5,7 @@ ...@@ -5,6 +5,7 @@
* *
* @todo Support different drivers for loading the meta data from different sources. * @todo Support different drivers for loading the meta data from different sources.
* @package Doctrine * @package Doctrine
* @deprecated
*/ */
class Doctrine_Table_Factory class Doctrine_Table_Factory
{ {
......
...@@ -51,7 +51,7 @@ class Doctrine_Table_Repository implements Countable, IteratorAggregate ...@@ -51,7 +51,7 @@ class Doctrine_Table_Repository implements Countable, IteratorAggregate
* *
* @param Doctrine_Table $table * @param Doctrine_Table $table
*/ */
public function __construct(Doctrine_Mapper_Abstract $mapper) public function __construct($mapper)
{ {
$this->table = $mapper; $this->table = $mapper;
} }
......
...@@ -54,14 +54,14 @@ class Doctrine_Query_Registry_TestCase extends Doctrine_UnitTestCase ...@@ -54,14 +54,14 @@ class Doctrine_Query_Registry_TestCase extends Doctrine_UnitTestCase
{ {
$registry = new Doctrine_Query_Registry(); $registry = new Doctrine_Query_Registry();
$registry->add('User/all', 'SELECT u.* FROM User u'); $registry->add('User.all', 'SELECT u.* FROM User u');
$this->assertEqual($registry->get('all', 'User')->getDql(), 'SELECT u.* FROM User u'); $this->assertEqual($registry->get('User.all')->getDql(), 'SELECT u.* FROM User u');
$this->manager->setQueryRegistry($registry); $this->manager->setQueryRegistry($registry);
$user = new User(); $user = new User();
$user->getMapper()->execute('all'); $user->getMapper()->executeNamedQuery('User.all');
} }
} }
...@@ -391,15 +391,12 @@ class Doctrine_Record_TestCase extends Doctrine_UnitTestCase ...@@ -391,15 +391,12 @@ class Doctrine_Record_TestCase extends Doctrine_UnitTestCase
$this->assertEqual($user->name, "Jack Daniels"); $this->assertEqual($user->name, "Jack Daniels");
$this->assertEqual($user->created, null); $this->assertEqual($user->created, null);
$this->assertEqual($user->updated, null); $this->assertEqual($user->updated, null);
$this->assertEqual($user->getMapper()->getData(), array());
} }
public function testNewOperator() public function testNewOperator()
{ {
$table = $this->connection->getClassMetadata("User"); $table = $this->connection->getClassMetadata("User");
$this->assertEqual($this->connection->getMapper("User")->getData(), array());
$user = new User(); $user = new User();
$this->assertEqual(Doctrine_Lib::getRecordStateAsString($user->state()), Doctrine_Lib::getRecordStateAsString(Doctrine_Record::STATE_TCLEAN)); $this->assertEqual(Doctrine_Lib::getRecordStateAsString($user->state()), Doctrine_Lib::getRecordStateAsString(Doctrine_Record::STATE_TCLEAN));
$user->name = "John Locke"; $user->name = "John Locke";
......
...@@ -78,6 +78,7 @@ class Doctrine_Relation_ManyToMany2_TestCase extends Doctrine_UnitTestCase ...@@ -78,6 +78,7 @@ class Doctrine_Relation_ManyToMany2_TestCase extends Doctrine_UnitTestCase
->from('TestMovie d, d.MovieBookmarks i, i.UserVotes u, u.User c') ->from('TestMovie d, d.MovieBookmarks i, i.UserVotes u, u.User c')
->execute() ->execute()
->getFirst(); ->getFirst();
$newdata['MovieBookmarks'][0]['UserVotes'][0]['User']['name'] = 'user2'; $newdata['MovieBookmarks'][0]['UserVotes'][0]['User']['name'] = 'user2';
try { try {
$newdata->save(); $newdata->save();
......
...@@ -137,11 +137,6 @@ class Doctrine_Table_TestCase extends Doctrine_UnitTestCase ...@@ -137,11 +137,6 @@ class Doctrine_Table_TestCase extends Doctrine_UnitTestCase
$this->assertTrue($this->objTable->getConnection() instanceof Doctrine_Connection); $this->assertTrue($this->objTable->getConnection() instanceof Doctrine_Connection);
} }
public function testGetData()
{
$this->assertTrue($this->objTable->getData() == array());
}
public function testSetSequenceName() public function testSetSequenceName()
{ {
$this->objTable->sequenceName = 'test-seq'; $this->objTable->sequenceName = 'test-seq';
......
<?php <?php
class PluginSymfonyRecordTable extends Doctrine_Mapper_TablePerClass class PluginSymfonyRecordTable extends Doctrine_Mapper
{ {
} }
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment