Query   A
last analyzed

Complexity

Total Complexity 35

Size/Duplication

Total Lines 454
Duplicated Lines 0 %

Test Coverage

Coverage 100%

Importance

Changes 3
Bugs 0 Features 0
Metric Value
wmc 35
eloc 81
c 3
b 0
f 0
dl 0
loc 454
ccs 116
cts 116
cp 1
rs 9.6

30 Methods

Rating   Name   Duplication   Size   Complexity  
A sql() 0 3 1
A __clone() 0 3 1
A bindings() 0 3 1
A condition() 0 15 3
A type() 0 3 1
A table() 0 3 1
A instance() 0 3 1
A insertInto() 0 7 1
A orHaving() 0 3 1
A andWhere() 0 3 1
A innerJoin() 0 7 1
A orderBy() 0 3 1
A builder() 0 5 1
A orWhere() 0 3 1
A reset() 0 17 1
A where() 0 3 1
A leftJoin() 0 7 1
A __construct() 0 3 1
A __toString() 0 3 1
A from() 0 11 1
A limit() 0 10 2
A rightJoin() 0 7 1
A update() 0 9 1
A having() 0 3 1
A select() 0 9 1
A groupBy() 0 5 1
A andHaving() 0 3 1
A deleteFrom() 0 13 1
A andOrderBy() 0 3 1
A alias() 0 17 3
1
<?php
2
3
namespace Rougin\Windstorm\Doctrine;
4
5
use Doctrine\DBAL\Query\QueryBuilder;
6
use Rougin\Windstorm\QueryInterface;
7
use Rougin\Windstorm\ResultInterface;
8
9
/**
10
 * Query
11
 *
12
 * @package Windstorm
13
 * @author  Rougin Gutib <[email protected]>
14
 */
15
class Query implements QueryInterface
16
{
17
    /**
18
     * @var \Doctrine\DBAL\Query\QueryBuilder
19
     */
20
    protected $builder;
21
22
    /**
23
     * @var string|null
24
     */
25
    protected $initial = null;
26
27
    /**
28
     * @var string
29
     */
30
    protected $table = '';
31
32
    /**
33
     * @var integer
34
     */
35
    protected $type = self::TYPE_SELECT;
36
37
    /**
38
     * Clones the builder instance.
39
     *
40
     * @return void
41
     */
42 9
    public function __clone()
43
    {
44 9
        $this->builder = clone $this->builder;
45 9
    }
46
47
    /**
48
     * Initializes the query instance.
49
     *
50
     * @param \Doctrine\DBAL\Query\QueryBuilder $builder
51
     */
52 231
    public function __construct(QueryBuilder $builder)
53
    {
54 231
        $this->builder = $builder;
55 231
    }
56
57
    /**
58
     * Returns the safe and compiled SQL.
59
     *
60
     * @return string
61
     */
62 5
    public function __toString()
63
    {
64 5
        return $this->sql();
65
    }
66
67
    /**
68
     * Generates an AND HAVING query.
69
     *
70
     * @param  string $key
71
     * @return \Rougin\Windstorm\HavingInterface
72
     */
73 6
    public function andHaving($key)
74
    {
75 6
        return new Having($this, $this->builder, $key, $this->initial, 'AND');
76
    }
77
78
    /**
79
     * Generates a multiple ORDER BY query.
80
     *
81
     * @param  string $key
82
     * @return \Rougin\Windstorm\OrderInterface
83
     */
84 6
    public function andOrderBy($key)
85
    {
86 6
        return new Order($this, $this->builder, $key, $this->initial, 'ADD');
87
    }
88
89
    /**
90
     * Generates an AND WHERE query.
91
     *
92
     * @param  string $key
93
     * @return \Rougin\Windstorm\WhereInterface
94
     */
95 6
    public function andWhere($key)
96
    {
97 6
        return new Where($this, $this->builder, $key, $this->initial, 'AND');
98
    }
99
100
    /**
101
     * Returns the SQL bindings specified.
102
     *
103
     * @return array
104
     */
105 42
    public function bindings()
106
    {
107 42
        return $this->builder->getParameters();
108
    }
109
110
    /**
111
     * Sets the Builder instance.
112
     *
113
     * @param  \Doctrine\DBAL\Query\QueryBuilder $builder
114
     * @return self
115
     */
116 156
    public function builder(QueryBuilder $builder)
117
    {
118 156
        $this->builder = $builder;
119
120 156
        return $this;
121
    }
122
123
    /**
124
     * Generates a DELETE FROM query.
125
     *
126
     * @param  string      $table
127
     * @param  string|null $alias
128
     * @return self
129
     */
130 30
    public function deleteFrom($table, $alias = null)
131
    {
132 30
        $this->reset();
133
134 30
        $this->initial = $alias;
135
136 30
        $this->table = $table;
137
138 30
        $this->type = self::TYPE_DELETE;
139
140 30
        $this->builder->delete($table, $this->initial);
141
142 30
        return $this;
143
    }
144
145
    /**
146
     * Generates a FROM query.
147
     *
148
     * @param  string      $table
149
     * @param  string|null $alias
150
     * @return self
151
     */
152 162
    public function from($table, $alias = null)
153
    {
154 162
        $this->initial = $alias;
155
156 162
        $this->table = $table;
157
158 162
        $this->type = self::TYPE_SELECT;
159
160 162
        $this->builder->from($table, $alias);
161
162 162
        return $this;
163
    }
164
165
    /**
166
     * Generates a GROUP BY query.
167
     *
168
     * @param  array|string $fields
169
     * @return self
170
     */
171 6
    public function groupBy($fields)
172
    {
173 6
        $this->builder->groupBy($fields);
174
175 6
        return $this;
176
    }
177
178
    /**
179
     * Generates a HAVING query.
180
     *
181
     * @param  string $key
182
     * @return \Rougin\Windstorm\HavingInterface
183
     */
184 18
    public function having($key)
185
    {
186 18
        return new Having($this, $this->builder, $key, $this->initial);
187
    }
188
189
    /**
190
     * Generates an INNER JOIN query.
191
     *
192
     * @param  string      $table
193
     * @param  string      $local
194
     * @param  string      $foreign
195
     * @param  string|null $alias
196
     * @return self
197
     */
198 6
    public function innerJoin($table, $local, $foreign, $alias = null)
199
    {
200 6
        list($alias, $where) = $this->condition($table, $local, $foreign, $alias);
201
202 6
        $this->builder->innerJoin($this->initial, $table, $alias, $where);
203
204 6
        return $this;
205
    }
206
207
    /**
208
     * Generates an INSERT INTO query.
209
     *
210
     * @param  string $table
211
     * @return \Rougin\Windstorm\InsertInterface
212
     */
213 9
    public function insertInto($table)
214
    {
215 9
        $this->reset();
216
217 9
        $this->type = self::TYPE_INSERT;
218
219 9
        return new Insert($this, $this->builder, $table);
220
    }
221
222
    /**
223
     * Returns the instance of the query builder, if available.
224
     *
225
     * @return mixed
226
     */
227 9
    public function instance()
228
    {
229 9
        return $this->builder;
230
    }
231
232
    /**
233
     * Generates a LEFT JOIN query.
234
     *
235
     * @param  string      $table
236
     * @param  string      $local
237
     * @param  string      $foreign
238
     * @param  string|null $alias
239
     * @return self
240
     */
241 6
    public function leftJoin($table, $local, $foreign, $alias = null)
242
    {
243 6
        list($alias, $where) = $this->condition($table, $local, $foreign, $alias);
244
245 6
        $this->builder->leftJoin($this->initial, $table, $alias, $where);
246
247 6
        return $this;
248
    }
249
250
    /**
251
     * Performs a LIMIT query.
252
     *
253
     * @param  integer      $limit
254
     * @param  integer|null $offset
255
     * @return self
256
     */
257 6
    public function limit($limit, $offset = null)
258
    {
259 6
        $this->builder->setMaxResults($limit);
260
261 6
        if ($offset !== null)
262 4
        {
263 6
            $this->builder->setFirstResult($offset);
264 4
        }
265
266 6
        return $this;
267
    }
268
269
    /**
270
     * Generates an OR HAVING query.
271
     *
272
     * @param  string $key
273
     * @return \Rougin\Windstorm\HavingInterface
274
     */
275 6
    public function orHaving($key)
276
    {
277 6
        return new Having($this, $this->builder, $key, $this->initial, 'OR');
278
    }
279
280
    /**
281
     * Generates an OR WHERE query.
282
     *
283
     * @param  string $key
284
     * @return \Rougin\Windstorm\WhereInterface
285
     */
286 6
    public function orWhere($key)
287
    {
288 6
        return new Where($this, $this->builder, $key, $this->initial, 'OR');
289
    }
290
291
    /**
292
     * Generates an ORDER BY query.
293
     *
294
     * @param  string $key
295
     * @return \Rougin\Windstorm\OrderInterface
296
     */
297 24
    public function orderBy($key)
298
    {
299 24
        return new Order($this, $this->builder, $key, $this->initial);
300
    }
301
302
    /**
303
     * Generates a RIGHT JOIN query.
304
     *
305
     * @param  string      $table
306
     * @param  string      $local
307
     * @param  string      $foreign
308
     * @param  string|null $alias
309
     * @return self
310
     */
311 6
    public function rightJoin($table, $local, $foreign, $alias = null)
312
    {
313 6
        list($alias, $where) = $this->condition($table, $local, $foreign, $alias);
314
315 6
        $this->builder->rightJoin($this->initial, $table, $alias, $where);
316
317 6
        return $this;
318
    }
319
320
    /**
321
     * Generates a SELECT query.
322
     *
323
     * @param  array|string $fields
324
     * @return self
325
     */
326 168
    public function select($fields)
327
    {
328 168
        $this->reset();
329
330 168
        $this->type = self::TYPE_SELECT;
331
332 168
        $this->builder->select($fields);
333
334 168
        return $this;
335
    }
336
337
    /**
338
     * Returns the safe and compiled SQL.
339
     *
340
     * @return string
341
     */
342 204
    public function sql()
343
    {
344 204
        return $this->builder->getSql();
345
    }
346
347
    /**
348
     * Returns the table name from the query.
349
     *
350
     * @return string
351
     */
352 6
    public function table()
353
    {
354 6
        return $this->table;
355
    }
356
357
    /**
358
     * Returns the type of the query.
359
     *
360
     * @return integer
361
     */
362 36
    public function type()
363
    {
364 36
        return $this->type;
365
    }
366
367
    /**
368
     * Generates an UPDATE query.
369
     *
370
     * @param  string      $table
371
     * @param  string|null $alias
372
     * @return \Rougin\Windstorm\UpdateInterface
373
     */
374 15
    public function update($table, $alias = null)
375
    {
376 15
        $this->reset();
377
378 15
        $this->type = self::TYPE_UPDATE;
379
380 15
        list($this->initial, $this->table) = array($alias, $table);
381
382 15
        return new Update($this, $this->builder, $table, $alias);
383
    }
384
385
    /**
386
     * Generates a WHERE query.
387
     *
388
     * @param  string $key
389
     * @return \Rougin\Windstorm\WhereInterface
390
     */
391 105
    public function where($key)
392
    {
393 105
        return new Where($this, $this->builder, $key, $this->initial);
394
    }
395
396
    /**
397
     * Returns an available table alias.
398
     *
399
     * @param  string $table
400
     * @return string
401
     */
402 18
    protected function alias($table)
403
    {
404 18
        $characters = str_split($table);
405
406 18
        $result = $characters[0];
407
408 18
        foreach ($characters as $character)
409
        {
410 18
            $character = strtolower($character);
411
412 18
            if ($this->initial !== $character)
413 12
            {
414 18
                $result = $character; break;
415
            }
416 12
        }
417
418 18
        return (string) $result;
419
    }
420
421
    /**
422
     * Returns a JOIN condition.
423
     *
424
     * @param  string      $table
425
     * @param  string      $local
426
     * @param  string      $foreign
427
     * @param  string|null $alias
428
     * @return string
429
     */
430 18
    protected function condition($table, $local, $foreign, $alias = null)
431
    {
432 18
        if (strpos($local, '.') === false)
433 12
        {
434 18
            $local = $this->initial . '.' . $local;
435 12
        }
436
437 18
        if ($alias === null)
438 12
        {
439 18
            $alias = $this->alias((string) $table);
440 12
        }
441
442 18
        $local .= ' = ' . $alias . '.' . $foreign;
443
444 18
        return array($alias, (string) $local);
445
    }
446
447
    /**
448
     * Resets the whole query builder.
449
     *
450
     * @return self
451
     */
452 222
    protected function reset()
453
    {
454 222
        $this->builder->setMaxResults(null);
455
456 222
        $this->builder->setFirstResult(null);
457
458 222
        $this->initial = (string) '';
459
460 222
        $this->builder->resetQueryParts();
461
462 222
        $this->table = (string) '';
463
464 222
        $this->builder->setParameters(array());
465
466 222
        $this->type = self::TYPE_SELECT;
467
468 222
        return $this;
469
    }
470
}
471