Skip to content

Commit 3d6c518

Browse files
authored
Merge pull request #68 from baopham/fix-composite-condition
Fix composite condition where conditions are not EQ
2 parents 72bc98b + e0234be commit 3d6c518

File tree

4 files changed

+88
-24
lines changed

4 files changed

+88
-24
lines changed

src/ComparisonOperator.php

Lines changed: 31 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -7,20 +7,32 @@
77
*/
88
class ComparisonOperator
99
{
10+
const EQ = 'EQ';
11+
const GT = 'GT';
12+
const GE = 'GE';
13+
const LT = 'LT';
14+
const LE = 'LE';
15+
const IN = 'IN';
16+
const NE = 'NE';
17+
const BEGINS_WITH = 'BEGINS_WITH';
18+
const BETWEEN = 'BETWEEN';
19+
const NOT_CONTAINS = 'NOT_CONTAINS';
20+
const CONTAINS = 'CONTAINS';
21+
1022
public static function getOperatorMapping()
1123
{
1224
return [
13-
'=' => 'EQ',
14-
'>' => 'GT',
15-
'>=' => 'GE',
16-
'<' => 'LT',
17-
'<=' => 'LE',
18-
'in' => 'IN',
19-
'!=' => 'NE',
20-
'begins_with' => 'BEGINS_WITH',
21-
'between' => 'BETWEEN',
22-
'not_contains' => 'NOT_CONTAINS',
23-
'contains' => 'CONTAINS',
25+
'=' => static::EQ,
26+
'>' => static::GT,
27+
'>=' => static::GE,
28+
'<' => static::LT,
29+
'<=' => static::LE,
30+
'in' => static::IN,
31+
'!=' => static::NE,
32+
'begins_with' => static::BEGINS_WITH,
33+
'between' => static::BETWEEN,
34+
'not_contains' => static::NOT_CONTAINS,
35+
'contains' => static::CONTAINS,
2436
];
2537
}
2638

@@ -51,17 +63,17 @@ public static function getQuerySupportedOperators($isRangeKey = false)
5163
{
5264
if ($isRangeKey) {
5365
return [
54-
'EQ',
55-
'LE',
56-
'LT',
57-
'GE',
58-
'GT',
59-
'BEGINS_WITH',
60-
'BETWEEN',
66+
static::EQ,
67+
static::LE,
68+
static::LT,
69+
static::GE,
70+
static::GT,
71+
static::BEGINS_WITH,
72+
static::BETWEEN,
6173
];
6274
}
6375

64-
return ['EQ'];
76+
return [static::EQ];
6577
}
6678

6779
public static function isValidQueryOperator($operator, $isRangeKey = false)

src/DynamoDbQueryBuilder.php

Lines changed: 29 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -210,9 +210,11 @@ public function count()
210210
protected function getAll($columns = [], $limit = -1, $use_iterator = true)
211211
{
212212
if ($conditionValue = $this->conditionsContainKey()) {
213-
$item = $this->find($conditionValue, $columns);
213+
if ($this->conditionsAreExactSearch()) {
214+
$item = $this->find($conditionValue, $columns);
214215

215-
return new Collection([$item]);
216+
return new Collection([$item]);
217+
}
216218
}
217219

218220
$query = [
@@ -260,6 +262,9 @@ protected function getAll($columns = [], $limit = -1, $use_iterator = true)
260262
$query['QueryFilter'] = $nonKeyConditions;
261263
}
262264
}
265+
} else if ($this->conditionsContainKey()) {
266+
$op = 'Query';
267+
$query['KeyConditions'] = $this->where;
263268
}
264269

265270
if ($op === 'Scan') {
@@ -270,7 +275,7 @@ protected function getAll($columns = [], $limit = -1, $use_iterator = true)
270275
if ($use_iterator) {
271276
$iterator = $this->client->getIterator($op, $query);
272277
} else {
273-
if ($op == 'Scan') {
278+
if ($op === 'Scan') {
274279
$res = $this->client->scan($query);
275280
} else {
276281
$res = $this->client->query($query);
@@ -293,10 +298,31 @@ protected function getAll($columns = [], $limit = -1, $use_iterator = true)
293298
return new Collection($results);
294299
}
295300

301+
protected function conditionsAreExactSearch()
302+
{
303+
if (empty($this->where)) {
304+
return false;
305+
}
306+
307+
foreach ($this->where as $condition) {
308+
if (array_get($condition, 'ComparisonOperator') !== ComparisonOperator::EQ) {
309+
return false;
310+
}
311+
}
312+
313+
return true;
314+
}
315+
296316
/**
297317
* Check if conditions "where" contain primary key or composite key.
298318
* For composite key, it will return false if the conditions don't have all composite key.
299319
*
320+
* For example:
321+
* Consider a composite key condition:
322+
* $model->where('partition_key', 'foo')->where('sort_key', 'bar')
323+
* We return ['partition_key' => 'foo', 'sort_key' => 'bar'] since the conditions
324+
* contain all the composite key.
325+
*
300326
* @return array|bool the condition value
301327
*/
302328
protected function conditionsContainKey()

tests/DynamoDbCompositeModelTest.php

Lines changed: 27 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -123,7 +123,7 @@ public function testDeleteRecord()
123123
$this->assertArrayNotHasKey('Item', $record);
124124
}
125125

126-
public function testLookingUpByKey()
126+
public function testLookUpByKey()
127127
{
128128
$this->seed();
129129

@@ -139,6 +139,32 @@ public function testLookingUpByKey()
139139
$this->assertEquals($this->testModel->unmarshalItem($item), $foundItems->first()->toArray());
140140
}
141141

142+
public function testSearchByHashAndSortKey()
143+
{
144+
$partitionKey = 'foo';
145+
$item1 = $this->seed([
146+
'id' => ['S' => $partitionKey],
147+
'id2' => ['S' => 'bar_1']
148+
]);
149+
$item2 = $this->seed([
150+
'id' => ['S' => $partitionKey],
151+
'id2' => ['S' => 'bar_2']
152+
]);
153+
$this->seed([
154+
'id' => ['S' => 'other'],
155+
'id2' => ['S' => 'foo_1']
156+
]);
157+
158+
$foundItems = $this->testModel
159+
->where('id', $partitionKey)
160+
->where('id2', 'begins_with', 'bar')
161+
->get();
162+
163+
$this->assertEquals(2, $foundItems->count());
164+
$this->assertEquals($this->testModel->unmarshalItem($item1), $foundItems->first()->toArray());
165+
$this->assertEquals($this->testModel->unmarshalItem($item2), $foundItems->last()->toArray());
166+
}
167+
142168
public function testStaticMethods()
143169
{
144170
$item = $this->seed(['name' => ['S' => 'Foo'], 'description' => ['S' => 'Bar']]);

tests/DynamoDbModelTest.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -281,7 +281,7 @@ public function testChainedMethods()
281281
$this->assertEquals($this->testModel->unmarshalItem($secondItem), $foundItems->first()->toArray());
282282
}
283283

284-
public function testLookingUpByKey()
284+
public function testLookUpByKey()
285285
{
286286
$this->seed();
287287

0 commit comments

Comments
 (0)