~canonical-sysadmins/wordpress/5.1

« back to all changes in this revision

Viewing changes to wp-includes/wp-db.php

  • Committer: Barry Price
  • Date: 2019-02-22 03:51:26 UTC
  • mfrom: (1.2.12 upstream)
  • Revision ID: barry.price@canonical.com-20190222035126-o28k38qs8jfyjsxt
Merge WP5.1 from upstream

Show diffs side-by-side

added added

removed removed

Lines of Context:
18
18
 * @since 0.71
19
19
 */
20
20
define( 'OBJECT', 'OBJECT' );
 
21
// phpcs:ignore Generic.NamingConventions.UpperCaseConstantName.ConstantNotUpperCase
21
22
define( 'object', 'OBJECT' ); // Back compat.
22
23
 
23
24
/**
174
175
        protected $col_info;
175
176
 
176
177
        /**
177
 
         * Saved queries that were executed
 
178
         * Log of queries that were executed, for debugging purposes.
178
179
         *
179
180
         * @since 1.5.0
180
 
         * @var array
 
181
         * @since 2.5.0 The third element in each query log was added to record the calling functions.
 
182
         * @since 5.1.0 The fourth element in each query log was added to record the start time.
 
183
         *
 
184
         * @var array[] {
 
185
         *     Array of queries that were executed.
 
186
         *
 
187
         *     @type array ...$0 {
 
188
         *         Data for each query.
 
189
         *
 
190
         *         @type string $0 The query's SQL.
 
191
         *         @type float  $1 Total time spent on the query, in seconds.
 
192
         *         @type string $2 Comma separated list of the calling functions.
 
193
         *         @type float  $3 Unix timestamp of the time at the start of the query.
 
194
         *     }
 
195
         * }
181
196
         */
182
197
        var $queries;
183
198
 
208
223
         * @since 3.0.0
209
224
         * @var string
210
225
         */
211
 
         public $base_prefix;
 
226
        public $base_prefix;
212
227
 
213
228
        /**
214
229
         * Whether the database queries are ready to start executing.
241
256
         * @see wpdb::tables()
242
257
         * @var array
243
258
         */
244
 
        var $tables = array( 'posts', 'comments', 'links', 'options', 'postmeta',
245
 
                'terms', 'term_taxonomy', 'term_relationships', 'termmeta', 'commentmeta' );
 
259
        var $tables = array(
 
260
                'posts',
 
261
                'comments',
 
262
                'links',
 
263
                'options',
 
264
                'postmeta',
 
265
                'terms',
 
266
                'term_taxonomy',
 
267
                'term_relationships',
 
268
                'termmeta',
 
269
                'commentmeta',
 
270
        );
246
271
 
247
272
        /**
248
273
         * List of deprecated WordPress tables
271
296
         * @see wpdb::tables()
272
297
         * @var array
273
298
         */
274
 
        var $ms_global_tables = array( 'blogs', 'signups', 'site', 'sitemeta',
275
 
                'sitecategories', 'registration_log', 'blog_versions' );
 
299
        var $ms_global_tables = array(
 
300
                'blogs',
 
301
                'blogmeta',
 
302
                'signups',
 
303
                'site',
 
304
                'sitemeta',
 
305
                'sitecategories',
 
306
                'registration_log',
 
307
                'blog_versions',
 
308
        );
276
309
 
277
310
        /**
278
311
         * WordPress Comments table
383
416
        public $blogs;
384
417
 
385
418
        /**
 
419
         * Multisite Blog Metadata table
 
420
         *
 
421
         * @since 5.1.0
 
422
         * @var string
 
423
         */
 
424
        public $blogmeta;
 
425
 
 
426
        /**
386
427
         * Multisite Blog Versions table
387
428
         *
388
429
         * @since 3.0.0
528
569
         * @since 3.9.0
529
570
         * @var array
530
571
         */
531
 
        protected $incompatible_modes = array( 'NO_ZERO_DATE', 'ONLY_FULL_GROUP_BY',
532
 
                'STRICT_TRANS_TABLES', 'STRICT_ALL_TABLES', 'TRADITIONAL' );
 
572
        protected $incompatible_modes = array(
 
573
                'NO_ZERO_DATE',
 
574
                'ONLY_FULL_GROUP_BY',
 
575
                'STRICT_TRANS_TABLES',
 
576
                'STRICT_ALL_TABLES',
 
577
                'TRADITIONAL',
 
578
        );
533
579
 
534
580
        /**
535
581
         * Whether to use mysqli over mysql.
567
613
        public function __construct( $dbuser, $dbpassword, $dbname, $dbhost ) {
568
614
                register_shutdown_function( array( $this, '__destruct' ) );
569
615
 
570
 
                if ( WP_DEBUG && WP_DEBUG_DISPLAY )
 
616
                if ( WP_DEBUG && WP_DEBUG_DISPLAY ) {
571
617
                        $this->show_errors();
 
618
                }
572
619
 
573
620
                // Use ext/mysqli if it exists unless WP_USE_EXT_MYSQL is defined as true
574
621
                if ( function_exists( 'mysqli_connect' ) ) {
579
626
                        }
580
627
                }
581
628
 
582
 
                $this->dbuser = $dbuser;
 
629
                $this->dbuser     = $dbuser;
583
630
                $this->dbpassword = $dbpassword;
584
 
                $this->dbname = $dbname;
585
 
                $this->dbhost = $dbhost;
 
631
                $this->dbname     = $dbname;
 
632
                $this->dbhost     = $dbhost;
586
633
 
587
634
                // wp-config.php creation will manually connect when ready.
588
635
                if ( defined( 'WP_SETUP_CONFIG' ) ) {
612
659
         * @return mixed The private member
613
660
         */
614
661
        public function __get( $name ) {
615
 
                if ( 'col_info' === $name )
 
662
                if ( 'col_info' === $name ) {
616
663
                        $this->load_col_info();
 
664
                }
617
665
 
618
666
                return $this->$name;
619
667
        }
632
680
                        'table_charset',
633
681
                        'check_current_query',
634
682
                );
635
 
                if (  in_array( $name, $protected_members, true ) ) {
 
683
                if ( in_array( $name, $protected_members, true ) ) {
636
684
                        return;
637
685
                }
638
686
                $this->$name = $value;
671
719
                $charset = '';
672
720
                $collate = '';
673
721
 
674
 
                if ( function_exists('is_multisite') && is_multisite() ) {
 
722
                if ( function_exists( 'is_multisite' ) && is_multisite() ) {
675
723
                        $charset = 'utf8';
676
724
                        if ( defined( 'DB_COLLATE' ) && DB_COLLATE ) {
677
725
                                $collate = DB_COLLATE;
744
792
         * @param string   $collate Optional. The collation. Default null.
745
793
         */
746
794
        public function set_charset( $dbh, $charset = null, $collate = null ) {
747
 
                if ( ! isset( $charset ) )
 
795
                if ( ! isset( $charset ) ) {
748
796
                        $charset = $this->charset;
749
 
                if ( ! isset( $collate ) )
 
797
                }
 
798
                if ( ! isset( $collate ) ) {
750
799
                        $collate = $this->collate;
 
800
                }
751
801
                if ( $this->has_cap( 'collation' ) && ! empty( $charset ) ) {
752
802
                        $set_charset_succeeded = true;
753
803
 
758
808
 
759
809
                                if ( $set_charset_succeeded ) {
760
810
                                        $query = $this->prepare( 'SET NAMES %s', $charset );
761
 
                                        if ( ! empty( $collate ) )
 
811
                                        if ( ! empty( $collate ) ) {
762
812
                                                $query .= $this->prepare( ' COLLATE %s', $collate );
 
813
                                        }
763
814
                                        mysqli_query( $dbh, $query );
764
815
                                }
765
816
                        } else {
768
819
                                }
769
820
                                if ( $set_charset_succeeded ) {
770
821
                                        $query = $this->prepare( 'SET NAMES %s', $charset );
771
 
                                        if ( ! empty( $collate ) )
 
822
                                        if ( ! empty( $collate ) ) {
772
823
                                                $query .= $this->prepare( ' COLLATE %s', $collate );
 
824
                                        }
773
825
                                        mysql_query( $query, $dbh );
774
826
                                }
775
827
                        }
852
904
         */
853
905
        public function set_prefix( $prefix, $set_table_names = true ) {
854
906
 
855
 
                if ( preg_match( '|[^a-z0-9_]|i', $prefix ) )
856
 
                        return new WP_Error('invalid_db_prefix', 'Invalid database prefix' );
 
907
                if ( preg_match( '|[^a-z0-9_]|i', $prefix ) ) {
 
908
                        return new WP_Error( 'invalid_db_prefix', 'Invalid database prefix' );
 
909
                }
857
910
 
858
911
                $old_prefix = is_multisite() ? '' : $prefix;
859
912
 
860
 
                if ( isset( $this->base_prefix ) )
 
913
                if ( isset( $this->base_prefix ) ) {
861
914
                        $old_prefix = $this->base_prefix;
 
915
                }
862
916
 
863
917
                $this->base_prefix = $prefix;
864
918
 
865
919
                if ( $set_table_names ) {
866
 
                        foreach ( $this->tables( 'global' ) as $table => $prefixed_table )
 
920
                        foreach ( $this->tables( 'global' ) as $table => $prefixed_table ) {
867
921
                                $this->$table = $prefixed_table;
 
922
                        }
868
923
 
869
 
                        if ( is_multisite() && empty( $this->blogid ) )
 
924
                        if ( is_multisite() && empty( $this->blogid ) ) {
870
925
                                return $old_prefix;
 
926
                        }
871
927
 
872
928
                        $this->prefix = $this->get_blog_prefix();
873
929
 
874
 
                        foreach ( $this->tables( 'blog' ) as $table => $prefixed_table )
 
930
                        foreach ( $this->tables( 'blog' ) as $table => $prefixed_table ) {
875
931
                                $this->$table = $prefixed_table;
 
932
                        }
876
933
 
877
 
                        foreach ( $this->tables( 'old' ) as $table => $prefixed_table )
 
934
                        foreach ( $this->tables( 'old' ) as $table => $prefixed_table ) {
878
935
                                $this->$table = $prefixed_table;
 
936
                        }
879
937
                }
880
938
                return $old_prefix;
881
939
        }
899
957
 
900
958
                $this->prefix = $this->get_blog_prefix();
901
959
 
902
 
                foreach ( $this->tables( 'blog' ) as $table => $prefixed_table )
 
960
                foreach ( $this->tables( 'blog' ) as $table => $prefixed_table ) {
903
961
                        $this->$table = $prefixed_table;
 
962
                }
904
963
 
905
 
                foreach ( $this->tables( 'old' ) as $table => $prefixed_table )
 
964
                foreach ( $this->tables( 'old' ) as $table => $prefixed_table ) {
906
965
                        $this->$table = $prefixed_table;
 
966
                }
907
967
 
908
968
                return $old_blog_id;
909
969
        }
917
977
         */
918
978
        public function get_blog_prefix( $blog_id = null ) {
919
979
                if ( is_multisite() ) {
920
 
                        if ( null === $blog_id )
 
980
                        if ( null === $blog_id ) {
921
981
                                $blog_id = $this->blogid;
 
982
                        }
922
983
                        $blog_id = (int) $blog_id;
923
 
                        if ( defined( 'MULTISITE' ) && ( 0 == $blog_id || 1 == $blog_id ) )
 
984
                        if ( defined( 'MULTISITE' ) && ( 0 == $blog_id || 1 == $blog_id ) ) {
924
985
                                return $this->base_prefix;
925
 
                        else
 
986
                        } else {
926
987
                                return $this->base_prefix . $blog_id . '_';
 
988
                        }
927
989
                } else {
928
990
                        return $this->base_prefix;
929
991
                }
958
1020
         */
959
1021
        public function tables( $scope = 'all', $prefix = true, $blog_id = 0 ) {
960
1022
                switch ( $scope ) {
961
 
                        case 'all' :
 
1023
                        case 'all':
962
1024
                                $tables = array_merge( $this->global_tables, $this->tables );
963
 
                                if ( is_multisite() )
 
1025
                                if ( is_multisite() ) {
964
1026
                                        $tables = array_merge( $tables, $this->ms_global_tables );
 
1027
                                }
965
1028
                                break;
966
 
                        case 'blog' :
 
1029
                        case 'blog':
967
1030
                                $tables = $this->tables;
968
1031
                                break;
969
 
                        case 'global' :
 
1032
                        case 'global':
970
1033
                                $tables = $this->global_tables;
971
 
                                if ( is_multisite() )
 
1034
                                if ( is_multisite() ) {
972
1035
                                        $tables = array_merge( $tables, $this->ms_global_tables );
 
1036
                                }
973
1037
                                break;
974
 
                        case 'ms_global' :
 
1038
                        case 'ms_global':
975
1039
                                $tables = $this->ms_global_tables;
976
1040
                                break;
977
 
                        case 'old' :
 
1041
                        case 'old':
978
1042
                                $tables = $this->old_tables;
979
1043
                                break;
980
 
                        default :
 
1044
                        default:
981
1045
                                return array();
982
1046
                }
983
1047
 
984
1048
                if ( $prefix ) {
985
 
                        if ( ! $blog_id )
 
1049
                        if ( ! $blog_id ) {
986
1050
                                $blog_id = $this->blogid;
987
 
                        $blog_prefix = $this->get_blog_prefix( $blog_id );
988
 
                        $base_prefix = $this->base_prefix;
 
1051
                        }
 
1052
                        $blog_prefix   = $this->get_blog_prefix( $blog_id );
 
1053
                        $base_prefix   = $this->base_prefix;
989
1054
                        $global_tables = array_merge( $this->global_tables, $this->ms_global_tables );
990
1055
                        foreach ( $tables as $k => $table ) {
991
 
                                if ( in_array( $table, $global_tables ) )
 
1056
                                if ( in_array( $table, $global_tables ) ) {
992
1057
                                        $tables[ $table ] = $base_prefix . $table;
993
 
                                else
 
1058
                                } else {
994
1059
                                        $tables[ $table ] = $blog_prefix . $table;
 
1060
                                }
995
1061
                                unset( $tables[ $k ] );
996
1062
                        }
997
1063
 
998
 
                        if ( isset( $tables['users'] ) && defined( 'CUSTOM_USER_TABLE' ) )
 
1064
                        if ( isset( $tables['users'] ) && defined( 'CUSTOM_USER_TABLE' ) ) {
999
1065
                                $tables['users'] = CUSTOM_USER_TABLE;
 
1066
                        }
1000
1067
 
1001
 
                        if ( isset( $tables['usermeta'] ) && defined( 'CUSTOM_USER_META_TABLE' ) )
 
1068
                        if ( isset( $tables['usermeta'] ) && defined( 'CUSTOM_USER_META_TABLE' ) ) {
1002
1069
                                $tables['usermeta'] = CUSTOM_USER_META_TABLE;
 
1070
                        }
1003
1071
                }
1004
1072
 
1005
1073
                return $tables;
1017
1085
         * @param resource|null $dbh Optional link identifier.
1018
1086
         */
1019
1087
        public function select( $db, $dbh = null ) {
1020
 
                if ( is_null($dbh) )
 
1088
                if ( is_null( $dbh ) ) {
1021
1089
                        $dbh = $this->dbh;
 
1090
                }
1022
1091
 
1023
1092
                if ( $this->use_mysqli ) {
1024
1093
                        $success = mysqli_select_db( $dbh, $db );
1044
1113
                                $message .= '<li>' . sprintf(
1045
1114
                                        /* translators: 1: database user, 2: database name */
1046
1115
                                        __( 'Does the user %1$s have permission to use the %2$s database?' ),
1047
 
                                        '<code>' . htmlspecialchars( $this->dbuser, ENT_QUOTES )  . '</code>',
 
1116
                                        '<code>' . htmlspecialchars( $this->dbuser, ENT_QUOTES ) . '</code>',
1048
1117
                                        '<code>' . htmlspecialchars( $db, ENT_QUOTES ) . '</code>'
1049
1118
                                ) . "</li>\n";
1050
1119
 
1052
1121
                                        /* translators: %s: database name */
1053
1122
                                        __( 'On some systems the name of your database is prefixed with your username, so it would be like <code>username_%1$s</code>. Could that be the problem?' ),
1054
1123
                                        htmlspecialchars( $db, ENT_QUOTES )
1055
 
                                ). "</li>\n";
 
1124
                                ) . "</li>\n";
1056
1125
 
1057
1126
                                $message .= "</ul>\n";
1058
1127
 
1081
1150
         * @return string
1082
1151
         */
1083
1152
        function _weak_escape( $string ) {
1084
 
                if ( func_num_args() === 1 && function_exists( '_deprecated_function' ) )
 
1153
                if ( func_num_args() === 1 && function_exists( '_deprecated_function' ) ) {
1085
1154
                        _deprecated_function( __METHOD__, '3.6.0', 'wpdb::prepare() or esc_sql()' );
 
1155
                }
1086
1156
                return addslashes( $string );
1087
1157
        }
1088
1158
 
1130
1200
                if ( is_array( $data ) ) {
1131
1201
                        foreach ( $data as $k => $v ) {
1132
1202
                                if ( is_array( $v ) ) {
1133
 
                                        $data[$k] = $this->_escape( $v );
 
1203
                                        $data[ $k ] = $this->_escape( $v );
1134
1204
                                } else {
1135
 
                                        $data[$k] = $this->_real_escape( $v );
 
1205
                                        $data[ $k ] = $this->_real_escape( $v );
1136
1206
                                }
1137
1207
                        }
1138
1208
                } else {
1156
1226
         * @return mixed
1157
1227
         */
1158
1228
        public function escape( $data ) {
1159
 
                if ( func_num_args() === 1 && function_exists( '_deprecated_function' ) )
 
1229
                if ( func_num_args() === 1 && function_exists( '_deprecated_function' ) ) {
1160
1230
                        _deprecated_function( __METHOD__, '3.6.0', 'wpdb::prepare() or esc_sql()' );
 
1231
                }
1161
1232
                if ( is_array( $data ) ) {
1162
1233
                        foreach ( $data as $k => $v ) {
1163
 
                                if ( is_array( $v ) )
1164
 
                                        $data[$k] = $this->escape( $v, 'recursive' );
1165
 
                                else
1166
 
                                        $data[$k] = $this->_weak_escape( $v, 'internal' );
 
1234
                                if ( is_array( $v ) ) {
 
1235
                                        $data[ $k ] = $this->escape( $v, 'recursive' );
 
1236
                                } else {
 
1237
                                        $data[ $k ] = $this->_weak_escape( $v, 'internal' );
 
1238
                                }
1167
1239
                        }
1168
1240
                } else {
1169
1241
                        $data = $this->_weak_escape( $data, 'internal' );
1182
1254
         * @param string $string to escape
1183
1255
         */
1184
1256
        public function escape_by_ref( &$string ) {
1185
 
                if ( ! is_float( $string ) )
 
1257
                if ( ! is_float( $string ) ) {
1186
1258
                        $string = $this->_real_escape( $string );
 
1259
                }
1187
1260
        }
1188
1261
 
1189
1262
        /**
1201
1274
         *
1202
1275
         * Literal percentage signs (%) in the query string must be written as %%. Percentage wildcards (for example,
1203
1276
         * to use in LIKE syntax) must be passed via a substitution argument containing the complete LIKE string, these
1204
 
         * cannot be inserted directly in the query string. Also see {@see esc_like()}.
 
1277
         * cannot be inserted directly in the query string. Also see {@see wpdb::esc_like()}.
1205
1278
         *
1206
1279
         * Arguments may be passed as individual arguments to the method, or as a single array containing all arguments. A combination
1207
1280
         * of the two is not supported.
1237
1310
                $passed_as_array = false;
1238
1311
                if ( is_array( $args[0] ) && count( $args ) == 1 ) {
1239
1312
                        $passed_as_array = true;
1240
 
                        $args = $args[0];
 
1313
                        $args            = $args[0];
1241
1314
                }
1242
1315
 
1243
1316
                foreach ( $args as $arg ) {
1269
1342
                $query = str_replace( '"%s"', '%s', $query ); // Strip any existing double quotes.
1270
1343
                $query = preg_replace( '/(?<!%)%s/', "'%s'", $query ); // Quote the strings, avoiding escaped strings like %%s.
1271
1344
 
1272
 
                $query = preg_replace( "/(?<!%)(%($allowed_format)?f)/" , '%\\2F', $query ); // Force floats to be locale unaware.
 
1345
                $query = preg_replace( "/(?<!%)(%($allowed_format)?f)/", '%\\2F', $query ); // Force floats to be locale unaware.
1273
1346
 
1274
1347
                $query = preg_replace( "/%(?:%|$|(?!($allowed_format)?[sdF]))/", '%%\\1', $query ); // Escape any unescaped percents.
1275
1348
 
1289
1362
                                 * or we were expecting multiple arguments in an array, throw a warning.
1290
1363
                                 */
1291
1364
                                wp_load_translations_early();
1292
 
                                _doing_it_wrong( 'wpdb::prepare',
 
1365
                                _doing_it_wrong(
 
1366
                                        'wpdb::prepare',
1293
1367
                                        /* translators: 1: number of placeholders, 2: number of arguments passed */
1294
 
                                        sprintf( __( 'The query does not contain the correct number of placeholders (%1$d) for the number of arguments passed (%2$d).' ),
 
1368
                                        sprintf(
 
1369
                                                __( 'The query does not contain the correct number of placeholders (%1$d) for the number of arguments passed (%2$d).' ),
1295
1370
                                                $placeholders,
1296
 
                                                count( $args ) ),
 
1371
                                                count( $args )
 
1372
                                        ),
1297
1373
                                        '4.8.3'
1298
1374
                                );
1299
1375
                        }
1344
1420
        public function print_error( $str = '' ) {
1345
1421
                global $EZSQL_ERROR;
1346
1422
 
1347
 
                if ( !$str ) {
 
1423
                if ( ! $str ) {
1348
1424
                        if ( $this->use_mysqli ) {
1349
1425
                                $str = mysqli_error( $this->dbh );
1350
1426
                        } else {
1351
1427
                                $str = mysql_error( $this->dbh );
1352
1428
                        }
1353
1429
                }
1354
 
                $EZSQL_ERROR[] = array( 'query' => $this->last_query, 'error_str' => $str );
 
1430
                $EZSQL_ERROR[] = array(
 
1431
                        'query'     => $this->last_query,
 
1432
                        'error_str' => $str,
 
1433
                );
1355
1434
 
1356
 
                if ( $this->suppress_errors )
 
1435
                if ( $this->suppress_errors ) {
1357
1436
                        return false;
 
1437
                }
1358
1438
 
1359
1439
                wp_load_translations_early();
1360
1440
 
1369
1449
                error_log( $error_str );
1370
1450
 
1371
1451
                // Are we showing errors?
1372
 
                if ( ! $this->show_errors )
 
1452
                if ( ! $this->show_errors ) {
1373
1453
                        return false;
 
1454
                }
1374
1455
 
1375
1456
                // If there is an error then take note of it
1376
1457
                if ( is_multisite() ) {
1415
1496
         * @return bool Old value for showing errors.
1416
1497
         */
1417
1498
        public function show_errors( $show = true ) {
1418
 
                $errors = $this->show_errors;
 
1499
                $errors            = $this->show_errors;
1419
1500
                $this->show_errors = $show;
1420
1501
                return $errors;
1421
1502
        }
1431
1512
         * @return bool Whether showing of errors was active
1432
1513
         */
1433
1514
        public function hide_errors() {
1434
 
                $show = $this->show_errors;
 
1515
                $show              = $this->show_errors;
1435
1516
                $this->show_errors = false;
1436
1517
                return $show;
1437
1518
        }
1448
1529
         * @return bool Old value
1449
1530
         */
1450
1531
        public function suppress_errors( $suppress = true ) {
1451
 
                $errors = $this->suppress_errors;
 
1532
                $errors                = $this->suppress_errors;
1452
1533
                $this->suppress_errors = (bool) $suppress;
1453
1534
                return $errors;
1454
1535
        }
1459
1540
         * @since 0.71
1460
1541
         */
1461
1542
        public function flush() {
1462
 
                $this->last_result = array();
1463
 
                $this->col_info    = null;
1464
 
                $this->last_query  = null;
 
1543
                $this->last_result   = array();
 
1544
                $this->col_info      = null;
 
1545
                $this->last_query    = null;
1465
1546
                $this->rows_affected = $this->num_rows = 0;
1466
 
                $this->last_error  = '';
 
1547
                $this->last_error    = '';
1467
1548
 
1468
1549
                if ( $this->use_mysqli && $this->result instanceof mysqli_result ) {
1469
1550
                        mysqli_free_result( $this->result );
1470
1551
                        $this->result = null;
1471
1552
 
1472
1553
                        // Sanity check before using the handle
1473
 
                        if ( empty( $this->dbh ) || !( $this->dbh instanceof mysqli ) ) {
 
1554
                        if ( empty( $this->dbh ) || ! ( $this->dbh instanceof mysqli ) ) {
1474
1555
                                return;
1475
1556
                        }
1476
1557
 
1502
1583
                 * Deprecated in 3.9+ when using MySQLi. No equivalent
1503
1584
                 * $new_link parameter exists for mysqli_* functions.
1504
1585
                 */
1505
 
                $new_link = defined( 'MYSQL_NEW_LINK' ) ? MYSQL_NEW_LINK : true;
 
1586
                $new_link     = defined( 'MYSQL_NEW_LINK' ) ? MYSQL_NEW_LINK : true;
1506
1587
                $client_flags = defined( 'MYSQL_CLIENT_FLAGS' ) ? MYSQL_CLIENT_FLAGS : 0;
1507
1588
 
1508
1589
                if ( $this->use_mysqli ) {
1538
1619
 
1539
1620
                                /*
1540
1621
                                 * It's possible ext/mysqli is misconfigured. Fall back to ext/mysql if:
1541
 
                                 *  - We haven't previously connected, and
1542
 
                                 *  - WP_USE_EXT_MYSQL isn't set to false, and
1543
 
                                 *  - ext/mysql is loaded.
1544
 
                                 */
 
1622
                                  *  - We haven't previously connected, and
 
1623
                                  *  - WP_USE_EXT_MYSQL isn't set to false, and
 
1624
                                  *  - ext/mysql is loaded.
 
1625
                                  */
1545
1626
                                $attempt_fallback = true;
1546
1627
 
1547
1628
                                if ( $this->has_connected ) {
1577
1658
                        $message = '<h1>' . __( 'Error establishing a database connection' ) . "</h1>\n";
1578
1659
 
1579
1660
                        $message .= '<p>' . sprintf(
1580
 
                                /* translators: 1: wp-config.php. 2: database host */
 
1661
                                /* translators: 1: wp-config.php, 2: database host */
1581
1662
                                __( 'This either means that the username and password information in your %1$s file is incorrect or we can&#8217;t contact the database server at %2$s. This could mean your host&#8217;s database server is down.' ),
1582
1663
                                '<code>wp-config.php</code>',
1583
1664
                                '<code>' . htmlspecialchars( $this->dbhost, ENT_QUOTES ) . '</code>'
1640
1721
                $socket_pos = strpos( $host, ':/' );
1641
1722
                if ( $socket_pos !== false ) {
1642
1723
                        $socket = substr( $host, $socket_pos + 1 );
1643
 
                        $host = substr( $host, 0, $socket_pos );
 
1724
                        $host   = substr( $host, 0, $socket_pos );
1644
1725
                }
1645
1726
 
1646
1727
                // We need to check for an IPv6 address first.
1654
1735
                }
1655
1736
 
1656
1737
                $matches = array();
1657
 
                $result = preg_match( $pattern, $host, $matches );
 
1738
                $result  = preg_match( $pattern, $host, $matches );
1658
1739
 
1659
1740
                if ( 1 !== $result ) {
1660
1741
                        // Couldn't parse the address, bail.
1768
1849
         * @since 0.71
1769
1850
         *
1770
1851
         * @param string $query Database query
1771
 
         * @return int|false Number of rows affected/selected or false on error
 
1852
         * @return int|bool Boolean true for CREATE, ALTER, TRUNCATE and DROP queries. Number of rows
 
1853
         *                  affected/selected for all other queries. Boolean false on error.
1772
1854
         */
1773
1855
        public function query( $query ) {
1774
1856
                if ( ! $this->ready ) {
1858
1940
 
1859
1941
                if ( $this->last_error ) {
1860
1942
                        // Clear insert_id on a subsequent failed insert.
1861
 
                        if ( $this->insert_id && preg_match( '/^\s*(insert|replace)\s/i', $query ) )
 
1943
                        if ( $this->insert_id && preg_match( '/^\s*(insert|replace)\s/i', $query ) ) {
1862
1944
                                $this->insert_id = 0;
 
1945
                        }
1863
1946
 
1864
1947
                        $this->print_error();
1865
1948
                        return false;
1887
1970
                        $num_rows = 0;
1888
1971
                        if ( $this->use_mysqli && $this->result instanceof mysqli_result ) {
1889
1972
                                while ( $row = mysqli_fetch_object( $this->result ) ) {
1890
 
                                        $this->last_result[$num_rows] = $row;
 
1973
                                        $this->last_result[ $num_rows ] = $row;
1891
1974
                                        $num_rows++;
1892
1975
                                }
1893
1976
                        } elseif ( is_resource( $this->result ) ) {
1894
1977
                                while ( $row = mysql_fetch_object( $this->result ) ) {
1895
 
                                        $this->last_result[$num_rows] = $row;
 
1978
                                        $this->last_result[ $num_rows ] = $row;
1896
1979
                                        $num_rows++;
1897
1980
                                }
1898
1981
                        }
1928
2011
                $this->num_queries++;
1929
2012
 
1930
2013
                if ( defined( 'SAVEQUERIES' ) && SAVEQUERIES ) {
1931
 
                        $this->queries[] = array( $query, $this->timer_stop(), $this->get_caller() );
 
2014
                        $this->queries[] = array(
 
2015
                                $query,
 
2016
                                $this->timer_stop(),
 
2017
                                $this->get_caller(),
 
2018
                                $this->time_start,
 
2019
                        );
1932
2020
                }
1933
2021
        }
1934
2022
 
2154
2242
                        }
2155
2243
 
2156
2244
                        $conditions[] = "`$field` = " . $value['format'];
2157
 
                        $values[] = $value['value'];
 
2245
                        $values[]     = $value['value'];
2158
2246
                }
2159
2247
 
2160
 
                $fields = implode( ', ', $fields );
 
2248
                $fields     = implode( ', ', $fields );
2161
2249
                $conditions = implode( ' AND ', $conditions );
2162
2250
 
2163
2251
                $sql = "UPDATE `$table` SET $fields WHERE $conditions";
2206
2294
                        }
2207
2295
 
2208
2296
                        $conditions[] = "`$field` = " . $value['format'];
2209
 
                        $values[] = $value['value'];
 
2297
                        $values[]     = $value['value'];
2210
2298
                }
2211
2299
 
2212
2300
                $conditions = implode( ' AND ', $conditions );
2381
2469
                }
2382
2470
 
2383
2471
                // Extract var out of cached results based x,y vals
2384
 
                if ( !empty( $this->last_result[$y] ) ) {
2385
 
                        $values = array_values( get_object_vars( $this->last_result[$y] ) );
 
2472
                if ( ! empty( $this->last_result[ $y ] ) ) {
 
2473
                        $values = array_values( get_object_vars( $this->last_result[ $y ] ) );
2386
2474
                }
2387
2475
 
2388
2476
                // If there is a value return it else return null
2389
 
                return ( isset( $values[$x] ) && $values[$x] !== '' ) ? $values[$x] : null;
 
2477
                return ( isset( $values[ $x ] ) && $values[ $x ] !== '' ) ? $values[ $x ] : null;
2390
2478
        }
2391
2479
 
2392
2480
        /**
2415
2503
                        return null;
2416
2504
                }
2417
2505
 
2418
 
                if ( !isset( $this->last_result[$y] ) )
 
2506
                if ( ! isset( $this->last_result[ $y ] ) ) {
2419
2507
                        return null;
 
2508
                }
2420
2509
 
2421
2510
                if ( $output == OBJECT ) {
2422
 
                        return $this->last_result[$y] ? $this->last_result[$y] : null;
 
2511
                        return $this->last_result[ $y ] ? $this->last_result[ $y ] : null;
2423
2512
                } elseif ( $output == ARRAY_A ) {
2424
 
                        return $this->last_result[$y] ? get_object_vars( $this->last_result[$y] ) : null;
 
2513
                        return $this->last_result[ $y ] ? get_object_vars( $this->last_result[ $y ] ) : null;
2425
2514
                } elseif ( $output == ARRAY_N ) {
2426
 
                        return $this->last_result[$y] ? array_values( get_object_vars( $this->last_result[$y] ) ) : null;
 
2515
                        return $this->last_result[ $y ] ? array_values( get_object_vars( $this->last_result[ $y ] ) ) : null;
2427
2516
                } elseif ( strtoupper( $output ) === OBJECT ) {
2428
2517
                        // Back compat for OBJECT being previously case insensitive.
2429
 
                        return $this->last_result[$y] ? $this->last_result[$y] : null;
 
2518
                        return $this->last_result[ $y ] ? $this->last_result[ $y ] : null;
2430
2519
                } else {
2431
 
                        $this->print_error( " \$db->get_row(string query, output type, int offset) -- Output type must be one of: OBJECT, ARRAY_A, ARRAY_N" );
 
2520
                        $this->print_error( ' $db->get_row(string query, output type, int offset) -- Output type must be one of: OBJECT, ARRAY_A, ARRAY_N' );
2432
2521
                }
2433
2522
        }
2434
2523
 
2445
2534
         * @param int         $x     Optional. Column to return. Indexed from 0.
2446
2535
         * @return array Database query result. Array indexed from 0 by SQL result row number.
2447
2536
         */
2448
 
        public function get_col( $query = null , $x = 0 ) {
 
2537
        public function get_col( $query = null, $x = 0 ) {
2449
2538
                if ( $this->check_current_query && $this->check_safe_collation( $query ) ) {
2450
2539
                        $this->check_current_query = false;
2451
2540
                }
2502
2591
                        if ( $this->last_result ) {
2503
2592
                                foreach ( $this->last_result as $row ) {
2504
2593
                                        $var_by_ref = get_object_vars( $row );
2505
 
                                        $key = array_shift( $var_by_ref );
 
2594
                                        $key        = array_shift( $var_by_ref );
2506
2595
                                        if ( ! isset( $new_array[ $key ] ) ) {
2507
2596
                                                $new_array[ $key ] = $row;
2508
2597
                                        }
2564
2653
                $charsets = $columns = array();
2565
2654
 
2566
2655
                $table_parts = explode( '.', $table );
2567
 
                $table = '`' . implode( '`.`', $table_parts ) . '`';
2568
 
                $results = $this->get_results( "SHOW FULL COLUMNS FROM $table" );
 
2656
                $table       = '`' . implode( '`.`', $table_parts ) . '`';
 
2657
                $results     = $this->get_results( "SHOW FULL COLUMNS FROM $table" );
2569
2658
                if ( ! $results ) {
2570
2659
                        return new WP_Error( 'wpdb_get_table_charset_failure' );
2571
2660
                }
2641
2730
         *                               character set. WP_Error object if there was an error.
2642
2731
         */
2643
2732
        public function get_col_charset( $table, $column ) {
2644
 
                $tablekey = strtolower( $table );
 
2733
                $tablekey  = strtolower( $table );
2645
2734
                $columnkey = strtolower( $column );
2646
2735
 
2647
2736
                /**
2706
2795
         *                              WP_Error object if there was an error.
2707
2796
         */
2708
2797
        public function get_col_length( $table, $column ) {
2709
 
                $tablekey = strtolower( $table );
 
2798
                $tablekey  = strtolower( $table );
2710
2799
                $columnkey = strtolower( $column );
2711
2800
 
2712
2801
                // Skip this entirely if this isn't a MySQL database.
2735
2824
                        $length = false;
2736
2825
                }
2737
2826
 
2738
 
                switch( $type ) {
 
2827
                switch ( $type ) {
2739
2828
                        case 'char':
2740
2829
                        case 'varchar':
2741
2830
                                return array(
2836
2925
                }
2837
2926
 
2838
2927
                $this->checking_collation = true;
2839
 
                $collation = $this->get_table_charset( $table );
 
2928
                $collation                = $this->get_table_charset( $table );
2840
2929
                $this->checking_collation = false;
2841
2930
 
2842
2931
                // Tables with no collation, or latin1 only, don't need extra checking.
2883
2972
                        $charset = $value['charset'];
2884
2973
 
2885
2974
                        if ( is_array( $value['length'] ) ) {
2886
 
                                $length = $value['length']['length'];
 
2975
                                $length                  = $value['length']['length'];
2887
2976
                                $truncate_by_byte_length = 'byte' === $value['length']['type'];
2888
2977
                        } else {
2889
2978
                                $length = false;
2912
3001
                                ( ! isset( $value['ascii'] ) && $this->check_ascii( $value['value'] ) )
2913
3002
                        ) {
2914
3003
                                $truncate_by_byte_length = true;
2915
 
                                $needs_validation = false;
 
3004
                                $needs_validation        = false;
2916
3005
                        }
2917
3006
 
2918
3007
                        if ( $truncate_by_byte_length ) {
2946
3035
                                        ';
2947
3036
                                }
2948
3037
 
2949
 
                                $regex .= '){1,40}                          # ...one or more times
 
3038
                                $regex         .= '){1,40}                          # ...one or more times
2950
3039
                                        )
2951
3040
                                        | .                                  # anything else
2952
3041
                                        /x';
2953
3042
                                $value['value'] = preg_replace( $regex, '$1', $value['value'] );
2954
3043
 
2955
 
 
2956
3044
                                if ( false !== $length && mb_strlen( $value['value'], 'UTF-8' ) > $length ) {
2957
3045
                                        $value['value'] = mb_substr( $value['value'], 0, $length, 'UTF-8' );
2958
3046
                                }
2987
3075
                                        }
2988
3076
 
2989
3077
                                        if ( is_array( $value['length'] ) ) {
2990
 
                                                $length = sprintf( '%.0f', $value['length']['length'] );
 
3078
                                                $length          = sprintf( '%.0f', $value['length']['length'] );
2991
3079
                                                $queries[ $col ] = $this->prepare( "CONVERT( LEFT( CONVERT( %s USING $charset ), $length ) USING $connection_charset )", $value['value'] );
2992
 
                                        } else if ( 'binary' !== $charset ) {
 
3080
                                        } elseif ( 'binary' !== $charset ) {
2993
3081
                                                // If we don't have a length, there's no need to convert binary - it will always return the same result.
2994
3082
                                                $queries[ $col ] = $this->prepare( "CONVERT( CONVERT( %s USING $charset ) USING $connection_charset )", $value['value'] );
2995
3083
                                        }
3008
3096
                        }
3009
3097
 
3010
3098
                        $this->check_current_query = false;
3011
 
                        $row = $this->get_row( "SELECT " . implode( ', ', $sql ), ARRAY_A );
 
3099
                        $row                       = $this->get_row( 'SELECT ' . implode( ', ', $sql ), ARRAY_A );
3012
3100
                        if ( ! $row ) {
3013
3101
                                return new WP_Error( 'wpdb_strip_invalid_text_failure' );
3014
3102
                        }
3015
3103
 
3016
3104
                        foreach ( array_keys( $data ) as $column ) {
3017
 
                                if ( isset( $row["x_$column"] ) ) {
3018
 
                                        $data[ $column ]['value'] = $row["x_$column"];
 
3105
                                if ( isset( $row[ "x_$column" ] ) ) {
 
3106
                                        $data[ $column ]['value'] = $row[ "x_$column" ];
3019
3107
                                }
3020
3108
                        }
3021
3109
                }
3097
3185
                                'value'   => $value,
3098
3186
                                'charset' => $charset,
3099
3187
                                'length'  => $this->get_col_length( $table, $column ),
3100
 
                        )
 
3188
                        ),
3101
3189
                );
3102
3190
 
3103
3191
                $data = $this->strip_invalid_text( $data );
3127
3215
                $query = preg_replace( '/\((?!\s*select)[^(]*?\)/is', '()', $query );
3128
3216
 
3129
3217
                // Quickly match most common queries.
3130
 
                if ( preg_match( '/^\s*(?:'
 
3218
                if ( preg_match(
 
3219
                        '/^\s*(?:'
3131
3220
                                . 'SELECT.*?\s+FROM'
3132
3221
                                . '|INSERT(?:\s+LOW_PRIORITY|\s+DELAYED|\s+HIGH_PRIORITY)?(?:\s+IGNORE)?(?:\s+INTO)?'
3133
3222
                                . '|REPLACE(?:\s+LOW_PRIORITY|\s+DELAYED)?(?:\s+INTO)?'
3134
3223
                                . '|UPDATE(?:\s+LOW_PRIORITY)?(?:\s+IGNORE)?'
3135
3224
                                . '|DELETE(?:\s+LOW_PRIORITY|\s+QUICK|\s+IGNORE)*(?:.+?FROM)?'
3136
 
                                . ')\s+((?:[0-9a-zA-Z$_.`-]|[\xC2-\xDF][\x80-\xBF])+)/is', $query, $maybe ) ) {
 
3225
                        . ')\s+((?:[0-9a-zA-Z$_.`-]|[\xC2-\xDF][\x80-\xBF])+)/is',
 
3226
                        $query,
 
3227
                        $maybe
 
3228
                ) ) {
3137
3229
                        return str_replace( '`', '', $maybe[1] );
3138
3230
                }
3139
3231
 
3152
3244
                }
3153
3245
 
3154
3246
                // Big pattern for the rest of the table-related queries.
3155
 
                if ( preg_match( '/^\s*(?:'
 
3247
                if ( preg_match(
 
3248
                        '/^\s*(?:'
3156
3249
                                . '(?:EXPLAIN\s+(?:EXTENDED\s+)?)?SELECT.*?\s+FROM'
3157
3250
                                . '|DESCRIBE|DESC|EXPLAIN|HANDLER'
3158
3251
                                . '|(?:LOCK|UNLOCK)\s+TABLE(?:S)?'
3166
3259
                                . '|LOAD\s+DATA.*INFILE.*INTO\s+TABLE'
3167
3260
                                . '|(?:GRANT|REVOKE).*ON\s+TABLE'
3168
3261
                                . '|SHOW\s+(?:.*FROM|.*TABLE)'
3169
 
                                . ')\s+\(*\s*((?:[0-9a-zA-Z$_.`-]|[\xC2-\xDF][\x80-\xBF])+)\s*\)*/is', $query, $maybe ) ) {
 
3262
                        . ')\s+\(*\s*((?:[0-9a-zA-Z$_.`-]|[\xC2-\xDF][\x80-\xBF])+)\s*\)*/is',
 
3263
                        $query,
 
3264
                        $maybe
 
3265
                ) ) {
3170
3266
                        return str_replace( '`', '', $maybe[1] );
3171
3267
                }
3172
3268
 
3177
3273
         * Load the column metadata from the last query.
3178
3274
         *
3179
3275
         * @since 3.5.0
3180
 
         *
3181
3276
         */
3182
3277
        protected function load_col_info() {
3183
 
                if ( $this->col_info )
 
3278
                if ( $this->col_info ) {
3184
3279
                        return;
 
3280
                }
3185
3281
 
3186
3282
                if ( $this->use_mysqli ) {
3187
3283
                        $num_fields = mysqli_num_fields( $this->result );
3210
3306
 
3211
3307
                if ( $this->col_info ) {
3212
3308
                        if ( $col_offset == -1 ) {
3213
 
                                $i = 0;
 
3309
                                $i         = 0;
3214
3310
                                $new_array = array();
3215
3311
                                foreach ( (array) $this->col_info as $col ) {
3216
 
                                        $new_array[$i] = $col->{$info_type};
 
3312
                                        $new_array[ $i ] = $col->{$info_type};
3217
3313
                                        $i++;
3218
3314
                                }
3219
3315
                                return $new_array;
3220
3316
                        } else {
3221
 
                                return $this->col_info[$col_offset]->{$info_type};
 
3317
                                return $this->col_info[ $col_offset ]->{$info_type};
3222
3318
                        }
3223
3319
                }
3224
3320
        }
3258
3354
         * @return false|void
3259
3355
         */
3260
3356
        public function bail( $message, $error_code = '500' ) {
3261
 
                if ( !$this->show_errors ) {
 
3357
                if ( $this->show_errors ) {
 
3358
                        $error = '';
 
3359
 
 
3360
                        if ( $this->use_mysqli ) {
 
3361
                                if ( $this->dbh instanceof mysqli ) {
 
3362
                                        $error = mysqli_error( $this->dbh );
 
3363
                                } elseif ( mysqli_connect_errno() ) {
 
3364
                                        $error = mysqli_connect_error();
 
3365
                                }
 
3366
                        } else {
 
3367
                                if ( is_resource( $this->dbh ) ) {
 
3368
                                        $error = mysql_error( $this->dbh );
 
3369
                                } else {
 
3370
                                        $error = mysql_error();
 
3371
                                }
 
3372
                        }
 
3373
 
 
3374
                        if ( $error ) {
 
3375
                                $message = '<p><code>' . $error . "</code></p>\n" . $message;
 
3376
                        }
 
3377
 
 
3378
                        wp_die( $message );
 
3379
                } else {
3262
3380
                        if ( class_exists( 'WP_Error', false ) ) {
3263
 
                                $this->error = new WP_Error($error_code, $message);
 
3381
                                $this->error = new WP_Error( $error_code, $message );
3264
3382
                        } else {
3265
3383
                                $this->error = $message;
3266
3384
                        }
 
3385
 
3267
3386
                        return false;
3268
3387
                }
3269
 
                wp_die($message);
3270
3388
        }
3271
3389
 
3272
3390
 
3290
3408
                }
3291
3409
 
3292
3410
                if ( $closed ) {
3293
 
                        $this->dbh = null;
3294
 
                        $this->ready = false;
 
3411
                        $this->dbh           = null;
 
3412
                        $this->ready         = false;
3295
3413
                        $this->has_connected = false;
3296
3414
                }
3297
3415
 
3311
3429
        public function check_database_version() {
3312
3430
                global $wp_version, $required_mysql_version;
3313
3431
                // Make sure the server has the required MySQL version
3314
 
                if ( version_compare($this->db_version(), $required_mysql_version, '<') ) {
 
3432
                if ( version_compare( $this->db_version(), $required_mysql_version, '<' ) ) {
3315
3433
                        /* translators: 1: WordPress version number, 2: Minimum required MySQL version number */
3316
 
                        return new WP_Error('database_version', sprintf( __( '<strong>ERROR</strong>: WordPress %1$s requires MySQL %2$s or higher' ), $wp_version, $required_mysql_version ));
 
3434
                        return new WP_Error( 'database_version', sprintf( __( '<strong>ERROR</strong>: WordPress %1$s requires MySQL %2$s or higher' ), $wp_version, $required_mysql_version ) );
3317
3435
                }
3318
3436
        }
3319
3437
 
3344
3462
        public function get_charset_collate() {
3345
3463
                $charset_collate = '';
3346
3464
 
3347
 
                if ( ! empty( $this->charset ) )
 
3465
                if ( ! empty( $this->charset ) ) {
3348
3466
                        $charset_collate = "DEFAULT CHARACTER SET $this->charset";
3349
 
                if ( ! empty( $this->collate ) )
 
3467
                }
 
3468
                if ( ! empty( $this->collate ) ) {
3350
3469
                        $charset_collate .= " COLLATE $this->collate";
 
3470
                }
3351
3471
 
3352
3472
                return $charset_collate;
3353
3473
        }
3370
3490
                $version = $this->db_version();
3371
3491
 
3372
3492
                switch ( strtolower( $db_cap ) ) {
3373
 
                        case 'collation' :    // @since 2.5.0
3374
 
                        case 'group_concat' : // @since 2.7.0
3375
 
                        case 'subqueries' :   // @since 2.7.0
 
3493
                        case 'collation':    // @since 2.5.0
 
3494
                        case 'group_concat': // @since 2.7.0
 
3495
                        case 'subqueries':   // @since 2.7.0
3376
3496
                                return version_compare( $version, '4.1', '>=' );
3377
 
                        case 'set_charset' :
 
3497
                        case 'set_charset':
3378
3498
                                return version_compare( $version, '5.0.7', '>=' );
3379
 
                        case 'utf8mb4' :      // @since 4.1.0
 
3499
                        case 'utf8mb4':      // @since 4.1.0
3380
3500
                                if ( version_compare( $version, '5.5.3', '<' ) ) {
3381
3501
                                        return false;
3382
3502
                                }
3396
3516
                                } else {
3397
3517
                                        return version_compare( $client_version, '5.5.3', '>=' );
3398
3518
                                }
3399
 
                        case 'utf8mb4_520' : // @since 4.6.0
 
3519
                        case 'utf8mb4_520': // @since 4.6.0
3400
3520
                                return version_compare( $version, '5.6', '>=' );
3401
3521
                }
3402
3522
 
3411
3531
         *
3412
3532
         * @since 2.5.0
3413
3533
         *
3414
 
         * @return string|array The name of the calling function
 
3534
         * @return string Comma separated list of the calling functions.
3415
3535
         */
3416
3536
        public function get_caller() {
3417
3537
                return wp_debug_backtrace_summary( __CLASS__ );