Completed
Push — master ( 9060a0...3152a4 )
by Hong
02:38
created

WhereTrait::buildWhere()   B

Complexity

Conditions 5
Paths 7

Size

Total Lines 18
Code Lines 13

Duplication

Lines 0
Ratio 0 %

Importance

Changes 3
Bugs 0 Features 0
Metric Value
c 3
b 0
f 0
dl 0
loc 18
rs 8.8571
cc 5
eloc 13
nc 7
nop 2
1
<?php
2
/**
3
 * Phossa Project
4
 *
5
 * PHP version 5.4
6
 *
7
 * @category  Library
8
 * @package   Phossa2\Query
9
 * @copyright Copyright (c) 2016 phossa.com
10
 * @license   http://mit-license.org/ MIT License
11
 * @link      http://www.phossa.com/
12
 */
13
/*# declare(strict_types=1); */
14
15
namespace Phossa2\Query\Traits\Clause;
16
17
use Phossa2\Query\Misc\Template;
18
use Phossa2\Query\Interfaces\Clause\WhereInterface;
19
use Phossa2\Query\Interfaces\Statement\SelectStatementInterface;
20
21
/**
22
 * WhereTrait
23
 *
24
 * Implementation of WhereInterface
25
 *
26
 * @package Phossa2\Query
27
 * @author  Hong Zhang <[email protected]>
28
 * @see     WhereInterface
29
 * @version 2.0.0
30
 * @since   2.0.0 added
31
 */
32
trait WhereTrait
33
{
34
    /**
35
     * {@inheritDoc}
36
     */
37
    public function where(
38
        $col,
39
        $operator = WhereInterface::NO_OPERATOR,
40
        $value = WhereInterface::NO_VALUE
41
    ) {
42
        return $this->realWhere($col, $operator, $value);
43
    }
44
45
    /**
46
     * {@inheritDoc}
47
     */
48
    public function whereTpl(/*# string */ $template, $col)
49
    {
50
        return $this->realWhere(new Template($template, $col),
51
            WhereInterface::NO_OPERATOR, WhereInterface::NO_VALUE,
52
            true, false, true);
53
    }
54
55
    /**
56
     * {@inheritDoc}
57
     */
58
    public function orWhereTpl(/*# string */ $template, $col)
59
    {
60
        return $this->realWhere(new Template($template, $col),
61
            WhereInterface::NO_OPERATOR, WhereInterface::NO_VALUE,
62
            false, false, true);
63
    }
64
65
    /**
66
     * {@inheritDoc}
67
     */
68
    public function whereRaw(/*# string */ $rawString)
69
    {
70
        return $this->realWhere($rawString, WhereInterface::NO_OPERATOR,
71
            WhereInterface::NO_VALUE, true, false, true);
72
    }
73
74
    /**
75
     * {@inheritDoc}
76
     */
77
    public function orWhereRaw(/*# string */ $rawString)
78
    {
79
        return $this->realWhere($rawString, WhereInterface::NO_OPERATOR,
80
            WhereInterface::NO_VALUE, false, false, true);
81
    }
82
83
    /**
84
     * {@inheritDoc}
85
     */
86
    public function andWhere(
87
        $col,
88
        $operator = WhereInterface::NO_OPERATOR,
89
        $value = WhereInterface::NO_VALUE
90
    ) {
91
        return $this->realWhere($col, $operator, $value);
92
    }
93
94
    /**
95
     * {@inheritDoc}
96
     */
97
    public function orWhere(
98
        $col,
99
        $operator = WhereInterface::NO_OPERATOR,
100
        $value = WhereInterface::NO_VALUE
101
    ) {
102
        return $this->realWhere($col, $operator, $value, false);
103
    }
104
105
    /**
106
     * {@inheritDoc}
107
     */
108
    public function whereNot(
109
        $col,
110
        $operator = WhereInterface::NO_OPERATOR,
111
        $value = WhereInterface::NO_VALUE
112
    ) {
113
        return $this->realWhere($col, $operator, $value, true, true);
114
    }
115
116
    /**
117
     * {@inheritDoc}
118
     */
119
    public function orWhereNot(
120
        $col,
121
        $operator = WhereInterface::NO_OPERATOR,
122
        $value = WhereInterface::NO_VALUE
123
    ) {
124
        return $this->realWhere($col, $operator, $value, false, true);
125
    }
126
127
    /**
128
     * {@inheritDoc}
129
     */
130
    public function whereIn(/*# string */ $col, $value)
131
    {
132
        return $this->realWhere($col, 'IN', $value);
133
    }
134
135
    /**
136
     * {@inheritDoc}
137
     */
138
    public function orWhereIn(/*# string */ $col, $value)
139
    {
140
        return $this->realWhere($col, 'IN', $value, false);
141
    }
142
143
    /**
144
     * {@inheritDoc}
145
     */
146
    public function whereNotIn(/*# string */ $col, $value)
147
    {
148
        return $this->realWhere($col, 'NOT IN', $value);
149
    }
150
151
    /**
152
     * {@inheritDoc}
153
     */
154
    public function orWhereNotIn(/*# string */ $col, $value)
155
    {
156
        return $this->realWhere($col, 'NOT IN', $value, false);
157
    }
158
159
    /**
160
     * {@inheritDoc}
161
     */
162
    public function whereBetween(/*# string */ $col, $value1, $value2)
163
    {
164
        $val = sprintf('%s AND %s', $value1, $value2);
165
        return $this->realWhere($col, 'BETWEEN', $val);
166
    }
167
168
    /**
169
     * {@inheritDoc}
170
     */
171
    public function orWhereBetween(/*# string */ $col, $value1, $value2)
172
    {
173
        $val = sprintf('%s AND %s', $value1, $value2);
174
        return $this->realWhere($col, 'BETWEEN', $val, false);
175
    }
176
177
    /**
178
     * {@inheritDoc}
179
     */
180
    public function whereNotBetween(/*# string */ $col, $value1, $value2)
181
    {
182
        $val = sprintf('%s AND %s', $value1, $value2);
183
        return $this->realWhere($col, 'NOT BETWEEN', $val);
184
    }
185
186
    /**
187
     * {@inheritDoc}
188
     */
189
    public function orWhereNotBetween(/*# string */ $col, $value1, $value2)
190
    {
191
        $val = sprintf('%s AND %s', $value1, $value2);
192
        return $this->realWhere($col, 'NOT BETWEEN', $val, false);
193
    }
194
195
    /**
196
     * {@inheritDoc}
197
     */
198
    public function whereNull(/*# string */ $col)
199
    {
200
        return $this->realWhere($col, 'IS', 'NULL');
201
    }
202
203
    /**
204
     * {@inheritDoc}
205
     */
206
    public function orWhereNull(/*# string */ $col)
207
    {
208
        return $this->realWhere($col, 'IS', 'NULL', false);
209
    }
210
211
    /**
212
     * {@inheritDoc}
213
     */
214
    public function whereNotNull(/*# string */ $col)
215
    {
216
        return $this->realWhere($col, 'IS', 'NOT NULL');
217
    }
218
219
    /**
220
     * {@inheritDoc}
221
     */
222
    public function orWhereNotNull(/*# string */ $col)
223
    {
224
        return $this->realWhere($col, 'IS', 'NOT NULL', false);
225
    }
226
227
    /**
228
     * WHERE EXISTS
229
     *
230
     * ```php
231
     * // WHERE EXISTS (SELECT `user_id` FROM `users`)
232
     * ->whereExists($users->select('user_id'))
233
     * ```
234
     *
235
     * @param  SelectStatementInterface $sel
236
     * @return $this
237
     * @see    WhereInterface::where()
238
     * @access public
239
     * @api
240
     */
241
    public function whereExists(SelectStatementInterface $sel)
242
    {
243
        return $this->realWhere('', 'EXISTS', $sel);
244
    }
245
246
    /**
247
     * {@inheritDoc}
248
     */
249
    public function orWhereExists(SelectStatementInterface $sel)
250
    {
251
        return $this->realWhere('', 'EXISTS', $sel, false);
252
    }
253
254
    /**
255
     * {@inheritDoc}
256
     */
257
    public function whereNotExists(SelectStatementInterface $sel)
258
    {
259
        return $this->realWhere('', 'NOT EXISTS', $sel);
260
    }
261
262
    /**
263
     * {@inheritDoc}
264
     */
265
    public function orWhereNotExists(SelectStatementInterface $sel)
266
    {
267
        return $this->realWhere('', 'NOT EXISTS', $sel, false);
268
    }
269
270
    /**
271
     * Real where
272
     *
273
     * @param  string|string[]|Template $col col or cols
274
     * @param  mixed $operator
275
     * @param  mixed $value
276
     * @param  bool $logicAnd 'AND'
277
     * @param  bool $whereNot 'WHERE NOT'
278
     * @param  bool $rawMode
279
     * @param  string $clause 'where' or 'having'
280
     * @return $this
281
     * @access protected
282
     */
283
    protected function realWhere(
284
        $col,
285
        $operator = WhereInterface::NO_OPERATOR,
286
        $value    = WhereInterface::NO_VALUE,
287
        /*# bool */ $logicAnd = true,
288
        /*# bool */ $whereNot = false,
289
        /*# bool */ $rawMode = false,
290
        /*# string */ $clause = 'WHERE'
291
    ) {
292
        $clause = &$this->getClause($clause);
293
        if (is_array($col)) {
294
            $this->multipleWhere($col, $logicAnd, $whereNot, $rawMode);
295
            return $this;
296
        }
297
        $this->fixOperatorValue($operator, $value, $rawMode);
298
299
        $clause[] = [$rawMode, $whereNot, $logicAnd, $col, $operator, $value];
300
        return $this;
301
    }
302
303
    /**
304
     * Fix operator and value
305
     *
306
     * @param  mixed $operator
307
     * @param  mixed $value
308
     * @param  bool $rawMode
309
     * @access protected
310
     */
311
    protected function fixOperatorValue(&$operator, &$value, &$rawMode)
312
    {
313
        if (WhereInterface::NO_OPERATOR === $operator) {
314
            $rawMode = true;
315
            $value = WhereInterface::NO_VALUE;
316
        } elseif (WhereInterface::NO_VALUE === $value) {
317
            $value = $operator;
318
            $operator = '=';
319
        }
320
    }
321
322
    /**
323
     * @param  array $cols
324
     * @param  bool $logicAnd
325
     * @param  bool $whereNot
326
     * @param  bool $rawMode
327
     * @access protected
328
     */
329
    protected function multipleWhere(
330
        array $cols,
331
        /*# bool */ $logicAnd = true,
332
        /*# bool */ $whereNot = false,
333
        /*# bool */ $rawMode  = false
334
    ) {
335
        foreach ($cols as $fld => $val) {
336
            if (is_array($val)) {
337
                $opr = $val[0];
338
                $val = $val[1];
339
            } else {
340
                $opr = '=';
341
            }
342
            $this->realWhere($fld, $opr, $val, $logicAnd, $whereNot, $rawMode);
343
        }
344
    }
345
346
    /**
347
     * Build WHERE
348
     *
349
     * @param  string $clause 'where|having'
350
     * @return array
351
     * @access protected
352
     */
353
    protected function buildWhere(
354
        array $settings,
355
        /*# string */ $clause = 'WHERE'
356
    )/*# : string */ {
357
        $result = [];
358
        $wheres = &$this->getClause($clause);
359
        foreach ($wheres as $idx => $where) {
360
            $cls = [];
361
            if ($idx) {
362
                $cls[] = $where[2] ? 'AND' : 'OR';
363
            }
364
            if ($where[1]) {
365
                $cls[] = 'NOT';
366
            }
367
            $result[] = $this->bulidWhereClause($cls, $where, $settings);
0 ignored issues
show
Bug introduced by
The method bulidWhereClause() does not exist on Phossa2\Query\Traits\Clause\WhereTrait. Did you maybe mean buildWhereClause()?

This check marks calls to methods that do not seem to exist on an object.

This is most likely the result of a method being renamed without all references to it being renamed likewise.

Loading history...
368
        }
369
        return $this->joinClause($clause, '', $result, $settings);
370
    }
371
372
    /**
373
     * Build 'col = val' part
374
     *
375
     * @param  array $cls
376
     * @param  array $where
377
     * @param  array $settings
378
     * @return string
379
     * @access protected
380
     */
381
    protected function buildWhereClause(array $cls, array $where, array $settings)
382
    {
383
        // col
384
        if (!empty($where[3])) {
385
            $cls[] = $this->quoteItem(
386
                $where[3], $settings, $this->isRaw($where[3], $where[0])
387
            );
388
        }
389
390
        // operator
391
        if (WhereInterface::NO_OPERATOR !== $where[4]) {
392
            $cls[] = $where[4];
393
        }
394
395
        // value
396
        if (WhereInterface::NO_VALUE !== $where[5]) {
397
            $cls[] = $this->processValue($where[5]);
398
        }
399
400
        return join(' ', $cls);
401
    }
402
403
    abstract protected function isRaw($str, /*# bool */ $rawMode)/*# : bool */;
404
    abstract protected function processValue($value)/*# : string */;
405
    abstract protected function &getClause(/*# string */ $clauseName)/*# : array */;
406
    abstract protected function quoteItem($item, array $settings, /*# bool */ $rawMode = false)/*# : string */;
407
    abstract protected function joinClause(
408
        /*# : string */ $prefix,
409
        /*# : string */ $seperator,
410
        array $clause,
411
        array $settings
412
    )/*# : string */;
413
}
414