• Publicidad

Búsqueda de archivos

¿Apenas comienzas con Perl? En este foro podrás encontrar y hacer preguntas básicas de Perl con respuestas aptas a tu nivel.

Búsqueda de archivos

Notapor coltx » 2016-04-25 12:10 @549

Estimados, tengo un problema. En el siguiente script pretendo buscar los archivos PDF de unas facturas que estoy rescatando de la BD. El tema es que si bien en la BD tengo varios números de factura el script siempre me imprime el primer PDF que encuentra:

Sintáxis: [ Descargar ] [ Ocultar ]
Using perl Syntax Highlighting
  1. #!/usr/bin/perl
  2.  
  3. use DBI;
  4. use File::Find;
  5.  
  6. my $database = "FACTURAS";
  7. my $data_source= "DBI:mysql:$database;" ;
  8. my $username = "usuariodb";
  9. my $password = "db2016";
  10.  
  11. my $sql = DBI->connect($data_source,$username,$password)
  12. or die "Couldn't connect to database: " . DBI->errstr;
  13.  
  14. $arrayI= $sql -> prepare ("SELECT fac_numero FROM Factura")
  15. or die $sql->errstr();
  16. $arrayI->execute() or die $arrayI->errstr();
  17. while(my @rowI = $arrayI->fetchrow_array)
  18. {
  19.    $NUMERO_FACTURA=@rowI[0];
  20.    $DIR="PDF/IN";
  21.    
  22.      find(\&buscar, $DIR);
  23.      sub buscar{
  24.        my $elemento = $_;
  25.        if(-f $elemento && $elemento =~ /$NUMERO_FACTURA.pdf$/)
  26.         {
  27.           print "$File::Find::name\n";
  28.         }
  29.                                        
  30.       }
  31. }
Coloreado en 0.003 segundos, usando GeSHi 1.0.8.4

Si tengo las facturas 1010, 1020, 1030 y 1040 en la BD, al ejecutar el script me muestra lo siguiente:

INV000001010.pdf
INV000001010.pdf
INV000001010.pdf
INV000001010.pdf

siendo que para las demás facturas también hay archivos pdf, me repite la primera factura encontrada.
coltx
Perlero nuevo
Perlero nuevo
 
Mensajes: 79
Registrado: 2011-09-16 08:01 @376

Publicidad

Re: Búsqueda de archivos.

Notapor audax » 2016-04-25 13:46 @615

Hola, coltx. Estoy viendo que tu while se está ejecutando cuatro veces (por cada línea en tu BD), y que cada vez está buscando el mismo elemento $NUMERO_FACTURA=@rowI[0]; por eso te está arrojando el mismo archivo. Como solución ejecútalo solo una vez. salu2
audax
Perlero nuevo
Perlero nuevo
 
Mensajes: 56
Registrado: 2013-06-03 13:16 @594

Re: Búsqueda de archivos

Notapor explorer » 2016-04-25 16:20 @722

Pues... audax no ha acertado ;)

Cambia la línea 27, de

print "$File::Find::name\n"

a

print "$NUMERO_FACTURA $File::Find::name\n"

y te llevarás una sorpresa. Verás que $NUMERO_FACTURA no cambia en cada vuelta del while(). Aunque estás cambiando la variable en la línea 19, no cambia dentro de la línea 25. ¿Por qué? Pues porque la definición de la subrutina buscar() solo sucede una vez, la primera vez que Perl se la encuentra. Como $NUMERO_FACTURA vale '1010', y está declarada dentro del propio bucle while (es local en ese ámbito), pues queda así para el resto del programa.

Hay varias soluciones. Una de ellas es declarar $NUMERO_FACTURA como variable global, fuera del bucle:

my $NUMERO_FACTURA;
while (...) {
# lo demás, igual
}


Hay otros problemas... @rowI[0] es incorrecto. Aunque te está funcionando, la forma correcta es $rowI[0], ya que lo que queremos ahí es recuperar un solo valor, y de ahí hace falta cambiar el '@' por un '$'. Si no, estarás ejecutando una sentencia en contexto de lista, y te puede llevar a sorpresas, en el futuro.

Yo no usaría el módulo File::Find. Si sé, más o menos, cómo se llama el archivo que busco, y sé el directorio dónde buscar, pues es fácil resolverlo.

Sintáxis: [ Descargar ] [ Ocultar ]
Using perl Syntax Highlighting
  1. #!/usr/bin/env perl
  2. use v5.14;
  3. use autodie;
  4.  
  5. use DBI;
  6.  
  7. my $database    = "FACTURAS";
  8. my $data_source = "DBI:mysql:$database;" ;
  9. my $username    = "usuariodb";
  10. my $password    = "db2016";
  11. my $DIR         = "PDF/IN";
  12.  
  13. my $dbh = DBI->connect($data_source, $username, $password)
  14.         or die "Couldn't connect to database: " . DBI->errstr;
  15.  
  16. my $sth = $dbh->prepare ("SELECT fac_numero FROM Factura")
  17.         or die $dbh->errstr();
  18.  
  19. $sth->execute()
  20.         or die $sth->errstr();
  21.  
  22. while (my @rowI = $sth->fetchrow_array) {
  23.     my $NUMERO_FACTURA = $rowI[0];
  24.  
  25.     # recorremos todos los archivos que coinciden con el patrón
  26.     for my $archivo  (glob "$DIR/*$NUMERO_FACTURA.pdf") {
  27.         say "$NUMERO_FACTURA:$archivo";
  28.     }
  29. }
  30.  
Coloreado en 0.001 segundos, usando GeSHi 1.0.8.4

glob() permite usar comodines como los del shell, así que solo tenemos que buscar por "*$NUMERO_FACTURA.pdf", y listo.
JF^D Perl programming & Raku programming. Grupo en Telegram: https://t.me/Perl_ES
Avatar de Usuario
explorer
Administrador
Administrador
 
Mensajes: 14476
Registrado: 2005-07-24 18:12 @800
Ubicación: Valladolid, España

Re: Búsqueda de archivos

Notapor coltx » 2016-04-26 12:18 @554

Con glob() es mucho mejor ya que conozco los directorios en dónde buscar. Muchas gracias por todo, explorer. ¡Me funcionó perfecto!
coltx
Perlero nuevo
Perlero nuevo
 
Mensajes: 79
Registrado: 2011-09-16 08:01 @376


Volver a Básico

¿Quién está conectado?

Usuarios navegando por este Foro: No hay usuarios registrados visitando el Foro y 10 invitados