Completed
Pull Request — master (#1427)
by Andreas
06:15
created

QueryExpressionVisitor   A

Complexity

Total Complexity 16

Size/Duplication

Total Lines 117
Duplicated Lines 0 %

Coupling/Cohesion

Components 1
Dependencies 6

Test Coverage

Coverage 0%

Importance

Changes 0
Metric Value
wmc 16
c 0
b 0
f 0
lcom 1
cbo 6
dl 0
loc 117
ccs 0
cts 45
cp 0
rs 10

4 Methods

Rating   Name   Duplication   Size   Complexity  
A __construct() 0 4 1
C walkComparison() 0 29 11
A walkCompositeExpression() 0 15 3
A walkValue() 0 4 1
1
<?php
2
/*
3
 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
4
 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
5
 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
6
 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
7
 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
8
 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
9
 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
10
 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
11
 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
12
 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
13
 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
14
 *
15
 * This software consists of voluntary contributions made by many individuals
16
 * and is licensed under the MIT license. For more information, see
17
 * <http://www.doctrine-project.org>.
18
 */
19
20
namespace Doctrine\ODM\MongoDB\Query;
21
22
use Doctrine\Common\Collections\Expr\Comparison;
23
use Doctrine\Common\Collections\Expr\CompositeExpression;
24
use Doctrine\Common\Collections\Expr\ExpressionVisitor;
25
use Doctrine\Common\Collections\Expr\Value;
26
27
/**
28
 * Converts Collection expressions to query expressions.
29
 *
30
 * @since  1.0
31
 */
32
class QueryExpressionVisitor extends ExpressionVisitor
33
{
34
    /**
35
     * Map Criteria API comparison operators to query builder methods
36
     *
37
     * @todo Implement support for Comparison::CONTAINS
38
     * @var array
39
     */
40
    private static $operatorMethods = array(
41
        Comparison::EQ => 'equals',
42
        Comparison::GT => 'gt',
43
        Comparison::GTE => 'gte',
44
        Comparison::IN => 'in',
45
        Comparison::IS => 'equals',
46
        Comparison::LT => 'lt',
47
        Comparison::LTE => 'lte',
48
        Comparison::NEQ => 'notEqual',
49
        Comparison::NIN => 'notIn',
50
    );
51
52
    /**
53
     * Map Criteria API composite types to query builder methods
54
     *
55
     * @var array
56
     */
57
    private static $compositeMethods = array(
58
        CompositeExpression::TYPE_AND => 'addAnd',
59
        CompositeExpression::TYPE_OR => 'addOr',
60
    );
61
62
    /**
63
     * @var Builder
64
     */
65
    protected $builder;
66
67
    /**
68
     * Constructor.
69
     *
70
     * @param Builder $builder
71
     */
72
    public function __construct(Builder $builder)
73
    {
74
        $this->builder = $builder;
75
    }
76
77
    /**
78
     * Converts a comparison expression into the target query language output.
79
     *
80
     * @see ExpressionVisitor::walkComparison()
81
     * @param Comparison $comparison
82
     * @return \Doctrine\ODM\MongoDB\Query\Expr
83
     */
84
    public function walkComparison(Comparison $comparison)
85
    {
86
        switch ($comparison->getOperator()) {
87
            case Comparison::EQ:
88
            case Comparison::GT:
89
            case Comparison::GTE:
90
            case Comparison::IN:
91
            case Comparison::IS:
92
            case Comparison::LT:
93
            case Comparison::LTE:
94
            case Comparison::NEQ:
95
            case Comparison::NIN:
96
                $method = self::$operatorMethods[$comparison->getOperator()];
97
98
                return $this->builder->expr()
99
                    ->field($comparison->getField())
100
                    ->{$method}($this->walkValue($comparison->getValue()));
101
102
            case Comparison::CONTAINS:
103
                $value = $this->walkValue($comparison->getValue());
104
105
                return $this->builder->expr()
106
                    ->field($comparison->getField())
107
                    ->equals(new \MongoRegex('/' . preg_quote($value, '/') . '/'));
108
109
            default:
110
                throw new \RuntimeException('Unknown comparison operator: ' . $comparison->getOperator());
111
        }
112
    }
113
114
    /**
115
     * Converts a composite expression into the target query language output.
116
     *
117
     * @see ExpressionVisitor::walkCompositeExpression()
118
     * @param CompositeExpression $compositeExpr
119
     * @return \Doctrine\ODM\MongoDB\Query\Expr
120
     */
121
    public function walkCompositeExpression(CompositeExpression $compositeExpr)
122
    {
123
        if ( ! isset(self::$compositeMethods[$compositeExpr->getType()])) {
124
            throw new \RuntimeException('Unknown composite ' . $compositeExpr->getType());
125
        }
126
127
        $method = self::$compositeMethods[$compositeExpr->getType()];
128
        $expr = $this->builder->expr();
129
130
        foreach ($compositeExpr->getExpressionList() as $child) {
131
            $expr->{$method}($this->dispatch($child));
132
        }
133
134
        return $expr;
135
    }
136
137
    /**
138
     * Converts a value expression into the target query language part.
139
     *
140
     * @see ExpressionVisitor::walkValue()
141
     * @param Value $value
142
     * @return mixed
143
     */
144
    public function walkValue(Value $value)
145
    {
146
        return $value->getValue();
147
    }
148
}
149