[ Index ]

PHP Cross Reference of WordPress Trunk (Updated Daily)

Search

title

Body

[close]

/wp-admin/includes/ -> upgrade.php (source)

   1  <?php
   2  /**
   3   * WordPress Upgrade API
   4   *
   5   * Most of the functions are pluggable and can be overwritten.
   6   *
   7   * @package WordPress
   8   * @subpackage Administration
   9   */
  10  
  11  /** Include user installation customization script. */
  12  if ( file_exists( WP_CONTENT_DIR . '/install.php' ) ) {
  13      require WP_CONTENT_DIR . '/install.php';
  14  }
  15  
  16  /** WordPress Administration API */
  17  require_once  ABSPATH . 'wp-admin/includes/admin.php';
  18  
  19  /** WordPress Schema API */
  20  require_once  ABSPATH . 'wp-admin/includes/schema.php';
  21  
  22  if ( ! function_exists( 'wp_install' ) ) :
  23      /**
  24       * Installs the site.
  25       *
  26       * Runs the required functions to set up and populate the database,
  27       * including primary admin user and initial options.
  28       *
  29       * @since 2.1.0
  30       *
  31       * @param string $blog_title    Site title.
  32       * @param string $user_name     User's username.
  33       * @param string $user_email    User's email.
  34       * @param bool   $is_public     Whether the site is public.
  35       * @param string $deprecated    Optional. Not used.
  36       * @param string $user_password Optional. User's chosen password. Default empty (random password).
  37       * @param string $language      Optional. Language chosen. Default empty.
  38       * @return array {
  39       *     Data for the newly installed site.
  40       *
  41       *     @type string $url              The URL of the site.
  42       *     @type int    $user_id          The ID of the site owner.
  43       *     @type string $password         The password of the site owner, if their user account didn't already exist.
  44       *     @type string $password_message The explanatory message regarding the password.
  45       * }
  46       */
  47  	function wp_install( $blog_title, $user_name, $user_email, $is_public, $deprecated = '', $user_password = '', $language = '' ) {
  48          if ( ! empty( $deprecated ) ) {
  49              _deprecated_argument( __FUNCTION__, '2.6.0' );
  50          }
  51  
  52          wp_check_mysql_version();
  53          wp_cache_flush();
  54          make_db_current_silent();
  55          populate_options();
  56          populate_roles();
  57  
  58          update_option( 'blogname', $blog_title );
  59          update_option( 'admin_email', $user_email );
  60          update_option( 'blog_public', $is_public );
  61  
  62          // Freshness of site - in the future, this could get more specific about actions taken, perhaps.
  63          update_option( 'fresh_site', 1 );
  64  
  65          if ( $language ) {
  66              update_option( 'WPLANG', $language );
  67          }
  68  
  69          $guessurl = wp_guess_url();
  70  
  71          update_option( 'siteurl', $guessurl );
  72  
  73          // If not a public site, don't ping.
  74          if ( ! $is_public ) {
  75              update_option( 'default_pingback_flag', 0 );
  76          }
  77  
  78          /*
  79           * Create default user. If the user already exists, the user tables are
  80           * being shared among sites. Just set the role in that case.
  81           */
  82          $user_id        = username_exists( $user_name );
  83          $user_password  = trim( $user_password );
  84          $email_password = false;
  85          $user_created   = false;
  86  
  87          if ( ! $user_id && empty( $user_password ) ) {
  88              $user_password = wp_generate_password( 12, false );
  89              $message       = __( '<strong><em>Note that password</em></strong> carefully! It is a <em>random</em> password that was generated just for you.' );
  90              $user_id       = wp_create_user( $user_name, $user_password, $user_email );
  91              update_user_meta( $user_id, 'default_password_nag', true );
  92              $email_password = true;
  93              $user_created   = true;
  94          } elseif ( ! $user_id ) {
  95              // Password has been provided.
  96              $message      = '<em>' . __( 'Your chosen password.' ) . '</em>';
  97              $user_id      = wp_create_user( $user_name, $user_password, $user_email );
  98              $user_created = true;
  99          } else {
 100              $message = __( 'User already exists. Password inherited.' );
 101          }
 102  
 103          $user = new WP_User( $user_id );
 104          $user->set_role( 'administrator' );
 105  
 106          if ( $user_created ) {
 107              $user->user_url = $guessurl;
 108              wp_update_user( $user );
 109          }
 110  
 111          wp_install_defaults( $user_id );
 112  
 113          wp_install_maybe_enable_pretty_permalinks();
 114  
 115          flush_rewrite_rules();
 116  
 117          wp_new_blog_notification( $blog_title, $guessurl, $user_id, ( $email_password ? $user_password : __( 'The password you chose during installation.' ) ) );
 118  
 119          wp_cache_flush();
 120  
 121          /**
 122           * Fires after a site is fully installed.
 123           *
 124           * @since 3.9.0
 125           *
 126           * @param WP_User $user The site owner.
 127           */
 128          do_action( 'wp_install', $user );
 129  
 130          return array(
 131              'url'              => $guessurl,
 132              'user_id'          => $user_id,
 133              'password'         => $user_password,
 134              'password_message' => $message,
 135          );
 136      }
 137  endif;
 138  
 139  if ( ! function_exists( 'wp_install_defaults' ) ) :
 140      /**
 141       * Creates the initial content for a newly-installed site.
 142       *
 143       * Adds the default "Uncategorized" category, the first post (with comment),
 144       * first page, and default widgets for default theme for the current version.
 145       *
 146       * @since 2.1.0
 147       *
 148       * @global wpdb       $wpdb         WordPress database abstraction object.
 149       * @global WP_Rewrite $wp_rewrite   WordPress rewrite component.
 150       * @global string     $table_prefix The database table prefix.
 151       *
 152       * @param int $user_id User ID.
 153       */
 154  	function wp_install_defaults( $user_id ) {
 155          global $wpdb, $wp_rewrite, $table_prefix;
 156  
 157          // Default category.
 158          $cat_name = __( 'Uncategorized' );
 159          /* translators: Default category slug. */
 160          $cat_slug = sanitize_title( _x( 'Uncategorized', 'Default category slug' ) );
 161  
 162          $cat_id = 1;
 163  
 164          $wpdb->insert(
 165              $wpdb->terms,
 166              array(
 167                  'term_id'    => $cat_id,
 168                  'name'       => $cat_name,
 169                  'slug'       => $cat_slug,
 170                  'term_group' => 0,
 171              )
 172          );
 173          $wpdb->insert(
 174              $wpdb->term_taxonomy,
 175              array(
 176                  'term_id'     => $cat_id,
 177                  'taxonomy'    => 'category',
 178                  'description' => '',
 179                  'parent'      => 0,
 180                  'count'       => 1,
 181              )
 182          );
 183          $cat_tt_id = $wpdb->insert_id;
 184  
 185          // First post.
 186          $now             = current_time( 'mysql' );
 187          $now_gmt         = current_time( 'mysql', 1 );
 188          $first_post_guid = get_option( 'home' ) . '/?p=1';
 189  
 190          if ( is_multisite() ) {
 191              $first_post = get_site_option( 'first_post' );
 192  
 193              if ( ! $first_post ) {
 194                  $first_post = "<!-- wp:paragraph -->\n<p>" .
 195                  /* translators: First post content. %s: Site link. */
 196                  __( 'Welcome to %s. This is your first post. Edit or delete it, then start writing!' ) .
 197                  "</p>\n<!-- /wp:paragraph -->";
 198              }
 199  
 200              $first_post = sprintf(
 201                  $first_post,
 202                  sprintf( '<a href="%s">%s</a>', esc_url( network_home_url() ), get_network()->site_name )
 203              );
 204  
 205              // Back-compat for pre-4.4.
 206              $first_post = str_replace( 'SITE_URL', esc_url( network_home_url() ), $first_post );
 207              $first_post = str_replace( 'SITE_NAME', get_network()->site_name, $first_post );
 208          } else {
 209              $first_post = "<!-- wp:paragraph -->\n<p>" .
 210              /* translators: First post content. %s: Site link. */
 211              __( 'Welcome to WordPress. This is your first post. Edit or delete it, then start writing!' ) .
 212              "</p>\n<!-- /wp:paragraph -->";
 213          }
 214  
 215          $wpdb->insert(
 216              $wpdb->posts,
 217              array(
 218                  'post_author'           => $user_id,
 219                  'post_date'             => $now,
 220                  'post_date_gmt'         => $now_gmt,
 221                  'post_content'          => $first_post,
 222                  'post_excerpt'          => '',
 223                  'post_title'            => __( 'Hello world!' ),
 224                  /* translators: Default post slug. */
 225                  'post_name'             => sanitize_title( _x( 'hello-world', 'Default post slug' ) ),
 226                  'post_modified'         => $now,
 227                  'post_modified_gmt'     => $now_gmt,
 228                  'guid'                  => $first_post_guid,
 229                  'comment_count'         => 1,
 230                  'to_ping'               => '',
 231                  'pinged'                => '',
 232                  'post_content_filtered' => '',
 233              )
 234          );
 235  
 236          if ( is_multisite() ) {
 237              update_posts_count();
 238          }
 239  
 240          $wpdb->insert(
 241              $wpdb->term_relationships,
 242              array(
 243                  'term_taxonomy_id' => $cat_tt_id,
 244                  'object_id'        => 1,
 245              )
 246          );
 247  
 248          // Default comment.
 249          if ( is_multisite() ) {
 250              $first_comment_author = get_site_option( 'first_comment_author' );
 251              $first_comment_email  = get_site_option( 'first_comment_email' );
 252              $first_comment_url    = get_site_option( 'first_comment_url', network_home_url() );
 253              $first_comment        = get_site_option( 'first_comment' );
 254          }
 255  
 256          $first_comment_author = ! empty( $first_comment_author ) ? $first_comment_author : __( 'A WordPress Commenter' );
 257          $first_comment_email  = ! empty( $first_comment_email ) ? $first_comment_email : 'wapuu@wordpress.example';
 258          $first_comment_url    = ! empty( $first_comment_url ) ? $first_comment_url : esc_url( __( 'https://wordpress.org/' ) );
 259          $first_comment        = ! empty( $first_comment ) ? $first_comment : sprintf(
 260              /* translators: %s: Gravatar URL. */
 261              __(
 262                  'Hi, this is a comment.
 263  To get started with moderating, editing, and deleting comments, please visit the Comments screen in the dashboard.
 264  Commenter avatars come from <a href="%s">Gravatar</a>.'
 265              ),
 266              esc_url( __( 'https://en.gravatar.com/' ) )
 267          );
 268          $wpdb->insert(
 269              $wpdb->comments,
 270              array(
 271                  'comment_post_ID'      => 1,
 272                  'comment_author'       => $first_comment_author,
 273                  'comment_author_email' => $first_comment_email,
 274                  'comment_author_url'   => $first_comment_url,
 275                  'comment_date'         => $now,
 276                  'comment_date_gmt'     => $now_gmt,
 277                  'comment_content'      => $first_comment,
 278                  'comment_type'         => 'comment',
 279              )
 280          );
 281  
 282          // First page.
 283          if ( is_multisite() ) {
 284              $first_page = get_site_option( 'first_page' );
 285          }
 286  
 287          if ( empty( $first_page ) ) {
 288              $first_page = "<!-- wp:paragraph -->\n<p>";
 289              /* translators: First page content. */
 290              $first_page .= __( "This is an example page. It's different from a blog post because it will stay in one place and will show up in your site navigation (in most themes). Most people start with an About page that introduces them to potential site visitors. It might say something like this:" );
 291              $first_page .= "</p>\n<!-- /wp:paragraph -->\n\n";
 292  
 293              $first_page .= "<!-- wp:quote -->\n<blockquote class=\"wp-block-quote\"><p>";
 294              /* translators: First page content. */
 295              $first_page .= __( "Hi there! I'm a bike messenger by day, aspiring actor by night, and this is my website. I live in Los Angeles, have a great dog named Jack, and I like pi&#241;a coladas. (And gettin' caught in the rain.)" );
 296              $first_page .= "</p></blockquote>\n<!-- /wp:quote -->\n\n";
 297  
 298              $first_page .= "<!-- wp:paragraph -->\n<p>";
 299              /* translators: First page content. */
 300              $first_page .= __( '...or something like this:' );
 301              $first_page .= "</p>\n<!-- /wp:paragraph -->\n\n";
 302  
 303              $first_page .= "<!-- wp:quote -->\n<blockquote class=\"wp-block-quote\"><p>";
 304              /* translators: First page content. */
 305              $first_page .= __( 'The XYZ Doohickey Company was founded in 1971, and has been providing quality doohickeys to the public ever since. Located in Gotham City, XYZ employs over 2,000 people and does all kinds of awesome things for the Gotham community.' );
 306              $first_page .= "</p></blockquote>\n<!-- /wp:quote -->\n\n";
 307  
 308              $first_page .= "<!-- wp:paragraph -->\n<p>";
 309              $first_page .= sprintf(
 310                  /* translators: First page content. %s: Site admin URL. */
 311                  __( 'As a new WordPress user, you should go to <a href="%s">your dashboard</a> to delete this page and create new pages for your content. Have fun!' ),
 312                  admin_url()
 313              );
 314              $first_page .= "</p>\n<!-- /wp:paragraph -->";
 315          }
 316  
 317          $first_post_guid = get_option( 'home' ) . '/?page_id=2';
 318          $wpdb->insert(
 319              $wpdb->posts,
 320              array(
 321                  'post_author'           => $user_id,
 322                  'post_date'             => $now,
 323                  'post_date_gmt'         => $now_gmt,
 324                  'post_content'          => $first_page,
 325                  'post_excerpt'          => '',
 326                  'comment_status'        => 'closed',
 327                  'post_title'            => __( 'Sample Page' ),
 328                  /* translators: Default page slug. */
 329                  'post_name'             => __( 'sample-page' ),
 330                  'post_modified'         => $now,
 331                  'post_modified_gmt'     => $now_gmt,
 332                  'guid'                  => $first_post_guid,
 333                  'post_type'             => 'page',
 334                  'to_ping'               => '',
 335                  'pinged'                => '',
 336                  'post_content_filtered' => '',
 337              )
 338          );
 339          $wpdb->insert(
 340              $wpdb->postmeta,
 341              array(
 342                  'post_id'    => 2,
 343                  'meta_key'   => '_wp_page_template',
 344                  'meta_value' => 'default',
 345              )
 346          );
 347  
 348          // Privacy Policy page.
 349          if ( is_multisite() ) {
 350              // Disable by default unless the suggested content is provided.
 351              $privacy_policy_content = get_site_option( 'default_privacy_policy_content' );
 352          } else {
 353              if ( ! class_exists( 'WP_Privacy_Policy_Content' ) ) {
 354                  require_once  ABSPATH . 'wp-admin/includes/class-wp-privacy-policy-content.php';
 355              }
 356  
 357              $privacy_policy_content = WP_Privacy_Policy_Content::get_default_content();
 358          }
 359  
 360          if ( ! empty( $privacy_policy_content ) ) {
 361              $privacy_policy_guid = get_option( 'home' ) . '/?page_id=3';
 362  
 363              $wpdb->insert(
 364                  $wpdb->posts,
 365                  array(
 366                      'post_author'           => $user_id,
 367                      'post_date'             => $now,
 368                      'post_date_gmt'         => $now_gmt,
 369                      'post_content'          => $privacy_policy_content,
 370                      'post_excerpt'          => '',
 371                      'comment_status'        => 'closed',
 372                      'post_title'            => __( 'Privacy Policy' ),
 373                      /* translators: Privacy Policy page slug. */
 374                      'post_name'             => __( 'privacy-policy' ),
 375                      'post_modified'         => $now,
 376                      'post_modified_gmt'     => $now_gmt,
 377                      'guid'                  => $privacy_policy_guid,
 378                      'post_type'             => 'page',
 379                      'post_status'           => 'draft',
 380                      'to_ping'               => '',
 381                      'pinged'                => '',
 382                      'post_content_filtered' => '',
 383                  )
 384              );
 385              $wpdb->insert(
 386                  $wpdb->postmeta,
 387                  array(
 388                      'post_id'    => 3,
 389                      'meta_key'   => '_wp_page_template',
 390                      'meta_value' => 'default',
 391                  )
 392              );
 393              update_option( 'wp_page_for_privacy_policy', 3 );
 394          }
 395  
 396          // Set up default widgets for default theme.
 397          update_option(
 398              'widget_block',
 399              array(
 400                  2              => array( 'content' => '<!-- wp:search /-->' ),
 401                  3              => array( 'content' => '<!-- wp:group --><div class="wp-block-group"><!-- wp:heading --><h2>' . __( 'Recent Posts' ) . '</h2><!-- /wp:heading --><!-- wp:latest-posts /--></div><!-- /wp:group -->' ),
 402                  4              => array( 'content' => '<!-- wp:group --><div class="wp-block-group"><!-- wp:heading --><h2>' . __( 'Recent Comments' ) . '</h2><!-- /wp:heading --><!-- wp:latest-comments {"displayAvatar":false,"displayDate":false,"displayExcerpt":false} /--></div><!-- /wp:group -->' ),
 403                  5              => array( 'content' => '<!-- wp:group --><div class="wp-block-group"><!-- wp:heading --><h2>' . __( 'Archives' ) . '</h2><!-- /wp:heading --><!-- wp:archives /--></div><!-- /wp:group -->' ),
 404                  6              => array( 'content' => '<!-- wp:group --><div class="wp-block-group"><!-- wp:heading --><h2>' . __( 'Categories' ) . '</h2><!-- /wp:heading --><!-- wp:categories /--></div><!-- /wp:group -->' ),
 405                  '_multiwidget' => 1,
 406              )
 407          );
 408          update_option(
 409              'sidebars_widgets',
 410              array(
 411                  'wp_inactive_widgets' => array(),
 412                  'sidebar-1'           => array(
 413                      0 => 'block-2',
 414                      1 => 'block-3',
 415                      2 => 'block-4',
 416                  ),
 417                  'sidebar-2'           => array(
 418                      0 => 'block-5',
 419                      1 => 'block-6',
 420                  ),
 421                  'array_version'       => 3,
 422              )
 423          );
 424  
 425          if ( ! is_multisite() ) {
 426              update_user_meta( $user_id, 'show_welcome_panel', 1 );
 427          } elseif ( ! is_super_admin( $user_id ) && ! metadata_exists( 'user', $user_id, 'show_welcome_panel' ) ) {
 428              update_user_meta( $user_id, 'show_welcome_panel', 2 );
 429          }
 430  
 431          if ( is_multisite() ) {
 432              // Flush rules to pick up the new page.
 433              $wp_rewrite->init();
 434              $wp_rewrite->flush_rules();
 435  
 436              $user = new WP_User( $user_id );
 437              $wpdb->update( $wpdb->options, array( 'option_value' => $user->user_email ), array( 'option_name' => 'admin_email' ) );
 438  
 439              // Remove all perms except for the login user.
 440              $wpdb->query( $wpdb->prepare( "DELETE FROM $wpdb->usermeta WHERE user_id != %d AND meta_key = %s", $user_id, $table_prefix . 'user_level' ) );
 441              $wpdb->query( $wpdb->prepare( "DELETE FROM $wpdb->usermeta WHERE user_id != %d AND meta_key = %s", $user_id, $table_prefix . 'capabilities' ) );
 442  
 443              /*
 444               * Delete any caps that snuck into the previously active blog. (Hardcoded to blog 1 for now.)
 445               * TODO: Get previous_blog_id.
 446               */
 447              if ( ! is_super_admin( $user_id ) && 1 != $user_id ) {
 448                  $wpdb->delete(
 449                      $wpdb->usermeta,
 450                      array(
 451                          'user_id'  => $user_id,
 452                          'meta_key' => $wpdb->base_prefix . '1_capabilities',
 453                      )
 454                  );
 455              }
 456          }
 457      }
 458  endif;
 459  
 460  /**
 461   * Maybe enable pretty permalinks on installation.
 462   *
 463   * If after enabling pretty permalinks don't work, fallback to query-string permalinks.
 464   *
 465   * @since 4.2.0
 466   *
 467   * @global WP_Rewrite $wp_rewrite WordPress rewrite component.
 468   *
 469   * @return bool Whether pretty permalinks are enabled. False otherwise.
 470   */
 471  function wp_install_maybe_enable_pretty_permalinks() {
 472      global $wp_rewrite;
 473  
 474      // Bail if a permalink structure is already enabled.
 475      if ( get_option( 'permalink_structure' ) ) {
 476          return true;
 477      }
 478  
 479      /*
 480       * The Permalink structures to attempt.
 481       *
 482       * The first is designed for mod_rewrite or nginx rewriting.
 483       *
 484       * The second is PATHINFO-based permalinks for web server configurations
 485       * without a true rewrite module enabled.
 486       */
 487      $permalink_structures = array(
 488          '/%year%/%monthnum%/%day%/%postname%/',
 489          '/index.php/%year%/%monthnum%/%day%/%postname%/',
 490      );
 491  
 492      foreach ( (array) $permalink_structures as $permalink_structure ) {
 493          $wp_rewrite->set_permalink_structure( $permalink_structure );
 494  
 495          /*
 496           * Flush rules with the hard option to force refresh of the web-server's
 497           * rewrite config file (e.g. .htaccess or web.config).
 498           */
 499          $wp_rewrite->flush_rules( true );
 500  
 501          $test_url = '';
 502  
 503          // Test against a real WordPress post.
 504          $first_post = get_page_by_path( sanitize_title( _x( 'hello-world', 'Default post slug' ) ), OBJECT, 'post' );
 505          if ( $first_post ) {
 506              $test_url = get_permalink( $first_post->ID );
 507          }
 508  
 509          /*
 510           * Send a request to the site, and check whether
 511           * the 'X-Pingback' header is returned as expected.
 512           *
 513           * Uses wp_remote_get() instead of wp_remote_head() because web servers
 514           * can block head requests.
 515           */
 516          $response          = wp_remote_get( $test_url, array( 'timeout' => 5 ) );
 517          $x_pingback_header = wp_remote_retrieve_header( $response, 'X-Pingback' );
 518          $pretty_permalinks = $x_pingback_header && get_bloginfo( 'pingback_url' ) === $x_pingback_header;
 519  
 520          if ( $pretty_permalinks ) {
 521              return true;
 522          }
 523      }
 524  
 525      /*
 526       * If it makes it this far, pretty permalinks failed.
 527       * Fallback to query-string permalinks.
 528       */
 529      $wp_rewrite->set_permalink_structure( '' );
 530      $wp_rewrite->flush_rules( true );
 531  
 532      return false;
 533  }
 534  
 535  if ( ! function_exists( 'wp_new_blog_notification' ) ) :
 536      /**
 537       * Notifies the site admin that the installation of WordPress is complete.
 538       *
 539       * Sends an email to the new administrator that the installation is complete
 540       * and provides them with a record of their login credentials.
 541       *
 542       * @since 2.1.0
 543       *
 544       * @param string $blog_title Site title.
 545       * @param string $blog_url   Site URL.
 546       * @param int    $user_id    Administrator's user ID.
 547       * @param string $password   Administrator's password. Note that a placeholder message is
 548       *                           usually passed instead of the actual password.
 549       */
 550  	function wp_new_blog_notification( $blog_title, $blog_url, $user_id, $password ) {
 551          $user      = new WP_User( $user_id );
 552          $email     = $user->user_email;
 553          $name      = $user->user_login;
 554          $login_url = wp_login_url();
 555  
 556          $message = sprintf(
 557              /* translators: New site notification email. 1: New site URL, 2: User login, 3: User password or password reset link, 4: Login URL. */
 558              __(
 559                  'Your new WordPress site has been successfully set up at:
 560  
 561  %1$s
 562  
 563  You can log in to the administrator account with the following information:
 564  
 565  Username: %2$s
 566  Password: %3$s
 567  Log in here: %4$s
 568  
 569  We hope you enjoy your new site. Thanks!
 570  
 571  --The WordPress Team
 572  https://wordpress.org/
 573  '
 574              ),
 575              $blog_url,
 576              $name,
 577              $password,
 578              $login_url
 579          );
 580  
 581          $installed_email = array(
 582              'to'      => $email,
 583              'subject' => __( 'New WordPress Site' ),
 584              'message' => $message,
 585              'headers' => '',
 586          );
 587  
 588          /**
 589           * Filters the contents of the email sent to the site administrator when WordPress is installed.
 590           *
 591           * @since 5.6.0
 592           *
 593           * @param array $installed_email {
 594           *     Used to build wp_mail().
 595           *
 596           *     @type string $to      The email address of the recipient.
 597           *     @type string $subject The subject of the email.
 598           *     @type string $message The content of the email.
 599           *     @type string $headers Headers.
 600           * }
 601           * @param WP_User $user          The site administrator user object.
 602           * @param string  $blog_title    The site title.
 603           * @param string  $blog_url      The site URL.
 604           * @param string  $password      The site administrator's password. Note that a placeholder message
 605           *                               is usually passed instead of the user's actual password.
 606           */
 607          $installed_email = apply_filters( 'wp_installed_email', $installed_email, $user, $blog_title, $blog_url, $password );
 608  
 609          wp_mail(
 610              $installed_email['to'],
 611              $installed_email['subject'],
 612              $installed_email['message'],
 613              $installed_email['headers']
 614          );
 615      }
 616  endif;
 617  
 618  if ( ! function_exists( 'wp_upgrade' ) ) :
 619      /**
 620       * Runs WordPress Upgrade functions.
 621       *
 622       * Upgrades the database if needed during a site update.
 623       *
 624       * @since 2.1.0
 625       *
 626       * @global int  $wp_current_db_version The old (current) database version.
 627       * @global int  $wp_db_version         The new database version.
 628       */
 629  	function wp_upgrade() {
 630          global $wp_current_db_version, $wp_db_version;
 631  
 632          $wp_current_db_version = __get_option( 'db_version' );
 633  
 634          // We are up to date. Nothing to do.
 635          if ( $wp_db_version == $wp_current_db_version ) {
 636              return;
 637          }
 638  
 639          if ( ! is_blog_installed() ) {
 640              return;
 641          }
 642  
 643          wp_check_mysql_version();
 644          wp_cache_flush();
 645          pre_schema_upgrade();
 646          make_db_current_silent();
 647          upgrade_all();
 648          if ( is_multisite() && is_main_site() ) {
 649              upgrade_network();
 650          }
 651          wp_cache_flush();
 652  
 653          if ( is_multisite() ) {
 654              update_site_meta( get_current_blog_id(), 'db_version', $wp_db_version );
 655              update_site_meta( get_current_blog_id(), 'db_last_updated', microtime() );
 656          }
 657  
 658          delete_transient( 'wp_core_block_css_files' );
 659  
 660          /**
 661           * Fires after a site is fully upgraded.
 662           *
 663           * @since 3.9.0
 664           *
 665           * @param int $wp_db_version         The new $wp_db_version.
 666           * @param int $wp_current_db_version The old (current) $wp_db_version.
 667           */
 668          do_action( 'wp_upgrade', $wp_db_version, $wp_current_db_version );
 669      }
 670  endif;
 671  
 672  /**
 673   * Functions to be called in installation and upgrade scripts.
 674   *
 675   * Contains conditional checks to determine which upgrade scripts to run,
 676   * based on database version and WP version being updated-to.
 677   *
 678   * @ignore
 679   * @since 1.0.1
 680   *
 681   * @global int $wp_current_db_version The old (current) database version.
 682   * @global int $wp_db_version         The new database version.
 683   */
 684  function upgrade_all() {
 685      global $wp_current_db_version, $wp_db_version;
 686  
 687      $wp_current_db_version = __get_option( 'db_version' );
 688  
 689      // We are up to date. Nothing to do.
 690      if ( $wp_db_version == $wp_current_db_version ) {
 691          return;
 692      }
 693  
 694      // If the version is not set in the DB, try to guess the version.
 695      if ( empty( $wp_current_db_version ) ) {
 696          $wp_current_db_version = 0;
 697  
 698          // If the template option exists, we have 1.5.
 699          $template = __get_option( 'template' );
 700          if ( ! empty( $template ) ) {
 701              $wp_current_db_version = 2541;
 702          }
 703      }
 704  
 705      if ( $wp_current_db_version < 6039 ) {
 706          upgrade_230_options_table();
 707      }
 708  
 709      populate_options();
 710  
 711      if ( $wp_current_db_version < 2541 ) {
 712          upgrade_100();
 713          upgrade_101();
 714          upgrade_110();
 715          upgrade_130();
 716      }
 717  
 718      if ( $wp_current_db_version < 3308 ) {
 719          upgrade_160();
 720      }
 721  
 722      if ( $wp_current_db_version < 4772 ) {
 723          upgrade_210();
 724      }
 725  
 726      if ( $wp_current_db_version < 4351 ) {
 727          upgrade_old_slugs();
 728      }
 729  
 730      if ( $wp_current_db_version < 5539 ) {
 731          upgrade_230();
 732      }
 733  
 734      if ( $wp_current_db_version < 6124 ) {
 735          upgrade_230_old_tables();
 736      }
 737  
 738      if ( $wp_current_db_version < 7499 ) {
 739          upgrade_250();
 740      }
 741  
 742      if ( $wp_current_db_version < 7935 ) {
 743          upgrade_252();
 744      }
 745  
 746      if ( $wp_current_db_version < 8201 ) {
 747          upgrade_260();
 748      }
 749  
 750      if ( $wp_current_db_version < 8989 ) {
 751          upgrade_270();
 752      }
 753  
 754      if ( $wp_current_db_version < 10360 ) {
 755          upgrade_280();
 756      }
 757  
 758      if ( $wp_current_db_version < 11958 ) {
 759          upgrade_290();
 760      }
 761  
 762      if ( $wp_current_db_version < 15260 ) {
 763          upgrade_300();
 764      }
 765  
 766      if ( $wp_current_db_version < 19389 ) {
 767          upgrade_330();
 768      }
 769  
 770      if ( $wp_current_db_version < 20080 ) {
 771          upgrade_340();
 772      }
 773  
 774      if ( $wp_current_db_version < 22422 ) {
 775          upgrade_350();
 776      }
 777  
 778      if ( $wp_current_db_version < 25824 ) {
 779          upgrade_370();
 780      }
 781  
 782      if ( $wp_current_db_version < 26148 ) {
 783          upgrade_372();
 784      }
 785  
 786      if ( $wp_current_db_version < 26691 ) {
 787          upgrade_380();
 788      }
 789  
 790      if ( $wp_current_db_version < 29630 ) {
 791          upgrade_400();
 792      }
 793  
 794      if ( $wp_current_db_version < 33055 ) {
 795          upgrade_430();
 796      }
 797  
 798      if ( $wp_current_db_version < 33056 ) {
 799          upgrade_431();
 800      }
 801  
 802      if ( $wp_current_db_version < 35700 ) {
 803          upgrade_440();
 804      }
 805  
 806      if ( $wp_current_db_version < 36686 ) {
 807          upgrade_450();
 808      }
 809  
 810      if ( $wp_current_db_version < 37965 ) {
 811          upgrade_460();
 812      }
 813  
 814      if ( $wp_current_db_version < 44719 ) {
 815          upgrade_510();
 816      }
 817  
 818      if ( $wp_current_db_version < 45744 ) {
 819          upgrade_530();
 820      }
 821  
 822      if ( $wp_current_db_version < 48575 ) {
 823          upgrade_550();
 824      }
 825  
 826      if ( $wp_current_db_version < 49752 ) {
 827          upgrade_560();
 828      }
 829  
 830      if ( $wp_current_db_version < 51917 ) {
 831          upgrade_590();
 832      }
 833  
 834      if ( $wp_current_db_version < 53011 ) {
 835          upgrade_600();
 836      }
 837  
 838      if ( $wp_current_db_version < 55853 ) {
 839          upgrade_630();
 840      }
 841  
 842      if ( $wp_current_db_version < 56657 ) {
 843          upgrade_640();
 844      }
 845  
 846      if ( $wp_current_db_version < 57155 ) {
 847          upgrade_650();
 848      }
 849  
 850      maybe_disable_link_manager();
 851  
 852      maybe_disable_automattic_widgets();
 853  
 854      update_option( 'db_version', $wp_db_version );
 855      update_option( 'db_upgraded', true );
 856  }
 857  
 858  /**
 859   * Execute changes made in WordPress 1.0.
 860   *
 861   * @ignore
 862   * @since 1.0.0
 863   *
 864   * @global wpdb $wpdb WordPress database abstraction object.
 865   */
 866  function upgrade_100() {
 867      global $wpdb;
 868  
 869      // Get the title and ID of every post, post_name to check if it already has a value.
 870      $posts = $wpdb->get_results( "SELECT ID, post_title, post_name FROM $wpdb->posts WHERE post_name = ''" );
 871      if ( $posts ) {
 872          foreach ( $posts as $post ) {
 873              if ( '' === $post->post_name ) {
 874                  $newtitle = sanitize_title( $post->post_title );
 875                  $wpdb->query( $wpdb->prepare( "UPDATE $wpdb->posts SET post_name = %s WHERE ID = %d", $newtitle, $post->ID ) );
 876              }
 877          }
 878      }
 879  
 880      $categories = $wpdb->get_results( "SELECT cat_ID, cat_name, category_nicename FROM $wpdb->categories" );
 881      foreach ( $categories as $category ) {
 882          if ( '' === $category->category_nicename ) {
 883              $newtitle = sanitize_title( $category->cat_name );
 884              $wpdb->update( $wpdb->categories, array( 'category_nicename' => $newtitle ), array( 'cat_ID' => $category->cat_ID ) );
 885          }
 886      }
 887  
 888      $sql = "UPDATE $wpdb->options
 889          SET option_value = REPLACE(option_value, 'wp-links/links-images/', 'wp-images/links/')
 890          WHERE option_name LIKE %s
 891          AND option_value LIKE %s";
 892      $wpdb->query( $wpdb->prepare( $sql, $wpdb->esc_like( 'links_rating_image' ) . '%', $wpdb->esc_like( 'wp-links/links-images/' ) . '%' ) );
 893  
 894      $done_ids = $wpdb->get_results( "SELECT DISTINCT post_id FROM $wpdb->post2cat" );
 895      if ( $done_ids ) :
 896          $done_posts = array();
 897          foreach ( $done_ids as $done_id ) :
 898              $done_posts[] = $done_id->post_id;
 899          endforeach;
 900          $catwhere = ' AND ID NOT IN (' . implode( ',', $done_posts ) . ')';
 901      else :
 902          $catwhere = '';
 903      endif;
 904  
 905      $allposts = $wpdb->get_results( "SELECT ID, post_category FROM $wpdb->posts WHERE post_category != '0' $catwhere" );
 906      if ( $allposts ) :
 907          foreach ( $allposts as $post ) {
 908              // Check to see if it's already been imported.
 909              $cat = $wpdb->get_row( $wpdb->prepare( "SELECT * FROM $wpdb->post2cat WHERE post_id = %d AND category_id = %d", $post->ID, $post->post_category ) );
 910              if ( ! $cat && 0 != $post->post_category ) { // If there's no result.
 911                  $wpdb->insert(
 912                      $wpdb->post2cat,
 913                      array(
 914                          'post_id'     => $post->ID,
 915                          'category_id' => $post->post_category,
 916                      )
 917                  );
 918              }
 919          }
 920      endif;
 921  }
 922  
 923  /**
 924   * Execute changes made in WordPress 1.0.1.
 925   *
 926   * @ignore
 927   * @since 1.0.1
 928   *
 929   * @global wpdb $wpdb WordPress database abstraction object.
 930   */
 931  function upgrade_101() {
 932      global $wpdb;
 933  
 934      // Clean up indices, add a few.
 935      add_clean_index( $wpdb->posts, 'post_name' );
 936      add_clean_index( $wpdb->posts, 'post_status' );
 937      add_clean_index( $wpdb->categories, 'category_nicename' );
 938      add_clean_index( $wpdb->comments, 'comment_approved' );
 939      add_clean_index( $wpdb->comments, 'comment_post_ID' );
 940      add_clean_index( $wpdb->links, 'link_category' );
 941      add_clean_index( $wpdb->links, 'link_visible' );
 942  }
 943  
 944  /**
 945   * Execute changes made in WordPress 1.2.
 946   *
 947   * @ignore
 948   * @since 1.2.0
 949   *
 950   * @global wpdb $wpdb WordPress database abstraction object.
 951   */
 952  function upgrade_110() {
 953      global $wpdb;
 954  
 955      // Set user_nicename.
 956      $users = $wpdb->get_results( "SELECT ID, user_nickname, user_nicename FROM $wpdb->users" );
 957      foreach ( $users as $user ) {
 958          if ( '' === $user->user_nicename ) {
 959              $newname = sanitize_title( $user->user_nickname );
 960              $wpdb->update( $wpdb->users, array( 'user_nicename' => $newname ), array( 'ID' => $user->ID ) );
 961          }
 962      }
 963  
 964      $users = $wpdb->get_results( "SELECT ID, user_pass from $wpdb->users" );
 965      foreach ( $users as $row ) {
 966          if ( ! preg_match( '/^[A-Fa-f0-9]{32}$/', $row->user_pass ) ) {
 967              $wpdb->update( $wpdb->users, array( 'user_pass' => md5( $row->user_pass ) ), array( 'ID' => $row->ID ) );
 968          }
 969      }
 970  
 971      // Get the GMT offset, we'll use that later on.
 972      $all_options = get_alloptions_110();
 973  
 974      $time_difference = $all_options->time_difference;
 975  
 976          $server_time = time() + gmdate( 'Z' );
 977      $weblogger_time  = $server_time + $time_difference * HOUR_IN_SECONDS;
 978      $gmt_time        = time();
 979  
 980      $diff_gmt_server       = ( $gmt_time - $server_time ) / HOUR_IN_SECONDS;
 981      $diff_weblogger_server = ( $weblogger_time - $server_time ) / HOUR_IN_SECONDS;
 982      $diff_gmt_weblogger    = $diff_gmt_server - $diff_weblogger_server;
 983      $gmt_offset            = -$diff_gmt_weblogger;
 984  
 985      // Add a gmt_offset option, with value $gmt_offset.
 986      add_option( 'gmt_offset', $gmt_offset );
 987  
 988      /*
 989       * Check if we already set the GMT fields. If we did, then
 990       * MAX(post_date_gmt) can't be '0000-00-00 00:00:00'.
 991       * <michel_v> I just slapped myself silly for not thinking about it earlier.
 992       */
 993      $got_gmt_fields = ( '0000-00-00 00:00:00' !== $wpdb->get_var( "SELECT MAX(post_date_gmt) FROM $wpdb->posts" ) );
 994  
 995      if ( ! $got_gmt_fields ) {
 996  
 997          // Add or subtract time to all dates, to get GMT dates.
 998          $add_hours   = (int) $diff_gmt_weblogger;
 999          $add_minutes = (int) ( 60 * ( $diff_gmt_weblogger - $add_hours ) );
1000          $wpdb->query( "UPDATE $wpdb->posts SET post_date_gmt = DATE_ADD(post_date, INTERVAL '$add_hours:$add_minutes' HOUR_MINUTE)" );
1001          $wpdb->query( "UPDATE $wpdb->posts SET post_modified = post_date" );
1002          $wpdb->query( "UPDATE $wpdb->posts SET post_modified_gmt = DATE_ADD(post_modified, INTERVAL '$add_hours:$add_minutes' HOUR_MINUTE) WHERE post_modified != '0000-00-00 00:00:00'" );
1003          $wpdb->query( "UPDATE $wpdb->comments SET comment_date_gmt = DATE_ADD(comment_date, INTERVAL '$add_hours:$add_minutes' HOUR_MINUTE)" );
1004          $wpdb->query( "UPDATE $wpdb->users SET user_registered = DATE_ADD(user_registered, INTERVAL '$add_hours:$add_minutes' HOUR_MINUTE)" );
1005      }
1006  }
1007  
1008  /**
1009   * Execute changes made in WordPress 1.5.
1010   *
1011   * @ignore
1012   * @since 1.5.0
1013   *
1014   * @global wpdb $wpdb WordPress database abstraction object.
1015   */
1016  function upgrade_130() {
1017      global $wpdb;
1018  
1019      // Remove extraneous backslashes.
1020      $posts = $wpdb->get_results( "SELECT ID, post_title, post_content, post_excerpt, guid, post_date, post_name, post_status, post_author FROM $wpdb->posts" );
1021      if ( $posts ) {
1022          foreach ( $posts as $post ) {
1023              $post_content = addslashes( deslash( $post->post_content ) );
1024              $post_title   = addslashes( deslash( $post->post_title ) );
1025              $post_excerpt = addslashes( deslash( $post->post_excerpt ) );
1026              if ( empty( $post->guid ) ) {
1027                  $guid = get_permalink( $post->ID );
1028              } else {
1029                  $guid = $post->guid;
1030              }
1031  
1032              $wpdb->update( $wpdb->posts, compact( 'post_title', 'post_content', 'post_excerpt', 'guid' ), array( 'ID' => $post->ID ) );
1033  
1034          }
1035      }
1036  
1037      // Remove extraneous backslashes.
1038      $comments = $wpdb->get_results( "SELECT comment_ID, comment_author, comment_content FROM $wpdb->comments" );
1039      if ( $comments ) {
1040          foreach ( $comments as $comment ) {
1041              $comment_content = deslash( $comment->comment_content );
1042              $comment_author  = deslash( $comment->comment_author );
1043  
1044              $wpdb->update( $wpdb->comments, compact( 'comment_content', 'comment_author' ), array( 'comment_ID' => $comment->comment_ID ) );
1045          }
1046      }
1047  
1048      // Remove extraneous backslashes.
1049      $links = $wpdb->get_results( "SELECT link_id, link_name, link_description FROM $wpdb->links" );
1050      if ( $links ) {
1051          foreach ( $links as $link ) {
1052              $link_name        = deslash( $link->link_name );
1053              $link_description = deslash( $link->link_description );
1054  
1055              $wpdb->update( $wpdb->links, compact( 'link_name', 'link_description' ), array( 'link_id' => $link->link_id ) );
1056          }
1057      }
1058  
1059      $active_plugins = __get_option( 'active_plugins' );
1060  
1061      /*
1062       * If plugins are not stored in an array, they're stored in the old
1063       * newline separated format. Convert to new format.
1064       */
1065      if ( ! is_array( $active_plugins ) ) {
1066          $active_plugins = explode( "\n", trim( $active_plugins ) );
1067          update_option( 'active_plugins', $active_plugins );
1068      }
1069  
1070      // Obsolete tables.
1071      $wpdb->query( 'DROP TABLE IF EXISTS ' . $wpdb->prefix . 'optionvalues' );
1072      $wpdb->query( 'DROP TABLE IF EXISTS ' . $wpdb->prefix . 'optiontypes' );
1073      $wpdb->query( 'DROP TABLE IF EXISTS ' . $wpdb->prefix . 'optiongroups' );
1074      $wpdb->query( 'DROP TABLE IF EXISTS ' . $wpdb->prefix . 'optiongroup_options' );
1075  
1076      // Update comments table to use comment_type.
1077      $wpdb->query( "UPDATE $wpdb->comments SET comment_type='trackback', comment_content = REPLACE(comment_content, '<trackback />', '') WHERE comment_content LIKE '<trackback />%'" );
1078      $wpdb->query( "UPDATE $wpdb->comments SET comment_type='pingback', comment_content = REPLACE(comment_content, '<pingback />', '') WHERE comment_content LIKE '<pingback />%'" );
1079  
1080      // Some versions have multiple duplicate option_name rows with the same values.
1081      $options = $wpdb->get_results( "SELECT option_name, COUNT(option_name) AS dupes FROM `$wpdb->options` GROUP BY option_name" );
1082      foreach ( $options as $option ) {
1083          if ( 1 != $option->dupes ) { // Could this be done in the query?
1084              $limit    = $option->dupes - 1;
1085              $dupe_ids = $wpdb->get_col( $wpdb->prepare( "SELECT option_id FROM $wpdb->options WHERE option_name = %s LIMIT %d", $option->option_name, $limit ) );
1086              if ( $dupe_ids ) {
1087                  $dupe_ids = implode( ',', $dupe_ids );
1088                  $wpdb->query( "DELETE FROM $wpdb->options WHERE option_id IN ($dupe_ids)" );
1089              }
1090          }
1091      }
1092  
1093      make_site_theme();
1094  }
1095  
1096  /**
1097   * Execute changes made in WordPress 2.0.
1098   *
1099   * @ignore
1100   * @since 2.0.0
1101   *
1102   * @global wpdb $wpdb                  WordPress database abstraction object.
1103   * @global int  $wp_current_db_version The old (current) database version.
1104   */
1105  function upgrade_160() {
1106      global $wpdb, $wp_current_db_version;
1107  
1108      populate_roles_160();
1109  
1110      $users = $wpdb->get_results( "SELECT * FROM $wpdb->users" );
1111      foreach ( $users as $user ) :
1112          if ( ! empty( $user->user_firstname ) ) {
1113              update_user_meta( $user->ID, 'first_name', wp_slash( $user->user_firstname ) );
1114          }
1115          if ( ! empty( $user->user_lastname ) ) {
1116              update_user_meta( $user->ID, 'last_name', wp_slash( $user->user_lastname ) );
1117          }
1118          if ( ! empty( $user->user_nickname ) ) {
1119              update_user_meta( $user->ID, 'nickname', wp_slash( $user->user_nickname ) );
1120          }
1121          if ( ! empty( $user->user_level ) ) {
1122              update_user_meta( $user->ID, $wpdb->prefix . 'user_level', $user->user_level );
1123          }
1124          if ( ! empty( $user->user_icq ) ) {
1125              update_user_meta( $user->ID, 'icq', wp_slash( $user->user_icq ) );
1126          }
1127          if ( ! empty( $user->user_aim ) ) {
1128              update_user_meta( $user->ID, 'aim', wp_slash( $user->user_aim ) );
1129          }
1130          if ( ! empty( $user->user_msn ) ) {
1131              update_user_meta( $user->ID, 'msn', wp_slash( $user->user_msn ) );
1132          }
1133          if ( ! empty( $user->user_yim ) ) {
1134              update_user_meta( $user->ID, 'yim', wp_slash( $user->user_icq ) );
1135          }
1136          if ( ! empty( $user->user_description ) ) {
1137              update_user_meta( $user->ID, 'description', wp_slash( $user->user_description ) );
1138          }
1139  
1140          if ( isset( $user->user_idmode ) ) :
1141              $idmode = $user->user_idmode;
1142              if ( 'nickname' === $idmode ) {
1143                  $id = $user->user_nickname;
1144              }
1145              if ( 'login' === $idmode ) {
1146                  $id = $user->user_login;
1147              }
1148              if ( 'firstname' === $idmode ) {
1149                  $id = $user->user_firstname;
1150              }
1151              if ( 'lastname' === $idmode ) {
1152                  $id = $user->user_lastname;
1153              }
1154              if ( 'namefl' === $idmode ) {
1155                  $id = $user->user_firstname . ' ' . $user->user_lastname;
1156              }
1157              if ( 'namelf' === $idmode ) {
1158                  $id = $user->user_lastname . ' ' . $user->user_firstname;
1159              }
1160              if ( ! $idmode ) {
1161                  $id = $user->user_nickname;
1162              }
1163              $wpdb->update( $wpdb->users, array( 'display_name' => $id ), array( 'ID' => $user->ID ) );
1164          endif;
1165  
1166          // FIXME: RESET_CAPS is temporary code to reset roles and caps if flag is set.
1167          $caps = get_user_meta( $user->ID, $wpdb->prefix . 'capabilities' );
1168          if ( empty( $caps ) || defined( 'RESET_CAPS' ) ) {
1169              $level = get_user_meta( $user->ID, $wpdb->prefix . 'user_level', true );
1170              $role  = translate_level_to_role( $level );
1171              update_user_meta( $user->ID, $wpdb->prefix . 'capabilities', array( $role => true ) );
1172          }
1173  
1174      endforeach;
1175      $old_user_fields = array( 'user_firstname', 'user_lastname', 'user_icq', 'user_aim', 'user_msn', 'user_yim', 'user_idmode', 'user_ip', 'user_domain', 'user_browser', 'user_description', 'user_nickname', 'user_level' );
1176      $wpdb->hide_errors();
1177      foreach ( $old_user_fields as $old ) {
1178          $wpdb->query( "ALTER TABLE $wpdb->users DROP $old" );
1179      }
1180      $wpdb->show_errors();
1181  
1182      // Populate comment_count field of posts table.
1183      $comments = $wpdb->get_results( "SELECT comment_post_ID, COUNT(*) as c FROM $wpdb->comments WHERE comment_approved = '1' GROUP BY comment_post_ID" );
1184      if ( is_array( $comments ) ) {
1185          foreach ( $comments as $comment ) {
1186              $wpdb->update( $wpdb->posts, array( 'comment_count' => $comment->c ), array( 'ID' => $comment->comment_post_ID ) );
1187          }
1188      }
1189  
1190      /*
1191       * Some alpha versions used a post status of object instead of attachment
1192       * and put the mime type in post_type instead of post_mime_type.
1193       */
1194      if ( $wp_current_db_version > 2541 && $wp_current_db_version <= 3091 ) {
1195          $objects = $wpdb->get_results( "SELECT ID, post_type FROM $wpdb->posts WHERE post_status = 'object'" );
1196          foreach ( $objects as $object ) {
1197              $wpdb->update(
1198                  $wpdb->posts,
1199                  array(
1200                      'post_status'    => 'attachment',
1201                      'post_mime_type' => $object->post_type,
1202                      'post_type'      => '',
1203                  ),
1204                  array( 'ID' => $object->ID )
1205              );
1206  
1207              $meta = get_post_meta( $object->ID, 'imagedata', true );
1208              if ( ! empty( $meta['file'] ) ) {
1209                  update_attached_file( $object->ID, $meta['file'] );
1210              }
1211          }
1212      }
1213  }
1214  
1215  /**
1216   * Execute changes made in WordPress 2.1.
1217   *
1218   * @ignore
1219   * @since 2.1.0
1220   *
1221   * @global int  $wp_current_db_version The old (current) database version.
1222   * @global wpdb $wpdb                  WordPress database abstraction object.
1223   */
1224  function upgrade_210() {
1225      global $wp_current_db_version, $wpdb;
1226  
1227      if ( $wp_current_db_version < 3506 ) {
1228          // Update status and type.
1229          $posts = $wpdb->get_results( "SELECT ID, post_status FROM $wpdb->posts" );
1230  
1231          if ( ! empty( $posts ) ) {
1232              foreach ( $posts as $post ) {
1233                  $status = $post->post_status;
1234                  $type   = 'post';
1235  
1236                  if ( 'static' === $status ) {
1237                      $status = 'publish';
1238                      $type   = 'page';
1239                  } elseif ( 'attachment' === $status ) {
1240                      $status = 'inherit';
1241                      $type   = 'attachment';
1242                  }
1243  
1244                  $wpdb->query( $wpdb->prepare( "UPDATE $wpdb->posts SET post_status = %s, post_type = %s WHERE ID = %d", $status, $type, $post->ID ) );
1245              }
1246          }
1247      }
1248  
1249      if ( $wp_current_db_version < 3845 ) {
1250          populate_roles_210();
1251      }
1252  
1253      if ( $wp_current_db_version < 3531 ) {
1254          // Give future posts a post_status of future.
1255          $now = gmdate( 'Y-m-d H:i:59' );
1256          $wpdb->query( "UPDATE $wpdb->posts SET post_status = 'future' WHERE post_status = 'publish' AND post_date_gmt > '$now'" );
1257  
1258          $posts = $wpdb->get_results( "SELECT ID, post_date FROM $wpdb->posts WHERE post_status ='future'" );
1259          if ( ! empty( $posts ) ) {
1260              foreach ( $posts as $post ) {
1261                  wp_schedule_single_event( mysql2date( 'U', $post->post_date, false ), 'publish_future_post', array( $post->ID ) );
1262              }
1263          }
1264      }
1265  }
1266  
1267  /**
1268   * Execute changes made in WordPress 2.3.
1269   *
1270   * @ignore
1271   * @since 2.3.0
1272   *
1273   * @global int  $wp_current_db_version The old (current) database version.
1274   * @global wpdb $wpdb                  WordPress database abstraction object.
1275   */
1276  function upgrade_230() {
1277      global $wp_current_db_version, $wpdb;
1278  
1279      if ( $wp_current_db_version < 5200 ) {
1280          populate_roles_230();
1281      }
1282  
1283      // Convert categories to terms.
1284      $tt_ids     = array();
1285      $have_tags  = false;
1286      $categories = $wpdb->get_results( "SELECT * FROM $wpdb->categories ORDER BY cat_ID" );
1287      foreach ( $categories as $category ) {
1288          $term_id     = (int) $category->cat_ID;
1289          $name        = $category->cat_name;
1290          $description = $category->category_description;
1291          $slug        = $category->category_nicename;
1292          $parent      = $category->category_parent;
1293          $term_group  = 0;
1294  
1295          // Associate terms with the same slug in a term group and make slugs unique.
1296          $exists = $wpdb->get_results( $wpdb->prepare( "SELECT term_id, term_group FROM $wpdb->terms WHERE slug = %s", $slug ) );
1297          if ( $exists ) {
1298              $term_group = $exists[0]->term_group;
1299              $id         = $exists[0]->term_id;
1300              $num        = 2;
1301              do {
1302                  $alt_slug = $slug . "-$num";
1303                  ++$num;
1304                  $slug_check = $wpdb->get_var( $wpdb->prepare( "SELECT slug FROM $wpdb->terms WHERE slug = %s", $alt_slug ) );
1305              } while ( $slug_check );
1306  
1307              $slug = $alt_slug;
1308  
1309              if ( empty( $term_group ) ) {
1310                  $term_group = $wpdb->get_var( "SELECT MAX(term_group) FROM $wpdb->terms GROUP BY term_group" ) + 1;
1311                  $wpdb->query( $wpdb->prepare( "UPDATE $wpdb->terms SET term_group = %d WHERE term_id = %d", $term_group, $id ) );
1312              }
1313          }
1314  
1315          $wpdb->query(
1316              $wpdb->prepare(
1317                  "INSERT INTO $wpdb->terms (term_id, name, slug, term_group) VALUES
1318          (%d, %s, %s, %d)",
1319                  $term_id,
1320                  $name,
1321                  $slug,
1322                  $term_group
1323              )
1324          );
1325  
1326          $count = 0;
1327          if ( ! empty( $category->category_count ) ) {
1328              $count    = (int) $category->category_count;
1329              $taxonomy = 'category';
1330              $wpdb->query( $wpdb->prepare( "INSERT INTO $wpdb->term_taxonomy (term_id, taxonomy, description, parent, count) VALUES ( %d, %s, %s, %d, %d)", $term_id, $taxonomy, $description, $parent, $count ) );
1331              $tt_ids[ $term_id ][ $taxonomy ] = (int) $wpdb->insert_id;
1332          }
1333  
1334          if ( ! empty( $category->link_count ) ) {
1335              $count    = (int) $category->link_count;
1336              $taxonomy = 'link_category';
1337              $wpdb->query( $wpdb->prepare( "INSERT INTO $wpdb->term_taxonomy (term_id, taxonomy, description, parent, count) VALUES ( %d, %s, %s, %d, %d)", $term_id, $taxonomy, $description, $parent, $count ) );
1338              $tt_ids[ $term_id ][ $taxonomy ] = (int) $wpdb->insert_id;
1339          }
1340  
1341          if ( ! empty( $category->tag_count ) ) {
1342              $have_tags = true;
1343              $count     = (int) $category->tag_count;
1344              $taxonomy  = 'post_tag';
1345              $wpdb->insert( $wpdb->term_taxonomy, compact( 'term_id', 'taxonomy', 'description', 'parent', 'count' ) );
1346              $tt_ids[ $term_id ][ $taxonomy ] = (int) $wpdb->insert_id;
1347          }
1348  
1349          if ( empty( $count ) ) {
1350              $count    = 0;
1351              $taxonomy = 'category';
1352              $wpdb->insert( $wpdb->term_taxonomy, compact( 'term_id', 'taxonomy', 'description', 'parent', 'count' ) );
1353              $tt_ids[ $term_id ][ $taxonomy ] = (int) $wpdb->insert_id;
1354          }
1355      }
1356  
1357      $select = 'post_id, category_id';
1358      if ( $have_tags ) {
1359          $select .= ', rel_type';
1360      }
1361  
1362      $posts = $wpdb->get_results( "SELECT $select FROM $wpdb->post2cat GROUP BY post_id, category_id" );
1363      foreach ( $posts as $post ) {
1364          $post_id  = (int) $post->post_id;
1365          $term_id  = (int) $post->category_id;
1366          $taxonomy = 'category';
1367          if ( ! empty( $post->rel_type ) && 'tag' === $post->rel_type ) {
1368              $taxonomy = 'tag';
1369          }
1370          $tt_id = $tt_ids[ $term_id ][ $taxonomy ];
1371          if ( empty( $tt_id ) ) {
1372              continue;
1373          }
1374  
1375          $wpdb->insert(
1376              $wpdb->term_relationships,
1377              array(
1378                  'object_id'        => $post_id,
1379                  'term_taxonomy_id' => $tt_id,
1380              )
1381          );
1382      }
1383  
1384      // < 3570 we used linkcategories. >= 3570 we used categories and link2cat.
1385      if ( $wp_current_db_version < 3570 ) {
1386          /*
1387           * Create link_category terms for link categories. Create a map of link
1388           * category IDs to link_category terms.
1389           */
1390          $link_cat_id_map  = array();
1391          $default_link_cat = 0;
1392          $tt_ids           = array();
1393          $link_cats        = $wpdb->get_results( 'SELECT cat_id, cat_name FROM ' . $wpdb->prefix . 'linkcategories' );
1394          foreach ( $link_cats as $category ) {
1395              $cat_id     = (int) $category->cat_id;
1396              $term_id    = 0;
1397              $name       = wp_slash( $category->cat_name );
1398              $slug       = sanitize_title( $name );
1399              $term_group = 0;
1400  
1401              // Associate terms with the same slug in a term group and make slugs unique.
1402              $exists = $wpdb->get_results( $wpdb->prepare( "SELECT term_id, term_group FROM $wpdb->terms WHERE slug = %s", $slug ) );
1403              if ( $exists ) {
1404                  $term_group = $exists[0]->term_group;
1405                  $term_id    = $exists[0]->term_id;
1406              }
1407  
1408              if ( empty( $term_id ) ) {
1409                  $wpdb->insert( $wpdb->terms, compact( 'name', 'slug', 'term_group' ) );
1410                  $term_id = (int) $wpdb->insert_id;
1411              }
1412  
1413              $link_cat_id_map[ $cat_id ] = $term_id;
1414              $default_link_cat           = $term_id;
1415  
1416              $wpdb->insert(
1417                  $wpdb->term_taxonomy,
1418                  array(
1419                      'term_id'     => $term_id,
1420                      'taxonomy'    => 'link_category',
1421                      'description' => '',
1422                      'parent'      => 0,
1423                      'count'       => 0,
1424                  )
1425              );
1426              $tt_ids[ $term_id ] = (int) $wpdb->insert_id;
1427          }
1428  
1429          // Associate links to categories.
1430          $links = $wpdb->get_results( "SELECT link_id, link_category FROM $wpdb->links" );
1431          if ( ! empty( $links ) ) {
1432              foreach ( $links as $link ) {
1433                  if ( 0 == $link->link_category ) {
1434                      continue;
1435                  }
1436                  if ( ! isset( $link_cat_id_map[ $link->link_category ] ) ) {
1437                      continue;
1438                  }
1439                  $term_id = $link_cat_id_map[ $link->link_category ];
1440                  $tt_id   = $tt_ids[ $term_id ];
1441                  if ( empty( $tt_id ) ) {
1442                      continue;
1443                  }
1444  
1445                  $wpdb->insert(
1446                      $wpdb->term_relationships,
1447                      array(
1448                          'object_id'        => $link->link_id,
1449                          'term_taxonomy_id' => $tt_id,
1450                      )
1451                  );
1452              }
1453          }
1454  
1455          // Set default to the last category we grabbed during the upgrade loop.
1456          update_option( 'default_link_category', $default_link_cat );
1457      } else {
1458          $links = $wpdb->get_results( "SELECT link_id, category_id FROM $wpdb->link2cat GROUP BY link_id, category_id" );
1459          foreach ( $links as $link ) {
1460              $link_id  = (int) $link->link_id;
1461              $term_id  = (int) $link->category_id;
1462              $taxonomy = 'link_category';
1463              $tt_id    = $tt_ids[ $term_id ][ $taxonomy ];
1464              if ( empty( $tt_id ) ) {
1465                  continue;
1466              }
1467              $wpdb->insert(
1468                  $wpdb->term_relationships,
1469                  array(
1470                      'object_id'        => $link_id,
1471                      'term_taxonomy_id' => $tt_id,
1472                  )
1473              );
1474          }
1475      }
1476  
1477      if ( $wp_current_db_version < 4772 ) {
1478          // Obsolete linkcategories table.
1479          $wpdb->query( 'DROP TABLE IF EXISTS ' . $wpdb->prefix . 'linkcategories' );
1480      }
1481  
1482      // Recalculate all counts.
1483      $terms = $wpdb->get_results( "SELECT term_taxonomy_id, taxonomy FROM $wpdb->term_taxonomy" );
1484      foreach ( (array) $terms as $term ) {
1485          if ( 'post_tag' === $term->taxonomy || 'category' === $term->taxonomy ) {
1486              $count = $wpdb->get_var( $wpdb->prepare( "SELECT COUNT(*) FROM $wpdb->term_relationships, $wpdb->posts WHERE $wpdb->posts.ID = $wpdb->term_relationships.object_id AND post_status = 'publish' AND post_type = 'post' AND term_taxonomy_id = %d", $term->term_taxonomy_id ) );
1487          } else {
1488              $count = $wpdb->get_var( $wpdb->prepare( "SELECT COUNT(*) FROM $wpdb->term_relationships WHERE term_taxonomy_id = %d", $term->term_taxonomy_id ) );
1489          }
1490          $wpdb->update( $wpdb->term_taxonomy, array( 'count' => $count ), array( 'term_taxonomy_id' => $term->term_taxonomy_id ) );
1491      }
1492  }
1493  
1494  /**
1495   * Remove old options from the database.
1496   *
1497   * @ignore
1498   * @since 2.3.0
1499   *
1500   * @global wpdb $wpdb WordPress database abstraction object.
1501   */
1502  function upgrade_230_options_table() {
1503      global $wpdb;
1504      $old_options_fields = array( 'option_can_override', 'option_type', 'option_width', 'option_height', 'option_description', 'option_admin_level' );
1505      $wpdb->hide_errors();
1506      foreach ( $old_options_fields as $old ) {
1507          $wpdb->query( "ALTER TABLE $wpdb->options DROP $old" );
1508      }
1509      $wpdb->show_errors();
1510  }
1511  
1512  /**
1513   * Remove old categories, link2cat, and post2cat database tables.
1514   *
1515   * @ignore
1516   * @since 2.3.0
1517   *
1518   * @global wpdb $wpdb WordPress database abstraction object.
1519   */
1520  function upgrade_230_old_tables() {
1521      global $wpdb;
1522      $wpdb->query( 'DROP TABLE IF EXISTS ' . $wpdb->prefix . 'categories' );
1523      $wpdb->query( 'DROP TABLE IF EXISTS ' . $wpdb->prefix . 'link2cat' );
1524      $wpdb->query( 'DROP TABLE IF EXISTS ' . $wpdb->prefix . 'post2cat' );
1525  }
1526  
1527  /**
1528   * Upgrade old slugs made in version 2.2.
1529   *
1530   * @ignore
1531   * @since 2.2.0
1532   *
1533   * @global wpdb $wpdb WordPress database abstraction object.
1534   */
1535  function upgrade_old_slugs() {
1536      // Upgrade people who were using the Redirect Old Slugs plugin.
1537      global $wpdb;
1538      $wpdb->query( "UPDATE $wpdb->postmeta SET meta_key = '_wp_old_slug' WHERE meta_key = 'old_slug'" );
1539  }
1540  
1541  /**
1542   * Execute changes made in WordPress 2.5.0.
1543   *
1544   * @ignore
1545   * @since 2.5.0
1546   *
1547   * @global int $wp_current_db_version The old (current) database version.
1548   */
1549  function upgrade_250() {
1550      global $wp_current_db_version;
1551  
1552      if ( $wp_current_db_version < 6689 ) {
1553          populate_roles_250();
1554      }
1555  }
1556  
1557  /**
1558   * Execute changes made in WordPress 2.5.2.
1559   *
1560   * @ignore
1561   * @since 2.5.2
1562   *
1563   * @global wpdb $wpdb WordPress database abstraction object.
1564   */
1565  function upgrade_252() {
1566      global $wpdb;
1567  
1568      $wpdb->query( "UPDATE $wpdb->users SET user_activation_key = ''" );
1569  }
1570  
1571  /**
1572   * Execute changes made in WordPress 2.6.
1573   *
1574   * @ignore
1575   * @since 2.6.0
1576   *
1577   * @global int $wp_current_db_version The old (current) database version.
1578   */
1579  function upgrade_260() {
1580      global $wp_current_db_version;
1581  
1582      if ( $wp_current_db_version < 8000 ) {
1583          populate_roles_260();
1584      }
1585  }
1586  
1587  /**
1588   * Execute changes made in WordPress 2.7.
1589   *
1590   * @ignore
1591   * @since 2.7.0
1592   *
1593   * @global int  $wp_current_db_version The old (current) database version.
1594   * @global wpdb $wpdb                  WordPress database abstraction object.
1595   */
1596  function upgrade_270() {
1597      global $wp_current_db_version, $wpdb;
1598  
1599      if ( $wp_current_db_version < 8980 ) {
1600          populate_roles_270();
1601      }
1602  
1603      // Update post_date for unpublished posts with empty timestamp.
1604      if ( $wp_current_db_version < 8921 ) {
1605          $wpdb->query( "UPDATE $wpdb->posts SET post_date = post_modified WHERE post_date = '0000-00-00 00:00:00'" );
1606      }
1607  }
1608  
1609  /**
1610   * Execute changes made in WordPress 2.8.
1611   *
1612   * @ignore
1613   * @since 2.8.0
1614   *
1615   * @global int  $wp_current_db_version The old (current) database version.
1616   * @global wpdb $wpdb                  WordPress database abstraction object.
1617   */
1618  function upgrade_280() {
1619      global $wp_current_db_version, $wpdb;
1620  
1621      if ( $wp_current_db_version < 10360 ) {
1622          populate_roles_280();
1623      }
1624      if ( is_multisite() ) {
1625          $start = 0;
1626          while ( $rows = $wpdb->get_results( "SELECT option_name, option_value FROM $wpdb->options ORDER BY option_id LIMIT $start, 20" ) ) {
1627              foreach ( $rows as $row ) {
1628                  $value = maybe_unserialize( $row->option_value );
1629                  if ( $value === $row->option_value ) {
1630                      $value = stripslashes( $value );
1631                  }
1632                  if ( $value !== $row->option_value ) {
1633                      update_option( $row->option_name, $value );
1634                  }
1635              }
1636              $start += 20;
1637          }
1638          clean_blog_cache( get_current_blog_id() );
1639      }
1640  }
1641  
1642  /**
1643   * Execute changes made in WordPress 2.9.
1644   *
1645   * @ignore
1646   * @since 2.9.0
1647   *
1648   * @global int $wp_current_db_version The old (current) database version.
1649   */
1650  function upgrade_290() {
1651      global $wp_current_db_version;
1652  
1653      if ( $wp_current_db_version < 11958 ) {
1654          /*
1655           * Previously, setting depth to 1 would redundantly disable threading,
1656           * but now 2 is the minimum depth to avoid confusion.
1657           */
1658          if ( get_option( 'thread_comments_depth' ) == '1' ) {
1659              update_option( 'thread_comments_depth', 2 );
1660              update_option( 'thread_comments', 0 );
1661          }
1662      }
1663  }
1664  
1665  /**
1666   * Execute changes made in WordPress 3.0.
1667   *
1668   * @ignore
1669   * @since 3.0.0
1670   *
1671   * @global int  $wp_current_db_version The old (current) database version.
1672   * @global wpdb $wpdb                  WordPress database abstraction object.
1673   */
1674  function upgrade_300() {
1675      global $wp_current_db_version, $wpdb;
1676  
1677      if ( $wp_current_db_version < 15093 ) {
1678          populate_roles_300();
1679      }
1680  
1681      if ( $wp_current_db_version < 14139 && is_multisite() && is_main_site() && ! defined( 'MULTISITE' ) && get_site_option( 'siteurl' ) === false ) {
1682          add_site_option( 'siteurl', '' );
1683      }
1684  
1685      // 3.0 screen options key name changes.
1686      if ( wp_should_upgrade_global_tables() ) {
1687          $sql    = "DELETE FROM $wpdb->usermeta
1688              WHERE meta_key LIKE %s
1689              OR meta_key LIKE %s
1690              OR meta_key LIKE %s
1691              OR meta_key LIKE %s
1692              OR meta_key LIKE %s
1693              OR meta_key LIKE %s
1694              OR meta_key = 'manageedittagscolumnshidden'
1695              OR meta_key = 'managecategoriescolumnshidden'
1696              OR meta_key = 'manageedit-tagscolumnshidden'
1697              OR meta_key = 'manageeditcolumnshidden'
1698              OR meta_key = 'categories_per_page'
1699              OR meta_key = 'edit_tags_per_page'";
1700          $prefix = $wpdb->esc_like( $wpdb->base_prefix );
1701          $wpdb->query(
1702              $wpdb->prepare(
1703                  $sql,
1704                  $prefix . '%' . $wpdb->esc_like( 'meta-box-hidden' ) . '%',
1705                  $prefix . '%' . $wpdb->esc_like( 'closedpostboxes' ) . '%',
1706                  $prefix . '%' . $wpdb->esc_like( 'manage-' ) . '%' . $wpdb->esc_like( '-columns-hidden' ) . '%',
1707                  $prefix . '%' . $wpdb->esc_like( 'meta-box-order' ) . '%',
1708                  $prefix . '%' . $wpdb->esc_like( 'metaboxorder' ) . '%',
1709                  $prefix . '%' . $wpdb->esc_like( 'screen_layout' ) . '%'
1710              )
1711          );
1712      }
1713  }
1714  
1715  /**
1716   * Execute changes made in WordPress 3.3.
1717   *
1718   * @ignore
1719   * @since 3.3.0
1720   *
1721   * @global int   $wp_current_db_version The old (current) database version.
1722   * @global wpdb  $wpdb                  WordPress database abstraction object.
1723   * @global array $wp_registered_widgets
1724   * @global array $sidebars_widgets
1725   */
1726  function upgrade_330() {
1727      global $wp_current_db_version, $wpdb, $wp_registered_widgets, $sidebars_widgets;
1728  
1729      if ( $wp_current_db_version < 19061 && wp_should_upgrade_global_tables() ) {
1730          $wpdb->query( "DELETE FROM $wpdb->usermeta WHERE meta_key IN ('show_admin_bar_admin', 'plugins_last_view')" );
1731      }
1732  
1733      if ( $wp_current_db_version >= 11548 ) {
1734          return;
1735      }
1736  
1737      $sidebars_widgets  = get_option( 'sidebars_widgets', array() );
1738      $_sidebars_widgets = array();
1739  
1740      if ( isset( $sidebars_widgets['wp_inactive_widgets'] ) || empty( $sidebars_widgets ) ) {
1741          $sidebars_widgets['array_version'] = 3;
1742      } elseif ( ! isset( $sidebars_widgets['array_version'] ) ) {
1743          $sidebars_widgets['array_version'] = 1;
1744      }
1745  
1746      switch ( $sidebars_widgets['array_version'] ) {
1747          case 1:
1748              foreach ( (array) $sidebars_widgets as $index => $sidebar ) {
1749                  if ( is_array( $sidebar ) ) {
1750                      foreach ( (array) $sidebar as $i => $name ) {
1751                          $id = strtolower( $name );
1752                          if ( isset( $wp_registered_widgets[ $id ] ) ) {
1753                              $_sidebars_widgets[ $index ][ $i ] = $id;
1754                              continue;
1755                          }
1756  
1757                          $id = sanitize_title( $name );
1758                          if ( isset( $wp_registered_widgets[ $id ] ) ) {
1759                              $_sidebars_widgets[ $index ][ $i ] = $id;
1760                              continue;
1761                          }
1762  
1763                          $found = false;
1764  
1765                          foreach ( $wp_registered_widgets as $widget_id => $widget ) {
1766                              if ( strtolower( $widget['name'] ) === strtolower( $name ) ) {
1767                                  $_sidebars_widgets[ $index ][ $i ] = $widget['id'];
1768  
1769                                  $found = true;
1770                                  break;
1771                              } elseif ( sanitize_title( $widget['name'] ) === sanitize_title( $name ) ) {
1772                                  $_sidebars_widgets[ $index ][ $i ] = $widget['id'];
1773  
1774                                  $found = true;
1775                                  break;
1776                              }
1777                          }
1778  
1779                          if ( $found ) {
1780                              continue;
1781                          }
1782  
1783                          unset( $_sidebars_widgets[ $index ][ $i ] );
1784                      }
1785                  }
1786              }
1787              $_sidebars_widgets['array_version'] = 2;
1788              $sidebars_widgets                   = $_sidebars_widgets;
1789              unset( $_sidebars_widgets );
1790  
1791              // Intentional fall-through to upgrade to the next version.
1792          case 2:
1793              $sidebars_widgets                  = retrieve_widgets();
1794              $sidebars_widgets['array_version'] = 3;
1795              update_option( 'sidebars_widgets', $sidebars_widgets );
1796      }
1797  }
1798  
1799  /**
1800   * Execute changes made in WordPress 3.4.
1801   *
1802   * @ignore
1803   * @since 3.4.0
1804   *
1805   * @global int  $wp_current_db_version The old (current) database version.
1806   * @global wpdb $wpdb                  WordPress database abstraction object.
1807   */
1808  function upgrade_340() {
1809      global $wp_current_db_version, $wpdb;
1810  
1811      if ( $wp_current_db_version < 19798 ) {
1812          $wpdb->hide_errors();
1813          $wpdb->query( "ALTER TABLE $wpdb->options DROP COLUMN blog_id" );
1814          $wpdb->show_errors();
1815      }
1816  
1817      if ( $wp_current_db_version < 19799 ) {
1818          $wpdb->hide_errors();
1819          $wpdb->query( "ALTER TABLE $wpdb->comments DROP INDEX comment_approved" );
1820          $wpdb->show_errors();
1821      }
1822  
1823      if ( $wp_current_db_version < 20022 && wp_should_upgrade_global_tables() ) {
1824          $wpdb->query( "DELETE FROM $wpdb->usermeta WHERE meta_key = 'themes_last_view'" );
1825      }
1826  
1827      if ( $wp_current_db_version < 20080 ) {
1828          if ( 'yes' === $wpdb->get_var( "SELECT autoload FROM $wpdb->options WHERE option_name = 'uninstall_plugins'" ) ) {
1829              $uninstall_plugins = get_option( 'uninstall_plugins' );
1830              delete_option( 'uninstall_plugins' );
1831              add_option( 'uninstall_plugins', $uninstall_plugins, null, 'no' );
1832          }
1833      }
1834  }
1835  
1836  /**
1837   * Execute changes made in WordPress 3.5.
1838   *
1839   * @ignore
1840   * @since 3.5.0
1841   *
1842   * @global int  $wp_current_db_version The old (current) database version.
1843   * @global wpdb $wpdb                  WordPress database abstraction object.
1844   */
1845  function upgrade_350() {
1846      global $wp_current_db_version, $wpdb;
1847  
1848      if ( $wp_current_db_version < 22006 && $wpdb->get_var( "SELECT link_id FROM $wpdb->links LIMIT 1" ) ) {
1849          update_option( 'link_manager_enabled', 1 ); // Previously set to 0 by populate_options().
1850      }
1851  
1852      if ( $wp_current_db_version < 21811 && wp_should_upgrade_global_tables() ) {
1853          $meta_keys = array();
1854          foreach ( array_merge( get_post_types(), get_taxonomies() ) as $name ) {
1855              if ( str_contains( $name, '-' ) ) {
1856                  $meta_keys[] = 'edit_' . str_replace( '-', '_', $name ) . '_per_page';
1857              }
1858          }
1859          if ( $meta_keys ) {
1860              $meta_keys = implode( "', '", $meta_keys );
1861              $wpdb->query( "DELETE FROM $wpdb->usermeta WHERE meta_key IN ('$meta_keys')" );
1862          }
1863      }
1864  
1865      if ( $wp_current_db_version < 22422 ) {
1866          $term = get_term_by( 'slug', 'post-format-standard', 'post_format' );
1867          if ( $term ) {
1868              wp_delete_term( $term->term_id, 'post_format' );
1869          }
1870      }
1871  }
1872  
1873  /**
1874   * Execute changes made in WordPress 3.7.
1875   *
1876   * @ignore
1877   * @since 3.7.0
1878   *
1879   * @global int $wp_current_db_version The old (current) database version.
1880   */
1881  function upgrade_370() {
1882      global $wp_current_db_version;
1883  
1884      if ( $wp_current_db_version < 25824 ) {
1885          wp_clear_scheduled_hook( 'wp_auto_updates_maybe_update' );
1886      }
1887  }
1888  
1889  /**
1890   * Execute changes made in WordPress 3.7.2.
1891   *
1892   * @ignore
1893   * @since 3.7.2
1894   *
1895   * @global int $wp_current_db_version The old (current) database version.
1896   */
1897  function upgrade_372() {
1898      global $wp_current_db_version;
1899  
1900      if ( $wp_current_db_version < 26148 ) {
1901          wp_clear_scheduled_hook( 'wp_maybe_auto_update' );
1902      }
1903  }
1904  
1905  /**
1906   * Execute changes made in WordPress 3.8.0.
1907   *
1908   * @ignore
1909   * @since 3.8.0
1910   *
1911   * @global int $wp_current_db_version The old (current) database version.
1912   */
1913  function upgrade_380() {
1914      global $wp_current_db_version;
1915  
1916      if ( $wp_current_db_version < 26691 ) {
1917          deactivate_plugins( array( 'mp6/mp6.php' ), true );
1918      }
1919  }
1920  
1921  /**
1922   * Execute changes made in WordPress 4.0.0.
1923   *
1924   * @ignore
1925   * @since 4.0.0
1926   *
1927   * @global int $wp_current_db_version The old (current) database version.
1928   */
1929  function upgrade_400() {
1930      global $wp_current_db_version;
1931  
1932      if ( $wp_current_db_version < 29630 ) {
1933          if ( ! is_multisite() && false === get_option( 'WPLANG' ) ) {
1934              if ( defined( 'WPLANG' ) && ( '' !== WPLANG ) && in_array( WPLANG, get_available_languages(), true ) ) {
1935                  update_option( 'WPLANG', WPLANG );
1936              } else {
1937                  update_option( 'WPLANG', '' );
1938              }
1939          }
1940      }
1941  }
1942  
1943  /**
1944   * Execute changes made in WordPress 4.2.0.
1945   *
1946   * @ignore
1947   * @since 4.2.0
1948   */
1949  function upgrade_420() {}
1950  
1951  /**
1952   * Executes changes made in WordPress 4.3.0.
1953   *
1954   * @ignore
1955   * @since 4.3.0
1956   *
1957   * @global int  $wp_current_db_version The old (current) database version.
1958   * @global wpdb $wpdb                  WordPress database abstraction object.
1959   */
1960  function upgrade_430() {
1961      global $wp_current_db_version, $wpdb;
1962  
1963      if ( $wp_current_db_version < 32364 ) {
1964          upgrade_430_fix_comments();
1965      }
1966  
1967      // Shared terms are split in a separate process.
1968      if ( $wp_current_db_version < 32814 ) {
1969          update_option( 'finished_splitting_shared_terms', 0 );
1970          wp_schedule_single_event( time() + ( 1 * MINUTE_IN_SECONDS ), 'wp_split_shared_term_batch' );
1971      }
1972  
1973      if ( $wp_current_db_version < 33055 && 'utf8mb4' === $wpdb->charset ) {
1974          if ( is_multisite() ) {
1975              $tables = $wpdb->tables( 'blog' );
1976          } else {
1977              $tables = $wpdb->tables( 'all' );
1978              if ( ! wp_should_upgrade_global_tables() ) {
1979                  $global_tables = $wpdb->tables( 'global' );
1980                  $tables        = array_diff_assoc( $tables, $global_tables );
1981              }
1982          }
1983  
1984          foreach ( $tables as $table ) {
1985              maybe_convert_table_to_utf8mb4( $table );
1986          }
1987      }
1988  }
1989  
1990  /**
1991   * Executes comments changes made in WordPress 4.3.0.
1992   *
1993   * @ignore
1994   * @since 4.3.0
1995   *
1996   * @global wpdb $wpdb WordPress database abstraction object.
1997   */
1998  function upgrade_430_fix_comments() {
1999      global $wpdb;
2000  
2001      $content_length = $wpdb->get_col_length( $wpdb->comments, 'comment_content' );
2002  
2003      if ( is_wp_error( $content_length ) ) {
2004          return;
2005      }
2006  
2007      if ( false === $content_length ) {
2008          $content_length = array(
2009              'type'   => 'byte',
2010              'length' => 65535,
2011          );
2012      } elseif ( ! is_array( $content_length ) ) {
2013          $length         = (int) $content_length > 0 ? (int) $content_length : 65535;
2014          $content_length = array(
2015              'type'   => 'byte',
2016              'length' => $length,
2017          );
2018      }
2019  
2020      if ( 'byte' !== $content_length['type'] || 0 === $content_length['length'] ) {
2021          // Sites with malformed DB schemas are on their own.
2022          return;
2023      }
2024  
2025      $allowed_length = (int) $content_length['length'] - 10;
2026  
2027      $comments = $wpdb->get_results(
2028          "SELECT `comment_ID` FROM `{$wpdb->comments}`
2029              WHERE `comment_date_gmt` > '2015-04-26'
2030              AND LENGTH( `comment_content` ) >= {$allowed_length}
2031              AND ( `comment_content` LIKE '%<%' OR `comment_content` LIKE '%>%' )"
2032      );
2033  
2034      foreach ( $comments as $comment ) {
2035          wp_delete_comment( $comment->comment_ID, true );
2036      }
2037  }
2038  
2039  /**
2040   * Executes changes made in WordPress 4.3.1.
2041   *
2042   * @ignore
2043   * @since 4.3.1
2044   */
2045  function upgrade_431() {
2046      // Fix incorrect cron entries for term splitting.
2047      $cron_array = _get_cron_array();
2048      if ( isset( $cron_array['wp_batch_split_terms'] ) ) {
2049          unset( $cron_array['wp_batch_split_terms'] );
2050          _set_cron_array( $cron_array );
2051      }
2052  }
2053  
2054  /**
2055   * Executes changes made in WordPress 4.4.0.
2056   *
2057   * @ignore
2058   * @since 4.4.0
2059   *
2060   * @global int  $wp_current_db_version The old (current) database version.
2061   * @global wpdb $wpdb                  WordPress database abstraction object.
2062   */
2063  function upgrade_440() {
2064      global $wp_current_db_version, $wpdb;
2065  
2066      if ( $wp_current_db_version < 34030 ) {
2067          $wpdb->query( "ALTER TABLE {$wpdb->options} MODIFY option_name VARCHAR(191)" );
2068      }
2069  
2070      // Remove the unused 'add_users' role.
2071      $roles = wp_roles();
2072      foreach ( $roles->role_objects as $role ) {
2073          if ( $role->has_cap( 'add_users' ) ) {
2074              $role->remove_cap( 'add_users' );
2075          }
2076      }
2077  }
2078  
2079  /**
2080   * Executes changes made in WordPress 4.5.0.
2081   *
2082   * @ignore
2083   * @since 4.5.0
2084   *
2085   * @global int  $wp_current_db_version The old (current) database version.
2086   * @global wpdb $wpdb                  WordPress database abstraction object.
2087   */
2088  function upgrade_450() {
2089      global $wp_current_db_version, $wpdb;
2090  
2091      if ( $wp_current_db_version < 36180 ) {
2092          wp_clear_scheduled_hook( 'wp_maybe_auto_update' );
2093      }
2094  
2095      // Remove unused email confirmation options, moved to usermeta.
2096      if ( $wp_current_db_version < 36679 && is_multisite() ) {
2097          $wpdb->query( "DELETE FROM $wpdb->options WHERE option_name REGEXP '^[0-9]+_new_email$'" );
2098      }
2099  
2100      // Remove unused user setting for wpLink.
2101      delete_user_setting( 'wplink' );
2102  }
2103  
2104  /**
2105   * Executes changes made in WordPress 4.6.0.
2106   *
2107   * @ignore
2108   * @since 4.6.0
2109   *
2110   * @global int $wp_current_db_version The old (current) database version.
2111   */
2112  function upgrade_460() {
2113      global $wp_current_db_version;
2114  
2115      // Remove unused post meta.
2116      if ( $wp_current_db_version < 37854 ) {
2117          delete_post_meta_by_key( '_post_restored_from' );
2118      }
2119  
2120      // Remove plugins with callback as an array object/method as the uninstall hook, see #13786.
2121      if ( $wp_current_db_version < 37965 ) {
2122          $uninstall_plugins = get_option( 'uninstall_plugins', array() );
2123  
2124          if ( ! empty( $uninstall_plugins ) ) {
2125              foreach ( $uninstall_plugins as $basename => $callback ) {
2126                  if ( is_array( $callback ) && is_object( $callback[0] ) ) {
2127                      unset( $uninstall_plugins[ $basename ] );
2128                  }
2129              }
2130  
2131              update_option( 'uninstall_plugins', $uninstall_plugins );
2132          }
2133      }
2134  }
2135  
2136  /**
2137   * Executes changes made in WordPress 5.0.0.
2138   *
2139   * @ignore
2140   * @since 5.0.0
2141   * @deprecated 5.1.0
2142   */
2143  function upgrade_500() {
2144  }
2145  
2146  /**
2147   * Executes changes made in WordPress 5.1.0.
2148   *
2149   * @ignore
2150   * @since 5.1.0
2151   */
2152  function upgrade_510() {
2153      delete_site_option( 'upgrade_500_was_gutenberg_active' );
2154  }
2155  
2156  /**
2157   * Executes changes made in WordPress 5.3.0.
2158   *
2159   * @ignore
2160   * @since 5.3.0
2161   */
2162  function upgrade_530() {
2163      /*
2164       * The `admin_email_lifespan` option may have been set by an admin that just logged in,
2165       * saw the verification screen, clicked on a button there, and is now upgrading the db,
2166       * or by populate_options() that is called earlier in upgrade_all().
2167       * In the second case `admin_email_lifespan` should be reset so the verification screen
2168       * is shown next time an admin logs in.
2169       */
2170      if ( function_exists( 'current_user_can' ) && ! current_user_can( 'manage_options' ) ) {
2171          update_option( 'admin_email_lifespan', 0 );
2172      }
2173  }
2174  
2175  /**
2176   * Executes changes made in WordPress 5.5.0.
2177   *
2178   * @ignore
2179   * @since 5.5.0
2180   *
2181   * @global int $wp_current_db_version The old (current) database version.
2182   */
2183  function upgrade_550() {
2184      global $wp_current_db_version;
2185  
2186      if ( $wp_current_db_version < 48121 ) {
2187          $comment_previously_approved = get_option( 'comment_whitelist', '' );
2188          update_option( 'comment_previously_approved', $comment_previously_approved );
2189          delete_option( 'comment_whitelist' );
2190      }
2191  
2192      if ( $wp_current_db_version < 48575 ) {
2193          // Use more clear and inclusive language.
2194          $disallowed_list = get_option( 'blacklist_keys' );
2195  
2196          /*
2197           * This option key was briefly renamed `blocklist_keys`.
2198           * Account for sites that have this key present when the original key does not exist.
2199           */
2200          if ( false === $disallowed_list ) {
2201              $disallowed_list = get_option( 'blocklist_keys' );
2202          }
2203  
2204          update_option( 'disallowed_keys', $disallowed_list );
2205          delete_option( 'blacklist_keys' );
2206          delete_option( 'blocklist_keys' );
2207      }
2208  
2209      if ( $wp_current_db_version < 48748 ) {
2210          update_option( 'finished_updating_comment_type', 0 );
2211          wp_schedule_single_event( time() + ( 1 * MINUTE_IN_SECONDS ), 'wp_update_comment_type_batch' );
2212      }
2213  }
2214  
2215  /**
2216   * Executes changes made in WordPress 5.6.0.
2217   *
2218   * @ignore
2219   * @since 5.6.0
2220   *
2221   * @global int  $wp_current_db_version The old (current) database version.
2222   * @global wpdb $wpdb                  WordPress database abstraction object.
2223   */
2224  function upgrade_560() {
2225      global $wp_current_db_version, $wpdb;
2226  
2227      if ( $wp_current_db_version < 49572 ) {
2228          /*
2229           * Clean up the `post_category` column removed from schema in version 2.8.0.
2230           * Its presence may conflict with `WP_Post::__get()`.
2231           */
2232          $post_category_exists = $wpdb->get_var( "SHOW COLUMNS FROM $wpdb->posts LIKE 'post_category'" );
2233          if ( ! is_null( $post_category_exists ) ) {
2234              $wpdb->query( "ALTER TABLE $wpdb->posts DROP COLUMN `post_category`" );
2235          }
2236  
2237          /*
2238           * When upgrading from WP < 5.6.0 set the core major auto-updates option to `unset` by default.
2239           * This overrides the same option from populate_options() that is intended for new installs.
2240           * See https://core.trac.wordpress.org/ticket/51742.
2241           */
2242          update_option( 'auto_update_core_major', 'unset' );
2243      }
2244  
2245      if ( $wp_current_db_version < 49632 ) {
2246          /*
2247           * Regenerate the .htaccess file to add the `HTTP_AUTHORIZATION` rewrite rule.
2248           * See https://core.trac.wordpress.org/ticket/51723.
2249           */
2250          save_mod_rewrite_rules();
2251      }
2252  
2253      if ( $wp_current_db_version < 49735 ) {
2254          delete_transient( 'dirsize_cache' );
2255      }
2256  
2257      if ( $wp_current_db_version < 49752 ) {
2258          $results = $wpdb->get_results(
2259              $wpdb->prepare(
2260                  "SELECT 1 FROM {$wpdb->usermeta} WHERE meta_key = %s LIMIT 1",
2261                  WP_Application_Passwords::USERMETA_KEY_APPLICATION_PASSWORDS
2262              )
2263          );
2264  
2265          if ( ! empty( $results ) ) {
2266              $network_id = get_main_network_id();
2267              update_network_option( $network_id, WP_Application_Passwords::OPTION_KEY_IN_USE, 1 );
2268          }
2269      }
2270  }
2271  
2272  /**
2273   * Executes changes made in WordPress 5.9.0.
2274   *
2275   * @ignore
2276   * @since 5.9.0
2277   *
2278   * @global int $wp_current_db_version The old (current) database version.
2279   */
2280  function upgrade_590() {
2281      global $wp_current_db_version;
2282  
2283      if ( $wp_current_db_version < 51917 ) {
2284          $crons = _get_cron_array();
2285  
2286          if ( $crons && is_array( $crons ) ) {
2287              // Remove errant `false` values, see #53950, #54906.
2288              $crons = array_filter( $crons );
2289              _set_cron_array( $crons );
2290          }
2291      }
2292  }
2293  
2294  /**
2295   * Executes changes made in WordPress 6.0.0.
2296   *
2297   * @ignore
2298   * @since 6.0.0
2299   *
2300   * @global int $wp_current_db_version The old (current) database version.
2301   */
2302  function upgrade_600() {
2303      global $wp_current_db_version;
2304  
2305      if ( $wp_current_db_version < 53011 ) {
2306          wp_update_user_counts();
2307      }
2308  }
2309  
2310  /**
2311   * Executes changes made in WordPress 6.3.0.
2312   *
2313   * @ignore
2314   * @since 6.3.0
2315   *
2316   * @global int $wp_current_db_version The old (current) database version.
2317   */
2318  function upgrade_630() {
2319      global $wp_current_db_version;
2320  
2321      if ( $wp_current_db_version < 55853 ) {
2322          if ( ! is_multisite() ) {
2323              // Replace non-autoload option can_compress_scripts with autoload option, see #55270
2324              $can_compress_scripts = get_option( 'can_compress_scripts', false );
2325              if ( false !== $can_compress_scripts ) {
2326                  delete_option( 'can_compress_scripts' );
2327                  add_option( 'can_compress_scripts', $can_compress_scripts, '', 'yes' );
2328              }
2329          }
2330      }
2331  }
2332  
2333  /**
2334   * Executes changes made in WordPress 6.4.0.
2335   *
2336   * @ignore
2337   * @since 6.4.0
2338   *
2339   * @global int $wp_current_db_version The old (current) database version.
2340   */
2341  function upgrade_640() {
2342      global $wp_current_db_version;
2343  
2344      if ( $wp_current_db_version < 56657 ) {
2345          // Enable attachment pages.
2346          update_option( 'wp_attachment_pages_enabled', 1 );
2347  
2348          // Remove the wp_https_detection cron. Https status is checked directly in an async Site Health check.
2349          $scheduled = wp_get_scheduled_event( 'wp_https_detection' );
2350          if ( $scheduled ) {
2351              wp_clear_scheduled_hook( 'wp_https_detection' );
2352          }
2353      }
2354  }
2355  
2356  /**
2357   * Executes changes made in WordPress 6.5.0.
2358   *
2359   * @ignore
2360   * @since 6.5.0
2361   *
2362   * @global int  $wp_current_db_version The old (current) database version.
2363   * @global wpdb $wpdb                  WordPress database abstraction object.
2364   */
2365  function upgrade_650() {
2366      global $wp_current_db_version, $wpdb;
2367  
2368      if ( $wp_current_db_version < 57155 ) {
2369          $stylesheet = get_stylesheet();
2370  
2371          // Set autoload=no for all themes except the current one.
2372          $theme_mods_options = $wpdb->get_col(
2373              $wpdb->prepare(
2374                  "SELECT option_name FROM $wpdb->options WHERE autoload = 'yes' AND option_name != %s AND option_name LIKE %s",
2375                  "theme_mods_$stylesheet",
2376                  $wpdb->esc_like( 'theme_mods_' ) . '%'
2377              )
2378          );
2379  
2380          $autoload = array_fill_keys( $theme_mods_options, 'no' );
2381          wp_set_option_autoload_values( $autoload );
2382      }
2383  }
2384  
2385  /**
2386   * Executes network-level upgrade routines.
2387   *
2388   * @since 3.0.0
2389   *
2390   * @global int  $wp_current_db_version The old (current) database version.
2391   * @global wpdb $wpdb                  WordPress database abstraction object.
2392   */
2393  function upgrade_network() {
2394      global $wp_current_db_version, $wpdb;
2395  
2396      // Always clear expired transients.
2397      delete_expired_transients( true );
2398  
2399      // 2.8.0
2400      if ( $wp_current_db_version < 11549 ) {
2401          $wpmu_sitewide_plugins   = get_site_option( 'wpmu_sitewide_plugins' );
2402          $active_sitewide_plugins = get_site_option( 'active_sitewide_plugins' );
2403          if ( $wpmu_sitewide_plugins ) {
2404              if ( ! $active_sitewide_plugins ) {
2405                  $sitewide_plugins = (array) $wpmu_sitewide_plugins;
2406              } else {
2407                  $sitewide_plugins = array_merge( (array) $active_sitewide_plugins, (array) $wpmu_sitewide_plugins );
2408              }
2409  
2410              update_site_option( 'active_sitewide_plugins', $sitewide_plugins );
2411          }
2412          delete_site_option( 'wpmu_sitewide_plugins' );
2413          delete_site_option( 'deactivated_sitewide_plugins' );
2414  
2415          $start = 0;
2416          while ( $rows = $wpdb->get_results( "SELECT meta_key, meta_value FROM {$wpdb->sitemeta} ORDER BY meta_id LIMIT $start, 20" ) ) {
2417              foreach ( $rows as $row ) {
2418                  $value = $row->meta_value;
2419                  if ( ! @unserialize( $value ) ) {
2420                      $value = stripslashes( $value );
2421                  }
2422                  if ( $value !== $row->meta_value ) {
2423                      update_site_option( $row->meta_key, $value );
2424                  }
2425              }
2426              $start += 20;
2427          }
2428      }
2429  
2430      // 3.0.0
2431      if ( $wp_current_db_version < 13576 ) {
2432          update_site_option( 'global_terms_enabled', '1' );
2433      }
2434  
2435      // 3.3.0
2436      if ( $wp_current_db_version < 19390 ) {
2437          update_site_option( 'initial_db_version', $wp_current_db_version );
2438      }
2439  
2440      if ( $wp_current_db_version < 19470 ) {
2441          if ( false === get_site_option( 'active_sitewide_plugins' ) ) {
2442              update_site_option( 'active_sitewide_plugins', array() );
2443          }
2444      }
2445  
2446      // 3.4.0
2447      if ( $wp_current_db_version < 20148 ) {
2448          // 'allowedthemes' keys things by stylesheet. 'allowed_themes' keyed things by name.
2449          $allowedthemes  = get_site_option( 'allowedthemes' );
2450          $allowed_themes = get_site_option( 'allowed_themes' );
2451          if ( false === $allowedthemes && is_array( $allowed_themes ) && $allowed_themes ) {
2452              $converted = array();
2453              $themes    = wp_get_themes();
2454              foreach ( $themes as $stylesheet => $theme_data ) {
2455                  if ( isset( $allowed_themes[ $theme_data->get( 'Name' ) ] ) ) {
2456                      $converted[ $stylesheet ] = true;
2457                  }
2458              }
2459              update_site_option( 'allowedthemes', $converted );
2460              delete_site_option( 'allowed_themes' );
2461          }
2462      }
2463  
2464      // 3.5.0
2465      if ( $wp_current_db_version < 21823 ) {
2466          update_site_option( 'ms_files_rewriting', '1' );
2467      }
2468  
2469      // 3.5.2
2470      if ( $wp_current_db_version < 24448 ) {
2471          $illegal_names = get_site_option( 'illegal_names' );
2472          if ( is_array( $illegal_names ) && count( $illegal_names ) === 1 ) {
2473              $illegal_name  = reset( $illegal_names );
2474              $illegal_names = explode( ' ', $illegal_name );
2475              update_site_option( 'illegal_names', $illegal_names );
2476          }
2477      }
2478  
2479      // 4.2.0
2480      if ( $wp_current_db_version < 31351 && 'utf8mb4' === $wpdb->charset ) {
2481          if ( wp_should_upgrade_global_tables() ) {
2482              $wpdb->query( "ALTER TABLE $wpdb->usermeta DROP INDEX meta_key, ADD INDEX meta_key(meta_key(191))" );
2483              $wpdb->query( "ALTER TABLE $wpdb->site DROP INDEX domain, ADD INDEX domain(domain(140),path(51))" );
2484              $wpdb->query( "ALTER TABLE $wpdb->sitemeta DROP INDEX meta_key, ADD INDEX meta_key(meta_key(191))" );
2485              $wpdb->query( "ALTER TABLE $wpdb->signups DROP INDEX domain_path, ADD INDEX domain_path(domain(140),path(51))" );
2486  
2487              $tables = $wpdb->tables( 'global' );
2488  
2489              // sitecategories may not exist.
2490              if ( ! $wpdb->get_var( "SHOW TABLES LIKE '{$tables['sitecategories']}'" ) ) {
2491                  unset( $tables['sitecategories'] );
2492              }
2493  
2494              foreach ( $tables as $table ) {
2495                  maybe_convert_table_to_utf8mb4( $table );
2496              }
2497          }
2498      }
2499  
2500      // 4.3.0
2501      if ( $wp_current_db_version < 33055 && 'utf8mb4' === $wpdb->charset ) {
2502          if ( wp_should_upgrade_global_tables() ) {
2503              $upgrade = false;
2504              $indexes = $wpdb->get_results( "SHOW INDEXES FROM $wpdb->signups" );
2505              foreach ( $indexes as $index ) {
2506                  if ( 'domain_path' === $index->Key_name && 'domain' === $index->Column_name && 140 != $index->Sub_part ) {
2507                      $upgrade = true;
2508                      break;
2509                  }
2510              }
2511  
2512              if ( $upgrade ) {
2513                  $wpdb->query( "ALTER TABLE $wpdb->signups DROP INDEX domain_path, ADD INDEX domain_path(domain(140),path(51))" );
2514              }
2515  
2516              $tables = $wpdb->tables( 'global' );
2517  
2518              // sitecategories may not exist.
2519              if ( ! $wpdb->get_var( "SHOW TABLES LIKE '{$tables['sitecategories']}'" ) ) {
2520                  unset( $tables['sitecategories'] );
2521              }
2522  
2523              foreach ( $tables as $table ) {
2524                  maybe_convert_table_to_utf8mb4( $table );
2525              }
2526          }
2527      }
2528  
2529      // 5.1.0
2530      if ( $wp_current_db_version < 44467 ) {
2531          $network_id = get_main_network_id();
2532          delete_network_option( $network_id, 'site_meta_supported' );
2533          is_site_meta_supported();
2534      }
2535  }
2536  
2537  //
2538  // General functions we use to actually do stuff.
2539  //
2540  
2541  /**
2542   * Creates a table in the database, if it doesn't already exist.
2543   *
2544   * This method checks for an existing database table and creates a new one if it's not
2545   * already present. It doesn't rely on MySQL's "IF NOT EXISTS" statement, but chooses
2546   * to query all tables first and then run the SQL statement creating the table.
2547   *
2548   * @since 1.0.0
2549   *
2550   * @global wpdb $wpdb WordPress database abstraction object.
2551   *
2552   * @param string $table_name Database table name.
2553   * @param string $create_ddl SQL statement to create table.
2554   * @return bool True on success or if the table already exists. False on failure.
2555   */
2556  function maybe_create_table( $table_name, $create_ddl ) {
2557      global $wpdb;
2558  
2559      $query = $wpdb->prepare( 'SHOW TABLES LIKE %s', $wpdb->esc_like( $table_name ) );
2560  
2561      if ( $wpdb->get_var( $query ) === $table_name ) {
2562          return true;
2563      }
2564  
2565      // Didn't find it, so try to create it.
2566      $wpdb->query( $create_ddl );
2567  
2568      // We cannot directly tell that whether this succeeded!
2569      if ( $wpdb->get_var( $query ) === $table_name ) {
2570          return true;
2571      }
2572  
2573      return false;
2574  }
2575  
2576  /**
2577   * Drops a specified index from a table.
2578   *
2579   * @since 1.0.1
2580   *
2581   * @global wpdb $wpdb WordPress database abstraction object.
2582   *
2583   * @param string $table Database table name.
2584   * @param string $index Index name to drop.
2585   * @return true True, when finished.
2586   */
2587  function drop_index( $table, $index ) {
2588      global $wpdb;
2589  
2590      $wpdb->hide_errors();
2591  
2592      $wpdb->query( "ALTER TABLE `$table` DROP INDEX `$index`" );
2593  
2594      // Now we need to take out all the extra ones we may have created.
2595      for ( $i = 0; $i < 25; $i++ ) {
2596          $wpdb->query( "ALTER TABLE `$table` DROP INDEX `{$index}_$i`" );
2597      }
2598  
2599      $wpdb->show_errors();
2600  
2601      return true;
2602  }
2603  
2604  /**
2605   * Adds an index to a specified table.
2606   *
2607   * @since 1.0.1
2608   *
2609   * @global wpdb $wpdb WordPress database abstraction object.
2610   *
2611   * @param string $table Database table name.
2612   * @param string $index Database table index column.
2613   * @return true True, when done with execution.
2614   */
2615  function add_clean_index( $table, $index ) {
2616      global $wpdb;
2617  
2618      drop_index( $table, $index );
2619      $wpdb->query( "ALTER TABLE `$table` ADD INDEX ( `$index` )" );
2620  
2621      return true;
2622  }
2623  
2624  /**
2625   * Adds column to a database table, if it doesn't already exist.
2626   *
2627   * @since 1.3.0
2628   *
2629   * @global wpdb $wpdb WordPress database abstraction object.
2630   *
2631   * @param string $table_name  Database table name.
2632   * @param string $column_name Table column name.
2633   * @param string $create_ddl  SQL statement to add column.
2634   * @return bool True on success or if the column already exists. False on failure.
2635   */
2636  function maybe_add_column( $table_name, $column_name, $create_ddl ) {
2637      global $wpdb;
2638  
2639      foreach ( $wpdb->get_col( "DESC $table_name", 0 ) as $column ) {
2640          if ( $column === $column_name ) {
2641              return true;
2642          }
2643      }
2644  
2645      // Didn't find it, so try to create it.
2646      $wpdb->query( $create_ddl );
2647  
2648      // We cannot directly tell that whether this succeeded!
2649      foreach ( $wpdb->get_col( "DESC $table_name", 0 ) as $column ) {
2650          if ( $column === $column_name ) {
2651              return true;
2652          }
2653      }
2654  
2655      return false;
2656  }
2657  
2658  /**
2659   * If a table only contains utf8 or utf8mb4 columns, convert it to utf8mb4.
2660   *
2661   * @since 4.2.0
2662   *
2663   * @global wpdb $wpdb WordPress database abstraction object.
2664   *
2665   * @param string $table The table to convert.
2666   * @return bool True if the table was converted, false if it wasn't.
2667   */
2668  function maybe_convert_table_to_utf8mb4( $table ) {
2669      global $wpdb;
2670  
2671      $results = $wpdb->get_results( "SHOW FULL COLUMNS FROM `$table`" );
2672      if ( ! $results ) {
2673          return false;
2674      }
2675  
2676      foreach ( $results as $column ) {
2677          if ( $column->Collation ) {
2678              list( $charset ) = explode( '_', $column->Collation );
2679              $charset         = strtolower( $charset );
2680              if ( 'utf8' !== $charset && 'utf8mb4' !== $charset ) {
2681                  // Don't upgrade tables that have non-utf8 columns.
2682                  return false;
2683              }
2684          }
2685      }
2686  
2687      $table_details = $wpdb->get_row( "SHOW TABLE STATUS LIKE '$table'" );
2688      if ( ! $table_details ) {
2689          return false;
2690      }
2691  
2692      list( $table_charset ) = explode( '_', $table_details->Collation );
2693      $table_charset         = strtolower( $table_charset );
2694      if ( 'utf8mb4' === $table_charset ) {
2695          return true;
2696      }
2697  
2698      return $wpdb->query( "ALTER TABLE $table CONVERT TO CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci" );
2699  }
2700  
2701  /**
2702   * Retrieve all options as it was for 1.2.
2703   *
2704   * @since 1.2.0
2705   *
2706   * @global wpdb $wpdb WordPress database abstraction object.
2707   *
2708   * @return stdClass List of options.
2709   */
2710  function get_alloptions_110() {
2711      global $wpdb;
2712      $all_options = new stdClass();
2713      $options     = $wpdb->get_results( "SELECT option_name, option_value FROM $wpdb->options" );
2714      if ( $options ) {
2715          foreach ( $options as $option ) {
2716              if ( 'siteurl' === $option->option_name || 'home' === $option->option_name || 'category_base' === $option->option_name ) {
2717                  $option->option_value = untrailingslashit( $option->option_value );
2718              }
2719              $all_options->{$option->option_name} = stripslashes( $option->option_value );
2720          }
2721      }
2722      return $all_options;
2723  }
2724  
2725  /**
2726   * Utility version of get_option that is private to installation/upgrade.
2727   *
2728   * @ignore
2729   * @since 1.5.1
2730   * @access private
2731   *
2732   * @global wpdb $wpdb WordPress database abstraction object.
2733   *
2734   * @param string $setting Option name.
2735   * @return mixed
2736   */
2737  function __get_option( $setting ) { // phpcs:ignore WordPress.NamingConventions.ValidFunctionName.FunctionDoubleUnderscore,PHPCompatibility.FunctionNameRestrictions.ReservedFunctionNames.FunctionDoubleUnderscore
2738      global $wpdb;
2739  
2740      if ( 'home' === $setting && defined( 'WP_HOME' ) ) {
2741          return untrailingslashit( WP_HOME );
2742      }
2743  
2744      if ( 'siteurl' === $setting && defined( 'WP_SITEURL' ) ) {
2745          return untrailingslashit( WP_SITEURL );
2746      }
2747  
2748      $option = $wpdb->get_var( $wpdb->prepare( "SELECT option_value FROM $wpdb->options WHERE option_name = %s", $setting ) );
2749  
2750      if ( 'home' === $setting && ! $option ) {
2751          return __get_option( 'siteurl' );
2752      }
2753  
2754      if ( in_array( $setting, array( 'siteurl', 'home', 'category_base', 'tag_base' ), true ) ) {
2755          $option = untrailingslashit( $option );
2756      }
2757  
2758      return maybe_unserialize( $option );
2759  }
2760  
2761  /**
2762   * Filters for content to remove unnecessary slashes.
2763   *
2764   * @since 1.5.0
2765   *
2766   * @param string $content The content to modify.
2767   * @return string The de-slashed content.
2768   */
2769  function deslash( $content ) {
2770      // Note: \\\ inside a regex denotes a single backslash.
2771  
2772      /*
2773       * Replace one or more backslashes followed by a single quote with
2774       * a single quote.
2775       */
2776      $content = preg_replace( "/\\\+'/", "'", $content );
2777  
2778      /*
2779       * Replace one or more backslashes followed by a double quote with
2780       * a double quote.
2781       */
2782      $content = preg_replace( '/\\\+"/', '"', $content );
2783  
2784      // Replace one or more backslashes with one backslash.
2785      $content = preg_replace( '/\\\+/', '\\', $content );
2786  
2787      return $content;
2788  }
2789  
2790  /**
2791   * Modifies the database based on specified SQL statements.
2792   *
2793   * Useful for creating new tables and updating existing tables to a new structure.
2794   *
2795   * @since 1.5.0
2796   * @since 6.1.0 Ignores display width for integer data types on MySQL 8.0.17 or later,
2797   *              to match MySQL behavior. Note: This does not affect MariaDB.
2798   *
2799   * @global wpdb $wpdb WordPress database abstraction object.
2800   *
2801   * @param string[]|string $queries Optional. The query to run. Can be multiple queries
2802   *                                 in an array, or a string of queries separated by
2803   *                                 semicolons. Default empty string.
2804   * @param bool            $execute Optional. Whether or not to execute the query right away.
2805   *                                 Default true.
2806   * @return array Strings containing the results of the various update queries.
2807   */
2808  function dbDelta( $queries = '', $execute = true ) { // phpcs:ignore WordPress.NamingConventions.ValidFunctionName.FunctionNameInvalid
2809      global $wpdb;
2810  
2811      if ( in_array( $queries, array( '', 'all', 'blog', 'global', 'ms_global' ), true ) ) {
2812          $queries = wp_get_db_schema( $queries );
2813      }
2814  
2815      // Separate individual queries into an array.
2816      if ( ! is_array( $queries ) ) {
2817          $queries = explode( ';', $queries );
2818          $queries = array_filter( $queries );
2819      }
2820  
2821      /**
2822       * Filters the dbDelta SQL queries.
2823       *
2824       * @since 3.3.0
2825       *
2826       * @param string[] $queries An array of dbDelta SQL queries.
2827       */
2828      $queries = apply_filters( 'dbdelta_queries', $queries );
2829  
2830      $cqueries   = array(); // Creation queries.
2831      $iqueries   = array(); // Insertion queries.
2832      $for_update = array();
2833  
2834      // Create a tablename index for an array ($cqueries) of recognized query types.
2835      foreach ( $queries as $qry ) {
2836          if ( preg_match( '|CREATE TABLE ([^ ]*)|', $qry, $matches ) ) {
2837              $cqueries[ trim( $matches[1], '`' ) ] = $qry;
2838              $for_update[ $matches[1] ]            = 'Created table ' . $matches[1];
2839              continue;
2840          }
2841  
2842          if ( preg_match( '|CREATE DATABASE ([^ ]*)|', $qry, $matches ) ) {
2843              array_unshift( $cqueries, $qry );
2844              continue;
2845          }
2846  
2847          if ( preg_match( '|INSERT INTO ([^ ]*)|', $qry, $matches ) ) {
2848              $iqueries[] = $qry;
2849              continue;
2850          }
2851  
2852          if ( preg_match( '|UPDATE ([^ ]*)|', $qry, $matches ) ) {
2853              $iqueries[] = $qry;
2854              continue;
2855          }
2856      }
2857  
2858      /**
2859       * Filters the dbDelta SQL queries for creating tables and/or databases.
2860       *
2861       * Queries filterable via this hook contain "CREATE TABLE" or "CREATE DATABASE".
2862       *
2863       * @since 3.3.0
2864       *
2865       * @param string[] $cqueries An array of dbDelta create SQL queries.
2866       */
2867      $cqueries = apply_filters( 'dbdelta_create_queries', $cqueries );
2868  
2869      /**
2870       * Filters the dbDelta SQL queries for inserting or updating.
2871       *
2872       * Queries filterable via this hook contain "INSERT INTO" or "UPDATE".
2873       *
2874       * @since 3.3.0
2875       *
2876       * @param string[] $iqueries An array of dbDelta insert or update SQL queries.
2877       */
2878      $iqueries = apply_filters( 'dbdelta_insert_queries', $iqueries );
2879  
2880      $text_fields = array( 'tinytext', 'text', 'mediumtext', 'longtext' );
2881      $blob_fields = array( 'tinyblob', 'blob', 'mediumblob', 'longblob' );
2882      $int_fields  = array( 'tinyint', 'smallint', 'mediumint', 'int', 'integer', 'bigint' );
2883  
2884      $global_tables  = $wpdb->tables( 'global' );
2885      $db_version     = $wpdb->db_version();
2886      $db_server_info = $wpdb->db_server_info();
2887  
2888      foreach ( $cqueries as $table => $qry ) {
2889          // Upgrade global tables only for the main site. Don't upgrade at all if conditions are not optimal.
2890          if ( in_array( $table, $global_tables, true ) && ! wp_should_upgrade_global_tables() ) {
2891              unset( $cqueries[ $table ], $for_update[ $table ] );
2892              continue;
2893          }
2894  
2895          // Fetch the table column structure from the database.
2896          $suppress    = $wpdb->suppress_errors();
2897          $tablefields = $wpdb->get_results( "DESCRIBE {$table};" );
2898          $wpdb->suppress_errors( $suppress );
2899  
2900          if ( ! $tablefields ) {
2901              continue;
2902          }
2903  
2904          // Clear the field and index arrays.
2905          $cfields                  = array();
2906          $indices                  = array();
2907          $indices_without_subparts = array();
2908  
2909          // Get all of the field names in the query from between the parentheses.
2910          preg_match( '|\((.*)\)|ms', $qry, $match2 );
2911          $qryline = trim( $match2[1] );
2912  
2913          // Separate field lines into an array.
2914          $flds = explode( "\n", $qryline );
2915  
2916          // For every field line specified in the query.
2917          foreach ( $flds as $fld ) {
2918              $fld = trim( $fld, " \t\n\r\0\x0B," ); // Default trim characters, plus ','.
2919  
2920              // Extract the field name.
2921              preg_match( '|^([^ ]*)|', $fld, $fvals );
2922              $fieldname            = trim( $fvals[1], '`' );
2923              $fieldname_lowercased = strtolower( $fieldname );
2924  
2925              // Verify the found field name.
2926              $validfield = true;
2927              switch ( $fieldname_lowercased ) {
2928                  case '':
2929                  case 'primary':
2930                  case 'index':
2931                  case 'fulltext':
2932                  case 'unique':
2933                  case 'key':
2934                  case 'spatial':
2935                      $validfield = false;
2936  
2937                      /*
2938                       * Normalize the index definition.
2939                       *
2940                       * This is done so the definition can be compared against the result of a
2941                       * `SHOW INDEX FROM $table_name` query which returns the current table
2942                       * index information.
2943                       */
2944  
2945                      // Extract type, name and columns from the definition.
2946                      preg_match(
2947                          '/^
2948                              (?P<index_type>             # 1) Type of the index.
2949                                  PRIMARY\s+KEY|(?:UNIQUE|FULLTEXT|SPATIAL)\s+(?:KEY|INDEX)|KEY|INDEX
2950                              )
2951                              \s+                         # Followed by at least one white space character.
2952                              (?:                         # Name of the index. Optional if type is PRIMARY KEY.
2953                                  `?                      # Name can be escaped with a backtick.
2954                                      (?P<index_name>     # 2) Name of the index.
2955                                          (?:[0-9a-zA-Z$_-]|[\xC2-\xDF][\x80-\xBF])+
2956                                      )
2957                                  `?                      # Name can be escaped with a backtick.
2958                                  \s+                     # Followed by at least one white space character.
2959                              )*
2960                              \(                          # Opening bracket for the columns.
2961                                  (?P<index_columns>
2962                                      .+?                 # 3) Column names, index prefixes, and orders.
2963                                  )
2964                              \)                          # Closing bracket for the columns.
2965                          $/imx',
2966                          $fld,
2967                          $index_matches
2968                      );
2969  
2970                      // Uppercase the index type and normalize space characters.
2971                      $index_type = strtoupper( preg_replace( '/\s+/', ' ', trim( $index_matches['index_type'] ) ) );
2972  
2973                      // 'INDEX' is a synonym for 'KEY', standardize on 'KEY'.
2974                      $index_type = str_replace( 'INDEX', 'KEY', $index_type );
2975  
2976                      // Escape the index name with backticks. An index for a primary key has no name.
2977                      $index_name = ( 'PRIMARY KEY' === $index_type ) ? '' : '`' . strtolower( $index_matches['index_name'] ) . '`';
2978  
2979                      // Parse the columns. Multiple columns are separated by a comma.
2980                      $index_columns                  = array_map( 'trim', explode( ',', $index_matches['index_columns'] ) );
2981                      $index_columns_without_subparts = $index_columns;
2982  
2983                      // Normalize columns.
2984                      foreach ( $index_columns as $id => &$index_column ) {
2985                          // Extract column name and number of indexed characters (sub_part).
2986                          preg_match(
2987                              '/
2988                                  `?                      # Name can be escaped with a backtick.
2989                                      (?P<column_name>    # 1) Name of the column.
2990                                          (?:[0-9a-zA-Z$_-]|[\xC2-\xDF][\x80-\xBF])+
2991                                      )
2992                                  `?                      # Name can be escaped with a backtick.
2993                                  (?:                     # Optional sub part.
2994                                      \s*                 # Optional white space character between name and opening bracket.
2995                                      \(                  # Opening bracket for the sub part.
2996                                          \s*             # Optional white space character after opening bracket.
2997                                          (?P<sub_part>
2998                                              \d+         # 2) Number of indexed characters.
2999                                          )
3000                                          \s*             # Optional white space character before closing bracket.
3001                                      \)                  # Closing bracket for the sub part.
3002                                  )?
3003                              /x',
3004                              $index_column,
3005                              $index_column_matches
3006                          );
3007  
3008                          // Escape the column name with backticks.
3009                          $index_column = '`' . $index_column_matches['column_name'] . '`';
3010  
3011                          // We don't need to add the subpart to $index_columns_without_subparts
3012                          $index_columns_without_subparts[ $id ] = $index_column;
3013  
3014                          // Append the optional sup part with the number of indexed characters.
3015                          if ( isset( $index_column_matches['sub_part'] ) ) {
3016                              $index_column .= '(' . $index_column_matches['sub_part'] . ')';
3017                          }
3018                      }
3019  
3020                      // Build the normalized index definition and add it to the list of indices.
3021                      $indices[]                  = "{$index_type} {$index_name} (" . implode( ',', $index_columns ) . ')';
3022                      $indices_without_subparts[] = "{$index_type} {$index_name} (" . implode( ',', $index_columns_without_subparts ) . ')';
3023  
3024                      // Destroy no longer needed variables.
3025                      unset( $index_column, $index_column_matches, $index_matches, $index_type, $index_name, $index_columns, $index_columns_without_subparts );
3026  
3027                      break;
3028              }
3029  
3030              // If it's a valid field, add it to the field array.
3031              if ( $validfield ) {
3032                  $cfields[ $fieldname_lowercased ] = $fld;
3033              }
3034          }
3035  
3036          // For every field in the table.
3037          foreach ( $tablefields as $tablefield ) {
3038              $tablefield_field_lowercased = strtolower( $tablefield->Field );
3039              $tablefield_type_lowercased  = strtolower( $tablefield->Type );
3040  
3041              $tablefield_type_without_parentheses = preg_replace(
3042                  '/'
3043                  . '(.+)'       // Field type, e.g. `int`.
3044                  . '\(\d*\)'    // Display width.
3045                  . '(.*)'       // Optional attributes, e.g. `unsigned`.
3046                  . '/',
3047                  '$1$2',
3048                  $tablefield_type_lowercased
3049              );
3050  
3051              // Get the type without attributes, e.g. `int`.
3052              $tablefield_type_base = strtok( $tablefield_type_without_parentheses, ' ' );
3053  
3054              // If the table field exists in the field array...
3055              if ( array_key_exists( $tablefield_field_lowercased, $cfields ) ) {
3056  
3057                  // Get the field type from the query.
3058                  preg_match( '|`?' . $tablefield->Field . '`? ([^ ]*( unsigned)?)|i', $cfields[ $tablefield_field_lowercased ], $matches );
3059                  $fieldtype            = $matches[1];
3060                  $fieldtype_lowercased = strtolower( $fieldtype );
3061  
3062                  $fieldtype_without_parentheses = preg_replace(
3063                      '/'
3064                      . '(.+)'       // Field type, e.g. `int`.
3065                      . '\(\d*\)'    // Display width.
3066                      . '(.*)'       // Optional attributes, e.g. `unsigned`.
3067                      . '/',
3068                      '$1$2',
3069                      $fieldtype_lowercased
3070                  );
3071  
3072                  // Get the type without attributes, e.g. `int`.
3073                  $fieldtype_base = strtok( $fieldtype_without_parentheses, ' ' );
3074  
3075                  // Is actual field type different from the field type in query?
3076                  if ( $tablefield->Type != $fieldtype ) {
3077                      $do_change = true;
3078                      if ( in_array( $fieldtype_lowercased, $text_fields, true ) && in_array( $tablefield_type_lowercased, $text_fields, true ) ) {
3079                          if ( array_search( $fieldtype_lowercased, $text_fields, true ) < array_search( $tablefield_type_lowercased, $text_fields, true ) ) {
3080                              $do_change = false;
3081                          }
3082                      }
3083  
3084                      if ( in_array( $fieldtype_lowercased, $blob_fields, true ) && in_array( $tablefield_type_lowercased, $blob_fields, true ) ) {
3085                          if ( array_search( $fieldtype_lowercased, $blob_fields, true ) < array_search( $tablefield_type_lowercased, $blob_fields, true ) ) {
3086                              $do_change = false;
3087                          }
3088                      }
3089  
3090                      if ( in_array( $fieldtype_base, $int_fields, true ) && in_array( $tablefield_type_base, $int_fields, true )
3091                          && $fieldtype_without_parentheses === $tablefield_type_without_parentheses
3092                      ) {
3093                          /*
3094                           * MySQL 8.0.17 or later does not support display width for integer data types,
3095                           * so if display width is the only difference, it can be safely ignored.
3096                           * Note: This is specific to MySQL and does not affect MariaDB.
3097                           */
3098                          if ( version_compare( $db_version, '8.0.17', '>=' )
3099                              && ! str_contains( $db_server_info, 'MariaDB' )
3100                          ) {
3101                              $do_change = false;
3102                          }
3103                      }
3104  
3105                      if ( $do_change ) {
3106                          // Add a query to change the column type.
3107                          $cqueries[] = "ALTER TABLE {$table} CHANGE COLUMN `{$tablefield->Field}` " . $cfields[ $tablefield_field_lowercased ];
3108  
3109                          $for_update[ $table . '.' . $tablefield->Field ] = "Changed type of {$table}.{$tablefield->Field} from {$tablefield->Type} to {$fieldtype}";
3110                      }
3111                  }
3112  
3113                  // Get the default value from the array.
3114                  if ( preg_match( "| DEFAULT '(.*?)'|i", $cfields[ $tablefield_field_lowercased ], $matches ) ) {
3115                      $default_value = $matches[1];
3116                      if ( $tablefield->Default != $default_value ) {
3117                          // Add a query to change the column's default value
3118                          $cqueries[] = "ALTER TABLE {$table} ALTER COLUMN `{$tablefield->Field}` SET DEFAULT '{$default_value}'";
3119  
3120                          $for_update[ $table . '.' . $tablefield->Field ] = "Changed default value of {$table}.{$tablefield->Field} from {$tablefield->Default} to {$default_value}";
3121                      }
3122                  }
3123  
3124                  // Remove the field from the array (so it's not added).
3125                  unset( $cfields[ $tablefield_field_lowercased ] );
3126              } else {
3127                  // This field exists in the table, but not in the creation queries?
3128              }
3129          }
3130  
3131          // For every remaining field specified for the table.
3132          foreach ( $cfields as $fieldname => $fielddef ) {
3133              // Push a query line into $cqueries that adds the field to that table.
3134              $cqueries[] = "ALTER TABLE {$table} ADD COLUMN $fielddef";
3135  
3136              $for_update[ $table . '.' . $fieldname ] = 'Added column ' . $table . '.' . $fieldname;
3137          }
3138  
3139          // Index stuff goes here. Fetch the table index structure from the database.
3140          $tableindices = $wpdb->get_results( "SHOW INDEX FROM {$table};" );
3141  
3142          if ( $tableindices ) {
3143              // Clear the index array.
3144              $index_ary = array();
3145  
3146              // For every index in the table.
3147              foreach ( $tableindices as $tableindex ) {
3148                  $keyname = strtolower( $tableindex->Key_name );
3149  
3150                  // Add the index to the index data array.
3151                  $index_ary[ $keyname ]['columns'][]  = array(
3152                      'fieldname' => $tableindex->Column_name,
3153                      'subpart'   => $tableindex->Sub_part,
3154                  );
3155                  $index_ary[ $keyname ]['unique']     = ( 0 == $tableindex->Non_unique ) ? true : false;
3156                  $index_ary[ $keyname ]['index_type'] = $tableindex->Index_type;
3157              }
3158  
3159              // For each actual index in the index array.
3160              foreach ( $index_ary as $index_name => $index_data ) {
3161  
3162                  // Build a create string to compare to the query.
3163                  $index_string = '';
3164                  if ( 'primary' === $index_name ) {
3165                      $index_string .= 'PRIMARY ';
3166                  } elseif ( $index_data['unique'] ) {
3167                      $index_string .= 'UNIQUE ';
3168                  }
3169  
3170                  if ( 'FULLTEXT' === strtoupper( $index_data['index_type'] ) ) {
3171                      $index_string .= 'FULLTEXT ';
3172                  }
3173  
3174                  if ( 'SPATIAL' === strtoupper( $index_data['index_type'] ) ) {
3175                      $index_string .= 'SPATIAL ';
3176                  }
3177  
3178                  $index_string .= 'KEY ';
3179                  if ( 'primary' !== $index_name ) {
3180                      $index_string .= '`' . $index_name . '`';
3181                  }
3182  
3183                  $index_columns = '';
3184  
3185                  // For each column in the index.
3186                  foreach ( $index_data['columns'] as $column_data ) {
3187                      if ( '' !== $index_columns ) {
3188                          $index_columns .= ',';
3189                      }
3190  
3191                      // Add the field to the column list string.
3192                      $index_columns .= '`' . $column_data['fieldname'] . '`';
3193                  }
3194  
3195                  // Add the column list to the index create string.
3196                  $index_string .= " ($index_columns)";
3197  
3198                  // Check if the index definition exists, ignoring subparts.
3199                  $aindex = array_search( $index_string, $indices_without_subparts, true );
3200                  if ( false !== $aindex ) {
3201                      // If the index already exists (even with different subparts), we don't need to create it.
3202                      unset( $indices_without_subparts[ $aindex ] );
3203                      unset( $indices[ $aindex ] );
3204                  }
3205              }
3206          }
3207  
3208          // For every remaining index specified for the table.
3209          foreach ( (array) $indices as $index ) {
3210              // Push a query line into $cqueries that adds the index to that table.
3211              $cqueries[] = "ALTER TABLE {$table} ADD $index";
3212  
3213              $for_update[] = 'Added index ' . $table . ' ' . $index;
3214          }
3215  
3216          // Remove the original table creation query from processing.
3217          unset( $cqueries[ $table ], $for_update[ $table ] );
3218      }
3219  
3220      $allqueries = array_merge( $cqueries, $iqueries );
3221      if ( $execute ) {
3222          foreach ( $allqueries as $query ) {
3223              $wpdb->query( $query );
3224          }
3225      }
3226  
3227      return $for_update;
3228  }
3229  
3230  /**
3231   * Updates the database tables to a new schema.
3232   *
3233   * By default, updates all the tables to use the latest defined schema, but can also
3234   * be used to update a specific set of tables in wp_get_db_schema().
3235   *
3236   * @since 1.5.0
3237   *
3238   * @uses dbDelta
3239   *
3240   * @param string $tables Optional. Which set of tables to update. Default is 'all'.
3241   */
3242  function make_db_current( $tables = 'all' ) {
3243      $alterations = dbDelta( $tables );
3244      echo "<ol>\n";
3245      foreach ( $alterations as $alteration ) {
3246          echo "<li>$alteration</li>\n";
3247      }
3248      echo "</ol>\n";
3249  }
3250  
3251  /**
3252   * Updates the database tables to a new schema, but without displaying results.
3253   *
3254   * By default, updates all the tables to use the latest defined schema, but can
3255   * also be used to update a specific set of tables in wp_get_db_schema().
3256   *
3257   * @since 1.5.0
3258   *
3259   * @see make_db_current()
3260   *
3261   * @param string $tables Optional. Which set of tables to update. Default is 'all'.
3262   */
3263  function make_db_current_silent( $tables = 'all' ) {
3264      dbDelta( $tables );
3265  }
3266  
3267  /**
3268   * Creates a site theme from an existing theme.
3269   *
3270   * {@internal Missing Long Description}}
3271   *
3272   * @since 1.5.0
3273   *
3274   * @param string $theme_name The name of the theme.
3275   * @param string $template   The directory name of the theme.
3276   * @return bool
3277   */
3278  function make_site_theme_from_oldschool( $theme_name, $template ) {
3279      $home_path   = get_home_path();
3280      $site_dir    = WP_CONTENT_DIR . "/themes/$template";
3281      $default_dir = WP_CONTENT_DIR . '/themes/' . WP_DEFAULT_THEME;
3282  
3283      if ( ! file_exists( "$home_path/index.php" ) ) {
3284          return false;
3285      }
3286  
3287      /*
3288       * Copy files from the old locations to the site theme.
3289       * TODO: This does not copy arbitrary include dependencies. Only the standard WP files are copied.
3290       */
3291      $files = array(
3292          'index.php'             => 'index.php',
3293          'wp-layout.css'         => 'style.css',
3294          'wp-comments.php'       => 'comments.php',
3295          'wp-comments-popup.php' => 'comments-popup.php',
3296      );
3297  
3298      foreach ( $files as $oldfile => $newfile ) {
3299          if ( 'index.php' === $oldfile ) {
3300              $oldpath = $home_path;
3301          } else {
3302              $oldpath = ABSPATH;
3303          }
3304  
3305          // Check to make sure it's not a new index.
3306          if ( 'index.php' === $oldfile ) {
3307              $index = implode( '', file( "$oldpath/$oldfile" ) );
3308              if ( str_contains( $index, 'WP_USE_THEMES' ) ) {
3309                  if ( ! copy( "$default_dir/$oldfile", "$site_dir/$newfile" ) ) {
3310                      return false;
3311                  }
3312  
3313                  // Don't copy anything.
3314                  continue;
3315              }
3316          }
3317  
3318          if ( ! copy( "$oldpath/$oldfile", "$site_dir/$newfile" ) ) {
3319              return false;
3320          }
3321  
3322          chmod( "$site_dir/$newfile", 0777 );
3323  
3324          // Update the blog header include in each file.
3325          $lines = explode( "\n", implode( '', file( "$site_dir/$newfile" ) ) );
3326          if ( $lines ) {
3327              $f = fopen( "$site_dir/$newfile", 'w' );
3328  
3329              foreach ( $lines as $line ) {
3330                  if ( preg_match( '/require.*wp-blog-header/', $line ) ) {
3331                      $line = '//' . $line;
3332                  }
3333  
3334                  // Update stylesheet references.
3335                  $line = str_replace(
3336                      "<?php echo __get_option('siteurl'); ?>/wp-layout.css",
3337                      "<?php bloginfo('stylesheet_url'); ?>",
3338                      $line
3339                  );
3340  
3341                  // Update comments template inclusion.
3342                  $line = str_replace(
3343                      "<?php include(ABSPATH . 'wp-comments.php'); ?>",
3344                      '<?php comments_template(); ?>',
3345                      $line
3346                  );
3347  
3348                  fwrite( $f, "{$line}\n" );
3349              }
3350              fclose( $f );
3351          }
3352      }
3353  
3354      // Add a theme header.
3355      $header = "/*\n" .
3356          "Theme Name: $theme_name\n" .
3357          'Theme URI: ' . __get_option( 'siteurl' ) . "\n" .
3358          "Description: A theme automatically created by the update.\n" .
3359          "Version: 1.0\n" .
3360          "Author: Moi\n" .
3361          "*/\n";
3362  
3363      $stylelines = file_get_contents( "$site_dir/style.css" );
3364      if ( $stylelines ) {
3365          $f = fopen( "$site_dir/style.css", 'w' );
3366  
3367          fwrite( $f, $header );
3368          fwrite( $f, $stylelines );
3369          fclose( $f );
3370      }
3371  
3372      return true;
3373  }
3374  
3375  /**
3376   * Creates a site theme from the default theme.
3377   *
3378   * {@internal Missing Long Description}}
3379   *
3380   * @since 1.5.0
3381   *
3382   * @param string $theme_name The name of the theme.
3383   * @param string $template   The directory name of the theme.
3384   * @return void|false
3385   */
3386  function make_site_theme_from_default( $theme_name, $template ) {
3387      $site_dir    = WP_CONTENT_DIR . "/themes/$template";
3388      $default_dir = WP_CONTENT_DIR . '/themes/' . WP_DEFAULT_THEME;
3389  
3390      /*
3391       * Copy files from the default theme to the site theme.
3392       * $files = array( 'index.php', 'comments.php', 'comments-popup.php', 'footer.php', 'header.php', 'sidebar.php', 'style.css' );
3393       */
3394  
3395      $theme_dir = @opendir( $default_dir );
3396      if ( $theme_dir ) {
3397          while ( ( $theme_file = readdir( $theme_dir ) ) !== false ) {
3398              if ( is_dir( "$default_dir/$theme_file" ) ) {
3399                  continue;
3400              }
3401  
3402              if ( ! copy( "$default_dir/$theme_file", "$site_dir/$theme_file" ) ) {
3403                  return;
3404              }
3405  
3406              chmod( "$site_dir/$theme_file", 0777 );
3407          }
3408  
3409          closedir( $theme_dir );
3410      }
3411  
3412      // Rewrite the theme header.
3413      $stylelines = explode( "\n", implode( '', file( "$site_dir/style.css" ) ) );
3414      if ( $stylelines ) {
3415          $f = fopen( "$site_dir/style.css", 'w' );
3416  
3417          $headers = array(
3418              'Theme Name:'  => $theme_name,
3419              'Theme URI:'   => __get_option( 'url' ),
3420              'Description:' => 'Your theme.',
3421              'Version:'     => '1',
3422              'Author:'      => 'You',
3423          );
3424  
3425          foreach ( $stylelines as $line ) {
3426              foreach ( $headers as $header => $value ) {
3427                  if ( str_contains( $line, $header ) ) {
3428                      $line = $header . ' ' . $value;
3429                      break;
3430                  }
3431              }
3432  
3433              fwrite( $f, $line . "\n" );
3434          }
3435  
3436          fclose( $f );
3437      }
3438  
3439      // Copy the images.
3440      umask( 0 );
3441      if ( ! mkdir( "$site_dir/images", 0777 ) ) {
3442          return false;
3443      }
3444  
3445      $images_dir = @opendir( "$default_dir/images" );
3446      if ( $images_dir ) {
3447          while ( ( $image = readdir( $images_dir ) ) !== false ) {
3448              if ( is_dir( "$default_dir/images/$image" ) ) {
3449                  continue;
3450              }
3451  
3452              if ( ! copy( "$default_dir/images/$image", "$site_dir/images/$image" ) ) {
3453                  return;
3454              }
3455  
3456              chmod( "$site_dir/images/$image", 0777 );
3457          }
3458  
3459          closedir( $images_dir );
3460      }
3461  }
3462  
3463  /**
3464   * Creates a site theme.
3465   *
3466   * {@internal Missing Long Description}}
3467   *
3468   * @since 1.5.0
3469   *
3470   * @return string|false
3471   */
3472  function make_site_theme() {
3473      // Name the theme after the blog.
3474      $theme_name = __get_option( 'blogname' );
3475      $template   = sanitize_title( $theme_name );
3476      $site_dir   = WP_CONTENT_DIR . "/themes/$template";
3477  
3478      // If the theme already exists, nothing to do.
3479      if ( is_dir( $site_dir ) ) {
3480          return false;
3481      }
3482  
3483      // We must be able to write to the themes dir.
3484      if ( ! is_writable( WP_CONTENT_DIR . '/themes' ) ) {
3485          return false;
3486      }
3487  
3488      umask( 0 );
3489      if ( ! mkdir( $site_dir, 0777 ) ) {
3490          return false;
3491      }
3492  
3493      if ( file_exists( ABSPATH . 'wp-layout.css' ) ) {
3494          if ( ! make_site_theme_from_oldschool( $theme_name, $template ) ) {
3495              // TODO: rm -rf the site theme directory.
3496              return false;
3497          }
3498      } else {
3499          if ( ! make_site_theme_from_default( $theme_name, $template ) ) {
3500              // TODO: rm -rf the site theme directory.
3501              return false;
3502          }
3503      }
3504  
3505      // Make the new site theme active.
3506      $current_template = __get_option( 'template' );
3507      if ( WP_DEFAULT_THEME == $current_template ) {
3508          update_option( 'template', $template );
3509          update_option( 'stylesheet', $template );
3510      }
3511      return $template;
3512  }
3513  
3514  /**
3515   * Translate user level to user role name.
3516   *
3517   * @since 2.0.0
3518   *
3519   * @param int $level User level.
3520   * @return string User role name.
3521   */
3522  function translate_level_to_role( $level ) {
3523      switch ( $level ) {
3524          case 10:
3525          case 9:
3526          case 8:
3527              return 'administrator';
3528          case 7:
3529          case 6:
3530          case 5:
3531              return 'editor';
3532          case 4:
3533          case 3:
3534          case 2:
3535              return 'author';
3536          case 1:
3537              return 'contributor';
3538          case 0:
3539          default:
3540              return 'subscriber';
3541      }
3542  }
3543  
3544  /**
3545   * Checks the version of the installed MySQL binary.
3546   *
3547   * @since 2.1.0
3548   *
3549   * @global wpdb $wpdb WordPress database abstraction object.
3550   */
3551  function wp_check_mysql_version() {
3552      global $wpdb;
3553      $result = $wpdb->check_database_version();
3554      if ( is_wp_error( $result ) ) {
3555          wp_die( $result );
3556      }
3557  }
3558  
3559  /**
3560   * Disables the Automattic widgets plugin, which was merged into core.
3561   *
3562   * @since 2.2.0
3563   */
3564  function maybe_disable_automattic_widgets() {
3565      $plugins = __get_option( 'active_plugins' );
3566  
3567      foreach ( (array) $plugins as $plugin ) {
3568          if ( 'widgets.php' === basename( $plugin ) ) {
3569              array_splice( $plugins, array_search( $plugin, $plugins, true ), 1 );
3570              update_option( 'active_plugins', $plugins );
3571              break;
3572          }
3573      }
3574  }
3575  
3576  /**
3577   * Disables the Link Manager on upgrade if, at the time of upgrade, no links exist in the DB.
3578   *
3579   * @since 3.5.0
3580   *
3581   * @global int  $wp_current_db_version The old (current) database version.
3582   * @global wpdb $wpdb                  WordPress database abstraction object.
3583   */
3584  function maybe_disable_link_manager() {
3585      global $wp_current_db_version, $wpdb;
3586  
3587      if ( $wp_current_db_version >= 22006 && get_option( 'link_manager_enabled' ) && ! $wpdb->get_var( "SELECT link_id FROM $wpdb->links LIMIT 1" ) ) {
3588          update_option( 'link_manager_enabled', 0 );
3589      }
3590  }
3591  
3592  /**
3593   * Runs before the schema is upgraded.
3594   *
3595   * @since 2.9.0
3596   *
3597   * @global int  $wp_current_db_version The old (current) database version.
3598   * @global wpdb $wpdb                  WordPress database abstraction object.
3599   */
3600  function pre_schema_upgrade() {
3601      global $wp_current_db_version, $wpdb;
3602  
3603      // Upgrade versions prior to 2.9.
3604      if ( $wp_current_db_version < 11557 ) {
3605          // Delete duplicate options. Keep the option with the highest option_id.
3606          $wpdb->query( "DELETE o1 FROM $wpdb->options AS o1 JOIN $wpdb->options AS o2 USING (`option_name`) WHERE o2.option_id > o1.option_id" );
3607  
3608          // Drop the old primary key and add the new.
3609          $wpdb->query( "ALTER TABLE $wpdb->options DROP PRIMARY KEY, ADD PRIMARY KEY(option_id)" );
3610  
3611          // Drop the old option_name index. dbDelta() doesn't do the drop.
3612          $wpdb->query( "ALTER TABLE $wpdb->options DROP INDEX option_name" );
3613      }
3614  
3615      // Multisite schema upgrades.
3616      if ( $wp_current_db_version < 25448 && is_multisite() && wp_should_upgrade_global_tables() ) {
3617  
3618          // Upgrade versions prior to 3.7.
3619          if ( $wp_current_db_version < 25179 ) {
3620              // New primary key for signups.
3621              $wpdb->query( "ALTER TABLE $wpdb->signups ADD signup_id BIGINT(20) NOT NULL AUTO_INCREMENT PRIMARY KEY FIRST" );
3622              $wpdb->query( "ALTER TABLE $wpdb->signups DROP INDEX domain" );
3623          }
3624  
3625          if ( $wp_current_db_version < 25448 ) {
3626              // Convert archived from enum to tinyint.
3627              $wpdb->query( "ALTER TABLE $wpdb->blogs CHANGE COLUMN archived archived varchar(1) NOT NULL default '0'" );
3628              $wpdb->query( "ALTER TABLE $wpdb->blogs CHANGE COLUMN archived archived tinyint(2) NOT NULL default 0" );
3629          }
3630      }
3631  
3632      // Upgrade versions prior to 4.2.
3633      if ( $wp_current_db_version < 31351 ) {
3634          if ( ! is_multisite() && wp_should_upgrade_global_tables() ) {
3635              $wpdb->query( "ALTER TABLE $wpdb->usermeta DROP INDEX meta_key, ADD INDEX meta_key(meta_key(191))" );
3636          }
3637          $wpdb->query( "ALTER TABLE $wpdb->terms DROP INDEX slug, ADD INDEX slug(slug(191))" );
3638          $wpdb->query( "ALTER TABLE $wpdb->terms DROP INDEX name, ADD INDEX name(name(191))" );
3639          $wpdb->query( "ALTER TABLE $wpdb->commentmeta DROP INDEX meta_key, ADD INDEX meta_key(meta_key(191))" );
3640          $wpdb->query( "ALTER TABLE $wpdb->postmeta DROP INDEX meta_key, ADD INDEX meta_key(meta_key(191))" );
3641          $wpdb->query( "ALTER TABLE $wpdb->posts DROP INDEX post_name, ADD INDEX post_name(post_name(191))" );
3642      }
3643  
3644      // Upgrade versions prior to 4.4.
3645      if ( $wp_current_db_version < 34978 ) {
3646          // If compatible termmeta table is found, use it, but enforce a proper index and update collation.
3647          if ( $wpdb->get_var( "SHOW TABLES LIKE '{$wpdb->termmeta}'" ) && $wpdb->get_results( "SHOW INDEX FROM {$wpdb->termmeta} WHERE Column_name = 'meta_key'" ) ) {
3648              $wpdb->query( "ALTER TABLE $wpdb->termmeta DROP INDEX meta_key, ADD INDEX meta_key(meta_key(191))" );
3649              maybe_convert_table_to_utf8mb4( $wpdb->termmeta );
3650          }
3651      }
3652  }
3653  
3654  /**
3655   * Determine if global tables should be upgraded.
3656   *
3657   * This function performs a series of checks to ensure the environment allows
3658   * for the safe upgrading of global WordPress database tables. It is necessary
3659   * because global tables will commonly grow to millions of rows on large
3660   * installations, and the ability to control their upgrade routines can be
3661   * critical to the operation of large networks.
3662   *
3663   * In a future iteration, this function may use `wp_is_large_network()` to more-
3664   * intelligently prevent global table upgrades. Until then, we make sure
3665   * WordPress is on the main site of the main network, to avoid running queries
3666   * more than once in multi-site or multi-network environments.
3667   *
3668   * @since 4.3.0
3669   *
3670   * @return bool Whether to run the upgrade routines on global tables.
3671   */
3672  function wp_should_upgrade_global_tables() {
3673  
3674      // Return false early if explicitly not upgrading.
3675      if ( defined( 'DO_NOT_UPGRADE_GLOBAL_TABLES' ) ) {
3676          return false;
3677      }
3678  
3679      // Assume global tables should be upgraded.
3680      $should_upgrade = true;
3681  
3682      // Set to false if not on main network (does not matter if not multi-network).
3683      if ( ! is_main_network() ) {
3684          $should_upgrade = false;
3685      }
3686  
3687      // Set to false if not on main site of current network (does not matter if not multi-site).
3688      if ( ! is_main_site() ) {
3689          $should_upgrade = false;
3690      }
3691  
3692      /**
3693       * Filters if upgrade routines should be run on global tables.
3694       *
3695       * @since 4.3.0
3696       *
3697       * @param bool $should_upgrade Whether to run the upgrade routines on global tables.
3698       */
3699      return apply_filters( 'wp_should_upgrade_global_tables', $should_upgrade );
3700  }


Generated : Thu Apr 18 08:20:02 2024 Cross-referenced by PHPXref