Skip to content
This repository was archived by the owner on Jan 24, 2024. It is now read-only.

Commit 626b7fc

Browse files
authored
Merge pull request #67 from roxblnfk/feature/order-by-ignore-dublicates
SelectQuery: `orderBy` twice by same field
2 parents 0e163b4 + bf9f357 commit 626b7fc

File tree

2 files changed

+49
-5
lines changed

2 files changed

+49
-5
lines changed

src/Query/SelectQuery.php

Lines changed: 19 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -52,7 +52,7 @@ class SelectQuery extends ActiveQuery implements
5252
/** @var array */
5353
protected $columns = ['*'];
5454

55-
/** @var array */
55+
/** @var string[][]|FragmentInterface[][] */
5656
protected $orderBy = [];
5757

5858
/** @var array */
@@ -165,18 +165,32 @@ public function forUpdate(): SelectQuery
165165
public function orderBy($expression, $direction = self::SORT_ASC): SelectQuery
166166
{
167167
if (!is_array($expression)) {
168-
$this->orderBy[] = [$expression, $direction];
169-
168+
$this->addOrder($expression, $direction);
170169
return $this;
171170
}
172171

173172
foreach ($expression as $nested => $dir) {
174-
$this->orderBy[] = [$nested, $dir];
173+
$this->addOrder($nested, $dir);
175174
}
176175

177176
return $this;
178177
}
179178

179+
/**
180+
* @param string|FragmentInterface $field
181+
* @param string $order Sorting direction, ASC|DESC.
182+
* @return self|$this
183+
*/
184+
private function addOrder($field, string $order): SelectQuery
185+
{
186+
if (!is_string($field)) {
187+
$this->orderBy[] = [$field, $order];
188+
} elseif (!array_key_exists($field, $this->orderBy)) {
189+
$this->orderBy[$field] = [$field, $order];
190+
}
191+
return $this;
192+
}
193+
180194
/**
181195
* Column or expression to group query by.
182196
*
@@ -420,7 +434,7 @@ public function getTokens(): array
420434
'where' => $this->whereTokens,
421435
'having' => $this->havingTokens,
422436
'groupBy' => $this->groupBy,
423-
'orderBy' => $this->orderBy,
437+
'orderBy' => array_values($this->orderBy),
424438
'limit' => $this->limit,
425439
'offset' => $this->offset,
426440
'union' => $this->unionTokens,

tests/Database/SelectQueryTest.php

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -815,6 +815,36 @@ public function testOrderByDesc3(): void
815815
);
816816
}
817817

818+
public function testOrderByTwiceBySameName(): void
819+
{
820+
$select = $this->database
821+
->select()
822+
->from(['users'])
823+
->where(['name' => 'Anton'])
824+
->orderBy('name', 'DESC')
825+
->orderBy('name', 'ASC');
826+
827+
$this->assertSameQuery(
828+
'SELECT * FROM {users} WHERE {name} = ? ORDER BY {name} DESC',
829+
$select
830+
);
831+
}
832+
833+
public function testOrderByTwiceBySameNameArray(): void
834+
{
835+
$select = $this->database
836+
->select()
837+
->from(['users'])
838+
->where(['name' => 'Anton'])
839+
->orderBy('name', 'DESC')
840+
->orderBy(['name' => 'ASC', 'foo' => 'DESC']);
841+
842+
$this->assertSameQuery(
843+
'SELECT * FROM {users} WHERE {name} = ? ORDER BY {name} DESC, {foo} DESC',
844+
$select
845+
);
846+
}
847+
818848
public function testMultipleOrderBy(): void
819849
{
820850
$select = $this->database

0 commit comments

Comments
 (0)