Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

PHP Inotify Non-blocking way

Tags:

linux

php

I am reading a file in linux which is a log file that keeps on updating weather the file has changed and output it to the webpage. i do it using php inotify but my problem is that it is blocking.

How can i make php inotify non-blocking so i can do other stuff while it is monitoring the text file?.

<?php

$fd = inotify_init();


$watch_descriptor = inotify_add_watch($fd, '/tmp/temp.txt', IN_MODIFY);


touch('/tmp/temp.txt');


    $events = inotify_read($fd);

    $contents = file_get_contents('/tmp/temp.txt');
    echo $contents;


inotify_rm_watch($fd, $watch_descriptor);
fclose($fd)

?>

Or can i do this in java?..Thanks.

like image 707
demic0de Avatar asked Oct 29 '12 14:10

demic0de


3 Answers

Yes you can. Did you take a look at the Manual? It provides non-blocking event callback examples? If this answer doesn't adequately answer you, please add more information.

http://php.net/manual/en/function.inotify-init.php

// Open an inotify instance
$fd = inotify_init();

// - Using stream_set_blocking() on $fd
stream_set_blocking($fd, 0);

// Watch __FILE__ for metadata changes (e.g. mtime)
$watch_descriptor = inotify_add_watch($fd, __FILE__, IN_ATTRIB);

// generate an event
touch(__FILE__);

// this is a loop
while(true){

  $events = inotify_read($fd); // Does no block, and return false if no events are pending  

  // do other stuff here, break when you want...
}

// Stop watching __FILE__ for metadata changes
inotify_rm_watch($fd, $watch_descriptor);

// Close the inotify instance
// This may have closed all watches if this was not already done
fclose($fd);
like image 141
Layke Avatar answered Oct 13 '22 05:10

Layke


It's like Layke said. You can have it either blocking or non-blocking. If it's non-blocking you have to poll. I think what you want is blocking in a multithreaded way. One thread works in blocking or non-blocking, frequent polling, mode whilst the other thread does something else.

like image 21
Seb Avatar answered Oct 13 '22 03:10

Seb


I suggest that it will be much easier to this thing by using node.js.

You only need the code below: (filename:watch.js)

    var fs = require('fs');
    var file = '/tmp/temp.txt/';
    fs.watchFile(file, function (curr, prev) {
        console.log('the current mtime is: ' + curr.mtime);
        console.log('the previous mtime was: ' + prev.mtime);
    });

then you can run it:

    node watch.js

It will run persistently.

The node.js using javascript to write server-side program, it has non-blocking I/O model. It can help you do this kind of thing easily.

Here is some related document fs.watchFile

like image 22
srain Avatar answered Oct 13 '22 03:10

srain