AIM/MOTIVATION
I want to write a service, which should run all the time. But it should not be possible to start the service again while it is already running.
USE CASE
User X opens the page myService.php and starts the service by clicking a button on the page. After that closes the browser. After a while an another user opens the browser and tries to start the service. But the service should be started only one time.
(SEMI) PSEUDO CODE
<?php
ignore_user_abort(TRUE);
set_time_limit(0);
$sleepTime = 60;
while(1){
if( serviceAlreadyStarted() ){
echo "Service has already been started.";
exit;
}
if( shouldServiceBeStopped() ){
echo "Service has been stopped.";
exit;
}
// DO SOMETHING
sleep($sleepTime);
}
?>
EXPECTED BEHAVIOUR
On the second call for switching on the service again, the user gets the message immediately.
ACTUAL BEHAVIOUR
The second call of the script gives no response until the first call exited by the second condition shouldServiceBeStopped()
tldr: Don't let the user enter a second loop, check whether the service is running before they can press a button to enter a loop.
I would store a value in a database or a JSON file (ini file is fine too). Then when the user first loads the page, read the value and see if it's already started. You can then display a message directly to the user that the process has already started, rather than have them press a button to start it and then show them a message. It cuts out a step and makes things easier for the user, it should also solve your issue where the second loop keeps running until the first is stopped.
The problem with this is if your script crashes while it is running it will leave the file marked as open. There's two ways to get around this. The first is your stopService function can force the file to exit, and in your where loop, if it detects this value exit. This requires the user stopping the service though. The second way, and the way I'd recommend, is to record the date/time stamp of the service, and every time the loop starts have it update the date/time in the file. Then in your serviceAlreadyStarted() function you can check to see if the date/time is within a valid period. If it's not you know the script crashed and can display an error message to the user.
I noticed you've added a comment that you pretty much do this already, but the file remains open. Make sure that you are closing the file after reading / setting the value, straight away. It's also possible that your loop is executing so fast that it's opening and closing the file too quickly for a second copy to access it too. If that is the case I'd only allow the loop to open the file every 100 or so loops, that should allow other instances of the program to access the file as well.
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