NAME IO::Default - replace select() with $DEFOUT, $DEFERR, $DEFIN SYNOPSIS use IO::Default; open LOG, ">/var/log/my.log"; $DEFOUT = LOG; # instead of select(LOG); open $DEFERR, ">/var/log/my.err"; warn "Badness!"; # sends to $DEFERR $DEFIN = \*STDIN; # barewords or globs work @data = <>; # reads from $DEFIN now use FileHandle; # provide OO file methods $DEFOUT = \*MYFILE; # need to use globs if want OO $DEFOUT->autoflush(1); # set $| on whatever $DEFOUT is $DEFERR->autoflush(1); # ditto $DEFIN->untaint; # untaint default input stream DESCRIPTION Currently, Perl provides a somewhat clumsy way of manipulating the default filehandle, and no easy way of manipulating default error and input handles. This module serves the dual purpose of providing a means around this, as well as serving as a prototype for a proposed Perl 6 feature. This module replaces the use of select() and the default filehandle with three variables, $DEFOUT, $DEFERR, and $DEFIN, that are the default output, input, and error filehandles. By default, they point to STDOUT, STDERR, and nothing, respectively. The reason $DEFIN doesn't do anything until you assign to it is because assigning to it wipes out @ARGV. See the BUGS below. To change what the default filehandle is for output, simply assign a filehandle or filehandle glob to $DEFOUT: open LOG, ">/var/log/my.log" or die; $DEFOUT = LOG; # bare filehandles ok print "Here's some data"; # goes to LOG The same can be easily done with $DEFERR for default errors: open ERR, ">/var/log/my.err" or die; $DEFERR = \*ERR unless $have_a_tty; # glob refs ok too warn "Danger, Will Robinson!"; # goes to ERR Finally, this module changes the semantics of <> if you assign to $DEFIN. Normally, the <> ARGV filehandle will iterate through command line arguments. This is still the default. However, if you explicitly assign a filehandle to $DEFIN, then this changes the semantics and input is instead read from the handle: open MOTD, "); # just reads /etc/motd Why do this? Well, passing filehandles in and out of functions is a pain in Perl 5, requiring you to use globs. If you simply want to change the default input for a sub function somewhere, have it read from <>: sub get_data { my @data = <>; # do more stuff return @data; } Then from the top level do something like this: # Figure out our input stream $DEFIN = get_handle || \*STDIN; @data = get_data; And now you don't have to pass filehandles in and out of functions anymore just for dealing with default input and output. Note that here <> and <$DEFIN> are synonymous. BUGS This module should NOT be used in production code because it is considered unstable and subject to change. Unfortunately, getting $DEFIN to work in Perl 5 is hairy, since ARGV is so special. As such, assigning to $DEFIN will wipe out whatever you have in @ARGV at the time. It also can't set $ARGV, since the file that was opened is unknown. Luckily, if you never assign or access $DEFIN, then <> retains its magic powers, so if you don't like this simply don't use $DEFIN. This module really just does some trickery to reopen the STD filehandles and point them to different places. As such, mixing print calls to $DEFERR and STDERR will send the output to the same place (contrary to the Perl 6 proposal). REFERENCES For complete details on the Perl 6 proposal, please visit http://dev.perl.org/rfc/129.html. Comments are welcome. AUTHOR Copyright (c) 2000, Nathan Wiger . All Rights Reserved. This module is free software; you may copy this under the terms of the GNU General Public License, or the Artistic License, copies of which should have accompanied your Perl kit.