Completed
Pull Request — master (#7184)
by
unknown
18:39
created

Expr::isInstanceOf()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 3
Code Lines 1

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 2
CRAP Score 1

Importance

Changes 0
Metric Value
cc 1
eloc 1
nc 1
nop 2
dl 0
loc 3
ccs 2
cts 2
cp 1
crap 1
rs 10
c 0
b 0
f 0
1
<?php
2
3
declare(strict_types=1);
4
5
namespace Doctrine\ORM\Query;
6
7
use function func_get_args;
8
use function implode;
9
use function is_array;
10
use function is_bool;
11
use function is_numeric;
12
use function is_string;
13
use function str_replace;
14
15
/**
16
 * This class is used to generate DQL expressions via a set of PHP static functions.
17
 * @todo Rename: ExpressionBuilder
18
 */
19
class Expr
20
{
21
    /**
22
     * Creates a conjunction of the given boolean expressions.
23
     *
24
     * Example:
25
     *
26
     *     [php]
27
     *     // (u.type = ?1) AND (u.role = ?2)
28
     *     $expr->andX($expr->eq('u.type', ':1'), $expr->eq('u.role', ':2'));
29
     *
30
     * @param Expr\Comparison|Expr\Func|Expr\Orx $x Optional clause. Defaults to null, but requires at least one
31
     *                                              defined when converting to string.
32
     *
33
     * @return Expr\Andx
34
     */
35 5
    public function andX($x = null)
36
    {
37 5
        return new Expr\Andx(func_get_args());
38
    }
39
40
    /**
41
     * Creates a disjunction of the given boolean expressions.
42
     *
43
     * Example:
44
     *
45
     *     [php]
46
     *     // (u.type = ?1) OR (u.role = ?2)
47
     *     $q->where($q->expr()->orX('u.type = ?1', 'u.role = ?2'));
48
     *
49
     * @param mixed $x Optional clause. Defaults to null, but requires
50
     *                 at least one defined when converting to string.
51
     *
52
     * @return Expr\Orx
53
     */
54 8
    public function orX($x = null)
55
    {
56 8
        return new Expr\Orx(func_get_args());
57
    }
58
59
    /**
60
     * Creates an ASCending order expression.
61
     *
62
     * @param mixed $expr
63
     *
64
     * @return Expr\OrderBy
65
     */
66 2
    public function asc($expr)
67
    {
68 2
        return new Expr\OrderBy($expr, 'ASC');
69
    }
70
71
    /**
72
     * Creates a DESCending order expression.
73
     *
74
     * @param mixed $expr
75
     *
76
     * @return Expr\OrderBy
77
     */
78 3
    public function desc($expr)
79
    {
80 3
        return new Expr\OrderBy($expr, 'DESC');
81
    }
82
83
    /**
84
     * Creates an equality comparison expression with the given arguments.
85
     *
86
     * First argument is considered the left expression and the second is the right expression.
87
     * When converted to string, it will generated a <left expr> = <right expr>. Example:
88
     *
89
     *     [php]
90
     *     // u.id = ?1
91
     *     $expr->eq('u.id', '?1');
92
     *
93
     * @param mixed $x Left expression.
94
     * @param mixed $y Right expression.
95
     *
96
     * @return Expr\Comparison
97
     */
98 27
    public function eq($x, $y)
99
    {
100 27
        return new Expr\Comparison($x, Expr\Comparison::EQ, $y);
101
    }
102
103
    /**
104
     * Creates an instance of Expr\Comparison, with the given arguments.
105
     * First argument is considered the left expression and the second is the right expression.
106
     * When converted to string, it will generated a <left expr> <> <right expr>. Example:
107
     *
108
     *     [php]
109
     *     // u.id <> ?1
110
     *     $q->where($q->expr()->neq('u.id', '?1'));
111
     *
112
     * @param mixed $x Left expression.
113
     * @param mixed $y Right expression.
114
     *
115
     * @return Expr\Comparison
116
     */
117 1
    public function neq($x, $y)
118
    {
119 1
        return new Expr\Comparison($x, Expr\Comparison::NEQ, $y);
120
    }
121
122
    /**
123
     * Creates an instance of Expr\Comparison, with the given arguments.
124
     * First argument is considered the left expression and the second is the right expression.
125
     * When converted to string, it will generated a <left expr> < <right expr>. Example:
126
     *
127
     *     [php]
128
     *     // u.id < ?1
129
     *     $q->where($q->expr()->lt('u.id', '?1'));
130
     *
131
     * @param mixed $x Left expression.
132
     * @param mixed $y Right expression.
133
     *
134
     * @return Expr\Comparison
135
     */
136 3
    public function lt($x, $y)
137
    {
138 3
        return new Expr\Comparison($x, Expr\Comparison::LT, $y);
139
    }
140
141
    /**
142
     * Creates an instance of Expr\Comparison, with the given arguments.
143
     * First argument is considered the left expression and the second is the right expression.
144
     * When converted to string, it will generated a <left expr> <= <right expr>. Example:
145
     *
146
     *     [php]
147
     *     // u.id <= ?1
148
     *     $q->where($q->expr()->lte('u.id', '?1'));
149
     *
150
     * @param mixed $x Left expression.
151
     * @param mixed $y Right expression.
152
     *
153
     * @return Expr\Comparison
154
     */
155 1
    public function lte($x, $y)
156
    {
157 1
        return new Expr\Comparison($x, Expr\Comparison::LTE, $y);
158
    }
159
160
    /**
161
     * Creates an instance of Expr\Comparison, with the given arguments.
162
     * First argument is considered the left expression and the second is the right expression.
163
     * When converted to string, it will generated a <left expr> > <right expr>. Example:
164
     *
165
     *     [php]
166
     *     // u.id > ?1
167
     *     $q->where($q->expr()->gt('u.id', '?1'));
168
     *
169
     * @param mixed $x Left expression.
170
     * @param mixed $y Right expression.
171
     *
172
     * @return Expr\Comparison
173
     */
174 2
    public function gt($x, $y)
175
    {
176 2
        return new Expr\Comparison($x, Expr\Comparison::GT, $y);
177
    }
178
179
    /**
180
     * Creates an instance of Expr\Comparison, with the given arguments.
181
     * First argument is considered the left expression and the second is the right expression.
182
     * When converted to string, it will generated a <left expr> >= <right expr>. Example:
183
     *
184
     *     [php]
185
     *     // u.id >= ?1
186
     *     $q->where($q->expr()->gte('u.id', '?1'));
187
     *
188
     * @param mixed $x Left expression.
189
     * @param mixed $y Right expression.
190
     *
191
     * @return Expr\Comparison
192
     */
193 1
    public function gte($x, $y)
194
    {
195 1
        return new Expr\Comparison($x, Expr\Comparison::GTE, $y);
196
    }
197
198
    /**
199
     * Creates an instance of AVG() function, with the given argument.
200
     *
201
     * @param mixed $x Argument to be used in AVG() function.
202
     *
203
     * @return Expr\Func
204
     */
205 1
    public function avg($x)
206
    {
207 1
        return new Expr\Func('AVG', [$x]);
208
    }
209
210
    /**
211
     * Creates an instance of MAX() function, with the given argument.
212
     *
213
     * @param mixed $x Argument to be used in MAX() function.
214
     *
215
     * @return Expr\Func
216
     */
217 2
    public function max($x)
218
    {
219 2
        return new Expr\Func('MAX', [$x]);
220
    }
221
222
    /**
223
     * Creates an instance of MIN() function, with the given argument.
224
     *
225
     * @param mixed $x Argument to be used in MIN() function.
226
     *
227
     * @return Expr\Func
228
     */
229 1
    public function min($x)
230
    {
231 1
        return new Expr\Func('MIN', [$x]);
232
    }
233
234
    /**
235
     * Creates an instance of COUNT() function, with the given argument.
236
     *
237
     * @param mixed $x Argument to be used in COUNT() function.
238
     *
239
     * @return Expr\Func
240
     */
241 1
    public function count($x)
242
    {
243 1
        return new Expr\Func('COUNT', [$x]);
244
    }
245
246
    /**
247
     * Creates an instance of COUNT(DISTINCT) function, with the given argument.
248
     *
249
     * @param mixed $x Argument to be used in COUNT(DISTINCT) function.
250
     *
251
     * @return string
252
     */
253 2
    public function countDistinct($x)
254
    {
255 2
        return 'COUNT(DISTINCT ' . implode(', ', func_get_args()) . ')';
256
    }
257
258
    /**
259
     * Creates an instance of EXISTS() function, with the given DQL Subquery.
260
     *
261
     * @param mixed $subquery DQL Subquery to be used in EXISTS() function.
262
     *
263
     * @return Expr\Func
264
     */
265 1
    public function exists($subquery)
266
    {
267 1
        return new Expr\Func('EXISTS', [$subquery]);
268
    }
269
270
    /**
271
     * Creates an instance of ALL() function, with the given DQL Subquery.
272
     *
273
     * @param mixed $subquery DQL Subquery to be used in ALL() function.
274
     *
275
     * @return Expr\Func
276
     */
277 2
    public function all($subquery)
278
    {
279 2
        return new Expr\Func('ALL', [$subquery]);
280
    }
281
282
    /**
283
     * Creates a SOME() function expression with the given DQL subquery.
284
     *
285
     * @param mixed $subquery DQL Subquery to be used in SOME() function.
286
     *
287
     * @return Expr\Func
288
     */
289 1
    public function some($subquery)
290
    {
291 1
        return new Expr\Func('SOME', [$subquery]);
292
    }
293
294
    /**
295
     * Creates an ANY() function expression with the given DQL subquery.
296
     *
297
     * @param mixed $subquery DQL Subquery to be used in ANY() function.
298
     *
299
     * @return Expr\Func
300
     */
301 1
    public function any($subquery)
302
    {
303 1
        return new Expr\Func('ANY', [$subquery]);
304
    }
305
306
    /**
307
     * Creates a negation expression of the given restriction.
308
     *
309
     * @param mixed $restriction Restriction to be used in NOT() function.
310
     *
311
     * @return Expr\Func
312
     */
313 2
    public function not($restriction)
314
    {
315 2
        return new Expr\Func('NOT', [$restriction]);
316
    }
317
318
    /**
319
     * Creates an ABS() function expression with the given argument.
320
     *
321
     * @param mixed $x Argument to be used in ABS() function.
322
     *
323
     * @return Expr\Func
324
     */
325 1
    public function abs($x)
326
    {
327 1
        return new Expr\Func('ABS', [$x]);
328
    }
329
330
    /**
331
     * Creates a product mathematical expression with the given arguments.
332
     *
333
     * First argument is considered the left expression and the second is the right expression.
334
     * When converted to string, it will generated a <left expr> * <right expr>. Example:
335
     *
336
     *     [php]
337
     *     // u.salary * u.percentAnnualSalaryIncrease
338
     *     $q->expr()->prod('u.salary', 'u.percentAnnualSalaryIncrease')
339
     *
340
     * @param mixed $x Left expression.
341
     * @param mixed $y Right expression.
342
     *
343
     * @return Expr\Math
344
     */
345 1
    public function prod($x, $y)
346
    {
347 1
        return new Expr\Math($x, '*', $y);
348
    }
349
350
    /**
351
     * Creates a difference mathematical expression with the given arguments.
352
     * First argument is considered the left expression and the second is the right expression.
353
     * When converted to string, it will generated a <left expr> - <right expr>. Example:
354
     *
355
     *     [php]
356
     *     // u.monthlySubscriptionCount - 1
357
     *     $q->expr()->diff('u.monthlySubscriptionCount', '1')
358
     *
359
     * @param mixed $x Left expression.
360
     * @param mixed $y Right expression.
361
     *
362
     * @return Expr\Math
363
     */
364 2
    public function diff($x, $y)
365
    {
366 2
        return new Expr\Math($x, '-', $y);
367
    }
368
369
    /**
370
     * Creates a sum mathematical expression with the given arguments.
371
     * First argument is considered the left expression and the second is the right expression.
372
     * When converted to string, it will generated a <left expr> + <right expr>. Example:
373
     *
374
     *     [php]
375
     *     // u.numChildren + 1
376
     *     $q->expr()->sum('u.numChildren', '1')
377
     *
378
     * @param mixed $x Left expression.
379
     * @param mixed $y Right expression.
380
     *
381
     * @return Expr\Math
382
     */
383 1
    public function sum($x, $y)
384
    {
385 1
        return new Expr\Math($x, '+', $y);
386
    }
387
388
    /**
389
     * Creates a quotient mathematical expression with the given arguments.
390
     * First argument is considered the left expression and the second is the right expression.
391
     * When converted to string, it will generated a <left expr> / <right expr>. Example:
392
     *
393
     *     [php]
394
     *     // u.total / u.period
395
     *     $expr->quot('u.total', 'u.period')
396
     *
397
     * @param mixed $x Left expression.
398
     * @param mixed $y Right expression.
399
     *
400
     * @return Expr\Math
401
     */
402 3
    public function quot($x, $y)
403
    {
404 3
        return new Expr\Math($x, '/', $y);
405
    }
406
407
    /**
408
     * Creates a SQRT() function expression with the given argument.
409
     *
410
     * @param mixed $x Argument to be used in SQRT() function.
411
     *
412
     * @return Expr\Func
413
     */
414 1
    public function sqrt($x)
415
    {
416 1
        return new Expr\Func('SQRT', [$x]);
417
    }
418
419
    /**
420
     * Creates an IN() expression with the given arguments.
421
     *
422
     * @param string $x Field in string format to be restricted by IN() function.
423
     * @param mixed  $y Argument to be used in IN() function.
424
     *
425
     * @return Expr\Func
426
     */
427 9
    public function in($x, $y)
428
    {
429 9
        if (is_array($y)) {
430 8
            foreach ($y as &$literal) {
431 8
                if (! ($literal instanceof Expr\Literal)) {
432 8
                    $literal = $this->quoteLiteral($literal);
433
                }
434
            }
435
        }
436
437 9
        return new Expr\Func($x . ' IN', (array) $y);
438
    }
439
440
    /**
441
     * Creates a NOT IN() expression with the given arguments.
442
     *
443
     * @param string $x Field in string format to be restricted by NOT IN() function.
444
     * @param mixed  $y Argument to be used in NOT IN() function.
445
     *
446
     * @return Expr\Func
447
     */
448 5
    public function notIn($x, $y)
449
    {
450 5
        if (is_array($y)) {
451 4
            foreach ($y as &$literal) {
452 4
                if (! ($literal instanceof Expr\Literal)) {
453 4
                    $literal = $this->quoteLiteral($literal);
454
                }
455
            }
456
        }
457
458 5
        return new Expr\Func($x . ' NOT IN', (array) $y);
459
    }
460
461
    /**
462
     * Creates an IS NULL expression with the given arguments.
463
     *
464
     * @param string $x Field in string format to be restricted by IS NULL.
465
     *
466
     * @return string
467
     */
468 3
    public function isNull($x)
469
    {
470 3
        return $x . ' IS NULL';
471
    }
472
473
    /**
474
     * Creates an IS NOT NULL expression with the given arguments.
475
     *
476
     * @param string $x Field in string format to be restricted by IS NOT NULL.
477
     *
478
     * @return string
479
     */
480 2
    public function isNotNull($x)
481
    {
482 2
        return $x . ' IS NOT NULL';
483
    }
484
485
    /**
486
     * Creates a LIKE() comparison expression with the given arguments.
487
     *
488
     * @param string $x Field in string format to be inspected by LIKE() comparison.
489
     * @param mixed  $y Argument to be used in LIKE() comparison.
490
     *
491
     * @return Expr\Comparison
492
     */
493 4
    public function like($x, $y)
494
    {
495 4
        return new Expr\Comparison($x, 'LIKE', $y);
496
    }
497
498
    /**
499
     * Creates a NOT LIKE() comparison expression with the given arguments.
500
     *
501
     * @param string $x Field in string format to be inspected by LIKE() comparison.
502
     * @param mixed  $y Argument to be used in LIKE() comparison.
503
     *
504
     * @return Expr\Comparison
505
     */
506 1
    public function notLike($x, $y)
507
    {
508 1
        return new Expr\Comparison($x, 'NOT LIKE', $y);
509
    }
510
511
    /**
512
     * Creates a CONCAT() function expression with the given arguments.
513
     *
514
     * @param mixed $x     First argument to be used in CONCAT() function.
515
     * @param mixed $y,... Other arguments to be used in CONCAT() function.
516
     *
517
     * @return Expr\Func
518
     */
519 1
    public function concat($x, $y)
520
    {
521 1
        return new Expr\Func('CONCAT', func_get_args());
522
    }
523
524
    /**
525
     * Creates a SUBSTRING() function expression with the given arguments.
526
     *
527
     * @param mixed    $x    Argument to be used as string to be cropped by SUBSTRING() function.
528
     * @param int      $from Initial offset to start cropping string. May accept negative values.
529
     * @param int|null $len  Length of crop. May accept negative values.
530
     *
531
     * @return Expr\Func
532
     */
533 2
    public function substring($x, $from, $len = null)
534
    {
535 2
        $args = [$x, $from];
536 2
        if ($len !== null) {
537 1
            $args[] = $len;
538
        }
539
540 2
        return new Expr\Func('SUBSTRING', $args);
541
    }
542
543
    /**
544
     * Creates a LOWER() function expression with the given argument.
545
     *
546
     * @param mixed $x Argument to be used in LOWER() function.
547
     *
548
     * @return Expr\Func A LOWER function expression.
549
     */
550 1
    public function lower($x)
551
    {
552 1
        return new Expr\Func('LOWER', [$x]);
553
    }
554
555
    /**
556
     * Creates an UPPER() function expression with the given argument.
557
     *
558
     * @param mixed $x Argument to be used in UPPER() function.
559
     *
560
     * @return Expr\Func An UPPER function expression.
561
     */
562 1
    public function upper($x)
563
    {
564 1
        return new Expr\Func('UPPER', [$x]);
565
    }
566
567
    /**
568
     * Creates a LENGTH() function expression with the given argument.
569
     *
570
     * @param mixed $x Argument to be used as argument of LENGTH() function.
571
     *
572
     * @return Expr\Func A LENGTH function expression.
573
     */
574 1
    public function length($x)
575
    {
576 1
        return new Expr\Func('LENGTH', [$x]);
577
    }
578
579
    /**
580
     * Creates a literal expression of the given argument.
581
     *
582
     * @param mixed $literal Argument to be converted to literal.
583
     *
584
     * @return Expr\Literal
585
     */
586 7
    public function literal($literal)
587
    {
588 7
        return new Expr\Literal($this->quoteLiteral($literal));
0 ignored issues
show
Bug introduced by
$this->quoteLiteral($literal) of type string is incompatible with the type array<mixed,mixed> expected by parameter $args of Doctrine\ORM\Query\Expr\Literal::__construct(). ( Ignorable by Annotation )

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

588
        return new Expr\Literal(/** @scrutinizer ignore-type */ $this->quoteLiteral($literal));
Loading history...
589
    }
590
591
    /**
592
     * Quotes a literal value, if necessary, according to the DQL syntax.
593
     *
594
     * @param mixed $literal The literal value.
595
     *
596
     * @return string
597
     */
598 18
    private function quoteLiteral($literal)
599
    {
600 18
        if (is_numeric($literal) && ! is_string($literal)) {
601 10
            return (string) $literal;
602 8
        } elseif (is_bool($literal)) {
603 1
            return $literal ? 'true' : 'false';
604
        }
605
606 7
        return "'" . str_replace("'", "''", $literal) . "'";
607
    }
608
609
    /**
610
     * Creates an instance of BETWEEN() function, with the given arguments.
611
     *
612
     * @param mixed      $val Valued to be inspected by range values.
613
     * @param int|string $x   Starting range value to be used in BETWEEN() function.
614
     * @param int|string $y   End point value to be used in BETWEEN() function.
615
     *
616
     * @return Expr\Between A BETWEEN expression.
617
     */
618 1
    public function between($val, $x, $y) : Expr\Between
619
    {
620 1
        return new Expr\Between(Expr\Between::BETWEEN, $val, $x, $y);
621
    }
622
623
    /**
624
     * Creates an instance of BETWEEN() function, with the given arguments.
625
     *
626
     * @param mixed      $val Valued to be inspected by range values.
627
     * @param int|string $x   Starting range value to be used in BETWEEN() function.
628
     * @param int|string $y   End point value to be used in BETWEEN() function.
629
     *
630
     * @return Expr\Between A BETWEEN expression.
631
     */
632 1
    public function notBetween($val, $x, $y) : Expr\Between
633
    {
634 1
        return new Expr\Between(Expr\Between::NOT_BETWEEN, $val, $x, $y);
635
    }
636
637
    /**
638
     * Creates an instance of TRIM() function, with the given argument.
639
     *
640
     * @param mixed $x Argument to be used as argument of TRIM() function.
641
     *
642
     * @return Expr\Func a TRIM expression.
643
     */
644 1
    public function trim($x)
645
    {
646 1
        return new Expr\Func('TRIM', $x);
647
    }
648
649
    /**
650
     * Creates an instance of MEMBER OF function, with the given arguments.
651
     *
652
     * @param string $x Value to be checked
653
     * @param string $y Value to be checked against
654
     *
655
     * @return Expr\Comparison
656
     */
657 1
    public function isMemberOf($x, $y)
658
    {
659 1
        return new Expr\Comparison($x, 'MEMBER OF', $y);
660
    }
661
662
    /**
663
     * Creates an instance of INSTANCE OF function, with the given arguments.
664
     *
665
     * @param string $x Value to be checked
666
     * @param string $y Value to be checked against
667
     *
668
     * @return Expr\Comparison
669
     */
670 1
    public function isInstanceOf($x, $y)
671
    {
672 1
        return new Expr\Comparison($x, 'INSTANCE OF', $y);
673
    }
674
}
675