Permalink
Browse files

The `'joined'` strategy now lazy load primary keys when needed.

  • Loading branch information...
1 parent 16969a8 commit c2ebb02706eb55cd57a3bb59c2ec48f5426c2389 @jails jails committed Dec 19, 2012
Showing with 27 additions and 17 deletions.
  1. +18 −11 data/source/Database.php
  2. +9 −6 tests/cases/data/source/DatabaseTest.php
View
@@ -182,7 +182,7 @@ public function __construct(array $config = array()) {
$with = $context->with();
- $strategy = function($me, $model, $tree, $path, $from, $needPks) use ($self, $context, $with) {
+ $strategy = function($me, $model, $tree, $path, $from, &$deps) use ($self, $context, $with) {
foreach ($tree as $name => $childs) {
if (!$rel = $model::relations($name)) {
throw new QueryException("Model relationship `{$name}` not found.");
@@ -205,9 +205,8 @@ public function __construct(array $config = array()) {
}
$to = $context->alias($alias, $relPath);
- if ($needPks) {
- $context->fields(array($to => (array) $model::meta('key')));
- }
+ $deps[$to] = $deps[$from];
+ $deps[$to][] = $from;
if ($context->relationships($relPath) === null) {
$context->relationships($relPath, array(
@@ -221,19 +220,27 @@ public function __construct(array $config = array()) {
}
if (!empty($childs)) {
- $me($me, $rel->to(), $childs, $relPath, $to, $needPks);
+ $me($me, $rel->to(), $childs, $relPath, $to, $deps);
}
}
};
$tree = Set::expand(Set::normalize(array_keys($with)));
$alias = $context->alias();
- $needPks = false;
- if ($context->fields()) {
- $needPks = true;
- $context->fields(array($alias => (array) $model::meta('key')));
+ $deps = array($alias => array());
+ $strategy($strategy, $model, $tree, '', $alias, $deps);
+
+ $models = $context->models();
+ foreach ($context->fields() as $field) {
+ list($alias, $field) = $self->invokeMethod('_splitFieldname', array($field));
+ $alias = $alias ?: $field;
+ if ($alias && isset($models[$alias])) {
+ foreach ($deps[$alias] as $depAlias) {
+ $depModel = $models[$depAlias];
+ $context->fields(array($depAlias => (array) $depModel::meta('key')));
+ }
+ }
}
- $strategy($strategy, $model, $tree, '', $context->alias(), $needPks);
},
'nested' => function($self, $model, $context) {
throw new QueryException("This strategy is not yet implemented.");
@@ -322,7 +329,7 @@ public function name($name) {
*/
protected function _splitFieldname($field) {
if (is_string($field)) {
- if (preg_match('/^[a-z0-9_-]+\.[a-z0-9_-]+$/i', $field)) {
+ if (preg_match('/^[a-z0-9_-]+\.([a-z0-9_-]+|\*)$/i', $field)) {
return explode('.', $field, 2);
}
}
@@ -181,7 +181,7 @@ public function testSchema() {
$options['fields'] = array('id', 'title');
$result = $this->db->schema(new Query($options));
- $expected = array($modelName => $options['fields'], 'MockDatabaseComment' => array('id'));
+ $expected = array($modelName => $options['fields']);
$this->assertEqual($expected, $result);
$options['fields'] = array(
@@ -192,7 +192,7 @@ public function testSchema() {
$result = $this->db->schema(new Query($options));
$expected = array(
$modelName => array('id', 'title'),
- 'MockDatabaseComment' => array('body', 'id')
+ 'MockDatabaseComment' => array('body')
);
$this->assertEqual($expected, $result);
@@ -203,7 +203,7 @@ public function testSchema() {
$result = $this->db->schema(new Query($options));
$expected = array(
$modelName => array('id', 'title'),
- 'MockDatabaseComment' => array('body', 'created', 'id')
+ 'MockDatabaseComment' => array('body', 'created')
);
$this->assertEqual($expected, $result);
@@ -1154,6 +1154,9 @@ public function testsplitFieldname() {
$result = $this->db->invokeMethod('_splitFieldname', array('lower(Alias.fieldname)'));
$this->assertEqual(array(null, 'lower(Alias.fieldname)'), $result);
+
+ $result = $this->db->invokeMethod('_splitFieldname', array('Alias.*'));
+ $this->assertEqual(array('Alias', '*'), $result);
}
public function testOn() {
@@ -1407,7 +1410,7 @@ public function testExportedFieldsWithJoinedStrategy() {
'with' => array('Image.ImageTag.Tag')
));
$result = $query->export($this->db);
- $expected = '{Gallery}.{id}, {Image}.{id}, {ImageTag}.{id}, {Tag}.{id}';
+ $expected = '{Gallery}.{id}';
$this->assertEqual($expected, $result['fields']);
$query = new Query(array(
@@ -1453,7 +1456,7 @@ public function testExportedFieldsWithJoinedStrategyAndRecursiveRelation() {
'with' => array('Parent.Parent')
));
$result = $query->export($this->db);
- $expected = '{Parent}.{name}, {Parent}.{id}, {Gallery}.{id}, {Parent__2}.{id}';
+ $expected = '{Parent}.{name}, {Gallery}.{id}';
$this->assertEqual($expected, $result['fields']);
$query = new Query(array(
@@ -1462,7 +1465,7 @@ public function testExportedFieldsWithJoinedStrategyAndRecursiveRelation() {
'with' => array('Parent.Parent' => array('alias' => 'ParentOfParent'))
));
$result = $query->export($this->db);
- $expected = '{ParentOfParent}.{name}, {ParentOfParent}.{id}, {Gallery}.{id}, {Parent}.{id}';
+ $expected = '{ParentOfParent}.{name}, {Gallery}.{id}, {Parent}.{id}';
$this->assertEqual($expected, $result['fields']);
}

0 comments on commit c2ebb02

Please sign in to comment.