zzurlencode: erro em caracteres UTF-8 #194

Closed
aureliojargas opened this Issue Mar 21, 2015 · 18 comments

Projects

None yet

2 participants

@aureliojargas
Member
$ zzurlencode 'foo bar?'      # ok
foo%20bar%3F

$ zzurlencode '¹²³£¢¬§'
fgrep: illegal byte sequence
%FFFFFFFFFFFFFFC2fgrep: illegal byte sequence
%FFFFFFFFFFFFFFB9fgrep: illegal byte sequence
%FFFFFFFFFFFFFFC2fgrep: illegal byte sequence
%FFFFFFFFFFFFFFB2fgrep: illegal byte sequence
%FFFFFFFFFFFFFFC2fgrep: illegal byte sequence
%FFFFFFFFFFFFFFB3fgrep: illegal byte sequence
%FFFFFFFFFFFFFFC2fgrep: illegal byte sequence
%FFFFFFFFFFFFFFA3fgrep: illegal byte sequence
%FFFFFFFFFFFFFFC2fgrep: illegal byte sequence
%FFFFFFFFFFFFFFA2fgrep: illegal byte sequence
%FFFFFFFFFFFFFFC2fgrep: illegal byte sequence
%FFFFFFFFFFFFFFACfgrep: illegal byte sequence
%FFFFFFFFFFFFFFC2fgrep: illegal byte sequence
%FFFFFFFFFFFFFFA7

$ zzurlencode '£'
fgrep: illegal byte sequence
%FFFFFFFFFFFFFFC2fgrep: illegal byte sequence
%FFFFFFFFFFFFFFA3

@itamarnet na sua máquina está ok esta função ou será que é problema exclusivo no BSD?

No issue #180 pode ter alguma informação útil pra investigar este caso.

@aureliojargas aureliojargas added the bug label Mar 21, 2015
@aureliojargas aureliojargas modified the milestone: Versão 2015 Mar 21, 2015
@itamarnet
Contributor

@aureliojargas na minha máquina funciona perfeitamente.
Mas o erro deve ser mais um capítulo das incompatibilidades entre Unix e BSD.
Notadamente é o fgrep que falha, para oferecer o retorno do caracteres que devem ou não serem convertidos.
Acho que esse terá que ser um caso novamente para o sed resolver.

@aureliojargas
Member

Putz, o problema é mais embaixo:

printf %s "$string" | while IFS= read -r -n 1 caractere

Esse read que é pra ler um caractere por vez, adivinha... Quando é UTF-8 lê meio caractere (um byte) e por isso dá o erro lá na frente no fgrep.

@itamarnet
Contributor

Já tem uma idéia do que fazer?
Eu pensei em usar um " for " usando " seq ", " wc -m " e " sed ".
Todavia o que eu fiz aqui não rolou, sempre dava erro.

@itamarnet
Contributor

@aureliojargas Tenta isso:

printf %s "$string" |
tr ' ' '\n' | sed 's/./& /g' |
tr ' ' '\n'| sed 's/^$/ /' |
while read -r caractere

Aqui continua funcionando com essa modificação.

@aureliojargas
Member

O testador rodou 100%? Porque acho que não vai funcionar se tiver quebra de linha no texto original.

@itamarnet
Contributor

O testador funcionou perfeito.
Mas você levantou uma questão interessante, e com base nos últimos acontecimentos, não descarto que o testador aqui na máquina tenha falhado em detectar essa circunstância.
Acho que ainda não é a solução ideal.

@itamarnet
Contributor

Tem razão @aureliojargas , isso não funciona mesmo.
Infelizmente, com quebra de linha não funciona, e espaços literais na string se perdem.
" De novo a prancheta de desenho! "

@aureliojargas
Member

Veja issue #201. Provavelmente a resolução dele resolverá este aqui.

@aureliojargas aureliojargas added a commit that referenced this issue Mar 26, 2015
@aureliojargas aureliojargas zzurlencode: suporte a UTF-8, opção nova -t e -n
Tive que reescrever a função para poder suportar UTF-8. O od é usado
para descobrir os códigos hexadecimais.

A parte de proteger alguns caracteres da conversão ficou muito mágica,
mas foi a solução mais robusta que encontrei das várias que tentei.
Usar loop no shell caractere a caractere deu problemas com alguns
caracteres especiais para o shell.

Os caracteres a não converter não são mais posicionais, e agora possuem
sua própria opção: -n.

Testador bem completo, tentando chegar nos limites do algoritmo.

Veja issues #194 e #201
495eeff
@aureliojargas
Member

Cara, tive que fazer mágica pra resolver essa, mas depois de dois dias quebrando a cabeça, cheguei no resultado esperado. Está no commit 495eeff. Por favor, testa se na tua máquina o testador roda tudo 100%:

$ ./run zzurlencode.sh 
...................................................................................................................................................................................
OK: 179 of 179 tests passed
$
@itamarnet
Contributor

Putz! Grande sacada, usar o bom e velho od.
Eu acredito que funcione sim.
👍

@itamarnet
Contributor

Cara em duas ficou perfeito! Show de bola 👍

Mas a porcaria do Mint que tenho instalado aqui deu erro de novo.
É o mesmo do caso do zzascii, que você comentou em #179 (comment)

Fazer a mesma jogada, de passar antes pelo octal, é viável?

@aureliojargas
Member

Putz, é então no printf lá no final, na hora de "desconverter" os caracteres protegidos. Esse vai ser complicado de fazer octal, pois não há cálculo, somente substituição de texto...

Eu já tou achando complicada demais essa função do jeito que está. Quem sabe essa podemos não suportar o Mint por enquanto, até que apareça uma solução mais simples?

@itamarnet
Contributor

Complicado isso!
Eu citei o Mint, mas ocorre o mesmo no Ubuntu, e justamente essas duas distros são as mais usadas.
Ao menos nos meios que frequento, é uma constante e acho complicado deixar passar.

Algo que me ocorreu como alternativa:
O zzascii apenas exibe todos os caracteres com vários códigos correspondentes, e esse comportamento poderia ser mantido como padrão, mas agregar a opção de fornecer o código (decimal, hexa ou octal) e ter o caractere como retorno.

Talvez esse caminho possa ser usado para "desconverter" os caracteres.
O que acha?

@itamarnet
Contributor

Não sei se pode ajudar, mas implementei a idéia do zzascii retornar o caractere ao fornecer o código decimal, hexadecimal ou octal.
Se não servir fica como mais um recurso.
Atualizar o testador farei na sequência.
Veja no commit 8c44bb3

@itamarnet
Contributor

Na verdade @aureliojargas acho que me expressei mal.
O que falha são os testes apenas, e estava tentando faze-los funcionar 100%.
Mas fora dos testes, no terminal roda perfeito.

Não é o melhor dos mundos, mas talvez seja melhor mesmo deixar com os testes falhando na família Ubuntu e seus derivados por enquanto.

E não quero ser pessimista, mas não sei se teremos alguma solução simples para cobrir essa caso.

@aureliojargas
Member

Ah, eu não tinha entendido que o problema era somente nos testes. Então sem crise, se ela funciona na execução normal, tudo bem.

Quanto à funcionalidade adicional na zzascii, agora (pré-release) não é o momento para incluir isso, ainda mais sem testes, ainda mais que envolve UTF-8. Vamos nos poupar do estresse, ok? :) Vou guardar este commit num branch e reverter no master.

@aureliojargas aureliojargas added a commit that referenced this issue Apr 5, 2015
@aureliojargas aureliojargas Revert "zzascii: Também exibir um caractere a partir do código decima…
…l, hexa ou octal."

This reverts commit 8c44bb3.

Estamos em pré-release, não é um bom momento para funcionalidades novas.
O commit original foi guardado no branch zzascii-opcoes-d-x-o.
Veja issue #194
4553c21
@aureliojargas
Member

Como o problema original da zzurlencode com UTF-8 foi resolvido, fecharei este issue.

@aureliojargas
Member

Abri o issue #207 para lidarmos com o problema do printf no Mint/Ubuntu de maneira genérica.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment