wordpresscronwpmu

Network Wide Cron Scheduling on Wordpress Multisite


I'm using WP Cron to schedule a network wide cron from a plugin.

I want to run the cron hourly no matter what blog it is activated from. Most importantly, I need to prevent the cron from running multiple times from different sites on the network.

Is there a way to set this using WordPress scheduling system?


Solution

  • wp-cron on multisite is (sub)domain dependent, so each instance is separate. So a call from  a.site.com is a completely separate instance from a call from b.site.com

    That means, by default, there's no way to stop it running more than once per network when you have the plugin running on more than one instance if the code which activates the cron can be run from any site in that network.

    There's a few ways that I can think of to get around this:

    1) (This is untested but I think it might work) There's a constant that you can define in wp-config called WP_CRON_LOCK_TIMEOUT which you could define as 3600. That would mean that all cron processes could only run once every hour. Not sure if that's an option for what you're after.

    2) Stop wp-cron running by itself and then set a server cron job to fire the wp-cron every hour in a crontab. You'd do define( 'DISABLE_WP_CRON', true ); in wp-config and then in the crontab just do a curl http://site.com/wp-cron.php to run every 3600 seconds (or wget instead of curl)

    3) You could set a network-wide site option which gets updated by the wp-cron when it's first run on the hour. You'd need to build in a check in the script which runs the cron job to get this option and see if the time stored is less than 3600 seconds ago. If it is, then don't allow the cron to run. If it isn't, then run the cron and update the site-wide option with the current time. (see add_site_option() update_site_option() and get_site_option() are essentially the same as their single-site counterparts, but are network-wide )

    4) There's a 'premium' plugin which basically spawns a PHP background process that runs independently of anyone visiting your site. By default it runs every 60 seconds, but it'd be easy to change that. http://codecanyon.net/item/improved-cron/176543

    wp-cron.php doesn't really give you any actions or filters, it does set transients which you could possibly look into trying to test, but I don't think that is the way forward.

    There are some really useful (free) plugins for cron:

    http://wordpress.org/extend/plugins/wp-crontrol/

    http://wordpress.org/extend/plugins/wp-cron-control/

    http://wordpress.org/extend/plugins/cron-view/