• Publicidad

Subida de ficheros

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

Subida de ficheros

Notapor husanga » 2010-12-06 09:34 @440

Buenas, en estos días he trabajado en relación a la subida de ficheros y he visto lo publicado en el foro varias soluciones que me dan respuestas a mi interrogante, pero queda una y es que cuando tomo los valores del input para guardar la dirección completa de donde he tomado mi archivo, éste automáticamente me toma el nombre del fichero sin realizarle las expresiones regulares para separar el nombre de la dirección.

No sé de por qué ha de pasar esto.

Necesito la dirección porque estoy trabajando con un módulo de Perl llamado File::Copy, pero no encuentro manera alguna de recoger ese valor.

Agradecería mucho su respuesta. Saludos
husanga
Perlero nuevo
Perlero nuevo
 
Mensajes: 3
Registrado: 2010-12-06 09:21 @431

Publicidad

Re: Subida de ficheros

Notapor explorer » 2010-12-06 13:12 @592

Bienvenido a los foros de Perl en Español, husanga.

Sin ver el código, es difícil saber dónde puede estar el error...
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: Subida de ficheros

Notapor husanga » 2010-12-10 13:54 @621

Este es el código:

Sintáxis: [ Descargar ] [ Ocultar ]
  1. <!-- TMPL_INCLUDE NAME="doc-head-open.inc" --> 
  2. <head><title>Subir archivos al servidor</title></head><!-- TMPL_INCLUDE NAME="doc-head-close.inc" --> 
  3. <body> 
  4.  
  5. <!-- TMPL_INCLUDE NAME="calendar.inc" --> 
  6. <form action="/cgi-bin/koha/uploadBooks/uploadBooks.pl" enctype="multipart/form-data"> 
  7. <table id="1" border="2" cellpadding="2" cellspacing="2" bgcolor="#1FAABB" > 
  8. <TR> 
  9.  <TD><input name="autor" type="text" id="autor"> Author</TD></tr><tr> 
  10.   <td><label for="date">Fecha</label> 
  11. <input id="date" type="text" name="date" size="15" value="" /> 
  12.         <img src="/intranet-tmpl/prog/es-ES/lib/calendar/cal.gif" alt="Mostrar Calendario" border="0" id="openCalendar" style="cursor: pointer;"> 
  13.  
  14.         <script type="text/javascript"> 
  15.           Calendar.setup( 
  16.           { 
  17.             button : "openCalendar", 
  18.             inputField : "date", 
  19.             ifFormat : "%Y-%m-%d", 
  20.           } 
  21.           ); 
  22.         </script> 
  23. </TD> <tr> 
  24.  <TD><input name="titulo" type="text" id="titulo"> Titulo</TD></tr> 
  25.  
  26.  <tr> 
  27.      <TD></label><input name="archivo" type="file" ></TD> 
  28.  </tr> 
  29.  
  30. </table> 
  31. <input type="submit" value="subir" name="subir"> 
  32. </form> 
  33. </body> 
  34.  
  35. <!-- TMPL_INCLUDE NAME="intranet-bottom.inc" --> 


Este es el pl:
Sintáxis: [ Descargar ] [ Ocultar ]
Using perl Syntax Highlighting
  1. #!/usr/bin/perl
  2.  
  3. # This file is part of Koha.
  4.  
  5. use strict;
  6. use CGI::Carp qw(fatalsToBrowser);
  7. use C4::Output;    # contains gettemplate
  8. use C4::Auth;
  9. use C4::Context;
  10. use CGI;
  11. use LWP::Simple;
  12. use XML::Simple;
  13. use Config;
  14. use CGI qw(:standard);
  15. use File::Find;
  16. use File::Copy;
  17.  
  18.  
  19.  
  20. my $query = new CGI;
  21. my $autor = $query->param('autor');
  22. my $titulo = $query->param('titulo');
  23. my $fecha = $query->param('date');
  24. my $file = $query->param('archivo');
  25. my $var= $query->param('subir');
  26.  
  27.  
  28. my ( $template, $loggedinuser, $cookie ) = get_template_and_user(
  29.     {
  30.         template_name   => "uploadBooks/uploadBooks.tmpl",
  31.         query           => $query,
  32.         type            => "intranet",
  33.         authnotrequired => 1,
  34.         flagsrequired   => {
  35.             catalogue => 1,
  36.         }
  37.     }
  38. );
  39.  
  40. if($var ){
  41.        
  42.  
  43.         my $dbh = C4::Context->dbh();
  44.         my $sth = $dbh->prepare("INSERT INTO `koha`.`books` (`id_books`, `autor`, `titulo`, `url`, `date_book`) VALUES (NULL, ?, ?, ?, ?)");
  45.         $sth->execute($autor,$titulo,$file,$fecha);
  46.         $sth->finish;
  47.        
  48.          
  49.  
  50. copy($fichero,"/usr/share/koha/files") or die("Fallo la copia");
  51.  
  52.  
  53.  
  54.  
  55. }
  56.  
  57. output_html_with_http_headers $query, $cookie, $template->output;
  58.  
Coloreado en 0.004 segundos, usando GeSHi 1.0.8.4

El problema es que cuando escojo el valor del param('archivo') no me toma la dirección completa sino el nombre del fichero.

Saludos.
husanga
Perlero nuevo
Perlero nuevo
 
Mensajes: 3
Registrado: 2010-12-06 09:21 @431

Re: Subida de ficheros

Notapor kidd » 2010-12-10 15:05 @670

Hola,

Cuando envías un archivo por medio de un formulario como el que tienes, CGI.pm hace un archivo temporal con la copia del archivo enviado; ahora cuando tu pides el valor del campo en contexto escalar te va a regresar el nombre del archivo enviado; por ejemplo como tienes:

Sintáxis: [ Descargar ] [ Ocultar ]
Using perl Syntax Highlighting
  1. my $file = $query->param('archivo');
  2. #Contexto escalar el valor será algo como c:/directorio/archivo.algo si es enviado en Windows
Coloreado en 0.001 segundos, usando GeSHi 1.0.8.4


Ahora, si tomas la variable en contexto de "filehandle" entonces te regresará un variable de ese tipo:

Sintáxis: [ Descargar ] [ Ocultar ]
Using perl Syntax Highlighting
  1. while ( $cgi->param('file') ){
  2.     print $_;
  3. }
Coloreado en 0.001 segundos, usando GeSHi 1.0.8.4


Como te comentaba, CGI.pm ya tiene una copia del archivo localmente, entonces para hacer el copy() como estás buscando, realmente lo que necesitas es saber dónde está el archivo local para poder copiarlo o moverlo al lugar donde lo quieres; para esto necesitamos acceder a una variable que está algo oculta del CGI.pm (oculta en el sentido que no encontrarás mucha documentación acerca de ella):

Sintáxis: [ Descargar ] [ Ocultar ]
Using perl Syntax Highlighting
  1.     my $file = $query->param('archivo');
  2.     my $temp_file = $query->tmpFileName($file);
Coloreado en 0.001 segundos, usando GeSHi 1.0.8.4


La función tmpFileName() nos regresará la ruta absoluta del lugar donde CGI.pm ha puesto la copia local del archivo enviado; ya con esto puedes entonces copiar el archivo a su destino final:

Sintáxis: [ Descargar ] [ Ocultar ]
Using perl Syntax Highlighting
  1. copy($temp_file,"/usr/share/koha/files") or die("Fallo la copia");
Coloreado en 0.001 segundos, usando GeSHi 1.0.8.4


Saludos
Uriel Lizama Perl programmer fundador de Perl en Español
Perl Programming Language
Avatar de Usuario
kidd
Creador de Perl en Español
Creador de Perl en Español
 
Mensajes: 1166
Registrado: 2003-10-15 16:52 @744
Ubicación: México

Re: Subida de ficheros

Notapor husanga » 2010-12-10 16:41 @737

Estos son los errores que me dan

Sintáxis: [ Descargar ] [ Ocultar ]
Using text Syntax Highlighting
Global symbol "$app" requires explicit package name at /usr/share/koha/intranet/cgi-bin/uploadBooks/uploadBooks.pl line 38.
Execution of /usr/share/koha/intranet/cgi-bin/uploadBooks/uploadBooks.pl aborted due to compilation errors.
Coloreado en 0.000 segundos, usando GeSHi 1.0.8.4



#38 my $temp_file = $app->query()->tmpFileName($file);

Disculpe las molestias.
husanga
Perlero nuevo
Perlero nuevo
 
Mensajes: 3
Registrado: 2010-12-06 09:21 @431

Re: Subida de ficheros

Notapor kidd » 2010-12-10 17:41 @778

Fue error mio, ya actualicé la respuesta ;)
Uriel Lizama Perl programmer fundador de Perl en Español
Perl Programming Language
Avatar de Usuario
kidd
Creador de Perl en Español
Creador de Perl en Español
 
Mensajes: 1166
Registrado: 2003-10-15 16:52 @744
Ubicación: México

Re: Subida de ficheros

Notapor explorer » 2010-12-10 19:43 @863

Aunque kidd ya te ha respondido, yo voy a ponerte la solución que el propio módulo CGI comenta en la sección PROCESSING A FILE UPLOAD FIELD. El método que comenta de usar el propio nombre del fichero como literal para ser usado como gestor de archivo, puede dar avisos en pantalla, sobre todo si usas el pragma strict. Y problemas de seguridad si el usuario, en lugar de mandar el nombre de un archivo, envía una simple cadena de caracteres. Para el programa, será entonces una cadena de caracteres, y el programa entrará en un bucle sin fin.

El módulo CGI tiene ahora una función que se llama upload(), para intentar resolver estos problemas, que recibe como argumento el nombre del campo del formulario -en tu caso, "archivo"- y devuelve un objeto de tipo IO::Handle que hace referencia al fichero temporal que kidd te ha comentado antes.

Para ti, solo tienes que quedarte con la idea de que lo que devuelve upload() es un objeto que te permitirá acceder al fichero que te ha mandado el usuario y poder realizar operaciones de fichero con él.

El proceso entonces queda así:

Sintáxis: [ Descargar ] [ Ocultar ]
Using perl Syntax Highlighting
  1.          $handle  = $query->upload('archivo');
  2.  
  3.          # Si no es un gestor de archivo válido, obtendremos un 'undef'
  4.          if (defined $handle) {
  5.              # Actualiza el gestor a uno compatible con IO::Handle:
  6.              my $io_handle = $handle->handle;
  7.  
  8.              # Ya podemos leer el fichero temporal y copiarlo a su lugar definitivo
  9.              # Abrimos el fichero de destino.
  10.              # Antes tenemos que haber configurado la variable $destino
  11.              open (SALIDA, '>', "/usr/local/web/users/archivero/$destino");
  12.              # $buffer temporal para ir pasando poco a poco del temporal al $destino
  13.              my $buffer;
  14.              # bucle mientras leamos desde $io_handle, en bloques de 1024 bytes, al $buffer
  15.              while (my $bytesleidos = $io_handle->read($buffer,1024)) {
  16.                  # mandamos el contenido del $buffer al fichero $destino
  17.                  print SALIDA $buffer;
  18.              }
  19.              # cerramos el fichero de salida (opcional)
  20.              close SALIDA;
  21.         }
Coloreado en 0.001 segundos, usando GeSHi 1.0.8.4

En la sección del módulo CGI se comentan más casos, como cómo obtener más información del fichero que nos mandan (tamaño, nombre, tipo MIME, etc.), cómo responder a casos extremos (parada de envío del fichero si el usuario pulsa el botón de parada en el navegador), o cómo crear barras de progreso, o cómo gestionar la subida de múltiples ficheros de una sola vez.
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


Volver a Básico

¿Quién está conectado?

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

cron