Search code examples
perlprocessreal-timefilehandle

Why does perl allow reading in real time from a process filehandle if I print $_?


I'm writing a perl program that captures the output of another program, and I noticed that in a while <FILEHANDLE> loop (so $_ contains the line read), the following occurs:

open XIN, "-|", "test_xsr"; # not getting in real time! FIX
while (<XIN>) {
    print ".";
}

prints

....

after the program finishes while

open XIN, "-|", "test_xsr"; # not getting in real time! FIX
while (<XIN>) {
    print $_;
}

prints

1
2
3
done

in real time while the program runs. (While I'm testing, the program always produces that output.)

Why does this inconsistency occur?
Is it possible to process output in real time without printing$_?


Solution

  • By default, if STDOUT is connected to a terminal, STDOUT is only flushed when a newline is encountered or when the buffer is full. There's a newline causing the buffer to be flushed in your second snippet, but not in your first snippet.

    Add the following after the print to force the output to be flushed:

    STDOUT->flush();
    

    Add the following to your program to always flush after writing to STDOUT:

    STDOUT->autoflush();
    

    (Older versions of Perl require use IO::Handle qw( ); to use these.)