Completed
Push — master ( 0da2c4...27db78 )
by François-Xavier
03:00
created

QueryTest   A

Complexity

Total Complexity 30

Size/Duplication

Total Lines 603
Duplicated Lines 18.57 %

Coupling/Cohesion

Components 2
Dependencies 16

Importance

Changes 0
Metric Value
wmc 30
lcom 2
cbo 16
dl 112
loc 603
rs 9.997
c 0
b 0
f 0

28 Methods

Rating   Name   Duplication   Size   Complexity  
A testRawQuery() 11 11 1
A testSuggestShouldNotRemoveOtherParameters() 0 16 1
A testArrayQuery() 0 17 1
A testSetSort() 0 43 1
A testAddSort() 0 8 1
A testSetTrackScores() 0 8 1
A testSetRawQuery() 0 9 1
A testSetStoredFields() 0 13 1
A testGetQuery() 0 17 2
A testSetQueryToArrayCast() 14 14 1
A testNotCloneInnerObjects() 0 13 1
A testSetQueryToArrayChangeQuery() 0 14 1
A testSetScriptFieldsToArrayCast() 0 15 1
A testAddScriptFieldsToArrayCast() 14 14 1
A testAddScriptFieldToExistingScriptFields() 0 21 1
A testAddAggregationToArrayCast() 15 15 1
A testSetSuggestToArrayCast() 15 15 1
A testSetRescoreToArrayCast() 15 15 1
A testSetPostFilterToArrayCast() 13 13 1
A testRawPostFilter() 0 22 1
A testNoSource() 0 35 1
A testSetCollapseToArrayCast() 15 15 1
A testCollapseArrayStructure() 0 32 1
A testCollapseSecondLevelArrayStructure() 0 39 1
A testSetTrackTotalHitsIsInParams() 0 7 1
A provideSetTrackTotalHitsInvalidValue() 0 7 1
A testSetTrackTotalHitsInvalidValue() 0 6 1
A testSetTrackTotalHits() 0 35 2

How to fix   Duplicated Code   

Duplicated Code

Duplicate code is one of the most pungent code smells. A rule that is often used is to re-structure code once it is duplicated in three or more places.

Common duplication problems, and corresponding solutions are:

1
<?php
2
3
namespace Elastica\Test;
4
5
use Elastica\Aggregation\Terms as TermsAggregation;
6
use Elastica\Collapse;
7
use Elastica\Collapse\InnerHits;
8
use Elastica\Document;
9
use Elastica\Exception\InvalidException;
10
use Elastica\Mapping;
11
use Elastica\Query;
12
use Elastica\Query\Term;
13
use Elastica\Query\Terms;
14
use Elastica\Rescore\Query as RescoreQuery;
15
use Elastica\Script\Script;
16
use Elastica\Script\ScriptFields;
17
use Elastica\Suggest;
18
use Elastica\Test\Base as BaseTest;
19
20
/**
21
 * @internal
22
 */
23
class QueryTest extends BaseTest
24
{
25
    /**
26
     * @group unit
27
     */
28 View Code Duplication
    public function testRawQuery(): void
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
29
    {
30
        $textQuery = new Term(['title' => 'test']);
31
32
        $query1 = Query::create($textQuery);
33
34
        $query2 = new Query();
35
        $query2->setRawQuery(['query' => ['term' => ['title' => 'test']]]);
36
37
        $this->assertEquals($query1->toArray(), $query2->toArray());
38
    }
39
40
    /**
41
     * @group unit
42
     */
43
    public function testSuggestShouldNotRemoveOtherParameters(): void
44
    {
45
        $query1 = new Query();
46
        $query2 = new Query();
47
48
        $suggest = new Suggest();
49
        $suggest->setGlobalText('test');
50
51
        $query1->setSize(40);
52
        $query1->setSuggest($suggest);
53
54
        $query2->setSuggest($suggest);
55
        $query2->setSize(40);
56
57
        $this->assertEquals($query1->toArray(), $query2->toArray());
58
    }
59
60
    /**
61
     * @group unit
62
     */
63
    public function testArrayQuery(): void
64
    {
65
        $query = [
66
            'query' => [
67
                'text' => [
68
                    'title' => 'test',
69
                ],
70
            ],
71
        ];
72
73
        $query1 = Query::create($query);
74
75
        $query2 = new Query();
76
        $query2->setRawQuery(['query' => ['text' => ['title' => 'test']]]);
77
78
        $this->assertEquals($query1->toArray(), $query2->toArray());
79
    }
80
81
    /**
82
     * @group functional
83
     */
84
    public function testSetSort(): void
85
    {
86
        $index = $this->_createIndex();
87
        $index->setMapping(new Mapping([
88
            'firstname' => ['type' => 'text', 'fielddata' => true],
89
            'lastname' => ['type' => 'text', 'fielddata' => true],
90
        ]));
91
92
        $index->addDocuments([
93
            new Document(1, ['name' => 'hello world']),
94
            new Document(2, ['firstname' => 'guschti', 'lastname' => 'ruflin']),
95
            new Document(3, ['firstname' => 'nicolas', 'lastname' => 'ruflin']),
96
        ]);
97
        $index->refresh();
98
99
        $queryTerm = new Term();
100
        $queryTerm->setTerm('lastname', 'ruflin');
101
        $query = Query::create($queryTerm);
102
103
        // ASC order
104
        $query->setSort([['firstname' => ['order' => 'asc']]]);
105
        $resultSet = $index->search($query);
106
        $this->assertEquals(2, $resultSet->count());
107
108
        $first = $resultSet->current()->getData();
109
        $resultSet->next();
110
        $second = $resultSet->current()->getData();
111
112
        $this->assertEquals('guschti', $first['firstname']);
113
        $this->assertEquals('nicolas', $second['firstname']);
114
115
        // DESC order
116
        $query->setSort(['firstname' => ['order' => 'desc']]);
117
        $resultSet = $index->search($query);
118
        $this->assertEquals(2, $resultSet->count());
119
120
        $first = $resultSet->current()->getData();
121
        $resultSet->next();
122
        $second = $resultSet->current()->getData();
123
124
        $this->assertEquals('nicolas', $first['firstname']);
125
        $this->assertEquals('guschti', $second['firstname']);
126
    }
127
128
    /**
129
     * @group unit
130
     */
131
    public function testAddSort(): void
132
    {
133
        $query = new Query();
134
        $sortParam = ['firstname' => ['order' => 'asc']];
135
        $query->addSort($sortParam);
136
137
        $this->assertEquals($query->getParam('sort'), [$sortParam]);
138
    }
139
140
    /**
141
     * @group unit
142
     */
143
    public function testSetTrackScores(): void
144
    {
145
        $query = new Query();
146
        $param = false;
147
        $query->setTrackScores($param);
148
149
        $this->assertEquals($param, $query->getParam('track_scores'));
150
    }
151
152
    /**
153
     * @group unit
154
     */
155
    public function testSetRawQuery(): void
156
    {
157
        $query = new Query();
158
159
        $params = ['query' => 'test'];
160
        $query->setRawQuery($params);
161
162
        $this->assertEquals($params, $query->toArray());
163
    }
164
165
    /**
166
     * @group unit
167
     */
168
    public function testSetStoredFields(): void
169
    {
170
        $query = (new Query())
171
            ->setStoredFields(['firstname', 'lastname'])
172
        ;
173
174
        $data = $query->toArray();
175
176
        $this->assertArrayHasKey('stored_fields', $data);
177
        $this->assertContains('firstname', $data['stored_fields']);
178
        $this->assertContains('lastname', $data['stored_fields']);
179
        $this->assertCount(2, $data['stored_fields']);
180
    }
181
182
    /**
183
     * @group unit
184
     */
185
    public function testGetQuery(): void
186
    {
187
        $query = new Query();
188
189
        try {
190
            $query->getQuery();
191
            $this->fail('should throw exception because query does not exist');
192
        } catch (InvalidException $e) {
193
            $this->assertTrue(true);
194
        }
195
196
        $termQuery = new Term();
197
        $termQuery->setTerm('text', 'value');
198
        $query->setQuery($termQuery);
199
200
        $this->assertSame($termQuery, $query->getQuery());
201
    }
202
203
    /**
204
     * @group unit
205
     */
206 View Code Duplication
    public function testSetQueryToArrayCast(): void
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
207
    {
208
        $query = new Query();
209
        $termQuery = new Term();
210
        $termQuery->setTerm('text', 'value');
211
        $query->setQuery($termQuery);
212
213
        $termQuery->setTerm('text', 'another value');
214
215
        $anotherQuery = new Query();
216
        $anotherQuery->setQuery($termQuery);
217
218
        $this->assertEquals($query->toArray(), $anotherQuery->toArray());
219
    }
220
221
    /**
222
     * @group unit
223
     */
224
    public function testNotCloneInnerObjects(): void
225
    {
226
        $query = new Query();
227
        $termQuery = new Term();
228
        $termQuery->setTerm('text', 'value');
229
        $query->setQuery($termQuery);
230
231
        $anotherQuery = clone $query;
232
233
        $termQuery->setTerm('text', 'another value');
234
235
        $this->assertEquals($query->toArray(), $anotherQuery->toArray());
236
    }
237
238
    /**
239
     * @group unit
240
     */
241
    public function testSetQueryToArrayChangeQuery(): void
242
    {
243
        $query = new Query();
244
        $termQuery = new Term();
245
        $termQuery->setTerm('text', 'value');
246
        $query->setQuery($termQuery);
247
248
        $queryArray = $query->toArray();
249
250
        $termQuery = $query->getQuery();
251
        $termQuery->setTerm('text', 'another value');
252
253
        $this->assertNotEquals($queryArray, $query->toArray());
254
    }
255
256
    /**
257
     * @group unit
258
     */
259
    public function testSetScriptFieldsToArrayCast(): void
260
    {
261
        $query = new Query();
262
        $scriptFields = new ScriptFields();
263
        $scriptFields->addScript('script', new Script('script'));
264
265
        $query->setScriptFields($scriptFields);
266
267
        $scriptFields->addScript('another script', new Script('another script'));
268
269
        $anotherQuery = new Query();
270
        $anotherQuery->setScriptFields($scriptFields);
271
272
        $this->assertEquals($query->toArray(), $anotherQuery->toArray());
273
    }
274
275
    /**
276
     * @group unit
277
     */
278 View Code Duplication
    public function testAddScriptFieldsToArrayCast(): void
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
279
    {
280
        $query = new Query();
281
        $scriptField = new Script('script');
282
283
        $query->addScriptField('script', $scriptField);
284
285
        $scriptField->setScript('another script');
286
287
        $anotherQuery = new Query();
288
        $anotherQuery->addScriptField('script', $scriptField);
289
290
        $this->assertEquals($query->toArray(), $anotherQuery->toArray());
291
    }
292
293
    /**
294
     * @group unit
295
     */
296
    public function testAddScriptFieldToExistingScriptFields(): void
297
    {
298
        $script1 = new Script('s1');
299
        $script2 = new Script('s2');
300
301
        // add script1, then add script2
302
        $query = new Query();
303
        $scriptFields1 = new ScriptFields();
304
        $scriptFields1->addScript('script1', $script1);
305
        $query->setScriptFields($scriptFields1);
306
        $query->addScriptField('script2', $script2);
307
308
        // add script1 and script2 at once
309
        $anotherQuery = new Query();
310
        $scriptFields2 = new ScriptFields();
311
        $scriptFields2->addScript('script1', $script1);
312
        $scriptFields2->addScript('script2', $script2);
313
        $anotherQuery->setScriptFields($scriptFields2);
314
315
        $this->assertEquals($query->toArray(), $anotherQuery->toArray());
316
    }
317
318
    /**
319
     * @group unit
320
     */
321 View Code Duplication
    public function testAddAggregationToArrayCast(): void
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
322
    {
323
        $query = new Query();
324
        $aggregation = new TermsAggregation('text');
325
        $aggregation->setField('field');
326
327
        $query->addAggregation($aggregation);
328
329
        $aggregation->setName('another text');
330
331
        $anotherQuery = new Query();
332
        $anotherQuery->addAggregation($aggregation);
333
334
        $this->assertEquals($query->toArray(), $anotherQuery->toArray());
335
    }
336
337
    /**
338
     * @group unit
339
     */
340 View Code Duplication
    public function testSetSuggestToArrayCast(): void
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
341
    {
342
        $query = new Query();
343
        $suggest = new Suggest();
344
        $suggest->setGlobalText('text');
345
346
        $query->setSuggest($suggest);
347
348
        $suggest->setGlobalText('another text');
349
350
        $anotherQuery = new Query();
351
        $anotherQuery->setSuggest($suggest);
352
353
        $this->assertEquals($query->toArray(), $anotherQuery->toArray());
354
    }
355
356
    /**
357
     * @group unit
358
     */
359 View Code Duplication
    public function testSetRescoreToArrayCast(): void
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
360
    {
361
        $query = new Query();
362
        $rescore = new RescoreQuery();
363
        $rescore->setQueryWeight(1);
364
365
        $query->setRescore($rescore);
366
367
        $rescore->setQueryWeight(2);
368
369
        $anotherQuery = new Query();
370
        $anotherQuery->setRescore($rescore);
371
372
        $this->assertEquals($query->toArray(), $anotherQuery->toArray());
373
    }
374
375
    /**
376
     * @group unit
377
     */
378 View Code Duplication
    public function testSetPostFilterToArrayCast(): void
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
379
    {
380
        $query = new Query();
381
        $postFilter = new Terms('key', ['term']);
382
        $query->setPostFilter($postFilter);
383
384
        $postFilter->addTerm('another term');
385
386
        $anotherQuery = new Query();
387
        $anotherQuery->setPostFilter($postFilter);
388
389
        $this->assertEquals($query->toArray(), $anotherQuery->toArray());
390
    }
391
392
    /**
393
     * @group unit
394
     */
395
    public function testRawPostFilter(): void
396
    {
397
        $query = (new Query())
398
            ->setQuery(new Term(['field' => 'value']))
399
            ->setParam('post_filter', [
400
                'term' => ['field' => 'value'],
401
            ])
402
        ;
403
404
        $this->assertSame([
405
            'query' => [
406
                'term' => [
407
                    'field' => 'value',
408
                ],
409
            ],
410
            'post_filter' => [
411
                'term' => [
412
                    'field' => 'value',
413
                ],
414
            ],
415
        ], $query->toArray());
416
    }
417
418
    /**
419
     * @group functional
420
     */
421
    public function testNoSource(): void
422
    {
423
        $index = $this->_createIndex();
424
425
        // Adds 1 document to the index
426
        $doc1 = new Document(
427
            1,
428
            ['username' => 'ruflin', 'test' => ['2', '3', '5']]
429
        );
430
        $index->addDocument($doc1);
431
432
        // To update index
433
        $index->refresh();
434
435
        $query = Query::create('ruflin');
436
        $resultSet = $index->search($query);
437
438
        // Disable source
439
        $query->setSource(false);
440
441
        $resultSetNoSource = $index->search($query);
442
443
        $this->assertEquals(1, $resultSet->count());
444
        $this->assertEquals(1, $resultSetNoSource->count());
445
446
        // Tests if no source is in response except id
447
        $result = $resultSetNoSource->current();
448
        $this->assertEquals(1, $result->getId());
449
        $this->assertEmpty($result->getData());
450
451
        // Tests if source is in response except id
452
        $result = $resultSet->current();
453
        $this->assertEquals(1, $result->getId());
454
        $this->assertNotEmpty($result->getData());
455
    }
456
457
    /**
458
     * @group unit
459
     */
460 View Code Duplication
    public function testSetCollapseToArrayCast(): void
0 ignored issues
show
Duplication introduced by
This method seems to be duplicated in your project.

Duplicated code is one of the most pungent code smells. If you need to duplicate the same code in three or more different places, we strongly encourage you to look into extracting the code into a single class or operation.

You can also find more detailed suggestions in the “Code” section of your repository.

Loading history...
461
    {
462
        $query = new Query();
463
        $collapse = new Collapse();
464
        $collapse->setFieldname('some_field');
465
466
        $query->setCollapse($collapse);
467
468
        $collapse->setFieldname('another_field');
469
470
        $anotherQuery = new Query();
471
        $anotherQuery->setCollapse($collapse);
472
473
        $this->assertEquals($query->toArray(), $anotherQuery->toArray());
474
    }
475
476
    /**
477
     * @group unit
478
     */
479
    public function testCollapseArrayStructure(): void
480
    {
481
        $query = new Query();
482
        $collapse = new Collapse();
483
        $collapse
484
            ->setFieldname('user')
485
            ->setInnerHits(
486
                (new InnerHits())
487
                    ->setName('last_tweets')
488
                    ->setSize(5)
489
                    ->setSort(['date' => 'asc'])
490
            )
491
            ->setMaxConcurrentGroupSearches(4)
492
        ;
493
494
        $query->setCollapse($collapse);
495
496
        $expected = [
497
            'field' => 'user',
498
            'inner_hits' => [
499
                'name' => 'last_tweets',
500
                'size' => 5,
501
                'sort' => ['date' => 'asc'],
502
            ],
503
            'max_concurrent_group_searches' => 4,
504
        ];
505
506
        $actual = $query->toArray();
507
508
        $this->assertArrayHasKey('collapse', $actual);
509
        $this->assertEquals($expected, $actual['collapse']);
510
    }
511
512
    /**
513
     * @group unit
514
     */
515
    public function testCollapseSecondLevelArrayStructure(): void
516
    {
517
        $query = new Query();
518
        $collapse = new Collapse();
519
        $collapse
520
            ->setFieldname('user')
521
            ->setInnerHits(
522
                (new InnerHits())
523
                    ->setName('last_tweets')
524
                    ->setSize(5)
525
                    ->setSort(['date' => 'asc'])
526
                    ->setCollapse(
527
                        (new Collapse())
528
                            ->setFieldname('date')
529
                    )
530
            )
531
            ->setMaxConcurrentGroupSearches(4)
532
        ;
533
534
        $query->setCollapse($collapse);
535
536
        $expected = [
537
            'field' => 'user',
538
            'inner_hits' => [
539
                'name' => 'last_tweets',
540
                'size' => 5,
541
                'sort' => ['date' => 'asc'],
542
                'collapse' => [
543
                    'field' => 'date',
544
                ],
545
            ],
546
            'max_concurrent_group_searches' => 4,
547
        ];
548
549
        $actual = $query->toArray();
550
551
        $this->assertArrayHasKey('collapse', $actual);
552
        $this->assertEquals($expected, $actual['collapse']);
553
    }
554
555
    /**
556
     * @group functional
557
     */
558
    public function testSetTrackTotalHitsIsInParams(): void
559
    {
560
        $query = new Query();
561
        $query->setTrackTotalHits(false);
562
563
        $this->assertFalse($query->getParam('track_total_hits'));
564
    }
565
566
    public function provideSetTrackTotalHitsInvalidValue(): iterable
567
    {
568
        yield 'string' => ['string string'];
569
        yield 'null' => [null];
570
        yield 'object' => [new \stdClass()];
571
        yield 'array' => [[]];
572
    }
573
574
    /**
575
     * @group functional
576
     * @dataProvider provideSetTrackTotalHitsInvalidValue
577
     *
578
     * @param mixed $value
579
     */
580
    public function testSetTrackTotalHitsInvalidValue($value): void
581
    {
582
        $this->expectException(InvalidException::class);
583
584
        (new Query())->setTrackTotalHits($value);
585
    }
586
587
    /**
588
     * @group functional
589
     */
590
    public function testSetTrackTotalHits(): void
591
    {
592
        $index = $this->_createIndex();
593
        $index->setMapping(new Mapping([
594
            'firstname' => ['type' => 'text', 'fielddata' => true],
595
        ]));
596
597
        $documents = [];
598
        for ($i = 0; $i < 50; ++$i) {
599
            $documents[] = new Document($i, ['firstname' => 'antoine '.$i]);
600
        }
601
602
        $index->addDocuments($documents);
603
604
        $queryTerm = new Term();
605
        $queryTerm->setTerm('firstname', 'antoine');
606
607
        $index->refresh();
608
609
        $query = Query::create($queryTerm);
610
611
        $resultSet = $index->search($query);
612
        $this->assertEquals(50, $resultSet->getTotalHits());
613
        $this->assertEquals('eq', $resultSet->getTotalHitsRelation());
614
615
        $query->setTrackTotalHits(false);
616
        $resultSet = $index->search($query);
617
        $this->assertEquals(0, $resultSet->getTotalHits());
618
        $this->assertEquals('eq', $resultSet->getTotalHitsRelation());
619
620
        $query->setTrackTotalHits(25);
621
        $resultSet = $index->search($query);
622
        $this->assertEquals(25, $resultSet->getTotalHits());
623
        $this->assertEquals('gte', $resultSet->getTotalHitsRelation());
624
    }
625
}
626