Passed
Push — refactor/improve-static-analys... ( efcf20...37f12c )
by Bas
03:04
created

CompilesFilters::filterBit()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 16
Code Lines 11

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 2

Importance

Changes 0
Metric Value
cc 1
eloc 11
c 0
b 0
f 0
nc 1
nop 2
dl 0
loc 16
ccs 0
cts 13
cp 0
crap 2
rs 9.9
1
<?php
2
3
namespace LaravelFreelancerNL\Aranguent\Query\Concerns;
4
5
use Illuminate\Database\Query\Builder as IlluminateQueryBuilder;
6
use Illuminate\Database\Query\Expression;
7
use Illuminate\Database\Query\JoinClause;
8
use LaravelFreelancerNL\Aranguent\Query\Builder;
9
10
trait CompilesFilters
11
{
12
    /**
13
     * Compile the "having" portions of the query.
14
     *
15
     * @param  \Illuminate\Database\Query\Builder  $query
16
     * @return string
17
     */
18 8
    protected function compileHavings(IlluminateQueryBuilder $query)
19
    {
20 8
        return 'FILTER ' . $this->removeLeadingBoolean(collect($query->havings)->map(function ($having) use ($query) {
0 ignored issues
show
Bug introduced by
It seems like removeLeadingBoolean() must be provided by classes using this trait. How about adding it as abstract method to this trait? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

20
        return 'FILTER ' . $this->/** @scrutinizer ignore-call */ removeLeadingBoolean(collect($query->havings)->map(function ($having) use ($query) {
Loading history...
Bug introduced by
$query->havings of type array is incompatible with the type Illuminate\Contracts\Support\Arrayable expected by parameter $value of collect(). ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

20
        return 'FILTER ' . $this->removeLeadingBoolean(collect(/** @scrutinizer ignore-type */ $query->havings)->map(function ($having) use ($query) {
Loading history...
21 8
            return $having['boolean'] . ' ' . $this->filter($query, $having);
22 8
        })->implode(' '));
23
    }
24
25
    /**
26
     * Get an array of all the where clauses for the query.
27
     *
28
     * @param  \Illuminate\Database\Query\Builder  $query
29
     * @return array<string>
30
     */
31 253
    protected function compileWheresToArray($query)
32
    {
33 253
        return collect($query->wheres)->map(function ($where) use ($query) {
0 ignored issues
show
Bug introduced by
$query->wheres of type array is incompatible with the type Illuminate\Contracts\Support\Arrayable expected by parameter $value of collect(). ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

33
        return collect(/** @scrutinizer ignore-type */ $query->wheres)->map(function ($where) use ($query) {
Loading history...
34 164
            return $where['boolean'] . ' ' . $this->{"filter{$where['type']}"}($query, $where);
35 253
        })->all();
36
    }
37
38
    /**
39
     * Format the where clause statements into one string.
40
     *
41
     * @param IlluminateQueryBuilder $query
42
     * @param  array<mixed>  $aql
43
     * @return string
44
     *
45
     * @SuppressWarnings(PHPMD.UnusedFormalParameter)
46
     */
47 164
    protected function concatenateWhereClauses($query, $aql)
48
    {
49 164
        return 'FILTER ' . $this->removeLeadingBoolean(implode(' ', $aql));
50
    }
51
52
    /**
53
     * @param string $type
54
     * @return string
55
     */
56
    protected function getOperatorByWhereType($type)
57
    {
58
        if (isset($this->whereTypeOperators[$type])) {
59
            return $this->whereTypeOperators[$type];
60
        }
61
62
        return '==';
63
    }
64
65
66
    /**
67
     * Compile a single having clause.
68
     *
69
     * @param IlluminateQueryBuilder $query
70
     * @param array<mixed> $filter
71
     * @return string
72
     * @throws \Exception
73
     */
74 8
    protected function filter(IlluminateQueryBuilder $query, array $filter)
75
    {
76
        // If the having clause is "raw", we can just return the clause straight away
77
        // without doing any more processing on it. Otherwise, we will compile the
78
        // clause into SQL based on the components that make it up from builder.
79 8
        return match ($filter['type']) {
80 8
            'Raw' => $filter['sql'],
81 8
            'between' => $this->filterBetween($query, $filter),
82 8
            'Null' => $this->filterNull($query, $filter),
83 8
            'NotNull' => $this->filterNotNull($query, $filter),
84 8
            'bit' => $this->filterBit($query, $filter),
85 8
            'Expression' => $this->filterExpression($query, $filter),
86 8
            'Nested' => $this->compileNestedHavings($filter),
0 ignored issues
show
Bug introduced by
It seems like compileNestedHavings() must be provided by classes using this trait. How about adding it as abstract method to this trait? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

86
            'Nested' => $this->/** @scrutinizer ignore-call */ compileNestedHavings($filter),
Loading history...
87 8
            default => $this->filterBasic($query, $filter),
88 8
        };
89
    }
90
91
    /**
92
     * Compile a basic having|filter clause.
93
     *
94
     * @param IlluminateQueryBuilder $query
95
     * @param array<mixed> $filter
96
     * @return string
97
     * @throws \Exception
98
     */
99 138
    protected function filterBasic(IlluminateQueryBuilder $query, $filter)
100
    {
101 138
        $predicate = [];
102
103 138
        $filter = $this->normalizeOperator($filter);
104
105 138
        if (!$filter['column'] instanceof expression) {
106 136
            $column = $this->normalizeColumn($query, $filter['column']);
0 ignored issues
show
Bug introduced by
It seems like normalizeColumn() must be provided by classes using this trait. How about adding it as abstract method to this trait? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

106
            /** @scrutinizer ignore-call */ 
107
            $column = $this->normalizeColumn($query, $filter['column']);
Loading history...
107
        }
108 138
        if ($filter['column'] instanceof expression) {
109 2
            $column = $filter['column']->getValue($this);
0 ignored issues
show
Bug introduced by
$this of type LaravelFreelancerNL\Aran...oncerns\CompilesFilters is incompatible with the type Illuminate\Database\Grammar expected by parameter $grammar of Illuminate\Database\Query\Expression::getValue(). ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

109
            $column = $filter['column']->getValue(/** @scrutinizer ignore-type */ $this);
Loading history...
110
        }
111
112 138
        $predicate[0] = $column;
0 ignored issues
show
Comprehensibility Best Practice introduced by
The variable $column does not seem to be defined for all execution paths leading up to this point.
Loading history...
113 138
        $predicate[1] = $filter['operator'];
114 138
        $predicate[2] = $this->parameter($filter['value']);
0 ignored issues
show
Bug introduced by
It seems like parameter() must be provided by classes using this trait. How about adding it as abstract method to this trait? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

114
        /** @scrutinizer ignore-call */ 
115
        $predicate[2] = $this->parameter($filter['value']);
Loading history...
115
116 138
        return implode(" ", $predicate);
117
    }
118
119
120
    /**
121
     * Compile a "between" filter clause.
122
     *
123
     * @param IlluminateQueryBuilder $query
124
     * @param array<mixed> $filter
125
     * @return string
126
     * @throws \Exception
127
     */
128 3
    protected function filterBetween(IlluminateQueryBuilder $query, $filter): string
129
    {
130 3
        $predicate = [];
131
132 3
        [$minOperator, $maxOperator, $boolean] = $this->getBetweenOperators($filter['not']);
133
134 3
        $min = $this->parameter(reset($filter['values']));
135 3
        $max = $this->parameter(end($filter['values']));
136
137 3
        $normalizedColumn = $this->normalizeColumn($query, $filter['column']);
138
139 3
        $predicate[0][0] = $normalizedColumn;
140 3
        $predicate[0][1] = $minOperator;
141 3
        $predicate[0][2] = $min;
142
143 3
        $predicate[1][0] = $normalizedColumn;
144 3
        $predicate[1][1] = $maxOperator;
145 3
        $predicate[1][2] = $max;
146
147 3
        return implode(" ", $predicate[0]) . " " . $boolean . " " . implode(" ", $predicate[1]);
148
    }
149
150
    /**
151
     * Compile a "between columns" filter clause.
152
     *
153
     * @param IlluminateQueryBuilder $query
154
     * @param array<mixed> $filter
155
     * @return string
156
     * @throws \Exception
157
     */
158 1
    protected function filterBetweenColumns(IlluminateQueryBuilder $query, $filter)
159
    {
160 1
        $predicate = [];
161
162 1
        [$minOperator, $maxOperator, $boolean] = $this->getBetweenOperators($filter['not']);
163
164 1
        $column = $this->normalizeColumn($query, $filter['column']);
165
166 1
        $predicate[0][0] = $column;
167 1
        $predicate[0][1] = $minOperator;
168 1
        $predicate[0][2] = $this->normalizeColumn($query, reset($filter['values']));
169
170 1
        $predicate[1][0] = $column;
171 1
        $predicate[1][1] = $maxOperator;
172 1
        $predicate[1][2] = $this->normalizeColumn($query, end($filter['values']));
173
174 1
        return implode(" ", $predicate[0]) . " " . $boolean . " " . implode(" ", $predicate[1]);
175
    }
176
177
    /**
178
     * Compile a filter clause comparing two columns..
179
     *
180
     * @param IlluminateQueryBuilder $query
181
     * @param array<mixed> $filter
182
     * @return string
183
     * @throws \Exception
184
     */
185 33
    protected function filterColumn(IlluminateQueryBuilder $query, $filter)
186
    {
187 33
        $predicate = [];
188
189 33
        $filter = $this->normalizeOperator($filter);
190 33
        $predicate[0] = $this->normalizeColumn($query, $filter['first']);
191 33
        $predicate[1] = $filter['operator'];
192 33
        $predicate[2] = $this->normalizeColumn($query, $filter['second']);
193
194 33
        return implode(" ", $predicate);
195
    }
196
197
    /**
198
     * Compile a "filter null" clause.
199
     *
200
     * @param IlluminateQueryBuilder $query
201
     * @param array<mixed> $filter
202
     * @return string
203
     * @throws \Exception
204
     */
205 20
    protected function filterNull(IlluminateQueryBuilder $query, $filter)
206
    {
207 20
        $predicate = [];
208
209 20
        $predicate[0] = $this->normalizeColumn($query, $filter['column']);
210 20
        $predicate[1] = '==';
211 20
        $predicate[2] = "null";
212
213 20
        return implode(" ", $predicate);
214
    }
215
216
    /**
217
     * Compile a "filter not null" clause.
218
     *
219
     * @param IlluminateQueryBuilder $query
220
     * @param array<mixed> $filter
221
     * @return string
222
     * @throws \Exception
223
     */
224 25
    protected function filterNotNull(IlluminateQueryBuilder $query, $filter)
225
    {
226 25
        $predicate = [];
227
228 25
        $predicate[0] = $this->normalizeColumn($query, $filter['column']);
229 25
        $predicate[1] = '!=';
230 25
        $predicate[2] = "null";
231
232 25
        return implode(" ", $predicate);
233
    }
234
235
    /**
236
     * Compile a "filter in" clause.
237
     *
238
     * @param  IlluminateQueryBuilder  $query
239
     * @param  array<mixed>  $filter
240
     * @return string
241
     */
242 12
    protected function filterIn(IlluminateQueryBuilder $query, $filter)
243
    {
244 12
        $predicate = [];
245
246 12
        $predicate[0] = $this->normalizeColumn($query, $filter['column']);
247 12
        $predicate[1] = 'IN';
248 12
        $predicate[2] = $this->parameter($filter['values']);
249
250 12
        return implode(" ", $predicate);
251
    }
252
253
    /**
254
     * Compile a "filter in raw" clause.
255
     *
256
     * For safety, filterIntegerInRaw ensures this method is only used with integer values.
257
     *
258
     * @param IlluminateQueryBuilder $query
259
     * @param array<mixed> $filter
260
     * @return string
261
     * @throws \Exception
262
     */
263 1
    protected function filterInRaw(IlluminateQueryBuilder $query, array $filter): string
264
    {
265 1
        $predicate = [];
266
267 1
        $predicate[0] = $this->normalizeColumn($query, $filter['column']);
268 1
        $predicate[1] = 'IN';
269 1
        $predicate[2] = '[' . implode(', ', $filter['values']) . ']';
270
271 1
        return implode(" ", $predicate);
272
    }
273
274
    /**
275
     * Compile a "filter not in" clause.
276
     *
277
     * @param IlluminateQueryBuilder $query
278
     * @param array<mixed> $filter
279
     * @return string
280
     * @throws \Exception
281
     */
282 1
    protected function filterNotIn(IlluminateQueryBuilder $query, array $filter): string
283
    {
284 1
        $predicate = [];
285
286 1
        $predicate[0] = $this->normalizeColumn($query, $filter['column']);
287 1
        $predicate[1] = 'NOT IN';
288 1
        $predicate[2] = $this->parameter($filter['values']);
289
290 1
        return implode(" ", $predicate);
291
    }
292
293
    /**
294
     * Compile a "filter not in raw" clause.
295
     *
296
     * For safety, filterIntegerInRaw ensures this method is only used with integer values.
297
     *
298
     * @param  IlluminateQueryBuilder  $query
299
     * @param  array<mixed>  $filter
300
     * @return string
301
     */
302 1
    protected function filterNotInRaw(IlluminateQueryBuilder $query, array $filter): string
303
    {
304 1
        $predicate = [];
305
306 1
        $predicate[0] = $this->normalizeColumn($query, $filter['column']);
307 1
        $predicate[1] = 'NOT IN';
308 1
        $predicate[2] = '[' . implode(', ', $filter['values']) . ']';
309
310 1
        return implode(" ", $predicate);
311
    }
312
313
    /**
314
     * Compile a "filter JSON contains" clause.
315
     *
316
     * @param IlluminateQueryBuilder $query
317
     * @param array<mixed> $filter
318
     * @return string
319
     * @throws \Exception
320
     */
321 1
    protected function filterJsonContains(IlluminateQueryBuilder $query, $filter)
322
    {
323 1
        $predicate = [];
324
325 1
        $operator = $filter['not'] ? 'NOT IN' : 'IN';
326
327 1
        $predicate[0] = $this->parameter($filter['value']);
328 1
        $predicate[1] = $operator;
329 1
        $predicate[2] = $this->normalizeColumn($query, $filter['column']);
330
331 1
        return implode(" ", $predicate);
332
    }
333
334
    /**
335
     * Compile a "filterJsonLength" clause.
336
     *
337
     * @param  IlluminateQueryBuilder  $query
338
     * @param  array<mixed>  $filter
339
     * @return string
340
     */
341 1
    protected function filterJsonLength(IlluminateQueryBuilder $query, array $filter): string
342
    {
343 1
        $predicate = [];
344
345 1
        $filter = $this->normalizeOperator($filter);
346
347 1
        $column = $this->normalizeColumn($query, $filter['column']);
348
349 1
        $predicate[0] = "LENGTH($column)";
350 1
        $predicate[1] = $filter['operator'];
351 1
        $predicate[2] = $this->parameter($filter['value']);
352
353 1
        return implode(" ", $predicate);
354
    }
355
356
    /**
357
     * @param array<mixed> $filter
358
     * @return mixed
359
     *
360
     * @SuppressWarnings(PHPMD.UnusedFormalParameter)
361
     */
362
    protected function filterExpression(IlluminateQueryBuilder $query, $filter)
363
    {
364
        return $filter['column']->getValue($this);
365
    }
366
367
    /**
368
     * Compile a filter date clause.
369
     *
370
     * @param IlluminateQueryBuilder $query
371
     * @param array<mixed> $filter
372
     * @return string
373
     * @throws \Exception
374
     */
375 1
    protected function filterDate(IlluminateQueryBuilder $query, $filter)
376
    {
377 1
        $predicate = [];
378
379 1
        $filter = $this->normalizeOperator($filter);
380 1
        $predicate[0] = 'DATE_FORMAT(' . $this->normalizeColumn($query, $filter['column']) . ', "%yyyy-%mm-%dd")';
381 1
        $predicate[1] = $filter['operator'];
382 1
        $predicate[2] = $this->parameter($filter['value']);
383
384 1
        return implode(' ', $predicate);
385
    }
386
387
    /**
388
     * Compile a filter year clause.
389
     *
390
     * @param IlluminateQueryBuilder $query
391
     * @param array<mixed> $filter
392
     * @return string
393
     * @throws \Exception
394
     */
395 1
    protected function filterYear(IlluminateQueryBuilder $query, $filter)
396
    {
397 1
        $predicate = [];
398
399 1
        $filter = $this->normalizeOperator($filter);
400
401 1
        $predicate[0] = 'DATE_YEAR(' . $this->normalizeColumn($query, $filter['column']) . ')';
402 1
        $predicate[1] = $filter['operator'];
403 1
        $predicate[2] = $this->parameter($filter['value']);
404
405 1
        return implode(' ', $predicate);
406
    }
407
408
    /**
409
     * Compile a filter month clause.
410
     *
411
     * @param IlluminateQueryBuilder $query
412
     * @param array<mixed> $filter
413
     * @return string
414
     * @throws \Exception
415
     */
416 1
    protected function filterMonth(IlluminateQueryBuilder $query, $filter)
417
    {
418 1
        $predicate = [];
419
420 1
        $filter = $this->normalizeOperator($filter);
421
422 1
        $predicate[0] =  'DATE_MONTH(' . $this->normalizeColumn($query, $filter['column']) . ')';
423 1
        $predicate[1] = $filter['operator'];
424 1
        $predicate[2] = $this->parameter($filter['value']);
425
426 1
        return implode(' ', $predicate);
427
    }
428
429
430
    /**
431
     * Compile a filter day clause.
432
     *
433
     * @param IlluminateQueryBuilder $query
434
     * @param array<mixed> $filter
435
     * @return string
436
     * @throws \Exception
437
     */
438 1
    protected function filterDay(IlluminateQueryBuilder $query, $filter)
439
    {
440 1
        $predicate = [];
441
442 1
        $filter = $this->normalizeOperator($filter);
443
444 1
        $predicate[0] = 'DATE_DAY(' . $this->normalizeColumn($query, $filter['column']) . ')';
445 1
        $predicate[1] = $filter['operator'];
446 1
        $predicate[2] = $this->parameter($filter['value']);
447
448 1
        return implode(' ', $predicate);
449
    }
450
451
    /**
452
     * Compile a filter time clause.
453
     *
454
     * @param  IlluminateQueryBuilder  $query
455
     * @param  array<mixed>  $filter
456
     * @return string
457
     */
458 1
    protected function filterTime(IlluminateQueryBuilder $query, $filter)
459
    {
460 1
        $predicate = [];
461
462 1
        $filter = $this->normalizeOperator($filter);
463
464 1
        $predicate[0] = 'DATE_FORMAT(' . $this->normalizeColumn($query, $filter['column']) . ", '%hh:%ii:%ss')";
465 1
        $predicate[1] = $filter['operator'];
466 1
        $predicate[2] = $this->parameter($filter['value']);
467
468 1
        return implode(' ', $predicate);
469
    }
470
471
    /**
472
     * Compile a filter condition with a sub-select.
473
     *
474
     * @param IlluminateQueryBuilder $query
475
     * @param array<mixed> $filter
476
     * @return string
477
     * @throws \Exception
478
     */
479 1
    protected function filterSub(IlluminateQueryBuilder $query, $filter)
480
    {
481 1
        $predicate = [];
482
483 1
        $filter = $this->normalizeOperator($filter);
484
485 1
        $predicate[0] = $this->normalizeColumn($query, $filter['column']);
486 1
        $predicate[1] = $filter['operator'];
487 1
        $predicate[2] = $filter['subquery'];
488
489 1
        return implode(' ', $predicate);
490
    }
491
492
    /**
493
     * Compile a filter exists clause.
494
     *
495
     * @param  \Illuminate\Database\Query\Builder  $query
496
     * @param  array<mixed>  $filter
497
     * @return string
498
     *
499
     * @SuppressWarnings(PHPMD.UnusedFormalParameter)
500
     */
501 4
    protected function filterExists(IlluminateQueryBuilder $query, $filter)
502
    {
503 4
        return 'LENGTH(' . $filter['subquery'] . ') > 0';
504
    }
505
506
    /**
507
     * Compile a filter exists clause.
508
     *
509
     * @param  \Illuminate\Database\Query\Builder  $query
510
     * @param  array<mixed>  $filter
511
     * @return string
512
     *
513
     * @SuppressWarnings(PHPMD.UnusedFormalParameter)
514
     */
515 3
    protected function filterNotExists(IlluminateQueryBuilder $query, $filter)
516
    {
517 3
        return 'LENGTH(' . $filter['subquery'] . ') == 0';
518
    }
519
520
    /**
521
     * Compile a nested where clause.
522
     *
523
     * @param  \Illuminate\Database\Query\Builder  $query
524
     * @param  array<mixed>  $filter
525
     * @return string
526
     *
527
     * @SuppressWarnings(PHPMD.UnusedFormalParameter)
528
     */
529 23
    protected function filterNested(IlluminateQueryBuilder $query, $filter)
530
    {
531
        // Here we will calculate what portion of the string we need to remove. If this
532
        // is a join clause query, we need to remove the "on" portion of the SQL and
533
        // if it is a normal query we need to take the leading "where" of queries.
534 23
        $offset = $filter['query'] instanceof JoinClause ? 3 : 6;
535
536 23
        return '(' . substr($this->compileWheres($filter['query']), $offset) . ')';
0 ignored issues
show
Bug introduced by
The method compileWheres() does not exist on LaravelFreelancerNL\Aran...oncerns\CompilesFilters. Did you maybe mean compileWheresToArray()? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

536
        return '(' . substr($this->/** @scrutinizer ignore-call */ compileWheres($filter['query']), $offset) . ')';

This check looks for calls to methods that do not seem to exist on a given type. It looks for the method on the type itself as well as in inherited classes or implemented interfaces.

This is most likely a typographical error or the method has been renamed.

Loading history...
537
    }
538
539
540
    /**
541
     * Compile a having clause involving a bit operator.
542
     *
543
     * @param IlluminateQueryBuilder $query
544
     * @param array<mixed> $filter
545
     * @return string
546
     * @throws \Exception
547
     */
548
    protected function filterBit(IlluminateQueryBuilder $query, $filter)
549
    {
550
        $column = $this->normalizeColumn($query, $filter['column']);
551
        $value = $this->parameter($filter['value']);
552
553
        $bitExpression = match ($filter['operator']) {
554
            '|' => $this->bitExpressionOr($column, $value),
555
            '^' => $this->bitExpressionXor($column, $value),
556
            '~' => $this->bitExpressionNegate($column),
557
            '&~' => $this->bitExpressionNegatedAnd($column, $value),
558
            '<<' => $this->bitExpressionLeftShift($column, $value),
559
            '>>' => $this->bitExpressionRightShift($column, $value),
560
            default =>  $this->bitExpressionAnd($column, $value),
561
        };
562
563
        return '(' . $bitExpression . ') != 0';
564
    }
565
566
    protected function bitExpressionAnd(string $column, int|string $value): string
567
    {
568
        return 'BIT_AND(' . $column . ', ' . $value . ')';
569
    }
570
571
    protected function bitExpressionOr(string $column, int|string $value): string
572
    {
573
        return 'BIT_AND(' . $column . ', ' . $value . ')';
574
    }
575
576
    protected function bitExpressionXor(string $column, int|string $value): string
577
    {
578
        return 'BIT_XOR(' . $column . ', ' . $value . ')';
579
    }
580
581
    protected function bitExpressionNegate(string $column): string
582
    {
583
        return 'BIT_NEGATE(' . $column . ', BIT_POPCOUNT(' . $column . '))';
584
    }
585
586
    protected function bitExpressionNegatedAnd(string $column, int|string $value): string
587
    {
588
        return 'BIT_AND(' . $column . ', BIT_NEGATE(' . $value . ', BIT_POPCOUNT(' . $value . '))';
589
    }
590
591
    protected function bitExpressionLeftShift(string $column, int|string $value): string
592
    {
593
        return 'BIT_SHIFT_LEFT(' . $column . ',  ' . $value . ', BIT_POPCOUNT(' . $column . '))';
594
    }
595
596
    protected function bitExpressionRightShift(string $column, int|string $value): string
597
    {
598
        return 'BIT_SHIFT_RIGHT(' . $column . ',  ' . $value . ', BIT_POPCOUNT(' . $column . '))';
599
    }
600
601
    /**
602
     * Generate operators for between and 'not between'
603
     * @param  bool  $notBetween
604
     * @return string[]
605
     */
606 4
    protected function getBetweenOperators(bool $notBetween)
607
    {
608 4
        $minOperator = '>=';
609 4
        $maxOperator = '<=';
610 4
        $boolean = 'AND';
611
612 4
        if ($notBetween) {
613 1
            $minOperator = '<';
614 1
            $maxOperator = '>';
615 1
            $boolean = 'OR';
616
        }
617
618 4
        return [$minOperator, $maxOperator, $boolean];
619
    }
620
621
    /**
622
     * @param array<mixed> $filter
623
     * @return array<mixed>
624
     */
625 155
    protected function normalizeOperator($filter)
626
    {
627 155
        if (isset($filter['operator'])) {
628 155
            $filter['operator'] = $this->translateOperator($filter['operator']);
0 ignored issues
show
Bug introduced by
It seems like translateOperator() must be provided by classes using this trait. How about adding it as abstract method to this trait? ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

628
            /** @scrutinizer ignore-call */ 
629
            $filter['operator'] = $this->translateOperator($filter['operator']);
Loading history...
629
        }
630 155
        if (!isset($filter['operator'])) {
631
            $filter['operator'] = $this->getOperatorByWhereType($filter['type']);
632
        }
633
634 155
        return $filter;
635
    }
636
}
637