2010-06-08 9 views
17

Si tengo una línea de comando como:¿Cómo puedo permitir opciones definidas al analizar args con Getopt

my_script.pl -foo -WHATEVER 

Mi script sabe de --foo, y quiero Getopt para establecer la variable $opt_foo, pero no lo sé cualquier cosa acerca de -WHATEVER. ¿Cómo puedo decirle a Getopt que analice las opciones sobre las que le he contado y luego obtenga el resto de los argumentos en una variable de cadena o en una lista?

Un ejemplo:

use strict; 
use warnings; 

use Getopt::Long; 

my $foo; 

GetOptions('foo' => \$foo); 

print 'remaining options: ', @ARGV; 

Entonces, la emisión de

perl getopttest.pl -foo -WHATEVER

da

 
Unknown option: whatever 
remaining options: 

Respuesta

20

es necesario configurar "pass_through" opción través Getopt::Long::Configure("pass_through");

Entonces admite las opciones reales (por ejemplo, las cosas que empieza con "-" y sin el especial "-" delimitador para indicar el final de opciones "reales") .

Aquí es cita perldoc:

  • pass_through (por defecto: desactivado)

    opciones que se desconocen, ambigua o se suministra con un valor de opción inválida se pasan a través de @ARGV en lugar de ser marcado como errores Esto permite escribir scripts de envoltura que procesan solo parte de los argumentos de línea de comando suministrados por el usuario, y pasar las opciones restantes a algún otro programa.

He aquí un ejemplo

$ cat my_script.pl 
#!/usr/local/bin/perl5.8 -w 

use Getopt::Long; 
Getopt::Long::Configure("pass_through"); 
use Data::Dumper; 
my %args; 
GetOptions(\%args, "foo") or die "GetOption returned 0\n"; 
print Data::Dumper->Dump([\@ARGV],["ARGV"]); 

$ ./my_script.pl -foo -WHATEVER   
$ARGV = [ 
      '-WHATEVER' 
     ]; 
+1

A ha, eso explicaría por qué no lo encontré ... :) – Ether

+4

Me resulta absolutamente exasperante leer acerca de una buena opción en el sitio web de Perldoc y luego volver a mi instalación mesoamericana de Perl y encontrar que la opción perfecta exacta He encontrado que requiere un condensador de flujo, o al menos una actualización del módulo CPAN – DVK

+1

¿Estás seguro de que 'pass_through' no está disponible con 5.8? Acabo de comprobar 'perldoc Getopt :: Long' para 5.6.1 (y pensaste que eras prehistórico;)) y está ahí. – Zaid

1

no son los valores restantes (no procesadas) simplemente dejado en @ARGV? Si su contenido extra se inicia con guiones, tendrá que indicar el final de la lista de opciones con un --:

#!/usr/bin/perl 
use strict; 
use warnings; 
use Getopt::Long; 
use Data::Dumper; 

my $foo; 
my $result = GetOptions ("foo" => \$foo); 
print Dumper([ $foo, \@ARGV ]); 

Entonces llamando a:

my_script.pl --foo -- --WHATEVER 

da:

$VAR1 = [ 
      1, 
      [ 
      '--WHATEVER' 
      ] 
     ]; 

PS . En MooseX::Getopt, las opciones "restantes" de la línea de comando se ponen en el atributo extra_argv como un arreglo de matriz, así que recomiendo convertir.

+0

No son si se ven como opciones. En su lugar, se emitirá un error como 'Opción Desconocida: WHATEVER' a STDERR. –

+0

@Robert: tu comentario y mi edición se cruzaron en el éter :) – Ether

+0

:] ¡De hecho! Jaja, agregué un ejemplo así a la pregunta, también. –

0

Creo que la respuesta aquí, lamentablemente, es "no, no hay una manera de hacerlo exactamente como preguntas, usando Getopt :: Long, sin analizar @ARGV por tu cuenta". Ether tiene una solución decente, sin embargo. Es una característica en lo que respecta a la mayoría de las personas que cualquier argumento de opción se captura como un error. Normalmente, se puede hacer

GetOptions('foo' => \$foo) 
    or die "Whups, got options we don't recognize!"; 

para capturar/prevenir opciones impares de ser aprobada, y luego se puede corregir el usuario en el uso. Alternativamente, puede pasar e ignorarlos.

Cuestiones relacionadas