WordPress.org

Make WordPress Core

Ticket #17462: 17462.diff

File 17462.diff, 4.1 KB (added by ryan, 7 years ago)
  • wp-includes/cache.php

     
    172172 *
    173173 * @since 2.6.0
    174174 */
    175 function wp_cache_reset() {
     175function wp_cache_reset( $group = '', $key = '' ) {
    176176        global $wp_object_cache;
    177177
    178         return $wp_object_cache->reset();
     178        return $wp_object_cache->reset( $group, $key );
    179179}
    180180
    181181/**
     
    390390         *
    391391         * @since 3.0.0
    392392         */
    393         function reset() {
    394                 // Clear out non-global caches since the blog ID has changed.
    395                 foreach ( array_keys($this->cache) as $group ) {
    396                         if ( !in_array($group, $this->global_groups) )
    397                                 unset($this->cache[$group]);
     393        function reset( $group = '', $id = '' ) {
     394                if ( ! empty( $group ) ) {
     395                        if ( !empty( $id ) ) {
     396                                // Clear out a particular key
     397                                if ( isset( $this->cache[$group][$id] ) )
     398                                        unset( $this->cache[$group][$id] );
     399                        } else {
     400                                // Clear out a particular group
     401                                if ( isset( $this->cache[$group] ) )
     402                                        unset( $this->cache[$group] );
     403                        }
     404                } else {
     405                        // Clear out non-global caches since the blog ID has changed.
     406                        foreach ( array_keys($this->cache) as $group ) {
     407                                if ( !in_array($group, $this->global_groups) )
     408                                        unset($this->cache[$group]);
     409                        }
    398410                }
    399411        }
    400412
  • wp-includes/cron.php

     
    204204        * multiple processes on multiple web servers can run this code concurrently
    205205        * try to make this as atomic as possible by setting doing_cron switch
    206206        */
    207         $flag = get_transient('doing_cron');
     207        $lock = get_transient('doing_cron');
    208208
    209         if ( $flag > $local_time + 10*60 )
    210                 $flag = 0;
     209        if ( $lock > $local_time + 10*60 )
     210                $lock = 0;
    211211
    212212        // don't run if another process is currently running it or more than once every 60 sec.
    213         if ( $flag + 60 > $local_time )
     213        if ( $lock + 60 > $local_time )
    214214                return;
    215215
    216216        //sanity check
     
    227227                        return;
    228228
    229229                set_transient( 'doing_cron', $local_time );
     230                $lock = $local_time;
    230231
    231232                ob_start();
    232233                wp_redirect( add_query_arg('doing_wp_cron', '', stripslashes($_SERVER['REQUEST_URI'])) );
     
    241242        }
    242243
    243244        set_transient( 'doing_cron', $local_time );
     245        $lock = $local_time;
    244246
    245         $cron_url = get_option( 'siteurl' ) . '/wp-cron.php?doing_wp_cron';
     247        $cron_url = get_option( 'siteurl' ) . '/wp-cron.php?lock=' . $lock;
    246248        wp_remote_post( $cron_url, array('timeout' => 0.01, 'blocking' => false, 'sslverify' => apply_filters('https_local_ssl_verify', true)) );
    247249}
    248250
  • wp-cron.php

     
    2626        require_once('./wp-load.php');
    2727}
    2828
     29// Uncached doing_cron transient fetch
     30function _get_cron_lock() {
     31        global $_wp_using_ext_object_cache, $wpdb;
     32
     33        $value = 0;
     34        if ( $_wp_using_ext_object_cache ) {
     35                // Clear the internal cache for the doing_cron transient to force a cache refresh
     36                if ( function_exists( 'wp_cache_reset' ) )
     37                        wp_cache_reset( 'transient', 'doing_cron' );
     38                $value = wp_cache_get( $transient, 'transient' );
     39        } else {
     40                $row = $wpdb->get_row( $wpdb->prepare( "SELECT option_value FROM $wpdb->options WHERE option_name = %s LIMIT 1", '_transient_doing_cron' ) );
     41                if ( is_object( $row ) )
     42                        $value = $row->option_value;
     43        }
     44
     45        return $value;
     46}
     47
    2948if ( false === $crons = _get_cron_array() )
    3049        die();
    3150
     51// Use global $lock otherwise GET lock.
     52if ( empty( $lock ) ) {
     53        if ( empty( $_GET[ 'lock' ] ) )
     54                return;
     55        $lock = $_GET[ 'lock' ];
     56}
     57
    3258$keys = array_keys( $crons );
    3359$local_time = time();
    3460
    3561if ( isset($keys[0]) && $keys[0] > $local_time )
    3662        die();
    3763
     64// Check lock
     65if ( get_transient( 'doing_cron') != $lock )
     66        return;
     67
    3868foreach ($crons as $timestamp => $cronhooks) {
    3969        if ( $timestamp > $local_time )
    4070                break;
     
    5383                        wp_unschedule_event($timestamp, $hook, $v['args']);
    5484
    5585                        do_action_ref_array($hook, $v['args']);
     86
     87                        // Has another cron process grabbed the lock?
     88                        if ( _get_cron_lock() != $lock )
     89                                return;
    5690                }
    5791        }
    5892}