How to Run Background PHP Script on WordPress with WP-Cron

Ever received promotional emails from a website? There might be many of them. But how do they have so much time to write and send these emails?

This is a tricky question with a simple answer and that is automating these promotional emails with a background process. This way they don’t have to manually write anything or press any button. The website does that automatically on schedule.

In WordPress, this scheduling of background tasks is done through WP-Cron, a concept that relates to crontab. By following the steps given below, you can easily schedule tasks based on PHP scripts.

Step 1: Adding Interval

Before actually scheduling the task, we need to figure out the time period we want to set for the script. By default WP-Cron provides us with the following time periods built in the WordPress:

  • hourly
  • twicedaily
  • daily
  • weekly

These are the keywords used to create a new task when scheduling with the above intervals. And as their name suggests, it is clear the time period for each keyword.

How about if we want to schedule a task with an interval different from these? For example, we want to run a database check every two hours. For that, we clearly need some code to register the new custom interval. Here is how we do that:

add_filter( 'cron_schedules', 'example_add_cron_interval' );
function example_add_cron_interval( $schedules ) { 
    $schedules['two_hours'] = array(
        'interval' => 2 * 60 * 60,             // Number of Seconds
        'display'  => esc_html__( 'Every Two Hours' ), );
    return $schedules;

This is the required filter to use in this case. You can see the ‘$schedules’ variable is returned from it. And this variable is an array containing the information of intervals. The key of each entry is the keyword we can use to schedule our tasks. For example, in the above case, the keyword is ‘two_hours’. You can use this code in a custom plugin or child theme.

Each entry of the ‘$schedules’ variable is also an array with two properties. First is the ‘interval’ which defines the number of seconds the tasks should be repeated after. So for this case, the interval is 2 * 60 * 60 which is 7200. This is because there are 7200 seconds in two hours. The second property is ‘display’ which is just the description of the interval. This is mostly used in visualizing the scheduled tasks with their intervals.

Step 2: Adding the Hook

After having your required interval decided, the next step is to add an action hook with the function to run from it. This will be used in the next step to schedule the task. This is very simple to achieve. You can do that as below:

add_action( 'bl_cron_hook', 'bl_cron_exec' );

Here the ‘bl_cron_hook’ will be used in the next step to schedule the task. And ‘bl_cron_exec’ is the function name to execute. So for example we can place the following function to send an email:

function bl_cron_exec() {
    $to = "";
    $subject = "Big Discount Offer";
    $message = "Get Upto 50% till 5th of September. Hurry up and don't miss the opportunity";
    wp_mail($to, $subject, $message);

This function will send a message of discount to the email you provide after every two hours.

Step 3: Scheduling Task

Clock for Scheduling

This is the most important part of this tutorial. Here you are going to define a code piece that will be responsible for scheduling the task. In WordPress, scheduling is done with wp_schedule_event() function. This takes three parameters which are timestamp, time interval, and action hook name. Time interval and action hook were defined in the earlier two steps. In order to add timestamp time() is simply used. So the code becomes as follows:

wp_schedule_event( time(), 'two_hours', 'bl_cron_hook' );

As in the code above the time interval created earlier is used here. You can also use the predefined time intervals as explained earlier. Similarly, the bl_cron_hook Hook defined earlier is also used as the third parameter. But before using the wp_schedule_event you might want to confirm if the schedule is not defined yet. This is to avoid redefining it, which might break the recurrence. In order to do that use wp_next_scheduled() function which uses one parameter as the hook name. It returns false if the event is not scheduled yet. So the code becomes as follows:

if ( ! wp_next_scheduled( 'bl_cron_hook' ) ) {
    wp_schedule_event( time(), 'two_hours', 'bl_cron_hook' );

It is recommended to schedule tasks through a custom plugin as unscheduling is a lot easier with that. The scheduled tasks are required to be unscheduled when no longer in use. Just removing the code doesn’t do that. In order to unschedule a task in a plugin, you can use the deactivation hook. An example is as follows:

register_deactivation_hook( __FILE__, 'bl_deactivate' ); 
function bl_deactivate() {
    $timestamp = wp_next_scheduled( 'bl_cron_hook' );
    wp_unschedule_event( $timestamp, 'bl_cron_hook' );

As you can see the wp_next_scheduled function used earlier returns the timestamp if already scheduled. And then wp_unschedule_event uses this timestamp and hook name to unschedule the task. This is done through the deactivation hook, so whenever the plugin will be deactivated it will unschedule the task bl_cron_hook.

For more similar tutorials related to WordPress, visit the WordPress category in the website.

Leave a Comment

Your email address will not be published. Required fields are marked *