PluginProbe ʕ •ᴥ•ʔ
Matomo Analytics – Powerful, Privacy-First Insights for WordPress / 4.3.0
Matomo Analytics – Powerful, Privacy-First Insights for WordPress v4.3.0
5.11.1 5.11.0 5.10.2 5.10.1 trunk 1.0.2 1.0.3 1.0.4 1.0.5 1.0.6 1.1.0 1.1.1 1.1.2 1.1.3 1.2.0 1.3.0 1.3.1 1.3.2 4.0.0 4.0.1 4.0.2 4.0.3 4.0.4 4.1.0 4.1.1 4.1.2 4.1.3 4.10.0 4.11.0 4.12.0 4.13.0 4.13.2 4.13.3 4.13.4 4.13.5 4.14.0 4.14.1 4.14.2 4.15.0 4.15.1 4.15.2 4.15.3 4.2.0 4.3.0 4.3.1 4.4.1 4.4.2 4.5.0 4.6.0 5.0.1 5.0.2 5.0.3 5.0.4 5.0.5 5.0.6 5.0.7 5.0.8 5.1.0 5.1.1 5.1.2 5.1.3 5.1.4 5.1.5 5.1.6 5.1.7 5.10.0 5.2.0 5.2.1 5.2.2 5.3.0 5.3.1 5.3.2 5.3.3 5.6.0 5.6.1 5.7.0 5.7.1 5.8.0 5.8.1 5.8.2
matomo / app / core / Db / Adapter / Mysqli.php
matomo / app / core / Db / Adapter Last commit date
Pdo 5 years ago Mysqli.php 5 years ago
Mysqli.php
257 lines
1 <?php
2 /**
3 * Matomo - free/libre analytics platform
4 *
5 * @link https://matomo.org
6 * @license http://www.gnu.org/licenses/gpl-3.0.html GPL v3 or later
7 *
8 */
9 namespace Piwik\Db\Adapter;
10
11 use Exception;
12 use Piwik\Config;
13 use Piwik\Db;
14 use Piwik\Db\AdapterInterface;
15 use Piwik\Piwik;
16 use Zend_Config;
17 use Zend_Db_Adapter_Mysqli;
18
19 /**
20 */
21 class Mysqli extends Zend_Db_Adapter_Mysqli implements AdapterInterface
22 {
23 /**
24 * Constructor
25 *
26 * @param array|Zend_Config $config database configuration
27 */
28 public function __construct($config)
29 {
30 // Enable LOAD DATA INFILE
31 $config['driver_options'][MYSQLI_OPT_LOCAL_INFILE] = true;
32
33 if ($config['enable_ssl']) {
34 if (!empty($config['ssl_key'])) {
35 $config['driver_options']['ssl_key'] = $config['ssl_key'];
36 }
37 if (!empty($config['ssl_cert'])) {
38 $config['driver_options']['ssl_cert'] = $config['ssl_cert'];
39 }
40 if (!empty($config['ssl_ca'])) {
41 $config['driver_options']['ssl_ca'] = $config['ssl_ca'];
42 }
43 if (!empty($config['ssl_ca_path'])) {
44 $config['driver_options']['ssl_ca_path'] = $config['ssl_ca_path'];
45 }
46 if (!empty($config['ssl_cipher'])) {
47 $config['driver_options']['ssl_cipher'] = $config['ssl_cipher'];
48 }
49 if (!empty($config['ssl_no_verify'])) {
50 $config['driver_options']['ssl_no_verify'] = $config['ssl_no_verify'];
51 }
52 }
53
54 parent::__construct($config);
55 }
56
57 /**
58 * Reset the configuration variables in this adapter.
59 */
60 public function resetConfig()
61 {
62 $this->_config = array();
63 }
64
65 /**
66 * Return default port.
67 *
68 * @return int
69 */
70 public static function getDefaultPort()
71 {
72 return 3306;
73 }
74
75 protected function _connect()
76 {
77 if ($this->_connection) {
78 return;
79 }
80
81 parent::_connect();
82
83 $this->_connection->query('SET sql_mode = "' . Db::SQL_MODE . '"');
84 }
85
86 /**
87 * Check MySQL version
88 *
89 * @throws Exception
90 */
91 public function checkServerVersion()
92 {
93 $serverVersion = $this->getServerVersion();
94 $requiredVersion = Config::getInstance()->General['minimum_mysql_version'];
95
96 if (version_compare($serverVersion, $requiredVersion) === -1) {
97 throw new Exception(Piwik::translate('General_ExceptionDatabaseVersion', array('MySQL', $serverVersion, $requiredVersion)));
98 }
99 }
100
101 /**
102 * Returns the MySQL server version
103 *
104 * @return null|string
105 */
106 public function getServerVersion()
107 {
108 // prioritizing SELECT @@VERSION in case the connection version string is incorrect (which can
109 // occur on Azure)
110 $versionInfo = $this->fetchAll('SELECT @@VERSION');
111
112 if (count($versionInfo)) {
113 return $versionInfo[0]['@@VERSION'];
114 }
115
116 return parent::getServerVersion();
117 }
118
119 /**
120 * Check client version compatibility against database server
121 *
122 * @throws Exception
123 */
124 public function checkClientVersion()
125 {
126 $serverVersion = $this->getServerVersion();
127 $clientVersion = $this->getClientVersion();
128
129 // incompatible change to DECIMAL implementation in 5.0.3
130 if (version_compare($serverVersion, '5.0.3') >= 0
131 && version_compare($clientVersion, '5.0.3') < 0
132 ) {
133 throw new Exception(Piwik::translate('General_ExceptionIncompatibleClientServerVersions', array('MySQL', $clientVersion, $serverVersion)));
134 }
135 }
136
137 /**
138 * Return number of affected rows in last query
139 *
140 * @param mixed $queryResult Result from query()
141 * @return int
142 */
143 public function rowCount($queryResult)
144 {
145 return mysqli_affected_rows($this->_connection);
146 }
147
148 /**
149 * Returns true if this adapter's required extensions are enabled
150 *
151 * @return bool
152 */
153 public static function isEnabled()
154 {
155 $extensions = @get_loaded_extensions();
156 return in_array('mysqli', $extensions);
157 }
158
159 /**
160 * Returns true if this adapter supports blobs as fields
161 *
162 * @return bool
163 */
164 public function hasBlobDataType()
165 {
166 return true;
167 }
168
169 /**
170 * Returns true if this adapter supports bulk loading
171 *
172 * @return bool
173 */
174 public function hasBulkLoader()
175 {
176 return true;
177 }
178
179 /**
180 * Test error number
181 *
182 * @param Exception $e
183 * @param string $errno
184 * @return bool
185 */
186 public function isErrNo($e, $errno)
187 {
188 return self::isMysqliErrorNumber($e, $this->_connection, $errno);
189 }
190
191 /**
192 * Test error number
193 *
194 * @param Exception $e
195 * @param string $errno
196 * @return bool
197 */
198 public static function isMysqliErrorNumber($e, $connection, $errno)
199 {
200 if (is_null($connection)) {
201 if (preg_match('/(?:\[|\s)([0-9]{4})(?:\]|\s)/', $e->getMessage(), $match)) {
202 return $match[1] == $errno;
203 }
204 return mysqli_connect_errno() == $errno;
205 }
206
207 return mysqli_errno($connection) == $errno;
208 }
209
210 /**
211 * Execute unprepared SQL query and throw away the result
212 *
213 * Workaround some SQL statements not compatible with prepare().
214 * See http://framework.zend.com/issues/browse/ZF-1398
215 *
216 * @param string $sqlQuery
217 * @return int Number of rows affected (SELECT/INSERT/UPDATE/DELETE)
218 */
219 public function exec($sqlQuery)
220 {
221 $rc = mysqli_query($this->_connection, $sqlQuery);
222 $rowsAffected = mysqli_affected_rows($this->_connection);
223 if (!is_bool($rc)) {
224 mysqli_free_result($rc);
225 }
226 return $rowsAffected;
227 }
228
229 /**
230 * Is the connection character set equal to utf8?
231 *
232 * @return bool
233 */
234 public function isConnectionUTF8()
235 {
236 $charset = mysqli_character_set_name($this->_connection);
237 return strpos($charset, 'utf8') === 0;
238 }
239
240 /**
241 * Get client version
242 *
243 * @return string
244 */
245 public function getClientVersion()
246 {
247 $this->_connect();
248
249 $version = $this->_connection->server_version;
250 $major = (int)($version / 10000);
251 $minor = (int)($version % 10000 / 100);
252 $revision = (int)($version % 100);
253
254 return $major . '.' . $minor . '.' . $revision;
255 }
256 }
257