Perl en Español

  1. Home
  2. Tutoriales
  3. Foro
  4. Artículos
  5. Donativos
  6. Publicidad
 
Índice general » Mundo Perl » Básico » Problema con codificación UTF-8 en CGI  RESUELTO Responder al tema
Nuevo tema


Página 1 de 1  [ 15 mensajes ] 
 
Nota 2011-12-19 08:52 @411

Perlero Nuevo
Registrado: 2011-11-08 11:19 @513
Mensajes: 27
Problema con codificación UTF-8 en CGI
Hola, ¿cómo están?, tengo un problemita con la codificación de mi página. El problema es que yo la definí en UTF-8 y veo los acentos y todo bien, pero hay una parte de la página en que yo hago clic a un enlace y la función de ese enlace es mostrarme información relacionada al texto que hice clic, pero cuando me traigo esa información y tiene acentos no me coloca los acentos sino otros caracteres (como en la imagen)

Imagen

Ahí en la imagen sale después de la flechas lo que recibe del GET.

Lo que yo creo que pasa es que al pasar la información a Perl en UTF-8 no pasa con los acentos y los transforma a los caracteres, lo que quiero saber es cómo hago para recibir esa información y transformarla a latín para que Perl la pueda reconocer (porque creo que esa es la solución).


Nota 2011-12-19 09:58 @457
Avatar de Usuario
Administrador
Registrado: 2005-07-24 18:12 @800
Ubicación: Valladolid, España
Mensajes: 10270
Re: Problema con codificación UTF-8 en CGI
La imagen no es importante. Lo que es importante es el código HTML generado por el Perl, y ese no le vemos.

De todas maneras, cuando salen codificaciones como %C3%AD, lo que vemos es la codificación de los bytes que forman el carácter tildado, pero en forma de entidades HTML.

El problema está en el código, seguro.

¿No puedes crear un pequeño programa para mostrarnos lo que haces?

_________________
JF^D Perl programming


Nota 2011-12-19 10:19 @471

Perlero Nuevo
Registrado: 2011-11-08 11:19 @513
Mensajes: 27
Re: Problema con codificación UTF-8 en CGI
Tienes razón, aquí está donde traigo la información y la busco en mi base de datos para mostrarla:

Syntax: [ Download ] [ Hide ]
  1. use DBI; 
  2. use DBD::Pg; 
  3. #use utf8; 
  4. binmode STDOUT, ":encoding(UTF-8)"; 
  5. #print "Content-type: text/html;charset=UTF-8\n\n"; 
  6. sub traerinfo { 
  7.     $obj = shift; 
  8.     $obj->{traerinfo} = shift if @_; 
  9.     my $tab; 
  10.  
  11. my $dbh = DBI->connect("DBI:Pg:dbname=directorio;host=10.16.105.174;port=5432","directorio", "directorio",{pg_enable_utf8 => 1}); 
  12. my @tablas = qw(institucion customer_user customer_user sede);  # nombres de las tablas 
  13. my @campos = qw(name     first_name  last_name   name );  # campos dentro de esas tablas# 
  14. my $buscamos = $obj->{traerinfo}; 
  15. print "aki esta pasado-->>$buscamos"; 
  16. for(my $i = 0; $i < @tablas; $i++) { # para todas las tablas...# 
  17.   my $sth = $dbh->prepare("SELECT $campos[$i] FROM $tablas[$i] WHERE $campos[$i]=?"); 
  18.   $sth->execute( $buscamos ); 
  19.   my @row = $sth->fetchrow_array; 
  20.     print @row; 
  21.   if (@row) { 
  22.      $tab=$tablas[$i]; 
  23.     print "dentro del bucle:$tab"; 
  24.     last; # salimos del bucle for() 
  25.        } 
  26.                  } 
  27.     print $tab; 
  28.  
  29. if ($tab eq "institucion"){ 
  30.     my $sth = $dbh->prepare("SELECT institucion.name, sede.name, ciudad.name, estado.name, institucion.url FROM sede INNER JOIN institucion ON institucion.id=sede.id_institucion JOIN ciudad ON sede.id_ciudad=ciudad.id JOIN estado ON ciudad.id_estado=estado.id WHERE institucion.name=?"); 
  31.     $sth->execute( $buscamos ); 
  32.     print $buscamos; 
  33.     my $q = new CGI; 
  34.     print $q->start_table({-border=>'1'}); 
  35.     print $q->Tr($q->th({-colspan=>4}, ["$buscamos"])); 
  36.     print $q->Tr($q->th(['Sede','Ciudad','Estado','Página Web'] ) ), "\n"; 
  37.     while ( @row = $sth->fetchrow_array ) { 
  38. #    print $q->Tr($q->th($row[0])); 
  39.     print $q->Tr($q->td($q->a({href=>"mostrar.pl?$row[1]", -target=>'_self'},$row[1])),$q->td($row[2]),$q->td($row[3]),$q->td($row[4])), "\n"; 


Cuando trae la información y busca algo con acentos en la BD obviamente no lo encuentra porque tiene otros caracteres.

y aquí el otro archivo donde está el GET con el que traigo la información del enlace:

Syntax: [ Download ] [ Hide ]
  1. #!/usr/bin/perl 
  2. binmode STDOUT, ":encoding(UTF-8)"; 
  3. use Mod_dir::buscar; 
  4. use CGI; 
  5. use CGI::Carp qw(fatalsToBrowser); 
  6. print error; 
  7.  
  8. print "Content-type: text/html;charset=UTF-8\n\n"; 
  9. my $most = $ENV{'QUERY_STRING'}; 
  10.  
  11.  
  12. foreach ($mos) { 
  13.   $most=~s/\+/ /g; 
  14.   $most=~s/%([0-9i][0-9])/pack("c",hex($1))/ge; 
  15.         } 
  16.  
  17.  
  18. my $info =buscar->new; 
  19. my @data = @{ $info->traerinfo($most) }; 
  20.  


Nota 2011-12-19 11:14 @510
Avatar de Usuario
Administrador
Registrado: 2005-07-24 18:12 @800
Ubicación: Valladolid, España
Mensajes: 10270
Re: Problema con codificación UTF-8 en CGI
Yo me refería al código HTML ya generado, que ahí también hay pistas.

En cuanto al código, veo cosas horribles... ¿por qué importas el módulo CGI si luego no haces uso de sus facilidades?

Sí que defines bien el binmode() para la salida, pero no lo defines para la entrada. ¿Los cgi no reciben datos desde la entrada estándar en formato utf8?

Luego, haces un pack("c",, que debería ser 'U', ya que suponemos que la entrada está en utf8. Es más, esa expresión regular y ese pack() no te hacen falta, con la ayuda del módulo CGI y param().

_________________
JF^D Perl programming


Nota 2011-12-20 11:01 @500

Perlero Nuevo
Registrado: 2011-11-08 11:19 @513
Mensajes: 27
Re: Problema con codificación UTF-8 en CGI
Ese cgi lo puse ahí porque estoy probando para pasar con el param() a CGI... y no, los cgi no reciben los datos en formato utf8, ¿me puedes explicar un poco? Que no sé cómo hacerlo, gracias.


Nota 2011-12-20 19:31 @855
Avatar de Usuario
Administrador
Registrado: 2005-07-24 18:12 @800
Ubicación: Valladolid, España
Mensajes: 10270
Re: Problema con codificación UTF-8 en CGI
Bueno, pues lo primero que hay que hacer es saber en qué codificaciones recibimos los parámetros, que, generalmente, serán en la codificación indicada en la página HTML donde se encuentra el formulario que ha generado la petición CGI.

Por defecto, Perl piensa que todo lo que lee está en latin1 (iso-8859-1). Y lo mismo para la salida. Así que debemos hacer transformaciones de lo que leemos, para pasarlo al formato Unicode interno de Perl, y a la salida, convertirlo de nuevo en la codificación que espera el usuario.

_________________
JF^D Perl programming


Nota 2011-12-22 12:47 @574

Perlero Nuevo
Registrado: 2011-11-08 11:19 @513
Mensajes: 27
Re: Problema con codificación UTF-8 en CGI
Investigué por ahí y lo intenté así (con el código antes mostrado, modifiqué)

Syntax: [ Download ] [ Hide ]
  1. my $deco=utf8::decode($most); 
  2. my $info =buscar->new; 
  3. my @data = @{ $info->traerinfo($deco) }; 


pero el resultado me arroja "1". ¿Qué estoy haciendo mal?


Nota 2011-12-22 17:53 @787
Avatar de Usuario
Administrador
Registrado: 2005-07-24 18:12 @800
Ubicación: Valladolid, España
Mensajes: 10270
Re: Problema con codificación UTF-8 en CGI
utf8::decode() hace la decodificación 'in-situ', devolviendo verdadero ('1') si la cadena pasada como argumento contiene una secuencia UTF-8 válida. Si no, devuelve falso.

Lo correcto es escribirlo así:

utf8::decode($most);
my $info = buscar->new;
my @data = @{ $info->traerinfo($most) };


Más información en perldoc utf8

_________________
JF^D Perl programming


Nota 2012-01-06 11:17 @512

Perlero Nuevo
Registrado: 2011-11-08 11:19 @513
Mensajes: 27
Re: Problema con codificación UTF-8 en CGI
explorer, ¿qué módulo podría usar para hacer lo que quiero?


Nota 2012-01-06 11:47 @533
Avatar de Usuario
Administrador
Registrado: 2005-07-24 18:12 @800
Ubicación: Valladolid, España
Mensajes: 10270
Re: Problema con codificación UTF-8 en CGI
El módulo recomendado para hacer transformaciones de códigos, es el Encode.

En uno de los últimos trabajos que hice, todos los argumentos recibidos eran sin caracteres tildados, así que por esa parte no tenía problemas. Pero sí a la salida, cosa que solucioné poniendo esta línea antes del final:

Syntax: [ Download ] [ Hide ]
Using perl Syntax Highlighting
  1.     utf8::encode( $salida_html ) if utf8::is_utf8($salida_html); # encode for UTF-8

Aquí, estoy preguntando si la variable $salida_html contiene caracteres unicode (algo que puede suceder si en las operaciones anteriores se incorporaron caracteres o plantillas así codificadas. En ese caso, llamo a utf8::encode para que convierta esos caracteres unicode a codificación utf8, ya que quiero que toda la salida sea en utf8.

Naturalmente, antes, le he dicho a CGI que debe aparecer esa codificación:
Syntax: [ Download ] [ Hide ]
Using perl Syntax Highlighting
  1.     $query->charset('UTF-8');                   # salida siempre en utf8

Esta línea creará una salida

Content-Type: text/html; charset=UTF-8

en la cabecera HTTP de respuesta hacia el navegador web. Y además, en $salida_html, hay en la cabecera así:

<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />

No sería necesaria, pero bueno, por si acaso.

En cuanto a tu problema, te pongo la recomendación que da el propio módulo CGI:
Citar:
-utf8
Hace que CGI.pm trate a todos los parámetros como cadenas UTF-8. Úselo con cuidado, ya que interferirá
con el procesado de las subidas binarias. Es mucho mejor seleccionar manualmente qué campos se espera
que devuelvan cadenas utf-8, y convertirlas usando un código como este:

use Encode;
my $arg = decode utf8=>param('foo');

Después de esa línea, $arg contendrá una cadena con caracteres Unicode, el formato interno que usa Perl, así que ya podrás realizar el resto de operaciones de cadena con ella.

_________________
JF^D Perl programming


Nota 2012-01-10 17:48 @783

Perlero Nuevo
Registrado: 2011-11-08 11:19 @513
Mensajes: 27
Re: Problema con codificación UTF-8 en CGI
Gracias por la sugerencia, pero aún no me salen las palabras con tilde. Te muestro el código (¡ojo! Ya coloqué el "use Encode;" más arriba en el archivo)

Syntax: [ Download ] [ Hide ]
Using perl Syntax Highlighting
  1. .
  2. .
  3. .
  4. $query = new CGI;
  5. $query->charset('UTF-8');
  6.  
  7. print "Content-type: text/html\n\n";
  8. my $most = $ENV{'QUERY_STRING'};
  9.  
  10.  
  11. foreach ($mos) {
  12.     $most=~s/\+/ /g;
  13.     $most=~s/%([0-9i][0-9])/pack('U',hex($1))/ge;
  14.                 }
  15.  
  16. my $deco = decode utf8=>$most;
  17. my $info =buscar->new;
  18. my @data = @{ $info->traerinfo($deco) };
  19.  
  20.  


Aquí me estoy trayendo de un GET que hice el texto y en $most queda la palabra, pero no me transforma la codificación. Gracias por la ayuda que me puedan dar.


Nota 2012-01-10 19:22 @849
Avatar de Usuario
Administrador
Registrado: 2005-07-24 18:12 @800
Ubicación: Valladolid, España
Mensajes: 10270
Re: Problema con codificación UTF-8 en CGI
Ya encontré el fallo.

El problema es que estás leyendo el argumento pasado al cgi, que está codificado de forma url-encoded. Y la estás leyendo de forma directa con

my $most = $ENV{'QUERY_STRING'};

Es en esa cadena donde aparecen los caracteres así:

Ministerio+del+Poder+Popular+para+la+Ciencia+y+Tecnolog%C3%ADa

Es decir, no es que vengan codificados en utf-8, es que vienen codificados URL-encoded.

Entonces, la solución es clara: no hacer eso, sino usar el param() del módulo CGI, que hace la transformación de URL-encoded a caracteres de forma automática. Y luego haces el decode() desde utf-8, para tener una verdadera cadena Unicode.

Ahora bien... eso es lo que estás haciendo en las líneas 12 a 15 del primer código que publicaste. Quizás los caracteres estén doblemente URL-encoded...

¿No puedes crear dos programas, completos, lo más pequeños posible (sin consultas a la base de datos, sin cargar plantillas HTML, solo generando el código HTML mínimo, etc) que repita el error y nos lo mandas?

A lo mejor así vemos qué pasa.

_________________
JF^D Perl programming


Nota 2012-01-10 23:06 @004
Avatar de Usuario
Administrador
Registrado: 2005-07-24 18:12 @800
Ubicación: Valladolid, España
Mensajes: 10270
Re: Problema con codificación UTF-8 en CGI
Añadido...

En el perlfaq 9, viene resuelta esa cuestión: How do I decode or create those %-encodings on the web? , usando el módulo URI::Escape.

_________________
JF^D Perl programming


Nota 2012-01-11 14:02 @626

Perlero Nuevo
Registrado: 2011-11-08 11:19 @513
Mensajes: 27
Re: Problema con codificación UTF-8 en CGI  RESUELTO
¡¡Lo arreglé!! :D ¡Era lo que tu decías!. La verdad, muchas gracias. Mira cómo quedó el código al final:

Syntax: [ Download ] [ Hide ]
Using perl Syntax Highlighting
  1. print $query->header('text/html');
  2. print $query->start_html();
  3. my $var= $query->param(traer=>$ENV{'QUERY_STRING'});
  4. my $temp=uri_unescape( $var );    
  5. my $deco = decode utf8=>$temp;
  6. my $info = buscar->new;
  7. my @data = @{ $info->traerinfo($deco) };
  8.  


Te agradezco por toda la ayuda que me has dado porque este problemita me tenía la vida a cuadros.


Última edición por explorer el 2012-01-11 18:55 @830, editado 1 vez en total
Marcas de código Perl.


Nota 2012-01-11 19:05 @837
Avatar de Usuario
Administrador
Registrado: 2005-07-24 18:12 @800
Ubicación: Valladolid, España
Mensajes: 10270
Re: Problema con codificación UTF-8 en CGI
Suponiendo que el parámetro del formulario que recibe la cadena se llama 'traer', ¿has probado con esto?

Syntax: [ Download ] [ Hide ]
Using perl Syntax Highlighting
  1. print $query->header('text/html');
  2. print $query->start_html();
  3. my $var  = $query->param('traer');
  4. my $deco = decode('utf8',$var);
  5. my $info = buscar->new;
  6. my @data = @{ $info->traerinfo($deco) };
  7.  

_________________
JF^D Perl programming


Responder al tema  [ 15 mensajes ] 

Reglas del Foro
No puedes abrir nuevos temas en este Foro
No puedes responder a temas en este Foro
No puedes editar tus mensajes en este Foro
No puedes borrar tus mensajes en este Foro
No puedes enviar adjuntos en este Foro

Publicidad

Socializa

Síguenos por Twitter

Suscríbete GRATUITAMENTE al Boletín de Perl en Español

Saltar a:  
Powered by phpBB © 2000, 2002, 2005, 2007 phpBB Group
Traducción al español por Huan Manwë para phpbb-es.com
phpBB SEO