2009-02-06 6 views
9

Estoy tratando de manejar la posibilidad de que no se pasen argumentos ni datos interconectados a una secuencia de comandos de Perl. Supongo que si no hay argumentos, la entrada se canaliza a través de STDIN. Sin embargo, si el usuario no proporciona argumentos y no canaliza nada a la secuencia de comandos, intentará ingresar el teclado. Mi objetivo es proporcionar un mensaje de error en su lugar.¿Cómo puedo verificar (mirar) STDIN para datos de canalización en Perl sin usar seleccionar?

Desafortunadamente, select() no es portátil para algunos sistemas que no sean POSIX. ¿Hay alguna otra manera de hacer esto con la máxima portabilidad?

Respuesta

19

Perl viene con el operador -t-test de archivos, que te dice si un gestor de archivo en particular está abierto a un TTY. Por lo tanto, usted debe ser capaz de hacer esto:

if (-t STDIN and not @ARGV) { 
    # We're talking to a terminal, but have no command line arguments. 
    # Complain loudly. 
} 
else { 
    # We're either reading from a file or pipe, or we have arguments in 
    # @ARGV to process. 
} 

Una prueba rápida revela que esto funciona bien en Windows con Perl 5.10.0, y Linux con Perl 5.8.8, por lo que debe ser portable a través del Perl más común ambientes.

Como han mencionado otros, select no sería una opción confiable ya que puede haber momentos en los que esté leyendo un proceso, pero ese proceso aún no ha comenzado a escribirse.

Todo lo mejor,

Paul

+0

Confirmado para funcionar en Mac OS X. +5 si pudiera, pero no puedo, así que +1. –

5
use POSIX 'isatty'; 
if (! @ARGV && isatty(*STDIN)) { 
    die "usage: ..."; 
} 

Ver: http://www.opengroup.org/onlinepubs/009695399/functions/isatty.html

Tenga en cuenta que seleccione no sería de mucha ayuda de todos modos, ya que producir resultados falsos si la información por tubería no estaba lista todavía. Ejemplo:

seq 100000|grep 99999|perl -we'$rin="";vec($rin,fileno(STDIN),1)=1;print 0+select($rin,"","",.01)' 
+0

Esto no es mejor que 'Select()', que está utilizando POSIX también. El OP dijo específicamente: * Desafortunadamente, select() no es portátil para algunos sistemas que no son POSIX. * – nyuszika7h

+0

Estoy explicando qué sería mejor que seleccionar donde la portabilidad no POSIX no es una preocupación. – ysth

Cuestiones relacionadas