diff --git a/lib/Cake/Model/Datasource/DboSource.php b/lib/Cake/Model/Datasource/DboSource.php index c3b109dab..1218c3829 100644 --- a/lib/Cake/Model/Datasource/DboSource.php +++ b/lib/Cake/Model/Datasource/DboSource.php @@ -1112,7 +1112,7 @@ class DboSource extends DataSource { $db->queryAssociation($model, $linkModel, $type, $assoc, $assocData, $array, true, $resultSet, $model->recursive - 1, $stack); unset($db); - if ($type === 'hasMany') { + if ($type === 'hasMany' || $type === 'hasAndBelongsToMany') { $filtered[] = $assoc; } } @@ -1138,6 +1138,9 @@ class DboSource extends DataSource { * @return array Array of results that have been filtered through $model->afterFind */ protected function _filterResults(&$results, Model $model, $filtered = array()) { + if (!is_array($results)) { + return array(); + } $current = reset($results); if (!is_array($current)) { return array(); @@ -1252,6 +1255,9 @@ class DboSource extends DataSource { } else { $fetch = null; } + if ($queryData['callbacks'] === true || $queryData['callbacks'] === 'after') { + $this->_filterResults($fetch, $model); + } } $modelAlias = $model->alias; @@ -1312,7 +1318,7 @@ class DboSource extends DataSource { } else { $this->_mergeAssociation($row, $fetch, $association, $type, $selfJoin); } - if (isset($row[$association])) { + if (isset($row[$association]) && $type !== 'hasAndBelongsToMany') { $row[$association] = $linkModel->afterFind($row[$association], false); } } else { diff --git a/lib/Cake/Test/Case/Model/ModelIntegrationTest.php b/lib/Cake/Test/Case/Model/ModelIntegrationTest.php index cbe20026c..4f2e81f06 100644 --- a/lib/Cake/Test/Case/Model/ModelIntegrationTest.php +++ b/lib/Cake/Test/Case/Model/ModelIntegrationTest.php @@ -1706,7 +1706,8 @@ class ModelIntegrationTest extends BaseModelTest { 'body' => 'First Post Body', 'published' => 'Y', 'created' => '2007-03-18 10:39:23', - 'updated' => '2007-03-18 10:41:31' + 'updated' => '2007-03-18 10:41:31', + 'afterFind' => 'Successfully added by AfterFind' ), 'Something' => array( array( @@ -1722,7 +1723,8 @@ class ModelIntegrationTest extends BaseModelTest { 'something_else_id' => '1', 'doomed' => true, 'created' => '2007-03-18 10:43:23', - 'updated' => '2007-03-18 10:45:31' + 'updated' => '2007-03-18 10:45:31', + 'afterFind' => 'Successfully added by AfterFind' )))), array( 'SomethingElse' => array( @@ -1731,7 +1733,8 @@ class ModelIntegrationTest extends BaseModelTest { 'body' => 'Second Post Body', 'published' => 'Y', 'created' => '2007-03-18 10:41:23', - 'updated' => '2007-03-18 10:43:31' + 'updated' => '2007-03-18 10:43:31', + 'afterFind' => 'Successfully added by AfterFind' ), 'Something' => array( array( @@ -1747,7 +1750,8 @@ class ModelIntegrationTest extends BaseModelTest { 'something_else_id' => '2', 'doomed' => true, 'created' => '2007-03-18 10:39:23', - 'updated' => '2007-03-18 10:41:31' + 'updated' => '2007-03-18 10:41:31', + 'afterFind' => 'Successfully added by AfterFind' )))), array( 'SomethingElse' => array( @@ -1756,7 +1760,8 @@ class ModelIntegrationTest extends BaseModelTest { 'body' => 'Third Post Body', 'published' => 'Y', 'created' => '2007-03-18 10:43:23', - 'updated' => '2007-03-18 10:45:31' + 'updated' => '2007-03-18 10:45:31', + 'afterFind' => 'Successfully added by AfterFind' ), 'Something' => array( array( @@ -1772,7 +1777,8 @@ class ModelIntegrationTest extends BaseModelTest { 'something_else_id' => '3', 'doomed' => false, 'created' => '2007-03-18 10:41:23', - 'updated' => '2007-03-18 10:43:31' + 'updated' => '2007-03-18 10:43:31', + 'afterFind' => 'Successfully added by AfterFind' ))))); $this->assertEquals($expected, $result); @@ -1798,8 +1804,11 @@ class ModelIntegrationTest extends BaseModelTest { 'JoinThing' => array( 'doomed' => true, 'something_id' => '1', - 'something_else_id' => '2' - )))), + 'something_else_id' => '2', + 'afterFind' => 'Successfully added by AfterFind' + ), + 'afterFind' => 'Successfully added by AfterFind' + ))), array( 'Something' => array( 'id' => '2', @@ -1820,8 +1829,11 @@ class ModelIntegrationTest extends BaseModelTest { 'JoinThing' => array( 'doomed' => false, 'something_id' => '2', - 'something_else_id' => '3' - )))), + 'something_else_id' => '3', + 'afterFind' => 'Successfully added by AfterFind' + ), + 'afterFind' => 'Successfully added by AfterFind' + ))), array( 'Something' => array( 'id' => '3', @@ -1842,8 +1854,11 @@ class ModelIntegrationTest extends BaseModelTest { 'JoinThing' => array( 'doomed' => true, 'something_id' => '3', - 'something_else_id' => '1' - ))))); + 'something_else_id' => '1', + 'afterFind' => 'Successfully added by AfterFind' + ), + 'afterFind' => 'Successfully added by AfterFind' + )))); $this->assertEquals($expected, $result); $result = $TestModel->findById(1); @@ -1867,8 +1882,11 @@ class ModelIntegrationTest extends BaseModelTest { 'JoinThing' => array( 'doomed' => true, 'something_id' => '1', - 'something_else_id' => '2' - )))); + 'something_else_id' => '2', + 'afterFind' => 'Successfully added by AfterFind' + ), + 'afterFind' => 'Successfully added by AfterFind' + ))); $this->assertEquals($expected, $result); $expected = $TestModel->findById(1); @@ -1908,8 +1926,10 @@ class ModelIntegrationTest extends BaseModelTest { 'JoinThing' => array( 'doomed' => true, 'something_id' => '1', - 'something_else_id' => '1' - ) + 'something_else_id' => '1', + 'afterFind' => 'Successfully added by AfterFind' + ), + 'afterFind' => 'Successfully added by AfterFind' ), array( 'id' => '2', @@ -1921,8 +1941,10 @@ class ModelIntegrationTest extends BaseModelTest { 'JoinThing' => array( 'doomed' => true, 'something_id' => '1', - 'something_else_id' => '2' - ) + 'something_else_id' => '2', + 'afterFind' => 'Successfully added by AfterFind' + ), + 'afterFind' => 'Successfully added by AfterFind' ), array( 'id' => '3', @@ -1934,10 +1956,12 @@ class ModelIntegrationTest extends BaseModelTest { 'JoinThing' => array( 'doomed' => false, 'something_id' => '1', - 'something_else_id' => '3') - ) + 'something_else_id' => '3', + 'afterFind' => 'Successfully added by AfterFind' + ), + 'afterFind' => 'Successfully added by AfterFind' ) - ); + )); $this->assertEquals(self::date(), $result['Something']['updated']); unset($result['Something']['updated']); $this->assertEquals($expected, $result); diff --git a/lib/Cake/Test/Case/Model/ModelReadTest.php b/lib/Cake/Test/Case/Model/ModelReadTest.php index 365da93ac..54796c9b6 100644 --- a/lib/Cake/Test/Case/Model/ModelReadTest.php +++ b/lib/Cake/Test/Case/Model/ModelReadTest.php @@ -6303,7 +6303,6 @@ class ModelReadTest extends BaseModelTest { $TestModel = new User(); $TestModel->cacheQueries = false; $TestModel->order = null; - $expected = array( 'conditions' => array( 'user' => 'larry' @@ -6849,9 +6848,7 @@ class ModelReadTest extends BaseModelTest { 'user' => 'mariano' )); $this->assertEquals('mariano', $result); - $TestModel->order = null; - $result = $TestModel->field('COUNT(*) AS count', true); $this->assertEquals(4, $result); @@ -6909,7 +6906,6 @@ class ModelReadTest extends BaseModelTest { $Article = new Article(); $Article->order = null; $Article->recursive = -1; - $expected = count($Article->find('all', array( 'fields' => array('Article.user_id'), 'group' => 'Article.user_id') @@ -7765,7 +7761,6 @@ class ModelReadTest extends BaseModelTest { 'limit' => 1 )); $this->assertEquals(2, $result['Post']['id']); - $Post->order = null; $Post->virtualFields = array('other_field' => 'Post.id + 1'); @@ -7994,4 +7989,247 @@ class ModelReadTest extends BaseModelTest { $this->assertEquals(1, count($result)); } +/** + * test after find callback on related model + * + * @return void + */ + public function testRelatedAfterFindCallback() { + $this->loadFixtures('Something', 'SomethingElse', 'JoinThing'); + $Something = new Something(); + + $Something->bindModel(array( + 'hasMany' => array( + 'HasMany' => array( + 'className' => 'JoinThing', + 'foreignKey' => 'something_id' + ) + ), + 'hasOne' => array( + 'HasOne' => array( + 'className' => 'JoinThing', + 'foreignKey' => 'something_id' + ) + ) + )); + + $results = $Something->find('all'); + + $expected = array( + array( + 'Something' => array( + 'id' => '1', + 'title' => 'First Post', + 'body' => 'First Post Body', + 'published' => 'Y', + 'created' => '2007-03-18 10:39:23', + 'updated' => '2007-03-18 10:41:31' + ), + 'HasOne' => array( + 'id' => '1', + 'something_id' => '1', + 'something_else_id' => '2', + 'doomed' => true, + 'created' => '2007-03-18 10:39:23', + 'updated' => '2007-03-18 10:41:31', + 'afterFind' => 'Successfully added by AfterFind' + ), + 'HasMany' => array( + array( + 'id' => '1', + 'something_id' => '1', + 'something_else_id' => '2', + 'doomed' => true, + 'created' => '2007-03-18 10:39:23', + 'updated' => '2007-03-18 10:41:31', + 'afterFind' => 'Successfully added by AfterFind' + ) + ), + 'SomethingElse' => array( + array( + 'id' => '2', + 'title' => 'Second Post', + 'body' => 'Second Post Body', + 'published' => 'Y', + 'created' => '2007-03-18 10:41:23', + 'updated' => '2007-03-18 10:43:31', + 'afterFind' => 'Successfully added by AfterFind', + 'JoinThing' => array( + 'doomed' => true, + 'something_id' => '1', + 'something_else_id' => '2', + 'afterFind' => 'Successfully added by AfterFind' + ) + ) + ) + ), + array( + 'Something' => array( + 'id' => '2', + 'title' => 'Second Post', + 'body' => 'Second Post Body', + 'published' => 'Y', + 'created' => '2007-03-18 10:41:23', + 'updated' => '2007-03-18 10:43:31' + ), + 'HasOne' => array( + 'id' => '2', + 'something_id' => '2', + 'something_else_id' => '3', + 'doomed' => false, + 'created' => '2007-03-18 10:41:23', + 'updated' => '2007-03-18 10:43:31', + 'afterFind' => 'Successfully added by AfterFind' + ), + 'HasMany' => array( + array( + 'id' => '2', + 'something_id' => '2', + 'something_else_id' => '3', + 'doomed' => false, + 'created' => '2007-03-18 10:41:23', + 'updated' => '2007-03-18 10:43:31', + 'afterFind' => 'Successfully added by AfterFind' + ) + ), + 'SomethingElse' => array( + array( + 'id' => '3', + 'title' => 'Third Post', + 'body' => 'Third Post Body', + 'published' => 'Y', + 'created' => '2007-03-18 10:43:23', + 'updated' => '2007-03-18 10:45:31', + 'afterFind' => 'Successfully added by AfterFind', + 'JoinThing' => array( + 'doomed' => false, + 'something_id' => '2', + 'something_else_id' => '3', + 'afterFind' => 'Successfully added by AfterFind' + ) + ) + ) + ), + array( + 'Something' => array( + 'id' => '3', + 'title' => 'Third Post', + 'body' => 'Third Post Body', + 'published' => 'Y', + 'created' => '2007-03-18 10:43:23', + 'updated' => '2007-03-18 10:45:31' + ), + 'HasOne' => array( + 'id' => '3', + 'something_id' => '3', + 'something_else_id' => '1', + 'doomed' => true, + 'created' => '2007-03-18 10:43:23', + 'updated' => '2007-03-18 10:45:31', + 'afterFind' => 'Successfully added by AfterFind' + ), + 'HasMany' => array( + array( + 'id' => '3', + 'something_id' => '3', + 'something_else_id' => '1', + 'doomed' => true, + 'created' => '2007-03-18 10:43:23', + 'updated' => '2007-03-18 10:45:31', + 'afterFind' => 'Successfully added by AfterFind' + ) + ), + 'SomethingElse' => array( + array( + 'id' => '1', + 'title' => 'First Post', + 'body' => 'First Post Body', + 'published' => 'Y', + 'created' => '2007-03-18 10:39:23', + 'updated' => '2007-03-18 10:41:31', + 'afterFind' => 'Successfully added by AfterFind', + 'JoinThing' => array( + 'doomed' => true, + 'something_id' => '3', + 'something_else_id' => '1', + 'afterFind' => 'Successfully added by AfterFind' + ) + ) + ) + ) + ); + $this->assertEquals($expected, $results, 'Model related with has* afterFind callback fails'); + + $JoinThing = new JoinThing(); + $JoinThing->unbindModel(array( + 'belongsTo' => array( + 'Something' + ) + )); + $results = $JoinThing->find('all'); + + $expected = array( + array( + 'JoinThing' => array( + 'id' => '1', + 'something_id' => '1', + 'something_else_id' => '2', + 'doomed' => true, + 'created' => '2007-03-18 10:39:23', + 'updated' => '2007-03-18 10:41:31', + 'afterFind' => 'Successfully added by AfterFind' + ), + 'SomethingElse' => array( + 'id' => '2', + 'title' => 'Second Post', + 'body' => 'Second Post Body', + 'published' => 'Y', + 'created' => '2007-03-18 10:41:23', + 'updated' => '2007-03-18 10:43:31', + 'afterFind' => 'Successfully added by AfterFind' + ) + ), + array( + 'JoinThing' => array( + 'id' => '2', + 'something_id' => '2', + 'something_else_id' => '3', + 'doomed' => false, + 'created' => '2007-03-18 10:41:23', + 'updated' => '2007-03-18 10:43:31', + 'afterFind' => 'Successfully added by AfterFind' + ), + 'SomethingElse' => array( + 'id' => '3', + 'title' => 'Third Post', + 'body' => 'Third Post Body', + 'published' => 'Y', + 'created' => '2007-03-18 10:43:23', + 'updated' => '2007-03-18 10:45:31', + 'afterFind' => 'Successfully added by AfterFind' + ) + ), + array( + 'JoinThing' => array( + 'id' => '3', + 'something_id' => '3', + 'something_else_id' => '1', + 'doomed' => true, + 'created' => '2007-03-18 10:43:23', + 'updated' => '2007-03-18 10:45:31', + 'afterFind' => 'Successfully added by AfterFind' + ), + 'SomethingElse' => array( + 'id' => '1', + 'title' => 'First Post', + 'body' => 'First Post Body', + 'published' => 'Y', + 'created' => '2007-03-18 10:39:23', + 'updated' => '2007-03-18 10:41:31', + 'afterFind' => 'Successfully added by AfterFind' + ) + ) + ); + $this->assertEquals($expected, $results, 'Model related with belongsTo afterFind callback fails'); + } } diff --git a/lib/Cake/Test/Case/Model/models.php b/lib/Cake/Test/Case/Model/models.php index 3655ee798..f92bcb9e0 100644 --- a/lib/Cake/Test/Case/Model/models.php +++ b/lib/Cake/Test/Case/Model/models.php @@ -1501,6 +1501,23 @@ class SomethingElse extends CakeTestModel { * @var array */ public $hasAndBelongsToMany = array('Something' => array('with' => 'JoinThing')); + +/** + * afterFind callBack + * + * @param array $results + * @param bool $primary + * @return array + */ + public function afterFind($results, $primary = false) { + foreach ($results as $key => $result) { + if (!empty($result[$this->alias]) && is_array($result[$this->alias])) { + $results[$key][$this->alias]['afterFind'] = 'Successfully added by AfterFind'; + } + } + return $results; + } + } /** @@ -1523,6 +1540,23 @@ class JoinThing extends CakeTestModel { * @var array */ public $belongsTo = array('Something', 'SomethingElse'); + +/** + * afterFind callBack + * + * @param array $results + * @param bool $primary + * @return array + */ + public function afterFind($results, $primary = false) { + foreach ($results as $key => $result) { + if (!empty($result[$this->alias]) && is_array($result[$this->alias])) { + $results[$key][$this->alias]['afterFind'] = 'Successfully added by AfterFind'; + } + } + return $results; + } + } /**