tags:

views:

59

answers:

4

I want to read a log file that is constantly being written to. It resides on the same server as the application. The catch is the file gets written to every few seconds, and I basically want to tail the file on the application in real-time.

Is this possible?

A: 

Just an idea..

Did you think of using the *nix tail command? execute the command from php (with a param that will return a certain number of lines) and process the results in your php script.

andreas
You can be never sure how many lines are written between calls :)
bisko
A: 

you can close the file handle when it is not used(once a portion of data has been written). or you can use a buffer to store the data and put it to the file only when it's full. this way you won't have the file open all the time.

if you want to get everything that is written to the file as soon as it is written there, you might need to extend the code, writing the data, so that it would output to other places too(screen, some variable, other file...)

kgb
+3  A: 

You need to loop with sleep:

$lastpos = 0;
while (true) {
    usleep(300000); //0.3 s
    clearstatcache(false, $file);
    $len = filesize($file);
    if ($len < $lastpos) {
        //file deleted or reset
        $lastpos = $len;
    }
    elseif ($len > $lastpos) {
        $f = fopen($file, "rb");
        if ($f === false)
            die()
        fseek($f, $lastpos);
        while (!feof($f)) {
            $buffer = fread($f, 4096);
            echo $buffer;
        }
        fclose($handle);
    }
}

(untested, but this is the idea)

Artefacto
The page doesn't load... looks it it's stuck in an infite loop
gAMBOOKa
@gAMBOOKa Try adding a flush after the echo. And yes, it's in an infinite loop. Isn't that the point?
Artefacto
A: 

For example :

$log_file = '/tmp/test/log_file.log';

$f = fopen($log_file, 'a+');
$fr = fopen($log_file, 'r' );

for ( $i = 1; $i < 10; $i++ )
{
    fprintf($f, "Line: %u\n", $i);
    sleep(2);
    echo fread($fr, 1024) . "\n";
}

fclose($fr);
fclose($f);

//Or if you want use tail

$f = fopen($log_file, 'a+');

for ( $i = 1; $i < 10; $i++ )
{
    fprintf($f, "Line: %u\n", $i);
    sleep(2);
    $result = array();
    exec( 'tail -n 1 ' . $log_file, $result );
    echo "\n".$result[0];
}

fclose($f);
Miroslav Asenov