How can I run a PHP script in the background, without the web page hanging, while logging errors to a log file?
I know I can use this command, exec("php -f background.php >/dev/null 2>&1 &");, but this won't output errors to a log file.
background.php is executed in the background when a user submits a form.
This is the script that runs after the user has submitted the form (this is not the background script):
# Execute the script in the background Linux style. Writes errors to a log file.
exec("php -f background.php 2>&1 &", $error_result);
# If $error_result is not empty, there was an error (2>&1).
if(!empty($error_result))
{
# If $error_result is an array, convert it to a string seperated by PHP End of Line.
if(is_array($error_result))
{
$error_result=implode(PHP_EOL, $error_result);
}
# Get the Logger Class.
require_once Utility::locateFile(MODULES.'Logger'.DS.'Logger.php');
# Create a new Logger object, and set the log file to use.
$logger_obj=new Logger('command_line.log');
# Write exec() output to log file.
$logger_obj->writeLogFile($error_result);
# Close log file.
$logger_obj->closeLogFile();
}
The above script works, but the page hangs until the background script has finished.
EDIT: So, I gather from the answers and comments there is no way to do this using the $error_result parameter, and my Logger class.
I am going to try to add a try and catch in the background.php and see if I can log the errors that way.
still run exec("php -f background.php >/dev/null 2>&1 &");
but in the file add:
ini_set("log_errors","1");
ini_set("error_log",'path/to/erroor.txt');
make sure you include a path if not the file will be created in the users home, the user will depend on how this is run (probably php).
If you want to output error stream to an external log file, you can do it like this:
exec("php background.php 1>/dev/null 2>background.log &", $output, $error_code);
In this case we redirect STDOUT to /dev/null and STDERR to file background.log, and run background.php in background because of final &. You don't need -f option for php.
You can actually skip $output and $error_code. I included them here so I could explain that $output will always be empty array, and $error_code will always be 0. All they mean is that OS (Linux) successfully created another process in background.
Since 1) background.php is run in background and exec command will return immediately, and 2) $output and $error_code will not tell you if something went wrong, you would need to check for errors somewhere else by checking background.log.
Let me know if my explanation is not very clear, and I will try to elaborate.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With