Página 2 de 2

Re: Unicode (UTF-8) en la salida de CGI

NotaPublicado: 2015-03-02 13:32 @605
por seafree
Hola, explorer. Respecto a tu pregunta respecto a la versión del CGI, es:

perl -MCGI -le 'print $CGI::VERSION'
3.15

Realizo la actualización de Perl:

perl-5.20.2]# ./Configure -des -Dprefix=$HOME/localperl
make test
make install

Vuelvo a verificar la versión del CGI:

# perl -MCGI -le 'print $CGI::VERSION'
3.15

Y el resultado es el mismo, ¿qué estoy haciendo mal?

Gracias por tu atención, explorer.

Re: Unicode (UTF-8) en la salida de CGI

NotaPublicado: 2015-03-02 15:03 @669
por explorer
La versión más moderna de CGI es la 4.13, pero perl v5.20.2 ya no lo trae (Perl v5.20.0 trae la versión v3.65).

En mi ordenador, con Perl v5.18.2, trae el CGI v3.63.

La instalación de Perl en un directorio local te recomiendo que no lo hagas de esa manera. Es mucho mejor usar perlbrew para esas tareas.

Recuerda que si quieres ejecutar el perl instalado en tu directorio local, debes luego acordarte de poner la ruta del nuevo Perl con una opción -I al llamar a perl. Por ejemplo:

perl -Iperl5/lib/perl5 -MJSON::PP -E 'say $INC{"JSON/PP.pm"}'

O usar local::lib. O mejor aún... usa perlbrew.

Yo no sé dónde está el problema. Repasando:
* si la terminal está en UTF-8, que sí lo hemos visto
* si el código está codificado en UTF-8 (NO lo hemos visto, pero es de suponer)
* si el CGI está programado para sacar código UTF-8 (que así es)
* entonces el resultado debería ser en UTF-8.

Si no sale... repasando el archivo CHANGES de CGI, vemos que es en la v3.43 de CGI donde se arregló el problema de la doble codificación de los parámetros, que es lo que veo que te puede pasar.

Te aconsejo que uses el comando cpan o cpanp o cpanm para que instales una versión más moderna del CGI. O instalar Perl v5.20.1.

Re: Unicode (UTF-8) en la salida de CGI

NotaPublicado: 2015-03-03 15:12 @675
por seafree
explorer, continúo con el problema de caracteres, analizando un poco más mi situación. Hallé:

1) Que el encoding de la base de datos está en SQL_ASCII

2) Los registro de la base de datos SÍ están acentuados

3) Logré que el charset del meta fuera utf8 (lo veo al compilar el script), pero al visualizar el código generado desde el navegador, este se genera como ISO-8859

Ojalá tengas alguna idea de lo que ocurre. Gracias.

Re: Unicode (UTF-8) en la salida de CGI

NotaPublicado: 2015-03-03 15:57 @706
por explorer
En ese caso, debes transformar los textos que sacas de la base de datos, al formato Unicode interno de Perl (con la función decode() del módulo Encode). Y como el programa ya tiene definido el 'use open' a utf-8, pues ya sale en utf-8.

Re: Unicode (UTF-8) en la salida de CGI

NotaPublicado: 2015-03-04 12:51 @577
por seafree
Configuré mi terminal a UTF-8:
# echo $LANG
es_ES.UTF-8

Creé una prueba
------------------------------------------------
#!/usr/bin/perl -w
use strict;
use warnings;
use CGI ":all";
use Encode;

my $cgi = new CGI;

$cgi->charset('utf-8');
print $cgi->header(-type=> 'text/html',
-charset=>'utf-8');
print $cgi->start_html(-title =>'PRUEBA',
-head => meta({-http_equiv => 'Content-Type',
-content => 'text/html; charset=utf-8'}));
my $hola='HELLO XÓCHITL';

decode::from_to($hola, 'latin1', 'utf8');
print $cgi->p($hola);
print $cgi->end_html;
------------------------------------------------

RESULTADO
---------------------------------------------------
#perl -w test1.pl
Content-Type: text/html; charset=utf-8

<!DOCTYPE html
PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" lang="en-US" xml:lang="en-US">
<head>
<title>PRUEBA</title>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<meta http-equiv="Content-Type" content="text/html; charset=iso-8859-1" />
</head>
<body>
<p>HELLO XÓCHITL</p>
</body>
</html>
--------------------------------------------------------------------------
¿Por qué no devuelve los caracteres UTF-8?

GRACIAS.

Re: Unicode (UTF-8) en la salida de CGI

NotaPublicado: 2015-03-04 15:39 @693
por explorer
Por favor, repasa los ejemplos que ya te he dado. Te faltan cosas.

Viendo el código que muestras:

* el método charset() sirve para hacer un auto-escapado de los textos que salen en las cajas de texto de los formularios. O sea, que no te sirve en este ejemplo tan sencillo.

* luego haces una llamada correcta al método header(). Y de hecho, sale bien en las cabeceras HTTP y HTML

* luego llamas a start_html(), y allí vuelves a llamar a head, que sobra completamente

* luego haces la decodificación de los datos de $hola (suponiendo que ese texto que vemos está escrito en latin1), pero a mi no me funciona como lo has escrito. Abajo lo pongo de forma correcta

* luego haces un print de un p(). Como el contenido de $hola ya contiene algo en utf8, pues eso es lo que emitimos

Lo siguiente me funciona:
Sintáxis: [ Descargar ] [ Ocultar ]
Using perl Syntax Highlighting
  1. #!/usr/bin/perl
  2. use strict;
  3. use warnings;
  4.  
  5. use CGI ":all";
  6. use Encode 'from_to';
  7.  
  8. my $cgi = CGI->new();
  9.  
  10. print $cgi->header(
  11.     -type    => 'text/html',
  12.     -charset => 'utf-8',
  13. );
  14.  
  15. print $cgi->start_html(
  16.     -title => 'PRUEBA',
  17. );
  18.  
  19. my $hola = 'HELLO XÓCHITL';             # este código está escrito en latin1
  20.  
  21. from_to( $hola, 'latin1', 'utf8' );     # lo pasamos a UTF8
  22.  
  23. print $cgi->p($hola);
  24. print $cgi->end_html;
Coloreado en 0.003 segundos, usando GeSHi 1.0.8.4

La salida es:
Sintáxis: [ Descargar ] [ Ocultar ]
Using html4strict Syntax Highlighting
  1. Content-Type: text/html; charset=utf-8
  2.  
  3. <!DOCTYPE html
  4.        PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
  5.         "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
  6. <html xmlns="http://www.w3.org/1999/xhtml" lang="en-US" xml:lang="en-US">
  7. <head>
  8. <title>PRUEBA</title>
  9. <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
  10. </head>
  11. <body>
  12. <p>HELLO XÓCHITL</p>
  13. </body>
  14. </html>
Coloreado en 0.001 segundos, usando GeSHi 1.0.8.4

Aclaraciones:
* el código del programa está escrito en latin1, NO en utf8, ya que quieres imitar la llegada de datos desde la base de datos
* la salida se ve bien en mi terminal configurada en UTF-8

Pero... la clave está en por qué aparece un content-type iso-8859-1. Yo no veo ninguna línea donde se vea esa doble salida.

Según el archivo Changes del CGI, esa doble línea podría ser debido a la presencia de CGI::Carp cuando se usa la opción 'FatalsToBrowser', pero yo no lo veo ahora en tu nuevo código.

Me temo que es debido a que usas un CGI muy viejo.

Esta es otra forma de hacerlo:
Sintáxis: [ Descargar ] [ Ocultar ]
Using perl Syntax Highlighting
  1. #!/usr/bin/perl
  2. use strict;
  3. use warnings;
  4.  
  5. use CGI ":all";
  6. use Encode 'decode';
  7.  
  8. use open qw(:utf8 :std);
  9.  
  10.  
  11. my $cgi = CGI->new();
  12.  
  13. print $cgi->header(
  14.     -type    => 'text/html',
  15.     -charset => 'utf-8',
  16. );
  17.  
  18. print $cgi->start_html(
  19.     -title => 'PRUEBA',
  20. );
  21.  
  22. my $hola = 'HELLO XÓCHITL';             # este código está escrito en latin1
  23.  
  24. $hola = decode('latin1', $hola);        # lo pasamos a Unicode, formato interno de Perl
  25.  
  26.  
  27. print $cgi->p($hola);                   # la capa del 'open' pasa de Unicode interno a utf8
  28. print $cgi->end_html;
Coloreado en 0.001 segundos, usando GeSHi 1.0.8.4
El resultado es el mismo.

Re: Unicode (UTF-8) en la salida de CGI

NotaPublicado: 2015-03-05 10:16 @469
por seafree
Sí, explorer, gracias por tu apoyo.

Saludos.