Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to get partial output when script is executing?

Tags:

javascript

php

Description:

I have a script which do multiple actions in longer time. In standard situation output from PHP script is sent after full execution of this script. User may be dissapointed if my script will load very long time without any response.

Problem to solve:

Let's say I have in this script a loop which will be working 10 times. After each one execution I want to get output to browser "Element X finished. Y time.". Value of X and Y will be changing.

Question:

Is there any way to reach that effect? Maybe with some kind of call from this script to new script which will sent data to browser throug AJAX.

Or is there any way to reach this effect only with PHP implementation?

EDIT:

I see that I have to clarify the matter. I want this information to appear dynamically on the page. I tried with output buffer functions already, and it still don't work as I need it. Output in browser is showing after full execute of script. Test code:

for ($i = 0; $i <= 10; $i++) {
    ob_start();
        
    echo "Output " . $i . "<br />";
        
    ob_flush(); //also only flush() etc.
    

    sleep(1);
}
like image 794
Xarvalus Avatar asked Dec 21 '13 10:12

Xarvalus


1 Answers

Yes, it should be achieveable with PHP alone. I remember seeing some code related to this when I was tracing through wordpress a while back, when it updates modules, it has to ftp, unzip, copy files, etc, which take a long time, and it likes to keep the user updated with what it's doing at the moment... after inspecting their send_message() function, and reading the PHP ob_flush() page, i think you want:

echo "stuff\n"; // adding a newline may be important here,
                // a lot of io routines use some variant of get_line()
ob_end_flush(); // to get php's internal buffers out into the operating system
flush(); // to tell the operating system to flush it's buffers to the user.

The people at the php manual also implied that it might help to explicitly set a header() with the mime-type and character set in it, so the browser would know that at the start and wouldn't wait for the entire binary object to become available before attempting to decypher what sort of entity it had.

If that doesn't work you'd need to further modify your system php.ini to turn output buffering and compression off, at which point you may as well go look at an ajax solution.

An ajax solution would look something like:

Your script spits out some html/javascript to hit an ajax request, flushes all it's buffers, and stops concerning itself with the user, then starts some operation, or perhaps merely indicates that some large operation is to commence in a database somewhere for a cron job to pick up. The javascript on your page would have a timer loop to poll an ajax endpoint for status until the ajax replied that it was complete. The ajax endpoint would check on the status of your task by querying the database, or examining output files, etc, and spit all it knew out at once and terminate, letting the client decide when to ask it if things were done again. It is a much more involved and complicated endevour with more moving parts, but achieves a very nice end product for the user, if it's worth your time to craft.

like image 125
Fluffycloud Avatar answered Sep 30 '22 20:09

Fluffycloud