Completed
Push — master ( 226980...c1625e )
by Hong
02:50
created

SetTrait   A

Complexity

Total Complexity 21

Size/Duplication

Total Lines 179
Duplicated Lines 0 %

Coupling/Cohesion

Components 1
Dependencies 0

Importance

Changes 0
Metric Value
wmc 21
lcom 1
cbo 0
dl 0
loc 179
rs 10
c 0
b 0
f 0

12 Methods

Rating   Name   Duplication   Size   Complexity  
A set() 0 15 4
A setWithArrayData() 0 14 4
A buildSet() 0 10 2
A buildInsertSet() 0 14 3
A buildUpdateSet() 0 11 2
A buildValues() 0 17 4
A nullOrDefault() 0 4 2
getType() 0 1 ?
getClause() 0 1 ?
processValue() 0 1 ?
joinClause() 0 6 ?
quote() 0 1 ?
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\Interfaces\ClauseInterface;
18
use Phossa2\Query\Interfaces\Clause\SetInterface;
19
20
/**
21
 * SetTrait
22
 *
23
 * Implementation of SetInterface
24
 *
25
 * @package Phossa2\Query
26
 * @author  Hong Zhang <[email protected]>
27
 * @see     SetInterface
28
 * @version 2.0.0
29
 * @since   2.0.0 added
30
 */
31
trait SetTrait
32
{
33
    /**
34
     * data storage
35
     *
36
     * @var    array
37
     * @access protected
38
     */
39
    protected $set_data = [];
40
41
    /**
42
     * data row number
43
     *
44
     * @var    int
45
     * @access protected
46
     */
47
    protected $set_row = 0;
48
49
    /**
50
     * storage for col names
51
     *
52
     * @var    array
53
     * @access protected
54
     */
55
    protected $set_col = [];
56
57
    /**
58
     * {@inheritDoc}
59
     */
60
    public function set($col, $value = ClauseInterface::NO_VALUE)
61
    {
62
        if (is_array($col)) { // array provided
63
            return $this->setWithArrayData($col);
64
        }
65
        if (!isset($this->set_col[$col])) { // save col names
66
            $this->set_col[$col] = true;
67
        }
68
        if (ClauseInterface::NO_VALUE === $value) { // auto positionedParam
69
            $this->setSettings(['positionedParam' => true]);
0 ignored issues
show
Bug introduced by
It seems like setSettings() must be provided by classes using this trait. How about adding it as abstract method to this trait?

This check looks for methods that are used by a trait but not required by it.

To illustrate, let’s look at the following code example

trait Idable {
    public function equalIds(Idable $other) {
        return $this->getId() === $other->getId();
    }
}

The trait Idable provides a method equalsId that in turn relies on the method getId(). If this method does not exist on a class mixing in this trait, the method will fail.

Adding the getId() as an abstract method to the trait will make sure it is available.

Loading history...
70
        }
71
72
        $this->set_data[$this->set_row][$col] = $value;
73
        return $this;
74
    }
75
76
    /**
77
     * Batch SET
78
     *
79
     * @param  array $data
80
     * @return $this
81
     * @access protected
82
     */
83
    protected function setWithArrayData(array $data)
84
    {
85
        if (isset($data[0])) { // multiple rows
86
            foreach ($data as $row) {
87
                $this->set($row);
88
            }
89
        } else { // multiple values
90
            foreach ($data as $col => $val) {
91
                $this->set($col, $val);
92
            }
93
            $this->set_row++;
94
        }
95
        return $this;
96
    }
97
98
    /**
99
     * Build SET
100
     *
101
     * @param  string $prefix
102
     * @param  array $settings
103
     * @return string
104
     * @access protected
105
     */
106
    protected function buildSet(
107
        /*# string */ $prefix,
108
        array $settings
109
    )/*# : array */ {
110
        if ('UPDATE' === $this->getType()) {
111
            return $this->buildUpdateSet($prefix, $settings);
112
        } else {
113
            return $this->buildInsertSet($prefix, $settings);
114
        }
115
    }
116
117
    /**
118
     * Build SET for INSERT
119
     *
120
     * @param  string $prefix
121
     * @param  array $settings
122
     * @return string
123
     * @access protected
124
     */
125
    protected function buildInsertSet(
126
        /*# string */ $prefix,
1 ignored issue
show
Unused Code introduced by
The parameter $prefix is not used and could be removed.

This check looks from parameters that have been defined for a function or method, but which are not used in the method body.

Loading history...
127
        array $settings
128
    )/*# : string */ {
129
        if (empty($this->set_data)) {
130
            return '';
131
        }
132
133
        $cols = [];
134
        foreach (array_keys($this->set_col) as $col) {
135
            $cols[] = $this->quote($col, $settings);
136
        }
137
        return $settings['seperator'] . '(' . join(', ', $cols) . ')';
138
    }
139
140
    /**
141
     * Build SET ... = ..., ... = ...
142
     *
143
     *
144
     * @param  string $prefix
145
     * @param  array $settings
146
     * @return string
147
     * @access protected
148
     */
149
    protected function buildUpdateSet(
150
        /*# string */ $prefix,
151
        array $settings
152
    )/*# : string */ {
153
        $result = [];
154
        foreach ($this->set_data[0] as $col => $val) {
155
            $result[] = $this->quote($col, $settings) . ' = ' .
156
                $this->processValue($val, $settings);
157
        }
158
        return $this->joinClause($prefix, ',', $result, $settings);
159
    }
160
161
    /**
162
     * Build VALUES ( ... )
163
     *
164
     * @param  string $prefix
165
     * @param  array $settings
166
     * @return string
167
     * @access protected
168
     */
169
    protected function buildValues(
170
        /*# string */ $prefix,
171
        array $settings
172
    )/*# : string */ {
173
        $rows = [];
174
        $cols = array_keys($this->set_col);
175
        foreach ($this->set_data as $num => $row) {
176
            $values = [];
177
            foreach ($cols as $col) {
178
                $values[] = isset($row[$col]) ?
179
                    $this->processValue($row[$col], $settings) :
180
                    $this->nullOrDefault($settings);
181
            }
182
            $rows[] = '(' . join(', ', $values) . ')';
183
        }
184
        return $this->joinClause($prefix, ',', $rows, $settings);
185
    }
186
187
    /**
188
     * Get NULL or DEFAULT for values base on the settings
189
     *
190
     * @param  array $settings
191
     * @return string
192
     * @access protected
193
     */
194
    protected function nullOrDefault(array $settings)/*# : string */
195
    {
196
        return $settings['useNullAsDefault'] ? 'NULL' : 'DEFAULT';
197
    }
198
199
    abstract protected function getType()/*# : string */;
200
    abstract protected function &getClause(/*# string */ $clauseName)/*# : array */;
201
    abstract protected function processValue($value, array $settings, /*# bool */ $between = false)/*# : string */;
202
    abstract protected function joinClause(
203
        /*# : string */ $prefix,
204
        /*# : string */ $seperator,
205
        array $clause,
206
        array $settings
207
    )/*# : string */;
208
    abstract protected function quote(/*# string */ $str, array $settings)/*# : string */;
209
}
210