Com o uso generalizado de vários conjuntos de caracteres multibyte, uma proporção muito alta de programadores que falam inglês no desenvolvimento de software não sabe muito sobre caracteres multibyte. É por isso que muitas vulnerabilidades nos últimos anos são uma causa. O autor deste artigo fala sobre seus próprios pontos de vista sobre o papel da arquitetura do conjunto de caracteres do MySQL. Nos últimos meses, sempre que uso o MySQL, quase sempre penso: a atual arquitetura de conjunto de caracteres hierárquicos do MySQL é realmente útil?
Processamento de conjunto de caracteres MySQL
Enviar solicitação
Cliente (character_set_client)=》Conexão de banco de dados (character_set_connection)=》Armazenamento (tabela, coluna)
solicitação de devolução
Armazenamento (tabela, coluna)=》Conexão de banco de dados (character_set_connection)=》Cliente (character_set_results)
Em cada nó não inicial, uma operação de conversão do conjunto de caracteres é executada do nó anterior para o nó atual. Por exemplo, considere o seguinte ambiente:
◆ conjunto de caracteres_conexão utf-8
◆ conjunto de caracteres_resultados gbk
◆ character_set_client gb2312
◆ Existe a tabela A e os conjuntos de caracteres do campo são todos BIG5
Ao enviar uma solicitação, os dados são primeiro convertidos de gbk para utf-8, depois para BIG5 e depois armazenados.
Ao retornar a solicitação, os dados são primeiro convertidos de BIG5 para utf-8, depois para gb2312 e depois enviados ao cliente.
O papel da arquitetura
1. Permita que clientes diferentes tenham conjuntos de caracteres diferentes. Um exemplo típico é que tenho um site UTF-8, que é um cliente com um cliente charset UTF-8. Ao mesmo tempo, posso precisar ler e gravar o banco de dados em um terminal gbk, que é outro cliente, mas seu conjunto de caracteres é gbk.
2. Ao operar o sistema de arquivos por meio do banco de dados, você precisa converter o caminho do arquivo no conjunto de caracteres do sistema de arquivos. Por exemplo, meu cliente é gbk e o sistema de arquivos do servidor é utf-8. Operação "/A slice/Rina.rmvb", dentre os dados enviados, os dados do "slice" são diferentes do servidor. Neste momento, é necessário que haja uma maneira de converter a "fatia" do GBK para utf-8. Aqui o MySQL introduz algo chamado character_filesystem para fazer isso.
Fora isso, não consigo pensar em nenhum outro uso no momento. Mas pense bem, será que realmente precisamos desse tipo de tratamento? Muitos sites apenas esperam que seus dados possam ser divulgados como desejarem. Existem mais duas situações aqui.
1. Espero poder classificar ou executar operações semelhantes com base nos dados. Vamos falar primeiro sobre classificação. Para campos que contêm chinês, o conceito de classificação baseada em conjuntos de caracteres é inútil. Ao classificar o chinês simplificado, geralmente você deseja classificar por Pinyin. Eu realmente não entendi a verificação no MySQL, mas a julgar pelos programas com os quais entrei em contato, se esse tipo de classificação for necessária, um campo é criado especialmente para armazenar o pinyin para classificação. Também existem caracteres polifônicos em Pinyin. Se for UTF-8, há também uma situação em que uma certa gama de chineses é partilhada pela China, Japão e Coreia do Sul ao mesmo tempo. Não é tão fácil de implementar, então nem o GBK nem o conjunto de verificação UTF-8 do MySQL devem implementar o Pinyin. Ouso dizer que a maioria dos sites na China que usam MySQL agora usam um conjunto de verificação que é apenas uma classificação de bytes. Com a classificação de bytes, não há necessidade de usar nenhum conjunto de caracteres. Portanto, para sites chineses, a verificação de caracteres do MySQL não tem significado na classificação.
Mas em termos de operação semelhante, tem um pouco de significado. Por exemplo, se eu gostar de '%a%', é possível corresponder um caractere chinês contendo a em uma determinada parte. É claro que esta situação não será encontrada em UTF-8, porque o formato de armazenamento de UTF-8 significa que a só pode ser a e não pode fazer parte de um caractere multibyte. Mas este problema pode ocorrer em outros conjuntos de caracteres. No final, semelhante torna-se igual a ordem, tornando a verificação sem sentido. desmaiar.
2. Se não houver necessidade de classificar os dados, como ou pesquisa de texto completo, pare de usar char, varchar, texto e similares. binário, varbinary, BLOB são as escolhas corretas. Binários e similares não realizarão conversão de conjunto de caracteres ao armazenar e recuperar, mas ao classificar, eles são classificados apenas de acordo com o conteúdo binário, portanto, a eficiência é muito maior do que char, varchar e texto.
Neste caso, não há necessidade de um conjunto de caracteres. No entanto, de acordo com a arquitetura MySQL atual, as operações de conjunto de caracteres entre os tipos de campos de ignorar cliente e conexão ainda serão realizadas entre esses dois nós.
Mencione também a configuração do conjunto de caracteres em PHP. Por favor, pare de usar instruções como mysql_query("setnames utf8"). mysql_set_charset() é o método de configuração de conjunto de caracteres mais completo. Este último tem mais uma configuração que o anterior, que é definir o membro charset da estrutura MySQL. Esta variável membro desempenha um papel muito importante no escape, especialmente para formatos de codificação como GBK que usam "" como parte do caractere. Se você usar apenas mysql_query("setnames XXX"), então em alguns conjuntos de caracteres, haverá grandes falhas de segurança, fazendo com que mysql_real_escape_string se torne tão inseguro quanto addlashes.
-