存储过程中字符集的混合使用不合法(utf8_general_ci,IMPLICIT)和(utf8_unicode_ci,IMPLICIT)。

15
  • 所有表格都采用 utf_unicode_ci 编码。

    我这样做是为了检查。

SELECT table_schema, table_name, column_name, character_set_name, collation_name
    FROM information_schema.columns
WHERE collation_name <> 'utf8_unicode_ci' AND table_schema LIKE 'my_database'
    ORDER BY table_schema, table_name, ordinal_position;

并转换了每个表格以防万一

ALTER TABLE `my_database`.`table_name` DEFAULT COLLATE utf8_unicode_ci;      
ALTER TABLE `my_database`.`table_name` CONVERT TO CHARACTER SET utf8 COLLATE utf8_unicode_ci;         
我的数据库排序设置为utf8_unicode_ci。字符集如下:character_set_client、character_set_connection、character_set_database、character_set_filesystem、character_set_results、character_set_server、character_set_system,所有值都为utf8。校对如下:collation_connection、collation_database和collation_server,所有值都为utf8_unicode_ci。触发错误的方式是无论是通过Web浏览器还是MySQL Bash客户端调用存储过程都会触发。我的Ubuntu / Linux语言环境设置为es_ES.UTF-8。目前唯一解决这个问题的方法是在每个导致错误的查询中使用convert(或在查询中使用COLLATE)。但问题是有许多相当复杂的存储过程,因此很难识别“不良”查询并且耗时很长。我想某种方式从我的系统(ubuntu:mysql客户端、浏览器)传递给存储过程的变量正在以utf8_general_ci的形式发送,因此与来自我的数据库的ut8_unicode_ci发生冲突。似乎操作系统正使用utf8_general_ci,即使MySQL连接设置为utf_unicode_ci。

1
我的猜测是正确的,系统似乎设置为utf8_general_ci。如果我将每个表格的排序规则转换为utf_general_ci,就不会再收到错误消息了。因此,问题似乎在于我的系统正在使用utf8_general_ci。 - Packet Tracer
4个回答

18

我解决了我的问题,原因是迁移过程中出现了错误的转换。我将字符集从utf8_unicode_ci转换为了utf_general_ci,导致源数据以错误的编码方式(utf8_general_ci)插入到mysql数据库中,尽管mysql数据库结构是正确的。

问题在于,即使mysql数据库中有正确的字符集和校对规则,在插入数据时,如果数据以另一种校对规则进行编码,就会出现“不兼容的校对规则”错误。

希望这能对未来遇到此类问题的人有所帮助。


1
不太可能。无论如何,影响数据存储方式的编码都是utf8,而你只是在改变排序规则。我曾遇到过类似的问题,其中一个存储过程出现了这个错误,但手动执行存储过程中的语句却没有出现错误,重新创建存储过程后问题消失了。MySQL在某个地方缓存了错误的排序规则,一旦你更改正确的内容,该缓存就会被清除。 - usethe4ce
在我的情况下,我不认为这是缓存问题,因为它发生在一个新迁移的数据库上,使用了新的程序,甚至重启了服务器。一旦我使用正确的编码迁移数据后,我再也没有遇到那种错误了。无论如何,感谢您的评论,因为它可以帮助其他用户。 - Packet Tracer
有没有办法在原地更改排序规则(即,无需重新导入)? - Doug
2
修改表 my_database.table_name 的默认字符集为 utf8_unicode_ci; 将表 my_database.table_name 转换为字符集为 utf8,校对规则为 utf8_unicode_ci。 - Packet Tracer

2

如果有帮助的话,我们在查询不同服务器上的不同数据库时遇到了相同的错误,其中一个是从另一个数据库迁移过来的。在我们的情况下,通过更改mysql.ini中的“collation_server”并重新启动mysql服务来解决了这个问题。


1
重新导入存储过程和存储函数,一旦您的编码和排序设置正确,将解决问题。遇到完全相同的问题。如果您怀疑表格数据格式存在问题,另一个有用的MySQL本机函数是select collation(some_col) from some_table。

在我的情况下,问题不是存储过程,而是数据库数据编码错误。感谢您对这个问题的贡献。 - Packet Tracer

0

在参数列表中添加CHARSET utf8后,我解决了我的问题。也许这对其他人有所帮助。


   PROCEDURE `USP_USR_AuthenticateUser`(
      IN ip_username VARCHAR(50) CHARSET utf8**,
      IN ip_pwd NVARCHAR(256)
   )

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接