LogicalExpression::where()   A
last analyzed

Complexity

Conditions 1
Paths 1

Size

Total Lines 4
Code Lines 2

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 2
CRAP Score 1

Importance

Changes 0
Metric Value
cc 1
eloc 2
nc 1
nop 3
dl 0
loc 4
ccs 2
cts 2
cp 1
crap 1
rs 10
c 0
b 0
f 0
1
<?php
2
namespace Wandu\Database\Query\Expression;
3
4
use Wandu\Database\Contracts\ExpressionInterface;
5
6
/**
7
 * LogicalExpression = '(' ComparisonExpression (' AND '|' OR ') LogicalExpression ')' | ComparisonExpression
8
 *
9
 * @example `abc` = 30
10
 * @example (`abc` = 30 AND `foo` = 30 OR `foo` = 40)
11
 */
12
class LogicalExpression implements ExpressionInterface
13
{
14
    /** @var array */
15
    protected $operators = [];
16
    
17
    /** @var \Wandu\Database\Contracts\ExpressionInterface[] */
18
    protected $expressions = [];
19
20
    /**
21
     * @param string|array|callable $name
22
     * @param string $operator
23
     * @param string $value
24
     * @return static
25
     */
26 33
    public function where($name, $operator = null, $value = null)
27
    {
28 33
        return $this->andWhere($name, $operator, $value);
29
    }
30
31
    /**
32
     * @param string|array|callable $name
33
     * @param string $operator
34
     * @param string $value
35
     * @return static
36
     */
37 33
    public function andWhere($name, $operator = null, $value = null)
38
    {
39 33
        $this->addWhereQuery('AND', $name, $operator, $value);
40 33
        return $this;
41
    }
42
43
    /**
44
     * @param string|array|callable $name
45
     * @param string $operator
46
     * @param string $value
47
     * @return static
48
     */
49 11
    public function orWhere($name, $operator = null, $value = null)
50
    {
51 11
        $this->addWhereQuery('OR', $name, $operator, $value);
52 11
        return $this;
53
    }
54
55 33
    protected function addWhereQuery($logicalOp, $name, $operator = null, $value = null)
56
    {
57 33
        if ($name instanceof ExpressionInterface) {
58 1
            $this->operators[] = $logicalOp;
59 1
            $this->expressions[] = $name;
60 33
        } elseif (!is_string($name) && is_callable($name)) {
61 2
            $newWhere = new LogicalExpression();
62 2
            $newWhereResult = call_user_func($name, $newWhere);
63 2
            $this->operators[] = $logicalOp;
64 2
            $this->expressions[] = $newWhereResult ?: $newWhere;
65 33
        } elseif (!is_array($name)) {
66 33
            $this->operators[] = $logicalOp;
67 33
            $this->expressions[] = new ComparisonExpression($name, $operator, $value);
68
        } else {
69 4
            foreach ($name as $column => $value) {
70 4
                if (is_array($value)) {
71 4
                    $newWhere = new LogicalExpression();
72 4
                    foreach ($value as $innerOperator => $innerValue) {
73 4
                        $newWhere->andWhere($column, $innerOperator, $innerValue);
0 ignored issues
show
Bug introduced by
It seems like $column can also be of type integer; however, Wandu\Database\Query\Exp...lExpression::andWhere() does only seem to accept callable, maybe add an additional type check?

If a method or function can return multiple different values and unless you are sure that you only can receive a single value in this context, we recommend to add an additional type check:

/**
 * @return array|string
 */
function returnsDifferentValues($x) {
    if ($x) {
        return 'foo';
    }

    return array();
}

$x = returnsDifferentValues($y);
if (is_array($x)) {
    // $x is an array.
}

If this a common case that PHP Analyzer should handle natively, please let us know by opening an issue.

Loading history...
74
                    }
75 4
                    $this->operators[] = $logicalOp;
76 4
                    $this->expressions[] = $newWhere;
77
                } else {
78 1
                    $this->operators[] = $logicalOp;
79 4
                    $this->expressions[] = new ComparisonExpression($column, '=', $value);
80
                }
81
            }
82
        }
83 33
    }
84
85
    /**
86
     * {@inheritdoc}
87
     */
88 6
    public function toSql()
89
    {
90 6
        $sql = '';
91 6
        foreach ($this->expressions as $index => $expression) {
92 6
            if ($index) {
93 3
                $sql .= ' ' . $this->operators[$index] . ' ';
94
            }
95 6
            $sql .= $expression->toSql();
96
        }
97 6
        if (count($this->expressions) > 1) {
98 3
            $sql = "(" . $sql . ")";
99
        }
100 6
        return $sql;
101
    }
102
103
    /**
104
     * {@inheritdoc}
105
     */
106
    public function getBindings()
107
    {
108 36
        return array_reduce($this->expressions, function ($carry, ExpressionInterface $expression) {
109 35
            return array_merge($carry, $expression->getBindings());
110 36
        }, []);
111
    }
112
}
113