Completed
Push — intermixed-snippets ( 1a61e3 )
by Paul
01:52
created

Select::limit()   A

Complexity

Conditions 2
Paths 2

Size

Total Lines 9
Code Lines 6

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 7
CRAP Score 2

Importance

Changes 0
Metric Value
dl 0
loc 9
ccs 7
cts 7
cp 1
rs 9.6666
c 0
b 0
f 0
cc 2
eloc 6
nc 2
nop 1
crap 2
1
<?php
2
/**
3
 *
4
 * This file is part of Aura for PHP.
5
 *
6
 * @license http://opensource.org/licenses/mit-license.php MIT
7
 *
8
 */
9
namespace Aura\SqlQuery\Common;
10
11
use Aura\SqlQuery\AbstractQuery;
12
use Aura\SqlQuery\Exception;
13
14
/**
15
 *
16
 * An object for SELECT queries.
17
 *
18
 * @package Aura.SqlQuery
19
 *
20
 */
21
class Select extends AbstractQuery implements SelectInterface
22
{
23
    use WhereTrait;
24
    use LimitOffsetTrait { limit as setLimit; offset as setOffset; }
25
26
    /**
27
     *
28
     * An array of union SELECT statements.
29
     *
30
     * @var array
31
     *
32
     */
33
    protected $union = array();
34
35
    /**
36
     *
37
     * Is this a SELECT FOR UPDATE?
38
     *
39
     * @var
40
     *
41
     */
42
    protected $for_update = false;
43
44
    /**
45
     *
46
     * The columns to be selected.
47
     *
48
     * @var array
49
     *
50
     */
51
    protected $cols = array();
52
53
    /**
54
     *
55
     * Select from these tables; includes JOIN clauses.
56
     *
57
     * @var array
58
     *
59
     */
60
    protected $from = array();
61
62
    /**
63
     *
64
     * The current key in the `$from` array.
65
     *
66
     * @var int
67
     *
68
     */
69
    protected $from_key = -1;
70
71
    /**
72
     *
73
     * Tracks which JOIN clauses are attached to which FROM tables.
74
     *
75
     * @var array
76
     *
77
     */
78
    protected $join = array();
79
80
    /**
81
     *
82
     * GROUP BY these columns.
83
     *
84
     * @var array
85
     *
86
     */
87
    protected $group_by = array();
88
89
    /**
90
     *
91
     * The list of HAVING conditions.
92
     *
93
     * @var array
94
     *
95
     */
96
    protected $having = array();
97
98
    /**
99
     *
100
     * The page number to select.
101
     *
102
     * @var int
103
     *
104
     */
105
    protected $page = 0;
106
107
    /**
108
     *
109
     * The number of rows per page.
110
     *
111
     * @var int
112
     *
113
     */
114
    protected $paging = 10;
115
116
    /**
117
     *
118
     * Tracks table references to avoid duplicate identifiers.
119
     *
120
     * @var array
121
     *
122
     */
123
    protected $table_refs = array();
124
125
    /**
126
     *
127
     * Returns this query object as an SQL statement string.
128
     *
129
     * @return string An SQL statement string.
130
     *
131
     */
132 199
    public function getStatement()
133
    {
134 199
        $union = '';
135 199
        if (! empty($this->union)) {
136 15
            $union = implode(PHP_EOL, $this->union) . PHP_EOL;
137 15
        }
138 199
        return $union . $this->build();
139
    }
140
141
    /**
142
     *
143
     * Sets the number of rows per page.
144
     *
145
     * @param int $paging The number of rows to page at.
146
     *
147
     * @return $this
148
     *
149
     */
150 10
    public function setPaging($paging)
151
    {
152 10
        $this->paging = (int) $paging;
153 10
        if ($this->page) {
154 5
            $this->setPagingLimitOffset();
155 5
        }
156 10
        return $this;
157
    }
158
159
    /**
160
     *
161
     * Gets the number of rows per page.
162
     *
163
     * @return int The number of rows per page.
164
     *
165
     */
166 10
    public function getPaging()
167
    {
168 10
        return $this->paging;
169
    }
170
171
    /**
172
     *
173
     * Makes the select FOR UPDATE (or not).
174
     *
175
     * @param bool $enable Whether or not the SELECT is FOR UPDATE (default
176
     * true).
177
     *
178
     * @return $this
179
     *
180
     */
181 25
    public function forUpdate($enable = true)
182
    {
183 25
        $this->for_update = (bool) $enable;
184 25
        return $this;
185
    }
186
187
    /**
188
     *
189
     * Makes the select DISTINCT (or not).
190
     *
191
     * @param bool $enable Whether or not the SELECT is DISTINCT (default
192
     * true).
193
     *
194
     * @return $this
195
     *
196
     */
197 16
    public function distinct($enable = true)
198
    {
199 16
        $this->setFlag('DISTINCT', $enable);
200 16
        return $this;
201
    }
202
203
    /**
204
     *
205
     * Is the select DISTINCT?
206
     *
207
     * @return bool
208
     *
209
     */
210 10
    public function isDistinct()
211
    {
212 10
        return $this->hasFlag('DISTINCT');
213
    }
214
215
    /**
216
     *
217
     * Adds columns to the query.
218
     *
219
     * Multiple calls to cols() will append to the list of columns, not
220
     * overwrite the previous columns.
221
     *
222
     * @param array $cols The column(s) to add to the query. The elements can be
223
     * any mix of these: `array("col", "col AS alias", "col" => "alias")`
224
     *
225
     * @return $this
226
     *
227
     */
228 239
    public function cols(array $cols)
229
    {
230 239
        foreach ($cols as $key => $val) {
231 239
            $this->addCol($key, $val);
232 239
        }
233 239
        return $this;
234
    }
235
236
    /**
237
     *
238
     * Adds a column and alias to the columns to be selected.
239
     *
240
     * @param mixed $key If an integer, ignored. Otherwise, the column to be
241
     * added.
242
     *
243
     * @param mixed $val If $key was an integer, the column to be added;
244
     * otherwise, the column alias.
245
     *
246
     * @return null
247
     *
248
     */
249 239
    protected function addCol($key, $val)
250
    {
251 239
        if (is_string($key)) {
252
            // [col => alias]
253 25
            $this->cols[$val] = $key;
254 25
        } else {
255 229
            $this->addColWithAlias($val);
256
        }
257 239
    }
258
259
    /**
260
     *
261
     * Adds a column with an alias to the columns to be selected.
262
     *
263
     * @param string $spec The column specification: "col alias",
264
     * "col AS alias", or something else entirely.
265
     *
266
     * @return null
267
     *
268
     */
269 229
    protected function addColWithAlias($spec)
270
    {
271 229
        $parts = explode(' ', $spec);
272 229
        $count = count($parts);
273 229
        if ($count == 2) {
274
            // "col alias"
275 5
            $this->cols[$parts[1]] = $parts[0];
276 229
        } elseif ($count == 3 && strtoupper($parts[1]) == 'AS') {
277
            // "col AS alias"
278 5
            $this->cols[$parts[2]] = $parts[0];
279 5
        } else {
280
            // no recognized alias
281 229
            $this->cols[] = $spec;
282
        }
283 229
    }
284
285
    /**
286
     *
287
     * Remove a column via its alias.
288
     *
289
     * @param string $alias The column to remove
290
     *
291
     * @return bool
292
     *
293
     */
294 15
    public function removeCol($alias)
295
    {
296 15
        if (isset($this->cols[$alias])) {
297 5
            unset($this->cols[$alias]);
298
299 5
            return true;
300
        }
301
302 10
        $index = array_search($alias, $this->cols);
303 10
        if ($index !== false) {
304 5
            unset($this->cols[$index]);
305 5
            return true;
306
        }
307
308 5
        return false;
309
    }
310
311
    /**
312
     *
313
     * Has the column or alias been added to the query?
314
     *
315
     * @param string $alias The column or alias to look for
316
     *
317
     * @return bool
318
     *
319
     */
320 5
    public function hasCol($alias)
321
    {
322 5
        return isset($this->cols[$alias]) || array_search($alias, $this->cols) !== false;
323
    }
324
325
    /**
326
     *
327
     * Does the query have any columns in it?
328
     *
329
     * @return bool
330
     *
331
     */
332 5
    public function hasCols()
333
    {
334 5
        return (bool) $this->cols;
335
    }
336
337
    /**
338
     *
339
     * Returns a list of columns.
340
     *
341
     * @return array
342
     *
343
     */
344 15
    public function getCols()
345
    {
346 15
        return $this->cols;
347
    }
348
349
    /**
350
     *
351
     * Tracks table references.
352
     *
353
     * @param string $type FROM, JOIN, etc.
354
     *
355
     * @param string $spec The table and alias name.
356
     *
357
     * @return null
358
     *
359
     * @throws Exception when the reference has already been used.
360
     *
361
     */
362 164
    protected function addTableRef($type, $spec)
363
    {
364 164
        $name = $spec;
365
366 164
        $pos = strripos($name, ' AS ');
367 164
        if ($pos !== false) {
368 35
            $name = trim(substr($name, $pos + 4));
369 35
        }
370
371 164
        if (isset($this->table_refs[$name])) {
372 25
            $used = $this->table_refs[$name];
373 25
            throw new Exception("Cannot reference '$type $spec' after '$used'");
374
        }
375
376 164
        $this->table_refs[$name] = "$type $spec";
377 164
    }
378
379
    /**
380
     *
381
     * Adds a FROM element to the query; quotes the table name automatically.
382
     *
383
     * @param string $spec The table specification; "foo" or "foo AS bar".
384
     *
385
     * @return $this
386
     *
387
     */
388 154
    public function from($spec)
389
    {
390 154
        $this->addTableRef('FROM', $spec);
391 154
        return $this->addFrom($this->quoter->quoteName($spec));
392
    }
393
394
    /**
395
     *
396
     * Adds a raw unquoted FROM element to the query; useful for adding FROM
397
     * elements that are functions.
398
     *
399
     * @param string $spec The table specification, e.g. "function_name()".
400
     *
401
     * @return $this
402
     *
403
     */
404 5
    public function fromRaw($spec)
405
    {
406 5
        $this->addTableRef('FROM', $spec);
407 5
        return $this->addFrom($spec);
408
    }
409
410
    /**
411
     *
412
     * Adds to the $from property and increments the key count.
413
     *
414
     * @param string $spec The table specification.
415
     *
416
     * @return $this
417
     *
418
     */
419 164
    protected function addFrom($spec)
420
    {
421 164
        $this->from[] = array($spec);
422 164
        $this->from_key ++;
423 164
        return $this;
424
    }
425
426
    /**
427
     *
428
     * Adds an aliased sub-select to the query.
429
     *
430
     * @param string|Select $spec If a Select object, use as the sub-select;
431
     * if a string, the sub-select string.
432
     *
433
     * @param string $name The alias name for the sub-select.
434
     *
435
     * @return $this
436
     *
437
     */
438 15
    public function fromSubSelect($spec, $name)
439
    {
440 15
        $this->addTableRef('FROM (SELECT ...) AS', $name);
441 10
        $spec = $this->subSelect($spec, '        ');
442 10
        $name = $this->quoter->quoteName($name);
443 10
        return $this->addFrom("({$spec}    ) AS $name");
444
    }
445
446
    /**
447
     *
448
     * Formats a sub-SELECT statement, binding values from a Select object as
449
     * needed.
450
     *
451
     * @param string|SelectInterface $spec A sub-SELECT specification.
452
     *
453
     * @param string $indent Indent each line with this string.
454
     *
455
     * @return string The sub-SELECT string.
456
     *
457
     */
458 25
    protected function subSelect($spec, $indent)
459
    {
460 25
        if ($spec instanceof SelectInterface) {
461 10
            $this->bindValues($spec->getBindValues());
462 10
        }
463
464 25
        return PHP_EOL . $indent
465 25
            . ltrim(preg_replace('/^/m', $indent, (string) $spec))
466 25
            . PHP_EOL;
467
    }
468
469
    /**
470
     *
471
     * Adds a JOIN table and columns to the query.
472
     *
473
     * @param string $join The join type: inner, left, natural, etc.
474
     *
475
     * @param string $spec The table specification; "foo" or "foo AS bar".
476
     *
477
     * @param string $cond Join on this condition.
478
     *
479
     * @param array $bind Values to bind to ?-placeholders in the condition.
0 ignored issues
show
Bug introduced by
There is no parameter named $bind. Was it maybe removed?

This check looks for PHPDoc comments describing methods or function parameters that do not exist on the corresponding method or function.

Consider the following example. The parameter $italy is not defined by the method finale(...).

/**
 * @param array $germany
 * @param array $island
 * @param array $italy
 */
function finale($germany, $island) {
    return "2:1";
}

The most likely cause is that the parameter was removed, but the annotation was not.

Loading history...
480
     *
481
     * @return $this
482
     *
483
     * @throws Exception
484
     *
485
     */
486 45
    public function join($join, $spec, ...$cond)
487
    {
488 45
        $join = strtoupper(ltrim("$join JOIN"));
489 45
        $this->addTableRef($join, $spec);
490
491 40
        $spec = $this->quoter->quoteName($spec);
492 40
        $cond = $this->fixJoinConditions($cond);
493 40
        return $this->addJoin(rtrim("$join $spec $cond"));
494
    }
495
496
    /**
497
     *
498
     * Fixes a JOIN condition to quote names in the condition and prefix it
499
     * with a condition type ('ON' is the default and 'USING' is recognized).
500
     *
501
     * @param string $cond Join on this condition.
502
     *
503
     * @param array $bind Values to bind to ?-placeholders in the condition.
0 ignored issues
show
Bug introduced by
There is no parameter named $bind. Was it maybe removed?

This check looks for PHPDoc comments describing methods or function parameters that do not exist on the corresponding method or function.

Consider the following example. The parameter $italy is not defined by the method finale(...).

/**
 * @param array $germany
 * @param array $island
 * @param array $italy
 */
function finale($germany, $island) {
    return "2:1";
}

The most likely cause is that the parameter was removed, but the annotation was not.

Loading history...
504
     *
505
     * @return string
506
     *
507
     */
508 55
    protected function fixJoinConditions(array $cond)
509
    {
510 55
        if (empty($cond)) {
511 25
            return '';
512
        }
513
514 55
        $cond = $this->fixConditions($cond);
515
516 55
        if (strtoupper(substr(ltrim($cond), 0, 3)) == 'ON ') {
517 5
            return $cond;
518
        }
519
520 55
        if (strtoupper(substr(ltrim($cond), 0, 6)) == 'USING ') {
521 5
            return $cond;
522
        }
523
524 50
        return 'ON ' . $cond;
525
    }
526
527
    /**
528
     *
529
     * Adds a INNER JOIN table and columns to the query.
530
     *
531
     * @param string $spec The table specification; "foo" or "foo AS bar".
532
     *
533
     * @param string $cond Join on this condition.
0 ignored issues
show
Bug introduced by
There is no parameter named $cond. Was it maybe removed?

This check looks for PHPDoc comments describing methods or function parameters that do not exist on the corresponding method or function.

Consider the following example. The parameter $italy is not defined by the method finale(...).

/**
 * @param array $germany
 * @param array $island
 * @param array $italy
 */
function finale($germany, $island) {
    return "2:1";
}

The most likely cause is that the parameter was removed, but the annotation was not.

Loading history...
534
     *
535
     * @param array $bind Values to bind to ?-placeholders in the condition.
0 ignored issues
show
Bug introduced by
There is no parameter named $bind. Was it maybe removed?

This check looks for PHPDoc comments describing methods or function parameters that do not exist on the corresponding method or function.

Consider the following example. The parameter $italy is not defined by the method finale(...).

/**
 * @param array $germany
 * @param array $island
 * @param array $italy
 */
function finale($germany, $island) {
    return "2:1";
}

The most likely cause is that the parameter was removed, but the annotation was not.

Loading history...
536
     *
537
     * @return $this
538
     *
539
     * @throws Exception
540
     *
541
     */
542 10
    public function innerJoin($spec, ...$conditions)
543
    {
544 10
        return $this->join('INNER', $spec, ...$conditions);
545
    }
546
547
    /**
548
     *
549
     * Adds a LEFT JOIN table and columns to the query.
550
     *
551
     * @param string $spec The table specification; "foo" or "foo AS bar".
552
     *
553
     * @param string $cond Join on this condition.
0 ignored issues
show
Bug introduced by
There is no parameter named $cond. Was it maybe removed?

This check looks for PHPDoc comments describing methods or function parameters that do not exist on the corresponding method or function.

Consider the following example. The parameter $italy is not defined by the method finale(...).

/**
 * @param array $germany
 * @param array $island
 * @param array $italy
 */
function finale($germany, $island) {
    return "2:1";
}

The most likely cause is that the parameter was removed, but the annotation was not.

Loading history...
554
     *
555
     * @param array $bind Values to bind to ?-placeholders in the condition.
0 ignored issues
show
Bug introduced by
There is no parameter named $bind. Was it maybe removed?

This check looks for PHPDoc comments describing methods or function parameters that do not exist on the corresponding method or function.

Consider the following example. The parameter $italy is not defined by the method finale(...).

/**
 * @param array $germany
 * @param array $island
 * @param array $italy
 */
function finale($germany, $island) {
    return "2:1";
}

The most likely cause is that the parameter was removed, but the annotation was not.

Loading history...
556
     *
557
     * @return $this
558
     *
559
     * @throws Exception
560
     *
561
     */
562 10
    public function leftJoin($spec, ...$conditions)
563
    {
564 10
        return $this->join('LEFT', $spec, ...$conditions);
565
    }
566
567
    /**
568
     *
569
     * Adds a JOIN to an aliased subselect and columns to the query.
570
     *
571
     * @param string $join The join type: inner, left, natural, etc.
572
     *
573
     * @param string|Select $spec If a Select
574
     * object, use as the sub-select; if a string, the sub-select
575
     * command string.
576
     *
577
     * @param string $name The alias name for the sub-select.
578
     *
579
     * @param string $cond Join on this condition.
0 ignored issues
show
Bug introduced by
There is no parameter named $cond. Was it maybe removed?

This check looks for PHPDoc comments describing methods or function parameters that do not exist on the corresponding method or function.

Consider the following example. The parameter $italy is not defined by the method finale(...).

/**
 * @param array $germany
 * @param array $island
 * @param array $italy
 */
function finale($germany, $island) {
    return "2:1";
}

The most likely cause is that the parameter was removed, but the annotation was not.

Loading history...
580
     *
581
     * @param array $bind Values to bind to ?-placeholders in the condition.
0 ignored issues
show
Bug introduced by
There is no parameter named $bind. Was it maybe removed?

This check looks for PHPDoc comments describing methods or function parameters that do not exist on the corresponding method or function.

Consider the following example. The parameter $italy is not defined by the method finale(...).

/**
 * @param array $germany
 * @param array $island
 * @param array $italy
 */
function finale($germany, $island) {
    return "2:1";
}

The most likely cause is that the parameter was removed, but the annotation was not.

Loading history...
582
     *
583
     * @return $this
584
     *
585
     * @throws Exception
586
     *
587
     */
588 20
    public function joinSubSelect($join, $spec, $name, ...$conditions)
589
    {
590 20
        $join = strtoupper(ltrim("$join JOIN"));
591 20
        $this->addTableRef("$join (SELECT ...) AS", $name);
592
593 15
        $spec = $this->subSelect($spec, '            ');
594 15
        $name = $this->quoter->quoteName($name);
595 15
        $cond = $this->fixJoinConditions($conditions);
596
597 15
        $text = rtrim("$join ($spec        ) AS $name $cond");
598 15
        return $this->addJoin('        ' . $text);
599
    }
600
601
    /**
602
     *
603
     * Adds the JOIN to the right place, given whether or not a FROM has been
604
     * specified yet.
605
     *
606
     * @param string $spec The JOIN clause.
607
     *
608
     * @return $this
609
     *
610
     */
611 55
    protected function addJoin($spec)
612
    {
613 55
        $from_key = ($this->from_key == -1) ? 0 : $this->from_key;
614 55
        $this->join[$from_key][] = $spec;
615 55
        return $this;
616
    }
617
618
    /**
619
     *
620
     * Adds grouping to the query.
621
     *
622
     * @param array $spec The column(s) to group by.
623
     *
624
     * @return $this
625
     *
626
     */
627 5
    public function groupBy(array $spec)
628
    {
629 5
        foreach ($spec as $col) {
630 5
            $this->group_by[] = $this->quoter->quoteNamesIn($col);
631 5
        }
632 5
        return $this;
633
    }
634
635
    /**
636
     *
637
     * Adds a HAVING condition to the query by AND.
638
     *
639
     * @return $this
640
     *
641
     */
642 15
    public function having(...$conditions)
643
    {
644 15
        $this->addClauseConditions('having', 'AND', $conditions);
645 15
        return $this;
646
    }
647
648
    /**
649
     *
650
     * Adds a HAVING condition to the query by OR.
651
     *
652
     * @param string $cond The HAVING condition.
0 ignored issues
show
Bug introduced by
There is no parameter named $cond. Was it maybe removed?

This check looks for PHPDoc comments describing methods or function parameters that do not exist on the corresponding method or function.

Consider the following example. The parameter $italy is not defined by the method finale(...).

/**
 * @param array $germany
 * @param array $island
 * @param array $italy
 */
function finale($germany, $island) {
    return "2:1";
}

The most likely cause is that the parameter was removed, but the annotation was not.

Loading history...
653
     *
654
     * @param array $bind arguments to bind to placeholders
0 ignored issues
show
Bug introduced by
There is no parameter named $bind. Was it maybe removed?

This check looks for PHPDoc comments describing methods or function parameters that do not exist on the corresponding method or function.

Consider the following example. The parameter $italy is not defined by the method finale(...).

/**
 * @param array $germany
 * @param array $island
 * @param array $italy
 */
function finale($germany, $island) {
    return "2:1";
}

The most likely cause is that the parameter was removed, but the annotation was not.

Loading history...
655
     *
656
     * @return $this
657
     *
658
     * @see having()
659
     *
660
     */
661 10
    public function orHaving(...$conditions)
662
    {
663 10
        $this->addClauseConditions('having', 'OR', $conditions);
664 10
        return $this;
665
    }
666
667
    /**
668
     *
669
     * Sets the limit and count by page number.
670
     *
671
     * @param int $page Limit results to this page number.
672
     *
673
     * @return $this
674
     *
675
     */
676 30
    public function page($page)
677
    {
678 30
        $this->page = (int) $page;
679 30
        $this->setPagingLimitOffset();
680 30
        return $this;
681
    }
682
683
    /**
684
     *
685
     * Updates the limit and offset values when changing pagination.
686
     *
687
     * @return null
688
     *
689
     */
690 30
    protected function setPagingLimitOffset()
691
    {
692 30
        $this->setLimit(0);
693 30
        $this->setOffset(0);
694 30
        if ($this->page) {
695 10
            $this->setLimit($this->paging);
696 10
            $this->setOffset($this->paging * ($this->page - 1));
697 10
        }
698 30
    }
699
700
    /**
701
     *
702
     * Returns the page number being selected.
703
     *
704
     * @return int
705
     *
706
     */
707 5
    public function getPage()
708
    {
709 5
        return $this->page;
710
    }
711
712
    /**
713
     *
714
     * Takes the current select properties and retains them, then sets
715
     * UNION for the next set of properties.
716
     *
717
     * @return $this
718
     *
719
     */
720 15
    public function union()
721
    {
722 15
        $this->union[] = $this->build() . PHP_EOL . 'UNION';
723 15
        $this->reset();
724 15
        return $this;
725
    }
726
727
    /**
728
     *
729
     * Takes the current select properties and retains them, then sets
730
     * UNION ALL for the next set of properties.
731
     *
732
     * @return $this
733
     *
734
     */
735 5
    public function unionAll()
736
    {
737 5
        $this->union[] = $this->build() . PHP_EOL . 'UNION ALL';
738 5
        $this->reset();
739 5
        return $this;
740
    }
741
742
    /**
743
     *
744
     * Clears the current select properties; generally used after adding a
745
     * union.
746
     *
747
     * @return null
748
     *
749
     */
750 20
    public function reset()
751
    {
752 20
        $this->resetFlags();
753 20
        $this->resetCols();
754 20
        $this->resetTables();
755 20
        $this->resetWhere();
756 20
        $this->resetGroupBy();
757 20
        $this->resetHaving();
758 20
        $this->resetOrderBy();
759 20
        $this->limit(0);
760 20
        $this->offset(0);
761 20
        $this->page(0);
762 20
        $this->forUpdate(false);
763 20
    }
764
765
    /**
766
     *
767
     * Resets the columns on the SELECT.
768
     *
769
     * @return $this
770
     *
771
     */
772 20
    public function resetCols()
773
    {
774 20
        $this->cols = array();
775 20
        return $this;
776
    }
777
778
    /**
779
     *
780
     * Resets the FROM and JOIN clauses on the SELECT.
781
     *
782
     * @return $this
783
     *
784
     */
785 20
    public function resetTables()
786
    {
787 20
        $this->from = array();
788 20
        $this->from_key = -1;
789 20
        $this->join = array();
790 20
        $this->table_refs = array();
791 20
        return $this;
792
    }
793
794
    /**
795
     *
796
     * Resets the WHERE clause on the SELECT.
797
     *
798
     * @return $this
799
     *
800
     */
801 20
    public function resetWhere()
802
    {
803 20
        $this->where = array();
804 20
        return $this;
805
    }
806
807
    /**
808
     *
809
     * Resets the GROUP BY clause on the SELECT.
810
     *
811
     * @return $this
812
     *
813
     */
814 20
    public function resetGroupBy()
815
    {
816 20
        $this->group_by = array();
817 20
        return $this;
818
    }
819
820
    /**
821
     *
822
     * Resets the HAVING clause on the SELECT.
823
     *
824
     * @return $this
825
     *
826
     */
827 20
    public function resetHaving()
828
    {
829 20
        $this->having = array();
830 20
        return $this;
831
    }
832
833
    /**
834
     *
835
     * Resets the ORDER BY clause on the SELECT.
836
     *
837
     * @return $this
838
     *
839
     */
840 20
    public function resetOrderBy()
841
    {
842 20
        $this->order_by = array();
843 20
        return $this;
844
    }
845
846
    /**
847
     *
848
     * Resets the UNION and UNION ALL clauses on the SELECT.
849
     *
850
     * @return $this
851
     *
852
     */
853 5
    public function resetUnions()
854
    {
855 5
        $this->union = array();
856 5
        return $this;
857
    }
858
859
    /**
860
     *
861
     * Builds this query object into a string.
862
     *
863
     * @return string
864
     *
865
     */
866 199
    protected function build()
867
    {
868 199
        $cols = array();
869 199
        foreach ($this->cols as $key => $val) {
870 194
            if (is_int($key)) {
871 194
                $cols[] = $this->quoter->quoteNamesIn($val);
872 194
            } else {
873 10
                $cols[] = $this->quoter->quoteNamesIn("$val AS $key");
874
            }
875 199
        }
876
877
        return 'SELECT'
878 199
            . $this->builder->buildFlags($this->flags)
879 199
            . $this->builder->buildCols($cols)
880 194
            . $this->builder->buildFrom($this->from, $this->join)
881 194
            . $this->builder->buildWhere($this->where)
882 194
            . $this->builder->buildGroupBy($this->group_by)
883 194
            . $this->builder->buildHaving($this->having)
884 194
            . $this->builder->buildOrderBy($this->order_by)
885 194
            . $this->builder->buildLimitOffset($this->limit, $this->offset)
886 194
            . $this->builder->buildForUpdate($this->for_update);
887
    }
888
889
    /**
890
     *
891
     * Sets a limit count on the query.
892
     *
893
     * @param int $limit The number of rows to select.
894
     *
895
     * @return $this
896
     *
897
     */
898 35
    public function limit($limit)
899
    {
900 35
        $this->setLimit($limit);
901 35
        if ($this->page) {
902 5
            $this->page = 0;
903 5
            $this->setOffset(0);
904 5
        }
905 35
        return $this;
906
    }
907
908
    /**
909
     *
910
     * Sets a limit offset on the query.
911
     *
912
     * @param int $offset Start returning after this many rows.
913
     *
914
     * @return $this
915
     *
916
     */
917 35
    public function offset($offset)
918
    {
919 35
        $this->setOffset($offset);
920 35
        if ($this->page) {
921 5
            $this->page = 0;
922 5
            $this->setLimit(0);
923 5
        }
924 35
        return $this;
925
    }
926
927
    /**
928
     *
929
     * Adds a column order to the query.
930
     *
931
     * @param array $spec The columns and direction to order by.
932
     *
933
     * @return $this
934
     *
935
     */
936 5
    public function orderBy(array $spec)
937
    {
938 5
        return $this->addOrderBy($spec);
939
    }
940
}
941