[FUG-BR] Mysql não aceita acentos.

Rafael Fernandes ragatol em netsite.com.br
Domingo Fevereiro 25 02:29:48 BRT 2007


Oi de novo! :D

Quando um cliente de mysql conecta ao banco, via o cliente padrão mysql ou  
biblioteca, existe a negociação de um charset para a interpretação do  
texto enviado entre ambos, independente dos dados do banco ou do texto da  
linguagem (em c++ ou no caso o php). Quer dizer, temos 1 "camada" de  
conversão de charsets internamente no servidor mysql quando ele lê/escreve  
nas tabelas, 1 "camada" de conversão de charsets quando os dados trafegam  
entre o servidor e o cliente/biblioteca mysql (esta camada tanto não segue  
locale, apenas uma negociação entre o servidor e o cliente/biblioteca,  
quanto é a causa do problema inicial), e + 1 "camada" quando o texto é  
trabalhado no programa do usuário.
Por exemplo, uma string no php usaria a codificação iso por padrão. Mas,  
se você usa um módulo de php que conecta ao servidor em utf-8, você deve  
codificar esta string em uft-8 antes de enviar por um mysql_query. Como a  
diferença mesmo entre as 2 codificações são os acentos e outros caracteres  
acima de 127 (o que não afeta a sintaxe do mysql, e claro não estou  
falando de codificações com 2 bytes ou mais como a unicode), ocorre o  
problema que foi colocado, a "não aceitação" de acentos, com o mysql  
recebendo os códigos de caractere em codificação diferente da informada  
pela conexão do cliente (no caso, o próprio módulo do php).

Ficar tomando cuidado com quando usar as funções utf8_encode e utf8_decode  
no PHP levaria às "aleatoriedades" que mencionei, principalmente quando  
você migra código e dados desenvolvidos com a espectativa de que estas  
funções não seriam necessárias. Usar o setlocale no php também não  
resolveria porque isto modificaria apenas o processamento interno do php  
em relação às strings (no caso do seu exemplo, mudaria a "colagem": qual  
caractere com acentuação é ligado com qual caractere "puro". O "case  
insensitive" é um tipo de colagem: cola minúsculas com maiúsculas, não  
diferenciando elas), horário, moeda e outras coisas, e não quando ele  
envia texto pelo módulo. Eu mesmo tive que arrumar muitas páginas php com  
as funções utf8 enquanto tentava descobrir esse detalhe da codificação da  
conexão.

No meu caso, mudar estas configurações no servidor mysql não resolveu. O  
servidor mudou sim de charset usado nas conexões, mas o módulo do php não.  
E o módulo do php depende da biblioteca do mysql, que por sua vez tem em  
seu código pre-definido quando compilado qual o charset padrão. Eu não sei  
como mudar o padrão da biblioteca sem recompilar, se você souber me  
desculpe mas é que não encontrei outro meio mesmo.

O que tinha sugerido para solução é justamente isto: recompilando o  
mysql-server, seria recompilada também a biblioteca, usando o mesmo  
charset para conexões por padrão, se o módulo do php dele fosse linkado  
dinamicamente isto já resolveria também o problema dentro do php (se o  
módulo for linkado estaticamente com a biblioteca mysql, seria necessário  
recompilá-lo também!), então ele não seria obrigado a usar as funções utf8  
sempre que quisesse fazer uma query ao banco. Se ele não tiver um  
computador que seja antigo a ponto de isto ser proibitivo, é mais simples  
fazer o que sugeri ao invéz de tudo o que envolveria se fosse resolver de  
outro modo. Claro que eu estava me baseando no meu caso, num site onde  
existem vários sub-sites, cada um feito por um tipo de pessoa, com nível  
de conhecimento também variável, pior seria se eu me preocupasse em  
ajustar isto pelo php. E acreditei que isto também serviria para ele, até  
porque seria uma chamada de função a menos para cada query.

O que eu tinha entendido, pela sua primeira mensagem, era que você  
esperava que o problema fosse solucionado com a mudança do charset da  
tabela, o que ele já havia tentado. Por isto, pensei que você não  
estivesse muito a par de outras causas para o problema inicial, assim como  
a pessoa que o colocou em questão. Não foi minha intenção caçoar de você,  
apenas esclarecer o porquê da minha sugestão. ;)

Até,

Rafael.


> Oi,
>
>>> O problema, Eder, é que pode haver uma diferença de charset usado na
>>> conexão entre o cliente e o servidor mysql.
>
> R = Obviamente que pode haver, por isso existem os locales. Tanto no
> banco quanto na linguagem, não entendo muito de PHP, mais em C, C++
> basta passar o locale.
>
>>> E o problema continua mesmo depois de mudado o charset
>>> de uma tabela que era utf-8 para latin1. Como disse, não é um problema  
>>> no
>>> chaset usado pelo servidor, mas sim pela conexão entre o servidor e um
>>> cliente mysql, pois nessa ele tenta fazer uma conversão de charsets.  
>>> Leia
>>> sobre isto aqui:
>
> R = Concordo, então no PHP set o locale,
>
> setlocale(LC_COLLATE,  "pt_BR.ISO8859-1");
>
>>> A única coisa que fez os resultados de queries serem consistentes foi
>>> certificando que ambos os binários (cliente e servidor) usavam o mesmo
>>> charset padrão para conexões. E infelizmente isto fica compilado com os
>>> binários, não fica em um arquivo de configuração. Senão não  
>>> precisaríamos
>>> de ajustar esta opção ao compilar o mysql, certo?
>
> R = Errado, não é necessário recompilar o MySQL para configurar isso, se  
> ele por
> padrão já é compilado com suporte aos characters.
>
> mysql> SHOW VARIABLES LIKE 'coll%';
> mysql> SHOW VARIABLES LIKE 'character%';
>
> No arquivo de configuração do mysql no /etc/my.cnf basta setar o locale.
>
> [mysqld]
> character_sets_dir=/usr/local/share/mysql/charsets/
> default-character-set=utf8
> default-collation=utf8_general_ci
>
> [client]
> default-character-set=utf8
>
>>> Então, me desculpe, mas listar os charsets disponíveis para as tabelas  
>>> não
>>> resolveria o problema do nosso amigo da lista.
>
> R = Realmente digitar o comando não resolveria em nada.
>
> Att Eder,
>
>
> On 2/24/07, Rafael Fernandes <ragatol em netsite.com.br> wrote:
>> O problema, Eder, é que pode haver uma diferença de charset usado na
>> conexão entre o cliente e o servidor mysql.
>>
>> Normalmente, no módulo php, isto acarreta em aleatoriamente você receber
>> os dados em latin1 e utf-8, mesmo quando uma tabela está com a opção de
>> charset em latin1. E o problema continua mesmo depois de mudado o  
>> charset
>> de uma tabela que era utf-8 para latin1. Como disse, não é um problema  
>> no
>> chaset usado pelo servidor, mas sim pela conexão entre o servidor e um
>> cliente mysql, pois nessa ele tenta fazer uma conversão de charsets.  
>> Leia
>> sobre isto aqui:
>> http://dev.mysql.com/doc/refman/5.0/en/charset-connection.html
>>
>> Este problema aconteceu comigo quando migrei um banco de dados de um
>> servidor para outro. Como o charset da tabela não foi alterado, não era
>> para ocorrer este tipo de problema. E a única diferença entre um  
>> servidor
>> e outro era que o charset padrão usado nas conexões era diferente  
>> (latin1
>> no antigo, utf-8 no novo).
>>
>> A única coisa que fez os resultados de queries serem consistentes foi
>> certificando que ambos os binários (cliente e servidor) usavam o mesmo
>> charset padrão para conexões. E infelizmente isto fica compilado com os
>> binários, não fica em um arquivo de configuração. Senão não  
>> precisaríamos
>> de ajustar esta opção ao compilar o mysql, certo?
>>
>> Então, me desculpe, mas listar os charsets disponíveis para as tabelas  
>> não
>> resolveria o problema do nosso amigo da lista.
>>
>> Até,
>>
>> Rafael.
>>
>> On Sat, 24 Feb 2007 15:20:04 -0200, Eder <ederbsd em gmail.com> wrote:
>>
>> > Olá,
>> >
>> > Basta alterar o character sets.
>> >
>> > mysql>  SHOW CHARACTER SET;
>> >
>> > http://dev.mysql.com/doc/refman/5.0/en/charset-mysql.html
>> >
>> > Att, eder.
>> >
>> > On 2/23/07, Rafael Fernandes <ragatol em netsite.com.br> wrote:
>> >> É amigo eu passei por isto e normalmente o mysql fica com o charset
>> >> compilado tanto no servidor quanto no cliente (ou bibliotecas usadas  
>> por
>> >> outros programas, no caso o php).
>> >> O que solucionou meu problema 100% foi recompilar o mysql-server (se  
>> não
>> >> me engano, isto já recompila a biblioteca mysql-server, mas confira).
>> >> Recompile também o módulo mysql do php se ele foi linkado  
>> estaticamente
>> >> com a biblioteca mysql.
>> >>
>> >> Lembre-se sempre que usamos latin1/iso-8859-1 (são a mesma coisa) e  
>> irá
>> >> evitar muita dor de cabeça.
>> >>
>> >> Até,
>> >>
>> >> Rafael.
>> >>
>> >> On Fri, 23 Feb 2007 11:56:32 -0200, Rafael Stockler
>> >> <rafael.stockler em gmail.com> wrote:
>> >>
>> >> > Bom dia a todos,
>> >> >
>> >> > Estou com o seguinte problema.
>> >> >
>> >> > Tenho aqui instalado o Apache 2, php 5 e mysql 5.
>> >> >
>> >> > O problema que estou enfrentando é o fato de o mysql não estar
>> >> > cadastrando palavras com acentos. Verifiquei se o php estava  
>> mostrando
>> >> > certo e pelo q vi sim.
>> >> >
>> >> > O charset no mysql eh o utf8-general. Jah tentei colocar o latin 1  
>> e
>> >> > outras e nada.
>> >> >
>> >> > Alguem já passou por isso ou saberia o q pode ser isso?
>> >> >
>> >> > Vlw.
>> >> > -------------------------
>> >> > Histórico: http://www.fug.com.br/historico/html/freebsd/
>> >> > Sair da lista: https://www.fug.com.br/mailman/listinfo/freebsd
>> >>
>> >>
>> >> -------------------------
>> >> Histórico: http://www.fug.com.br/historico/html/freebsd/
>> >> Sair da lista: https://www.fug.com.br/mailman/listinfo/freebsd
>> >>
>> >
>> >
>>
>>
>> -------------------------
>> Histórico: http://www.fug.com.br/historico/html/freebsd/
>> Sair da lista: https://www.fug.com.br/mailman/listinfo/freebsd
>>
>
>




Mais detalhes sobre a lista de discussão freebsd