Completed
Pull Request — master (#541)
by Richard
07:06
created

XoopsMySQLDatabase   B

Complexity

Total Complexity 54

Size/Duplication

Total Lines 474
Duplicated Lines 4.22 %

Coupling/Cohesion

Components 1
Dependencies 4

Test Coverage

Coverage 100%

Importance

Changes 0
Metric Value
dl 20
loc 474
rs 7.0642
c 0
b 0
f 0
ccs 12
cts 12
cp 1
wmc 54
lcom 1
cbo 4

24 Methods

Rating   Name   Duplication   Size   Complexity  
A deprecated() 0 13 2
A connect() 0 7 1
A genId() 0 5 1
A fetchRow() 0 8 2
A fetchArray() 0 9 2
A fetchBoth() 0 9 2
A fetchObject() 0 9 2
A getInsertId() 0 5 1
A getRowsNum() 0 6 1
A getAffectedRows() 0 5 1
A close() 0 5 1
A freeRecordSet() 0 6 1
A error() 0 6 1
A errno() 0 6 1
A quoteString() 0 6 1
A quote() 0 6 1
A escape() 0 7 1
A queryFromFile() 20 20 4
A getFieldName() 0 12 2
A getFieldsNum() 0 6 1
B queryF() 0 28 5
A query() 0 4 1
F getFieldType() 0 28 17
A getServerVersion() 0 9 2

How to fix   Duplicated Code    Complexity   

Duplicated Code

Duplicate code is one of the most pungent code smells. A rule that is often used is to re-structure code once it is duplicated in three or more places.

Common duplication problems, and corresponding solutions are:

Complex Class

 Tip:   Before tackling complexity, make sure that you eliminate any duplication first. This often can reduce the size of classes significantly.

Complex classes like XoopsMySQLDatabase often do a lot of different things. To break such a class down, we need to identify a cohesive component within that class. A common approach to find such a component is to look for fields/methods that share the same prefixes, or suffixes. You can also have a look at the cohesion graph to spot any un-connected, or weakly-connected components.

Once you have determined the fields that belong together, you can apply the Extract Class refactoring. If the component makes sense as a sub-class, Extract Subclass is also a candidate, and is often faster.

While breaking up the class, it is a good idea to analyze how other classes use XoopsMySQLDatabase, and based on these observations, apply Extract Interface, too.

1
<?php
2
/**
3
 * You may not change or alter any portion of this comment or credits
4
 * of supporting developers from this source code or any supporting source code
5
 * which is considered copyrighted (c) material of the original comment or credit authors.
6
 *
7
 * This program is distributed in the hope that it will be useful,
8
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
9
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
10
 */
11
12
/**
13
 * connection to a mysql database - legacy support only
14
 *
15
 * PHP version 5.3
16
 *
17
 * @category   Xoops\Class\Database\MySQLDatabase
18
 * @package    MySQLDatabase
19
 * @author     Kazumi Ono <[email protected]>
20
 * @author     readheadedrod <[email protected]>
21
 * @author     Richard Griffith <[email protected]>
22
 * @copyright  2013 XOOPS Project (http://xoops.org)
23
 * @license    GNU GPL 2 or later (http://www.gnu.org/licenses/gpl-2.0.html)
24
 * @version    Release: 2.6
25
 * @link       http://xoops.org
26
 * @since      2.6.0
27
 * @deprecated since version 2.6.0 - alpha 3. Switch to doctrine connector.
28
 *
29
 */
30
class XoopsMySQLDatabase extends XoopsDatabase
0 ignored issues
show
Deprecated Code introduced by
The class XoopsDatabase has been deprecated with message: since version 2.6.0 - alpha 3. Switch to doctrine connector.

This class, trait or interface has been deprecated. The supplier of the file has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the type will be removed from the class and what other constant to use instead.

Loading history...
31
{
32
33
    /**
34
     * @var object keep track of last result since we need it for getAffectedRows
35
     */
36
    private $lastResult = null;
37
38
    /**
39
     * Database connection
40
     *
41
     * @var Xoops\Core\Database\Connection;
42
     */
43
    public $conn;
44
45
    /**
46
     * Database connection is established
47
     *
48
     * @var boolean
49
     */
50
    private $connect = false;
51
52
    /**
53
     * Database connection
54
     *
55
     * @var resource
56
     */
57
    private $selectdb;
58
59
    /**
60
     * Issue a deprecated warning once per session
61
     *
62
     * @return void
63
     */
64 1
    protected function deprecated()
65
    {
66 1
        static $warning_issued = false;
67 1
        if (!$warning_issued) {
68 1
            $warning_issued = true;
69 1
            $stack = debug_backtrace();
70 1
            $frame = $stack[1];
71 1
            Xoops::getInstance()->deprecated(
72
                'Legacy XoopsDB is deprecated since 2.6.0; all calls should be using Doctrine through $xoops->db(). '
73 1
                . 'Called from ' . $frame['function'] . '() in ' . $frame['file'] . ' line '. $frame['line']
74
            );
75
        }
76 1
    }
77
78
79
    /**
80
     * connect to the database
81
     *
82
     * @param bool $selectdb select the database now?
83
     *
84
     * @return bool successful?
85
     * @deprecated since version 2.6.0 - alpha 3. Switch to doctrine connector.
86
     */
87
    public function connect($selectdb = true)
0 ignored issues
show
Coding Style introduced by
connect uses the super-global variable $_SERVER which is generally not recommended.

Instead of super-globals, we recommend to explicitly inject the dependencies of your class. This makes your code less dependent on global state and it becomes generally more testable:

// Bad
class Router
{
    public function generate($path)
    {
        return $_SERVER['HOST'].$path;
    }
}

// Better
class Router
{
    private $host;

    public function __construct($host)
    {
        $this->host = $host;
    }

    public function generate($path)
    {
        return $this->host.$path;
    }
}

class Controller
{
    public function myAction(Request $request)
    {
        // Instead of
        $page = isset($_GET['page']) ? intval($_GET['page']) : 1;

        // Better (assuming you use the Symfony2 request)
        $page = $request->query->get('page', 1);
    }
}
Loading history...
88
    {
89
        $this->connect = (is_object($this->conn));
90
        $this->selectdb = $selectdb;
0 ignored issues
show
Documentation Bug introduced by
It seems like $selectdb of type boolean is incompatible with the declared type resource of property $selectdb.

Our type inference engine has found an assignment to a property that is incompatible with the declared type of that property.

Either this assignment is in error or the assigned type should be added to the documentation/type hint for that property..

Loading history...
91
        $this->allowWebChanges = ($_SERVER['REQUEST_METHOD'] !== 'GET');
92
        return $this->connect;
93
    }
94
95
96
    /**
97
     * generate an ID for a new row
98
     *
99
     * This is for compatibility only. Will always return 0, because MySQL supports
100
     * autoincrement for primary keys.
101
     *
102
     * @param string $sequence name of the sequence from which to get the next ID
103
     *
104
     * @return int always 0, because mysql has support for autoincrement
105
     * @deprecated since version 2.6.0 - alpha 3. Switch to doctrine connector.
106
     */
107 1
    public function genId($sequence)
108
    {
109 1
        $this->deprecated();
110 1
        return 0; // will use auto_increment
111
    }
112
113
    /**
114
     * Get a result row as an enumerated array
115
     *
116
     * @param resource $result resource to get result from
117
     *
118
     * @return array
119
     * @deprecated since version 2.6.0 - alpha 3. Switch to doctrine connector.
120
     */
121
    public function fetchRow($result)
122
    {
123
        $this->deprecated();
124
        if (!is_object($result)) {
125
            return null;
126
        }
127
        return $result->fetch(\PDO::FETCH_NUM);
128
    }
129
130
    /**
131
     * Fetch a result row as an associative array
132
     *
133
     * @param resource $result resource to get result from
134
     *
135
     * @return array
136
     * @deprecated since version 2.6.0 - alpha 3. Switch to doctrine connector.
137
     */
138
    public function fetchArray($result)
139
    {
140
        $this->deprecated();
141
142
        if (!is_object($result)) {
143
            return null;
144
        }
145
        return $result->fetch(\PDO::FETCH_ASSOC);
146
    }
147
148
    /**
149
     * Fetch a result row as an associative array
150
     *
151
     * @param resource $result resource to get result from
152
     *
153
     * @return array
154
     * @deprecated since version 2.6.0 - alpha 3. Switch to doctrine connector.
155
     */
156
    public function fetchBoth($result)
157
    {
158
        $this->deprecated();
159
160
        if (!is_object($result)) {
161
            return null;
162
        }
163
        return $result->fetch(\PDO::FETCH_BOTH);
164
    }
165
166
    /**
167
     * Fetch a result row as an object
168
     *
169
     * @param resource $result resource to get result from
170
     *
171
     * @return object|stdClass
172
     * @deprecated since version 2.6.0 - alpha 3. Switch to doctrine connector.
173
     */
174
    public function fetchObject($result)
175
    {
176
        $this->deprecated();
177
178
        if (!is_object($result)) {
179
            return null;
180
        }
181
        return $result->fetch(\PDO::FETCH_OBJ);
182
    }
183
184
    /**
185
     * Get the ID generated from the previous INSERT operation
186
     *
187
     * @return int
188
     * @deprecated since version 2.6.0 - alpha 3. Switch to doctrine connector.
189
     */
190
    public function getInsertId()
191
    {
192
        $this->deprecated();
193
        return $this->conn->lastInsertId();
194
    }
195
196
    /**
197
     * Get number of rows in result
198
     *
199
     * @param resource $result the resource containing the number of rows
200
     *
201
     * @return int the number of rows to return
202
     * @deprecated since version 2.6.0 - alpha 3. Switch to doctrine connector.
203
     */
204
    public function getRowsNum($result)
205
    {
206
        Xoops::getInstance()->deprecated('getRowsNum is deprecated and not dependable.');
207
        //$this->deprecated();
208
        return $result->rowCount();
0 ignored issues
show
Bug introduced by
The method rowCount cannot be called on $result (of type resource).

Methods can only be called on objects. This check looks for methods being called on variables that have been inferred to never be objects.

Loading history...
209
    }
210
211
    /**
212
     * Get number of affected rows
213
     *
214
     * @return int
215
     * @deprecated since version 2.6.0 - alpha 3. Switch to doctrine connector.
216
     */
217
    public function getAffectedRows()
218
    {
219
        $this->deprecated();
220
        return $this->lastResult->rowCount();
221
    }
222
223
    /**
224
     * Close MySQL connection
225
     *
226
     * @return void
227
     * @deprecated since version 2.6.0 - alpha 3. Switch to doctrine connector.
228
     */
229
    public function close()
230
    {
231
        $this->deprecated();
232
        return $this->conn->close();
233
    }
234
235
    /**
236
     * will free all memory associated with the result identifier result.
237
     *
238
     * @param resource $result query result
239
     *
240
     * @return bool TRUE on success or FALSE on failure.
241
     * @deprecated since version 2.6.0 - alpha 3. Switch to doctrine connector.
242
     */
243
    public function freeRecordSet($result)
244
    {
245
        $this->deprecated();
246
247
        return $result->closeCursor();
0 ignored issues
show
Bug introduced by
The method closeCursor cannot be called on $result (of type resource).

Methods can only be called on objects. This check looks for methods being called on variables that have been inferred to never be objects.

Loading history...
248
    }
249
250
    /**
251
     * Returns the text of the error message from previous MySQL operation
252
     *
253
     * @return bool Returns the error text from the last MySQL function,
254
     * or '' (the empty string) if no error occurred.
255
     * @deprecated since version 2.6.0 - alpha 3. Switch to doctrine connector.
256
     */
257
    public function error()
258
    {
259
        $this->deprecated();
260
261
        return $this->conn->errorInfo();
262
    }
263
264
    /**
265
     * Returns the numerical value of the error message from previous
266
     * MySQL operation
267
     *
268
     * @return int Returns the error number from the last MySQL function
269
     * , or 0 (zero) if no error occurred.
270
     * @deprecated since version 2.6.0 - alpha 3. Switch to doctrine connector.
271
     */
272
    public function errno()
273
    {
274
        $this->deprecated();
275
276
        return $this->conn->errorCode();
277
    }
278
279
    /**
280
     * Returns escaped string text with single
281
     * quotes around it to be safely stored in database
282
     *
283
     * @param string $str unescaped string text
284
     *
285
     * @return string escaped string text with single quotes around
286
     * @deprecated since version 2.6.0 - alpha 3. Switch to doctrine connector.
287
     */
288
    public function quoteString($str)
289
    {
290
        $this->deprecated();
291
292
        return $this->quote($str);
0 ignored issues
show
Deprecated Code introduced by
The method XoopsMySQLDatabase::quote() has been deprecated with message: since version 2.6.0 - alpha 3. Switch to doctrine connector.

This method has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the method will be removed from the class and what other method or class to use instead.

Loading history...
293
    }
294
295
    /**
296
     * Quotes a string for use in a query.
297
     *
298
     * @param string $string string to quote
299
     *
300
     * @return string
301
     * @deprecated since version 2.6.0 - alpha 3. Switch to doctrine connector.
302
     */
303
    public function quote($string)
304
    {
305
        $this->deprecated();
306
307
        return  $this->conn->quote($string);
308
    }
309
310
    /**
311
     * Escapes a string for use in a query. Does not add quotes.
312
     *
313
     * @param string $string string to escape
314
     *
315
     * @return string
316
     * @deprecated since version 2.6.0 - alpha 3. Switch to doctrine connector.
317
     */
318
    public function escape($string)
319
    {
320
        $this->deprecated();
321
322
        $string = $this->quote($string);
0 ignored issues
show
Deprecated Code introduced by
The method XoopsMySQLDatabase::quote() has been deprecated with message: since version 2.6.0 - alpha 3. Switch to doctrine connector.

This method has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the method will be removed from the class and what other method or class to use instead.

Loading history...
323
        return substr($string, 1, -1);
324
    }
325
326
    /**
327
     * perform a query on the database
328
     *
329
     * @param string $sql   a valid MySQL query
330
     * @param int    $limit number of records to return
331
     * @param int    $start offset of first record to return
332
     *
333
     * @return bool|resource query result or FALSE if successful
334
     * or TRUE if successful and no result
335
     * @deprecated since version 2.6.0 - alpha 3. Switch to doctrine connector.
336
     */
337
    public function queryF($sql, $limit = 0, $start = 0)
338
    {
339
        $this->deprecated();
340
341
        if (!empty($limit)) {
342
            if (empty($start)) {
343
                $start = 0;
344
            }
345
            $sql = $sql . ' LIMIT ' . (int) $start . ', ' . (int) $limit;
346
        }
347
        $events = \Xoops::getInstance()->events();
348
        $events->triggerEvent('core.database.query.start');
349
        try {
350
            $result = $this->conn->query($sql);
351
        } catch (Exception $e) {
352
            $result=false;
353
        }
354
        $this->lastResult = $result;
355
        $events->triggerEvent('core.database.query.end');
356
357
        if ($result) {
358
            $events->triggerEvent('core.database.query.success', (array($sql)));
359
            return $result;
360
        } else {
361
            $events->triggerEvent('core.database.query.failure', (array($sql, $this)));
362
            return false;
363
        }
364
    }
365
366
    /**
367
     * perform a query
368
     *
369
     * This method is empty and does nothing! It should therefore only be
370
     * used if nothing is exactly what you want done! ;-)
371
     *
372
     * @param string $sql   a valid MySQL query
373
     * @param int    $limit number of records to return
374
     * @param int    $start offset of first record to return
375
     *
376
     * @return void
377
     * @deprecated since version 2.6.0 - alpha 3. Switch to doctrine connector.
378
     */
379
    public function query($sql, $limit = 0, $start = 0)
380
    {
381
        $this->deprecated();
382
    }
383
384
    /**
385
     * perform queries from SQL dump file in a batch
386
     *
387
     * @param string $file file path to an SQL dump file
388
     *
389
     * @return bool FALSE if failed reading SQL file or TRUE
390
     * if the file has been read and queries executed
391
     * @deprecated since version 2.6.0 - alpha 3. Switch to doctrine connector.
392
     */
393 View Code Duplication
    public function queryFromFile($file)
394
    {
395
        $this->deprecated();
396
397
        if (false !== ($fp = fopen($file, 'r'))) {
398
            $sql_queries = trim(fread($fp, filesize($file)));
399
            SqlUtility::splitMySqlFile($pieces, $sql_queries);
400
            foreach ($pieces as $query) {
401
                // [0] contains the prefixed query
402
                // [4] contains unprefixed table name
403
                $prefixed_query
404
                    = SqlUtility::prefixQuery(trim($query), $this->prefix());
0 ignored issues
show
Deprecated Code introduced by
The method XoopsDatabase::prefix() has been deprecated with message: since version 2.6.0 - alpha 3. Switch to doctrine connector.

This method has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the method will be removed from the class and what other method or class to use instead.

Loading history...
405
                if ($prefixed_query != false) {
406
                    $this->query($prefixed_query[0]);
0 ignored issues
show
Deprecated Code introduced by
The method XoopsMySQLDatabase::query() has been deprecated with message: since version 2.6.0 - alpha 3. Switch to doctrine connector.

This method has been deprecated. The supplier of the class has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the method will be removed from the class and what other method or class to use instead.

Loading history...
407
                }
408
            }
409
            return true;
410
        }
411
        return false;
412
    }
413
414
    /**
415
     * Get field name
416
     *
417
     * @param resource $result query result
418
     * @param int      $offset numerical field index
419
     *
420
     * @return string
421
     * @deprecated since version 2.6.0 - alpha 3. Switch to doctrine connector.
422
     */
423
    public function getFieldName($result, $offset)
424
    {
425
        $this->deprecated();
426
427
        try {
428
            $temp = $result->getColumnMeta($offset);
0 ignored issues
show
Bug introduced by
The method getColumnMeta cannot be called on $result (of type resource).

Methods can only be called on objects. This check looks for methods being called on variables that have been inferred to never be objects.

Loading history...
429
            return $temp['name'];
430
        } catch (PDOException $e) {
431
            return null;
432
        }
433
434
    }
435
436
    /**
437
     * Get field type
438
     *
439
     * @param resource $result query result
440
     * @param int      $offset numerical field index
441
     *
442
     * @return string
443
     * @deprecated since version 2.6.0 - alpha 3. Switch to doctrine connector.
444
     */
445
    public function getFieldType($result, $offset)
446
    {
447
        $this->deprecated();
448
449
        try {
450
            $temp = ($result->getColumnMeta($offset));
0 ignored issues
show
Bug introduced by
The method getColumnMeta cannot be called on $result (of type resource).

Methods can only be called on objects. This check looks for methods being called on variables that have been inferred to never be objects.

Loading history...
451
            $t = $temp['native_type'];
452
453
            $temp = (string)(
454
                ((($t === 'STRING') || ($t === 'VAR_STRING') ) ? 'string' : '' ) .
455
                ( (in_array($t, array('TINY', 'SHORT', 'LONG', 'LONGLONG', 'INT24'))) ? 'int' : '' ) .
456
                ( (in_array($t, array('FLOAT', 'DOUBLE', 'DECIMAL', 'NEWDECIMAL'))) ? 'real' : '' ) .
457
                ( ($t === 'TIMESTAMP') ? 'timestamp' : '' ) .
458
                ( ($t === 'YEAR') ? 'year' : '') .
459
                ( (($t === 'DATE') || ($t === 'NEWDATE') ) ? 'date' : '' ) .
460
                ( ($t === 'TIME') ? 'time' : '' ) .
461
                ( ($t === 'SET') ? 'set' : '' ) .
462
                ( ($t === 'ENUM') ? 'enum' : '' ) .
463
                ( ($t === 'GEOMETRY') ? 'geometry' : '' ) .
464
                ( ($t === 'DATETIME') ? 'datetime' : '' ) .
465
                ( (in_array($t, array('TINY_BLOB', 'BLOB', 'MEDIUM_BLOB', 'LONG_BLOB' ))) ? 'blob' : '' ) .
466
                ( ($t === 'NULL') ? 'null' : '' )
467
            );
468
            return $temp;
469
        } catch (PDOException $e) {
470
            return null;
471
        }
472
    }
473
474
    /**
475
     * Get number of fields in result
476
     *
477
     * @param resource $result query result
478
     *
479
     * @return int
480
     * @deprecated since version 2.6.0 - alpha 3. Switch to doctrine connector.
481
     */
482
    public function getFieldsNum($result)
483
    {
484
        $this->deprecated();
485
486
        return $result->columnCount();
0 ignored issues
show
Bug introduced by
The method columnCount cannot be called on $result (of type resource).

Methods can only be called on objects. This check looks for methods being called on variables that have been inferred to never be objects.

Loading history...
487
    }
488
489
    /**
490
     * getServerVersion get version of the mysql server
491
     *
492
     * @return string
493
     */
494
    public function getServerVersion()
495
    {
496
        $conn = \Xoops::getInstance()->db()->getWrappedConnection();
497
        $version = '(not available)';
498
        if ($conn instanceof \PDO) {
499
            $version = $conn->getAttribute(\PDO::ATTR_SERVER_VERSION);
500
        }
501
        return $version;
502
    }
503
}
504