home *** CD-ROM | disk | FTP | other *** search
/ HTML Examples / WP.iso / wordpress / wp-includes / update.php < prev    next >
Encoding:
PHP Script  |  2018-02-06  |  24.1 KB  |  763 lines

  1. <?php
  2. /**
  3.  * A simple set of functions to check our version 1.0 update service.
  4.  *
  5.  * @package WordPress
  6.  * @since 2.3.0
  7.  */
  8.  
  9. /**
  10.  * Check WordPress version against the newest version.
  11.  *
  12.  * The WordPress version, PHP version, and Locale is sent. Checks against the
  13.  * WordPress server at api.wordpress.org server. Will only check if WordPress
  14.  * isn't installing.
  15.  *
  16.  * @since 2.3.0
  17.  * @global string $wp_version Used to check against the newest WordPress version.
  18.  * @global wpdb   $wpdb
  19.  * @global string $wp_local_package
  20.  *
  21.  * @param array $extra_stats Extra statistics to report to the WordPress.org API.
  22.  * @param bool  $force_check Whether to bypass the transient cache and force a fresh update check. Defaults to false, true if $extra_stats is set.
  23.  */
  24. function wp_version_check( $extra_stats = array(), $force_check = false ) {
  25.     if ( wp_installing() ) {
  26.         return;
  27.     }
  28.  
  29.     global $wpdb, $wp_local_package;
  30.     // include an unmodified $wp_version
  31.     include( ABSPATH . WPINC . '/version.php' );
  32.     $php_version = phpversion();
  33.  
  34.     $current = get_site_transient( 'update_core' );
  35.     $translations = wp_get_installed_translations( 'core' );
  36.  
  37.     // Invalidate the transient when $wp_version changes
  38.     if ( is_object( $current ) && $wp_version != $current->version_checked )
  39.         $current = false;
  40.  
  41.     if ( ! is_object($current) ) {
  42.         $current = new stdClass;
  43.         $current->updates = array();
  44.         $current->version_checked = $wp_version;
  45.     }
  46.  
  47.     if ( ! empty( $extra_stats ) )
  48.         $force_check = true;
  49.  
  50.     // Wait 60 seconds between multiple version check requests
  51.     $timeout = 60;
  52.     $time_not_changed = isset( $current->last_checked ) && $timeout > ( time() - $current->last_checked );
  53.     if ( ! $force_check && $time_not_changed ) {
  54.         return;
  55.     }
  56.  
  57.     /**
  58.      * Filters the locale requested for WordPress core translations.
  59.      *
  60.      * @since 2.8.0
  61.      *
  62.      * @param string $locale Current locale.
  63.      */
  64.     $locale = apply_filters( 'core_version_check_locale', get_locale() );
  65.  
  66.     // Update last_checked for current to prevent multiple blocking requests if request hangs
  67.     $current->last_checked = time();
  68.     set_site_transient( 'update_core', $current );
  69.  
  70.     if ( method_exists( $wpdb, 'db_version' ) )
  71.         $mysql_version = preg_replace('/[^0-9.].*/', '', $wpdb->db_version());
  72.     else
  73.         $mysql_version = 'N/A';
  74.  
  75.     if ( is_multisite() ) {
  76.         $user_count = get_user_count();
  77.         $num_blogs = get_blog_count();
  78.         $wp_install = network_site_url();
  79.         $multisite_enabled = 1;
  80.     } else {
  81.         $user_count = count_users();
  82.         $user_count = $user_count['total_users'];
  83.         $multisite_enabled = 0;
  84.         $num_blogs = 1;
  85.         $wp_install = home_url( '/' );
  86.     }
  87.  
  88.     $query = array(
  89.         'version'            => $wp_version,
  90.         'php'                => $php_version,
  91.         'locale'             => $locale,
  92.         'mysql'              => $mysql_version,
  93.         'local_package'      => isset( $wp_local_package ) ? $wp_local_package : '',
  94.         'blogs'              => $num_blogs,
  95.         'users'              => $user_count,
  96.         'multisite_enabled'  => $multisite_enabled,
  97.         'initial_db_version' => get_site_option( 'initial_db_version' ),
  98.     );
  99.  
  100.     /**
  101.      * Filter the query arguments sent as part of the core version check.
  102.      *
  103.      * WARNING: Changing this data may result in your site not receiving security updates.
  104.      * Please exercise extreme caution.
  105.      *
  106.      * @since 4.9.0
  107.      *
  108.      * @param array $query {
  109.      *     Version check query arguments. 
  110.      *
  111.      *     @type string $version            WordPress version number.
  112.      *     @type string $php                PHP version number.
  113.      *     @type string $locale             The locale to retrieve updates for.
  114.      *     @type string $mysql              MySQL version number.
  115.      *     @type string $local_package      The value of the $wp_local_package global, when set.
  116.      *     @type int    $blogs              Number of sites on this WordPress installation.
  117.      *     @type int    $users              Number of users on this WordPress installation.
  118.      *     @type int    $multisite_enabled  Whether this WordPress installation uses Multisite.
  119.      *     @type int    $initial_db_version Database version of WordPress at time of installation.
  120.      * }
  121.      */
  122.     $query = apply_filters( 'core_version_check_query_args', $query );
  123.  
  124.     $post_body = array(
  125.         'translations' => wp_json_encode( $translations ),
  126.     );
  127.  
  128.     if ( is_array( $extra_stats ) )
  129.         $post_body = array_merge( $post_body, $extra_stats );
  130.  
  131.     $url = $http_url = 'http://api.wordpress.org/core/version-check/1.7/?' . http_build_query( $query, null, '&' );
  132.     if ( $ssl = wp_http_supports( array( 'ssl' ) ) )
  133.         $url = set_url_scheme( $url, 'https' );
  134.  
  135.     $doing_cron = wp_doing_cron();
  136.  
  137.     $options = array(
  138.         'timeout' => $doing_cron ? 30 : 3,
  139.         'user-agent' => 'WordPress/' . $wp_version . '; ' . home_url( '/' ),
  140.         'headers' => array(
  141.             'wp_install' => $wp_install,
  142.             'wp_blog' => home_url( '/' )
  143.         ),
  144.         'body' => $post_body,
  145.     );
  146.  
  147.     $response = wp_remote_post( $url, $options );
  148.     if ( $ssl && is_wp_error( $response ) ) {
  149.         trigger_error(
  150.             sprintf(
  151.                 /* translators: %s: support forums URL */
  152.                 __( 'An unexpected error occurred. Something may be wrong with WordPress.org or this server’s configuration. If you continue to have problems, please try the <a href="%s">support forums</a>.' ),
  153.                 __( 'https://wordpress.org/support/' )
  154.             ) . ' ' . __( '(WordPress could not establish a secure connection to WordPress.org. Please contact your server administrator.)' ),
  155.             headers_sent() || WP_DEBUG ? E_USER_WARNING : E_USER_NOTICE
  156.         );
  157.         $response = wp_remote_post( $http_url, $options );
  158.     }
  159.  
  160.     if ( is_wp_error( $response ) || 200 != wp_remote_retrieve_response_code( $response ) ) {
  161.         return;
  162.     }
  163.  
  164.     $body = trim( wp_remote_retrieve_body( $response ) );
  165.     $body = json_decode( $body, true );
  166.  
  167.     if ( ! is_array( $body ) || ! isset( $body['offers'] ) ) {
  168.         return;
  169.     }
  170.  
  171.     $offers = $body['offers'];
  172.  
  173.     foreach ( $offers as &$offer ) {
  174.         foreach ( $offer as $offer_key => $value ) {
  175.             if ( 'packages' == $offer_key )
  176.                 $offer['packages'] = (object) array_intersect_key( array_map( 'esc_url', $offer['packages'] ),
  177.                     array_fill_keys( array( 'full', 'no_content', 'new_bundled', 'partial', 'rollback' ), '' ) );
  178.             elseif ( 'download' == $offer_key )
  179.                 $offer['download'] = esc_url( $value );
  180.             else
  181.                 $offer[ $offer_key ] = esc_html( $value );
  182.         }
  183.         $offer = (object) array_intersect_key( $offer, array_fill_keys( array( 'response', 'download', 'locale',
  184.             'packages', 'current', 'version', 'php_version', 'mysql_version', 'new_bundled', 'partial_version', 'notify_email', 'support_email', 'new_files' ), '' ) );
  185.     }
  186.  
  187.     $updates = new stdClass();
  188.     $updates->updates = $offers;
  189.     $updates->last_checked = time();
  190.     $updates->version_checked = $wp_version;
  191.  
  192.     if ( isset( $body['translations'] ) )
  193.         $updates->translations = $body['translations'];
  194.  
  195.     set_site_transient( 'update_core', $updates );
  196.  
  197.     if ( ! empty( $body['ttl'] ) ) {
  198.         $ttl = (int) $body['ttl'];
  199.         if ( $ttl && ( time() + $ttl < wp_next_scheduled( 'wp_version_check' ) ) ) {
  200.             // Queue an event to re-run the update check in $ttl seconds.
  201.             wp_schedule_single_event( time() + $ttl, 'wp_version_check' );
  202.         }
  203.     }
  204.  
  205.     // Trigger background updates if running non-interactively, and we weren't called from the update handler.
  206.     if ( $doing_cron && ! doing_action( 'wp_maybe_auto_update' ) ) {
  207.         do_action( 'wp_maybe_auto_update' );
  208.     }
  209. }
  210.  
  211. /**
  212.  * Check plugin versions against the latest versions hosted on WordPress.org.
  213.  *
  214.  * The WordPress version, PHP version, and Locale is sent along with a list of
  215.  * all plugins installed. Checks against the WordPress server at
  216.  * api.wordpress.org. Will only check if WordPress isn't installing.
  217.  *
  218.  * @since 2.3.0
  219.  * @global string $wp_version Used to notify the WordPress version.
  220.  *
  221.  * @param array $extra_stats Extra statistics to report to the WordPress.org API.
  222.  */
  223. function wp_update_plugins( $extra_stats = array() ) {
  224.     if ( wp_installing() ) {
  225.         return;
  226.     }
  227.  
  228.     // include an unmodified $wp_version
  229.     include( ABSPATH . WPINC . '/version.php' );
  230.  
  231.     // If running blog-side, bail unless we've not checked in the last 12 hours
  232.     if ( !function_exists( 'get_plugins' ) )
  233.         require_once( ABSPATH . 'wp-admin/includes/plugin.php' );
  234.  
  235.     $plugins = get_plugins();
  236.     $translations = wp_get_installed_translations( 'plugins' );
  237.  
  238.     $active  = get_option( 'active_plugins', array() );
  239.     $current = get_site_transient( 'update_plugins' );
  240.     if ( ! is_object($current) )
  241.         $current = new stdClass;
  242.  
  243.     $new_option = new stdClass;
  244.     $new_option->last_checked = time();
  245.  
  246.     $doing_cron = wp_doing_cron();
  247.  
  248.     // Check for update on a different schedule, depending on the page.
  249.     switch ( current_filter() ) {
  250.         case 'upgrader_process_complete' :
  251.             $timeout = 0;
  252.             break;
  253.         case 'load-update-core.php' :
  254.             $timeout = MINUTE_IN_SECONDS;
  255.             break;
  256.         case 'load-plugins.php' :
  257.         case 'load-update.php' :
  258.             $timeout = HOUR_IN_SECONDS;
  259.             break;
  260.         default :
  261.             if ( $doing_cron ) {
  262.                 $timeout = 2 * HOUR_IN_SECONDS;
  263.             } else {
  264.                 $timeout = 12 * HOUR_IN_SECONDS;
  265.             }
  266.     }
  267.  
  268.     $time_not_changed = isset( $current->last_checked ) && $timeout > ( time() - $current->last_checked );
  269.  
  270.     if ( $time_not_changed && ! $extra_stats ) {
  271.         $plugin_changed = false;
  272.         foreach ( $plugins as $file => $p ) {
  273.             $new_option->checked[ $file ] = $p['Version'];
  274.  
  275.             if ( !isset( $current->checked[ $file ] ) || strval($current->checked[ $file ]) !== strval($p['Version']) )
  276.                 $plugin_changed = true;
  277.         }
  278.  
  279.         if ( isset ( $current->response ) && is_array( $current->response ) ) {
  280.             foreach ( $current->response as $plugin_file => $update_details ) {
  281.                 if ( ! isset($plugins[ $plugin_file ]) ) {
  282.                     $plugin_changed = true;
  283.                     break;
  284.                 }
  285.             }
  286.         }
  287.  
  288.         // Bail if we've checked recently and if nothing has changed
  289.         if ( ! $plugin_changed ) {
  290.             return;
  291.         }
  292.     }
  293.  
  294.     // Update last_checked for current to prevent multiple blocking requests if request hangs
  295.     $current->last_checked = time();
  296.     set_site_transient( 'update_plugins', $current );
  297.  
  298.     $to_send = compact( 'plugins', 'active' );
  299.  
  300.     $locales = array_values( get_available_languages() );
  301.  
  302.     /**
  303.      * Filters the locales requested for plugin translations.
  304.      *
  305.      * @since 3.7.0
  306.      * @since 4.5.0 The default value of the `$locales` parameter changed to include all locales.
  307.      *
  308.      * @param array $locales Plugin locales. Default is all available locales of the site.
  309.      */
  310.     $locales = apply_filters( 'plugins_update_check_locales', $locales );
  311.     $locales = array_unique( $locales );
  312.  
  313.     if ( $doing_cron ) {
  314.         $timeout = 30;
  315.     } else {
  316.         // Three seconds, plus one extra second for every 10 plugins
  317.         $timeout = 3 + (int) ( count( $plugins ) / 10 );
  318.     }
  319.  
  320.     $options = array(
  321.         'timeout' => $timeout,
  322.         'body' => array(
  323.             'plugins'      => wp_json_encode( $to_send ),
  324.             'translations' => wp_json_encode( $translations ),
  325.             'locale'       => wp_json_encode( $locales ),
  326.             'all'          => wp_json_encode( true ),
  327.         ),
  328.         'user-agent' => 'WordPress/' . $wp_version . '; ' . home_url( '/' )
  329.     );
  330.  
  331.     if ( $extra_stats ) {
  332.         $options['body']['update_stats'] = wp_json_encode( $extra_stats );
  333.     }
  334.  
  335.     $url = $http_url = 'http://api.wordpress.org/plugins/update-check/1.1/';
  336.     if ( $ssl = wp_http_supports( array( 'ssl' ) ) )
  337.         $url = set_url_scheme( $url, 'https' );
  338.  
  339.     $raw_response = wp_remote_post( $url, $options );
  340.     if ( $ssl && is_wp_error( $raw_response ) ) {
  341.         trigger_error(
  342.             sprintf(
  343.                 /* translators: %s: support forums URL */
  344.                 __( 'An unexpected error occurred. Something may be wrong with WordPress.org or this server’s configuration. If you continue to have problems, please try the <a href="%s">support forums</a>.' ),
  345.                 __( 'https://wordpress.org/support/' )
  346.             ) . ' ' . __( '(WordPress could not establish a secure connection to WordPress.org. Please contact your server administrator.)' ),
  347.             headers_sent() || WP_DEBUG ? E_USER_WARNING : E_USER_NOTICE
  348.         );
  349.         $raw_response = wp_remote_post( $http_url, $options );
  350.     }
  351.  
  352.     if ( is_wp_error( $raw_response ) || 200 != wp_remote_retrieve_response_code( $raw_response ) ) {
  353.         return;
  354.     }
  355.  
  356.     $response = json_decode( wp_remote_retrieve_body( $raw_response ), true );
  357.     foreach ( $response['plugins'] as &$plugin ) {
  358.         $plugin = (object) $plugin;
  359.         if ( isset( $plugin->compatibility ) ) {
  360.             $plugin->compatibility = (object) $plugin->compatibility;
  361.             foreach ( $plugin->compatibility as &$data ) {
  362.                 $data = (object) $data;
  363.             }
  364.         }
  365.     }
  366.     unset( $plugin, $data );
  367.     foreach ( $response['no_update'] as &$plugin ) {
  368.         $plugin = (object) $plugin;
  369.     }
  370.     unset( $plugin );
  371.  
  372.     if ( is_array( $response ) ) {
  373.         $new_option->response = $response['plugins'];
  374.         $new_option->translations = $response['translations'];
  375.         // TODO: Perhaps better to store no_update in a separate transient with an expiry?
  376.         $new_option->no_update = $response['no_update'];
  377.     } else {
  378.         $new_option->response = array();
  379.         $new_option->translations = array();
  380.         $new_option->no_update = array();
  381.     }
  382.  
  383.     set_site_transient( 'update_plugins', $new_option );
  384. }
  385.  
  386. /**
  387.  * Check theme versions against the latest versions hosted on WordPress.org.
  388.  *
  389.  * A list of all themes installed in sent to WP. Checks against the
  390.  * WordPress server at api.wordpress.org. Will only check if WordPress isn't
  391.  * installing.
  392.  *
  393.  * @since 2.7.0
  394.  *
  395.  * @param array $extra_stats Extra statistics to report to the WordPress.org API.
  396.  */
  397. function wp_update_themes( $extra_stats = array() ) {
  398.     if ( wp_installing() ) {
  399.         return;
  400.     }
  401.  
  402.     // include an unmodified $wp_version
  403.     include( ABSPATH . WPINC . '/version.php' );
  404.  
  405.     $installed_themes = wp_get_themes();
  406.     $translations = wp_get_installed_translations( 'themes' );
  407.  
  408.     $last_update = get_site_transient( 'update_themes' );
  409.     if ( ! is_object($last_update) )
  410.         $last_update = new stdClass;
  411.  
  412.     $themes = $checked = $request = array();
  413.  
  414.     // Put slug of current theme into request.
  415.     $request['active'] = get_option( 'stylesheet' );
  416.  
  417.     foreach ( $installed_themes as $theme ) {
  418.         $checked[ $theme->get_stylesheet() ] = $theme->get('Version');
  419.  
  420.         $themes[ $theme->get_stylesheet() ] = array(
  421.             'Name'       => $theme->get('Name'),
  422.             'Title'      => $theme->get('Name'),
  423.             'Version'    => $theme->get('Version'),
  424.             'Author'     => $theme->get('Author'),
  425.             'Author URI' => $theme->get('AuthorURI'),
  426.             'Template'   => $theme->get_template(),
  427.             'Stylesheet' => $theme->get_stylesheet(),
  428.         );
  429.     }
  430.  
  431.     $doing_cron = wp_doing_cron();
  432.  
  433.     // Check for update on a different schedule, depending on the page.
  434.     switch ( current_filter() ) {
  435.         case 'upgrader_process_complete' :
  436.             $timeout = 0;
  437.             break;
  438.         case 'load-update-core.php' :
  439.             $timeout = MINUTE_IN_SECONDS;
  440.             break;
  441.         case 'load-themes.php' :
  442.         case 'load-update.php' :
  443.             $timeout = HOUR_IN_SECONDS;
  444.             break;
  445.         default :
  446.             if ( $doing_cron ) {
  447.                 $timeout = 2 * HOUR_IN_SECONDS;
  448.             } else {
  449.                 $timeout = 12 * HOUR_IN_SECONDS;
  450.             }
  451.     }
  452.  
  453.     $time_not_changed = isset( $last_update->last_checked ) && $timeout > ( time() - $last_update->last_checked );
  454.  
  455.     if ( $time_not_changed && ! $extra_stats ) {
  456.         $theme_changed = false;
  457.         foreach ( $checked as $slug => $v ) {
  458.             if ( !isset( $last_update->checked[ $slug ] ) || strval($last_update->checked[ $slug ]) !== strval($v) )
  459.                 $theme_changed = true;
  460.         }
  461.  
  462.         if ( isset ( $last_update->response ) && is_array( $last_update->response ) ) {
  463.             foreach ( $last_update->response as $slug => $update_details ) {
  464.                 if ( ! isset($checked[ $slug ]) ) {
  465.                     $theme_changed = true;
  466.                     break;
  467.                 }
  468.             }
  469.         }
  470.  
  471.         // Bail if we've checked recently and if nothing has changed
  472.         if ( ! $theme_changed ) {
  473.             return;
  474.         }
  475.     }
  476.  
  477.     // Update last_checked for current to prevent multiple blocking requests if request hangs
  478.     $last_update->last_checked = time();
  479.     set_site_transient( 'update_themes', $last_update );
  480.  
  481.     $request['themes'] = $themes;
  482.  
  483.     $locales = array_values( get_available_languages() );
  484.  
  485.     /**
  486.      * Filters the locales requested for theme translations.
  487.      *
  488.      * @since 3.7.0
  489.      * @since 4.5.0 The default value of the `$locales` parameter changed to include all locales.
  490.      *
  491.      * @param array $locales Theme locales. Default is all available locales of the site.
  492.      */
  493.     $locales = apply_filters( 'themes_update_check_locales', $locales );
  494.     $locales = array_unique( $locales );
  495.  
  496.     if ( $doing_cron ) {
  497.         $timeout = 30;
  498.     } else {
  499.         // Three seconds, plus one extra second for every 10 themes
  500.         $timeout = 3 + (int) ( count( $themes ) / 10 );
  501.     }
  502.  
  503.     $options = array(
  504.         'timeout' => $timeout,
  505.         'body' => array(
  506.             'themes'       => wp_json_encode( $request ),
  507.             'translations' => wp_json_encode( $translations ),
  508.             'locale'       => wp_json_encode( $locales ),
  509.         ),
  510.         'user-agent'    => 'WordPress/' . $wp_version . '; ' . home_url( '/' )
  511.     );
  512.  
  513.     if ( $extra_stats ) {
  514.         $options['body']['update_stats'] = wp_json_encode( $extra_stats );
  515.     }
  516.  
  517.     $url = $http_url = 'http://api.wordpress.org/themes/update-check/1.1/';
  518.     if ( $ssl = wp_http_supports( array( 'ssl' ) ) )
  519.         $url = set_url_scheme( $url, 'https' );
  520.  
  521.     $raw_response = wp_remote_post( $url, $options );
  522.     if ( $ssl && is_wp_error( $raw_response ) ) {
  523.         trigger_error(
  524.             sprintf(
  525.                 /* translators: %s: support forums URL */
  526.                 __( 'An unexpected error occurred. Something may be wrong with WordPress.org or this server’s configuration. If you continue to have problems, please try the <a href="%s">support forums</a>.' ),
  527.                 __( 'https://wordpress.org/support/' )
  528.             ) . ' ' . __( '(WordPress could not establish a secure connection to WordPress.org. Please contact your server administrator.)' ),
  529.             headers_sent() || WP_DEBUG ? E_USER_WARNING : E_USER_NOTICE
  530.         );
  531.         $raw_response = wp_remote_post( $http_url, $options );
  532.     }
  533.  
  534.     if ( is_wp_error( $raw_response ) || 200 != wp_remote_retrieve_response_code( $raw_response ) ) {
  535.         return;
  536.     }
  537.  
  538.     $new_update = new stdClass;
  539.     $new_update->last_checked = time();
  540.     $new_update->checked = $checked;
  541.  
  542.     $response = json_decode( wp_remote_retrieve_body( $raw_response ), true );
  543.  
  544.     if ( is_array( $response ) ) {
  545.         $new_update->response     = $response['themes'];
  546.         $new_update->translations = $response['translations'];
  547.     }
  548.  
  549.     set_site_transient( 'update_themes', $new_update );
  550. }
  551.  
  552. /**
  553.  * Performs WordPress automatic background updates.
  554.  *
  555.  * @since 3.7.0
  556.  */
  557. function wp_maybe_auto_update() {
  558.     include_once( ABSPATH . '/wp-admin/includes/admin.php' );
  559.     include_once( ABSPATH . '/wp-admin/includes/class-wp-upgrader.php' );
  560.  
  561.     $upgrader = new WP_Automatic_Updater;
  562.     $upgrader->run();
  563. }
  564.  
  565. /**
  566.  * Retrieves a list of all language updates available.
  567.  *
  568.  * @since 3.7.0
  569.  *
  570.  * @return array
  571.  */
  572. function wp_get_translation_updates() {
  573.     $updates = array();
  574.     $transients = array( 'update_core' => 'core', 'update_plugins' => 'plugin', 'update_themes' => 'theme' );
  575.     foreach ( $transients as $transient => $type ) {
  576.         $transient = get_site_transient( $transient );
  577.         if ( empty( $transient->translations ) )
  578.             continue;
  579.  
  580.         foreach ( $transient->translations as $translation ) {
  581.             $updates[] = (object) $translation;
  582.         }
  583.     }
  584.     return $updates;
  585. }
  586.  
  587. /**
  588.  * Collect counts and UI strings for available updates
  589.  *
  590.  * @since 3.3.0
  591.  *
  592.  * @return array
  593.  */
  594. function wp_get_update_data() {
  595.     $counts = array( 'plugins' => 0, 'themes' => 0, 'wordpress' => 0, 'translations' => 0 );
  596.  
  597.     if ( $plugins = current_user_can( 'update_plugins' ) ) {
  598.         $update_plugins = get_site_transient( 'update_plugins' );
  599.         if ( ! empty( $update_plugins->response ) )
  600.             $counts['plugins'] = count( $update_plugins->response );
  601.     }
  602.  
  603.     if ( $themes = current_user_can( 'update_themes' ) ) {
  604.         $update_themes = get_site_transient( 'update_themes' );
  605.         if ( ! empty( $update_themes->response ) )
  606.             $counts['themes'] = count( $update_themes->response );
  607.     }
  608.  
  609.     if ( ( $core = current_user_can( 'update_core' ) ) && function_exists( 'get_core_updates' ) ) {
  610.         $update_wordpress = get_core_updates( array('dismissed' => false) );
  611.         if ( ! empty( $update_wordpress ) && ! in_array( $update_wordpress[0]->response, array('development', 'latest') ) && current_user_can('update_core') )
  612.             $counts['wordpress'] = 1;
  613.     }
  614.  
  615.     if ( ( $core || $plugins || $themes ) && wp_get_translation_updates() )
  616.         $counts['translations'] = 1;
  617.  
  618.     $counts['total'] = $counts['plugins'] + $counts['themes'] + $counts['wordpress'] + $counts['translations'];
  619.     $titles = array();
  620.     if ( $counts['wordpress'] ) {
  621.         /* translators: 1: Number of updates available to WordPress */
  622.         $titles['wordpress'] = sprintf( __( '%d WordPress Update'), $counts['wordpress'] );
  623.     }
  624.     if ( $counts['plugins'] ) {
  625.         /* translators: 1: Number of updates available to plugins */
  626.         $titles['plugins'] = sprintf( _n( '%d Plugin Update', '%d Plugin Updates', $counts['plugins'] ), $counts['plugins'] );
  627.     }
  628.     if ( $counts['themes'] ) {
  629.         /* translators: 1: Number of updates available to themes */
  630.         $titles['themes'] = sprintf( _n( '%d Theme Update', '%d Theme Updates', $counts['themes'] ), $counts['themes'] );
  631.     }
  632.     if ( $counts['translations'] ) {
  633.         $titles['translations'] = __( 'Translation Updates' );
  634.     }
  635.  
  636.     $update_title = $titles ? esc_attr( implode( ', ', $titles ) ) : '';
  637.  
  638.     $update_data = array( 'counts' => $counts, 'title' => $update_title );
  639.     /**
  640.      * Filters the returned array of update data for plugins, themes, and WordPress core.
  641.      *
  642.      * @since 3.5.0
  643.      *
  644.      * @param array $update_data {
  645.      *     Fetched update data.
  646.      *
  647.      *     @type array   $counts       An array of counts for available plugin, theme, and WordPress updates.
  648.      *     @type string  $update_title Titles of available updates.
  649.      * }
  650.      * @param array $titles An array of update counts and UI strings for available updates.
  651.      */
  652.     return apply_filters( 'wp_get_update_data', $update_data, $titles );
  653. }
  654.  
  655. /**
  656.  * Determines whether core should be updated.
  657.  *
  658.  * @since 2.8.0
  659.  *
  660.  * @global string $wp_version
  661.  */
  662. function _maybe_update_core() {
  663.     // include an unmodified $wp_version
  664.     include( ABSPATH . WPINC . '/version.php' );
  665.  
  666.     $current = get_site_transient( 'update_core' );
  667.  
  668.     if ( isset( $current->last_checked, $current->version_checked ) &&
  669.         12 * HOUR_IN_SECONDS > ( time() - $current->last_checked ) &&
  670.         $current->version_checked == $wp_version ) {
  671.         return;
  672.     }
  673.     wp_version_check();
  674. }
  675. /**
  676.  * Check the last time plugins were run before checking plugin versions.
  677.  *
  678.  * This might have been backported to WordPress 2.6.1 for performance reasons.
  679.  * This is used for the wp-admin to check only so often instead of every page
  680.  * load.
  681.  *
  682.  * @since 2.7.0
  683.  * @access private
  684.  */
  685. function _maybe_update_plugins() {
  686.     $current = get_site_transient( 'update_plugins' );
  687.     if ( isset( $current->last_checked ) && 12 * HOUR_IN_SECONDS > ( time() - $current->last_checked ) )
  688.         return;
  689.     wp_update_plugins();
  690. }
  691.  
  692. /**
  693.  * Check themes versions only after a duration of time.
  694.  *
  695.  * This is for performance reasons to make sure that on the theme version
  696.  * checker is not run on every page load.
  697.  *
  698.  * @since 2.7.0
  699.  * @access private
  700.  */
  701. function _maybe_update_themes() {
  702.     $current = get_site_transient( 'update_themes' );
  703.     if ( isset( $current->last_checked ) && 12 * HOUR_IN_SECONDS > ( time() - $current->last_checked ) )
  704.         return;
  705.     wp_update_themes();
  706. }
  707.  
  708. /**
  709.  * Schedule core, theme, and plugin update checks.
  710.  *
  711.  * @since 3.1.0
  712.  */
  713. function wp_schedule_update_checks() {
  714.     if ( ! wp_next_scheduled( 'wp_version_check' ) && ! wp_installing() )
  715.         wp_schedule_event(time(), 'twicedaily', 'wp_version_check');
  716.  
  717.     if ( ! wp_next_scheduled( 'wp_update_plugins' ) && ! wp_installing() )
  718.         wp_schedule_event(time(), 'twicedaily', 'wp_update_plugins');
  719.  
  720.     if ( ! wp_next_scheduled( 'wp_update_themes' ) && ! wp_installing() )
  721.         wp_schedule_event(time(), 'twicedaily', 'wp_update_themes');
  722. }
  723.  
  724. /**
  725.  * Clear existing update caches for plugins, themes, and core.
  726.  *
  727.  * @since 4.1.0
  728.  */
  729. function wp_clean_update_cache() {
  730.     if ( function_exists( 'wp_clean_plugins_cache' ) ) {
  731.         wp_clean_plugins_cache();
  732.     } else {
  733.         delete_site_transient( 'update_plugins' );
  734.     }
  735.     wp_clean_themes_cache();
  736.     delete_site_transient( 'update_core' );
  737. }
  738.  
  739. if ( ( ! is_main_site() && ! is_network_admin() ) || wp_doing_ajax() ) {
  740.     return;
  741. }
  742.  
  743. add_action( 'admin_init', '_maybe_update_core' );
  744. add_action( 'wp_version_check', 'wp_version_check' );
  745.  
  746. add_action( 'load-plugins.php', 'wp_update_plugins' );
  747. add_action( 'load-update.php', 'wp_update_plugins' );
  748. add_action( 'load-update-core.php', 'wp_update_plugins' );
  749. add_action( 'admin_init', '_maybe_update_plugins' );
  750. add_action( 'wp_update_plugins', 'wp_update_plugins' );
  751.  
  752. add_action( 'load-themes.php', 'wp_update_themes' );
  753. add_action( 'load-update.php', 'wp_update_themes' );
  754. add_action( 'load-update-core.php', 'wp_update_themes' );
  755. add_action( 'admin_init', '_maybe_update_themes' );
  756. add_action( 'wp_update_themes', 'wp_update_themes' );
  757.  
  758. add_action( 'update_option_WPLANG', 'wp_clean_update_cache' , 10, 0 );
  759.  
  760. add_action( 'wp_maybe_auto_update', 'wp_maybe_auto_update' );
  761.  
  762. add_action( 'init', 'wp_schedule_update_checks' );
  763.