How to run background tasks in PHP

This post is mostly to introduce some cool ways of doing tasks in PHP, that you may not be aware of. The recommended approach for anything like this is to use a cron job however.

One of things I often do in PHP is create code that needs to run occasionally and perform some function that can take several minutes or more. A good example of this would be parsing an uploaded file into a structured format like a database. You don’t want to keep the user waiting for this, and you may not always have the option to do it properly via a cron job.

An alternative solution exists, and that is to call the task after the page has been loaded. You do this by ignoring a dropped browser connection, via the function ignore_user_abort(). PHP scripts are basically limited by two factors: The maximum execution time, which defaults to 30 seconds, and the connection to the web browser. If the maximum execution time is passed, PHP will kill the script. If the user aborts, A.K.A hits the stop button in their browser, the PHP script will also be killed. You bypass both of these by doing this:

<?php
ignore_user_abort();
set_time_limit(0); // No time limit

Now the next issue is to not tie up the web browser. We can do this pretty easily as well:

<?php
ignore_user_abort();
set_time_limit(0);

ob_start(); // This is required
include 'somefile.php';

echo $someString;

$content_size = ob_get_length();
$content = ob_get_contents();
ob_end_clean();

header( 'Content-Length: ' . $content_size );
header( 'Connection: close' );
echo $content;
flush();

// The browser should no longer show the page loading bar and should 
// consider the page fully loaded. Nothing else that you output will 
// be displayed to the user
echo "I'm never seen!";

Now, one thing to keep in mind is that by setting ignore_user_abort() and the time limit to zero, if your script enters an infinite loop nothing will stop it. The PHP interpreter or web server will likely need to be reloaded. Be careful 🙂

Here’s a case that I used this for recently. I have a script that admins can use to reload a gigantic cache. I use the above code to render a barebones page with a bit of JavaScript that polls a static file and displays the contents of that static file in a designated div. The rest of the script writes to that static file everytime a cache is regenerated. That way the user can see the progress of the cache building operation. I also use lock files to prevent the cache from being rebuilt multiple times simultaneously.

Recommended Reading:

One Reply to “How to run background tasks in PHP”

  1. Thanks bro, what if i set time limit to 30 minutes when my script has enters an loop, does it would end on 30 minutes ? even theres error on that loop

Leave a Reply