anselmorenato / cdpedia

Automatically exported from code.google.com/p/cdpedia
0 stars 0 forks source link

anomalia de crawler + logging encoding en ciertas paginas #147

Open GoogleCodeExporter opened 9 years ago

GoogleCodeExporter commented 9 years ago
Siguiendo la investigacion e tracebacks abtenidos con el crawler [0], teniamos 
en cdpedia.log dos tracebacks:

Traceback (most recent call last):
  File "D:\tmp\pyinstaller-2.0\cdpedia\build\pyi.win32\cdpedia\out00-PYZ.pyz\logging", line 869, in emit
UnicodeDecodeError: 'ascii' codec can't decode byte 0xc3 in position 58: 
ordinal not in range(128)
Logged from file _internal.py, line 116

y

Traceback (most recent call last):
  File "D:\tmp\pyinstaller-2.0\cdpedia\build\pyi.win32\cdpedia\out00-PYZ.pyz\logging", line 869, in emit
UnicodeDecodeError: 'ascii' codec can't decode byte 0xc3 in position 66: 
ordinal not in range(128)
Logged from file _internal.py, line 116

Despues de aplicar el workaround de issue 146 volvi a correr el crawler, otros 
tracebacks desaparecieron pero estos dos quedaron, exactamente iguales.

Corrí el server con el python local y los tracebacks se transformaron en:

Traceback (most recent call last):
  File "C:\Python27\lib\logging\__init__.py", line 869, in emit
    stream.write(fs % msg.encode("UTF-8"))
UnicodeDecodeError: 'ascii' codec can't decode byte 0xc3 in position 58: 
ordinal not in range(128)
Logged from file _internal.py, line 116

y

Traceback (most recent call last):
  File "C:\Python27\lib\logging\__init__.py", line 869, in emit
    stream.write(fs % msg.encode("UTF-8"))
UnicodeDecodeError: 'ascii' codec can't decode byte 0xc3 in position 66: 
ordinal not in range(128)
Logged from file _internal.py, line 116

_internal.py parece ser werkzeug/_internal.py
y logging es el modulo standard de python.

Edito logging/__init__.py

Cambiando en StreamHandler.emit

las lineas

                except UnicodeError:
                    stream.write(fs % msg.encode("UTF-8"))

por

                except UnicodeError:
                    try:
                        stream.write(fs % msg.encode("UTF-8"))
                    except:
                        stream.write('\n*** logging exception:\n')
                        stream.write('type(msg): %s\n'%type(msg))
                        stream.write('repr(msg): %s'%repr(msg))

Corriendo otra vez con el crawler me saca

*** logging exception:
type(msg): <type 'str'>
repr(msg): '127.0.0.1 - - [03/Oct/2012 16:45:50] "GET 
/institucional/T\xc3\xa9rminos_de_Uso.htm HTTP/1.1" 200 -'

y

*** logging exception:
type(msg): <type 'str'>
repr(msg): '127.0.0.1 - - [03/Oct/2012 16:45:51] "GET 
/wiki/Wikipedia:Limitaci\xc3\xb3n_general_de_responsabilidad HTTP/1.1" 200 -'

Parece que la falla es que intenta encodear a utf-8 lo que ya está en utf-8

Las páginas serian
http://localhost:8000/institucional/Términos_de_Uso.htm
http://localhost:8000/wiki/Wikipedia:Limitación_general_de_responsabilidad

Ahora, si yo copio estos ultimos links y los pego en el navegador, el 
cdpedia.log marca para esas paginas:

"GET /institucional/T%C3%A9rminos_de_Uso.htm HTTP/1.1" 200 -
"GET /wiki/Wikipedia:Limitaci%C3%B3n_general_de_responsabilidad HTTP/1.1" 200 -

O sea que con la direccion directa el logging no falla.
El crawler sacó la direccion de alguna pagina, posiblemente la home de cdpedia.
Inspeccionando el html de la pagina home los links son:

<a href="/institucional/Términos_de_Uso.htm">términos de uso</a>

<a href="/wiki/Wikipedia:Limitación_general_de_responsabilidad" 
title="Wikipedia:Limitación general de responsabilidad">Aviso legal</a>

Ummm. Los href no deberian estar encodeados ? Los otros href de la página que 
tienen acentos están encodeados. En la es.wikipedia también.

Y, de dónde vienen esos href ? de algún template ?
Si, de cdpedia_base.html
Encodeo alli los href de los dos links problematicos, corro el crawler, ahora 
no hay problema; el cdpedia.log muestra

127.0.0.1 - - [04/Oct/2012 00:48:57] "GET 
/institucional/T%C3%A9rminos_de_Uso.htm HTTP/1.1" 200 -
127.0.0.1 - - [04/Oct/2012 00:48:59] "GET 
/wiki/Wikipedia:Limitaci%C3%B3n_general_de_responsabilidad HTTP/1.1" 200 -

y ningún traceback.

Les parece si se cambia el template para eliminar el problema de logging ?

[0] http://code.google.com/p/cdpedia/issues/detail?id=143#c4

Original issue reported on code.google.com by ccanepacc@gmail.com on 4 Oct 2012 at 3:59

GoogleCodeExporter commented 9 years ago
Sí, las urls deberían estar urlencodeadas según los RFC. Podemos
agregar un filtro a jinja2 para que hacer esto no sea patada en las
pelotas:

from urllib import quote

def do_urlencode(value, encoding="utf-8"):
    """Return the urlencoded value. For detailed informations have a look at the
        help page of "urllib.quote".
    """
    return quote(value.encode(encoding))

y luego registrarlo como explica aca
http://jinja.pocoo.org/docs/api/#custom-filters
entonces podemos hacer:

<a href="/institucional/{{ Términos_de_Uso.htm|urlencode }}">términos de 
uso</a>

De paso, muy buena idea la del crawler!

Original comment by gringotu...@gmail.com on 4 Oct 2012 at 2:11