I discovered that I have 29,000 cron jobs in my WordPress database from deactivated and deleted plugins. I have tried a number of optimizer plugins but the huge number of cron jobs means I can't delete them using plugins.

I also tried this in my functions.php without success:

add_action("init", "clear_crons_left");
function clear_crons_left() {
    wp_clear_scheduled_hook("cron_name");
}

Is there any SQL command I can use in phpmyadmin to search by cron hook and remove them?

up vote 18 down vote accepted

Thanks Privateer for the prompt reply and advice.

I found a way around it before I saw your answer. Here is a step-by-step method for deleting thousands of old cron jobs and may be of use to someone else.

I logged on to phpMyAdmin. I clicked on my database and then the 'search' tab. I typed in 'cron' then selected 'all tables' and clicked 'Go'. I scrolled down the search results list to my wp_options table. I clicked 'Browse'. At the top of the list was option_name 'cron'. I clicked 'Edit' then waited for the page to load. I clicked on the box that showed the list of cron jobs. The cron list was so long that it took about 80 seconds for my cursor to respond. I then used Ctrl-A on the keyboard to select all before hitting the delete button. It took about 2 minutes before my browser completed the deletion (chrome timed-out so I tried Firefox which worked).

After another couple of minutes the cron jobs for my current active plugins re-populated the list. There were 9 cron jobs (down from over 29,000!). Six years of duplicate cron jobs from badly coded plugins, some of which I just installed for a day to try out. Also hundreds from common plugins such as Wordfence, BackupBuddy, Nextgen Gallery, and AutoOptimizer - all of which I had uninstalled in the past. My site now loads like it's been turbo-charged. The admin area is much quicker. Admin timeout errors have disappeared. I had spent so much time on optimising my website trying to decrease the load time. I even moved hosts and upgraded my hosting plans. Nothing increased the speed of my site like deleting all the outdated cron jobs. Mobile download time decreased from 20 seconds to 6 seconds. Desktop download time decreased from about 12 to 4 seconds.

In my search for a solution I found very little information on the effect of cron jobs on website performance. Many said it made little difference and for a small number of cron jobs that's true. But years into the life of a WordPress site I wonder how many are bloated with hundreds if not thousands of old cron jobs from deleted plugins. Instead of asking users to check their php memory limit I would suggest that developers first ask users to check the number of cron jobs in wp_options when problem-solving fatal memory errors. You may be surprised/shocked at what you find! :-)

  • 1
    I found the same problem. I don't now how much cron jobs I had , but it was around 15 Mb in database. After deletion admin area load time decrased from 5-7 to 0.3 seconds. Frontend load time decreased from 2 to 0.4 sec. – Alexey Sep 5 '15 at 20:10
  • 1
    damn it! this solution saved us! had 35000 cron jobs in this table. now it seems turbocharged as described. – Riccardo Sep 14 '15 at 11:41
  • Very good to know indeed since I was thinking to install one of the mentioned plugins for a client. So now I know what to look out for when performance slowly deteriorates. – lowtechsun Jun 27 at 22:24

Try

SELECT * FROM `wp_options` WHERE option_name = 'cron'

If you find it you might try:

  • In SQL: UPDATE wp_options SET option_value = '' WHERE option_name = 'cron'
  • In wordpress: update_option('cron', '');

You might need to either delete the cron option or set the value to an empty serialized array.

Using update_option would be safer as I'm not certain as to whether the value should be a serialized empty array or an empty string. You could check in wp-includes/options.php though ... but using update_option will handle it properly without worrying about the database.

An even simpler solution is to call delete_option( 'cron' ); once in some plugin. All automatically added cron jobs will get added again on the next visit/request of your site.

As a one case (mu) plugin that only runs whenever you activate it:

<?php
/** Plugin Name: Clean Cron */
register_activation_hook( __FILE__, function()
{
    delete_option( 'cron' );
} );
  • Thanks kaiser! For those not comfortable with creating/editing plugins (it is simple!), you can use what kaiser noted in your functions.php file. Just add it, save it, load your site, then remove it and save it again. – Privateer Oct 10 '15 at 20:02
  • What about cron jobs that have been created on plugin activation? These cron jobs would not be recreated until you de- and reactivate the plugin. – alpipego Mar 15 '16 at 21:30
  • Well, that's not possible per default, neither with this nor with the other questions. What you would have to do is to either de- and reactivate those plugins (~3 minutes of work), or – in case you are searching for an automated answer – search up the functions in those plugins and trigger them from within your plugin. – kaiser Mar 15 '16 at 21:36

Wordpress cron events can also be cleared from the command line, using WP-CLI:

wp cron event list
wp cron event delete your_example_event

More details in the wp-cli docs.

  • 1
    Or delete all events wp option delete cron – Samuel Elh Apr 19 at 22:12

In case someone wanted to clear a specific cron name (say 'CRON_NAME'), this solution worked for me:

    $crons = _get_cron_array();
    //echo "Found total ".count($crons)."<br />";
    //Keep only the ones that don't match the cron name
    $updated = array_filter($crons, function($v){return !array_key_exists("CRON_NAME",$v);});
    //echo "Reduced to ".count($updated)."<br />";        
    _set_cron_array($updated);

I had an year full of pending cron jobs, about 5 Mb data for this single database entry. Deleted the cron jobs from the database. Disabled cron jobs in wp-config.php

Set up a manual cron job in cpanel. Now my site is literally flying. I had been upgrading servers, buying more CPU/RAM, but all was a waste of money and time.

To delete all pending cron jobs run this query in phpmyadmin>Run query:

UPDATE wp_options SET option_value = '' WHERE option_name = 'cron'

Thanks a lot Pádraig Ó Beirn.

  • You're welcome Preetinder! I'm delighted it was of help. Thanks for the tip on pending cron jobs as well. – Pádraig Ó Beirn Jan 12 '17 at 19:16

If you clear your cron tasks this way and you use UpdraftPlus, you will need to re-save your settings in order to regenerate the cron tasks. Until you do this, your automated backups will not run (but manual backups will).

The settings will still be there, and you don't need to edit anything. Just go to [UpdraftPlus top menu]->Settings, and the scroll down to the bottom and click "Save Changes".

I got here because of the huge amount of sm_ping cronjobs in wp_options. If that is your problem, you could try the following :

Put this in functions.php (child theme) if you don't have access to phpmyadmin, especially if your site is bloated with ping cronjobs (sm_ping) :

if (isset($_GET['doing_wp_cron'])) {
remove_action('do_pings', 'do_all_pings');
wp_clear_scheduled_hook('do_pings');
}

I ran into a similar issue, where because of one of my own coding errors, thousands of copies of one particular cron job had been added to a site. The wp_clear_scheduled_hook function appeared to time out and fail. I got around it with a script that unset all instances of the cron function within the array and then adds the filtered array as the new cron option in the options table. See below.

In this way, I avoided blowing away the desirable cron jobs previously added to the site.

This could be modified as a function that takes an array of handles to eliminate or an array of handles to be preserved.

$crons = _get_cron_array();
    $hook = 'tj_flush_w3tc_cache';
    foreach ( $crons as $timestamp => $cron ) {
    if ( isset( $cron[ $hook ] ) ) {
        unset($cron[$hook]);
    }
    if(!empty($cron))
        $newcron[$timestamp] = $cron;       
    }
    update_option('cron',$newcron);

Your Answer

By clicking "Post Your Answer", you acknowledge that you have read our updated terms of service, privacy policy and cookie policy, and that your continued use of the website is subject to these policies.

Not the answer you're looking for? Browse other questions tagged or ask your own question.