Browse Source

Fixed activequery select issue.

tags/2.0.0-beta
Qiang Xue 11 years ago
parent
commit
39667aa6b7
  1. 51
      framework/db/QueryBuilder.php
  2. 7
      framework/db/oci/QueryBuilder.php
  3. 2
      tests/unit/framework/db/ActiveRecordTest.php

51
framework/db/QueryBuilder.php

@ -65,18 +65,7 @@ class QueryBuilder extends \yii\base\Object
public function build($query, $params = [])
{
$params = empty($params) ? $query->params : array_merge($params, $query->params);
$select = $query->select;
$from = $query->from;
if ($from === null && $query instanceof ActiveQuery) {
/** @var ActiveRecord $modelClass */
$modelClass = $query->modelClass;
$tableName = $modelClass::tableName();
$from = [$tableName];
if ($select === null && !empty($query->join)) {
$select = ["$tableName.*"];
}
}
list ($select, $from) = $this->adjustSelectFrom($query);
$clauses = [
$this->buildSelect($select, $params, $query->distinct, $query->selectOption),
@ -100,6 +89,44 @@ class QueryBuilder extends \yii\base\Object
}
/**
* Adjusts the select and from parts of the query when it is an ActiveQuery.
* When ActiveQuery does not specify "from", or if it is a join query without explicit "select",
* certain adjustments need to be made. This method is put here so that QueryBuilder can
* support sub-queries.
* @param Query $query
* @return array the select and from parts.
*/
protected function adjustSelectFrom($query)
{
$select = $query->select;
$from = $query->from;
if ($query instanceof ActiveQuery && (empty($select) || empty($from))) {
/** @var ActiveRecord $modelClass */
$modelClass = $query->modelClass;
$tableName = $modelClass::tableName();
if (empty($from)) {
$from = [$tableName];
}
if (empty($select) && !empty($query->join)) {
foreach ((array)$from as $alias => $table) {
if (is_string($alias)) {
$select = ["$alias.*"];
} elseif (is_string($table)) {
if (preg_match('/^(.*?)\s+({{\w+}}|\w+)$/', $table, $matches)) {
$alias = $matches[2];
} else {
$alias = $tableName;
}
$select = ["$alias.*"];
}
break;
}
}
}
return [$select, $from];
}
/**
* Creates an INSERT SQL statement.
* For example,
*

7
framework/db/oci/QueryBuilder.php

@ -8,6 +8,8 @@
namespace yii\db\oci;
use yii\base\InvalidParamException;
use yii\db\ActiveQuery;
use yii\db\ActiveRecord;
/**
* QueryBuilder is the query builder for Oracle databases.
@ -26,10 +28,11 @@ class QueryBuilder extends \yii\db\QueryBuilder
public function build($query, $params = [])
{
$params = empty($params) ? $query->params : array_merge($params, $query->params);
list ($select, $from) = $this->adjustSelectFrom($query);
$clauses = [
$this->buildSelect($query->select, $params, $query->distinct, $query->selectOption),
$this->buildFrom($query->from, $params),
$this->buildSelect($select, $params, $query->distinct, $query->selectOption),
$this->buildFrom($from, $params),
$this->buildJoin($query->join, $params),
$this->buildWhere($query->where, $params),
$this->buildGroupBy($query->groupBy),

2
tests/unit/framework/db/ActiveRecordTest.php

@ -413,7 +413,7 @@ class ActiveRecordTest extends DatabaseTestCase
'items' => function ($q) {
$q->from(['items' => 'tbl_item']);
},
])->one();
])->orderBy('tbl_order.id')->one();
}
public function testJoinWithAndScope()

Loading…
Cancel
Save