【问题标题】:why does a parameter passed into a stored procedure cause MySQL error 1267?为什么传递给存储过程的参数会导致 MySQL 错误 1267?
【发布时间】:2014-06-15 16:25:28
【问题描述】:

这两个存储过程都在我的 MySQL 5.1.73 服务器中编译:

delimiter $$
CREATE PROCEDURE get_admins()
    BEGIN
            SELECT *
            FROM Accounts
                INNER JOIN LINK_Account_Status ON Accounts.account_id=LINK_Account_Status.account_id
                    AND LINK_Account_Status.active_ind=1
            WHERE Accounts.active_ind=1
                AND Accounts.`type`='admin';
    END $$
delimiter ;

delimiter $$
CREATE PROCEDURE get_admins2(
    IN  p_type  varchar(50)
)
    BEGIN
            SELECT *
            FROM Accounts
                INNER JOIN LINK_Account_Status ON Accounts.account_id=LINK_Account_Status.account_id
                    AND LINK_Account_Status.active_ind=1
            WHERE Accounts.active_ind=1
                AND Accounts.`type`=p_type;
    END $$
delimiter ;

执行CALL get_admins();会返回我期望的结果。

执行CALL get_admins2('admin'); 错误:

错误代码:1267。非法混合排序规则 (utf8_general_ci,IMPLICIT) 和 (utf8_unicode_ci,IMPLICIT) 用于操作 '='

细心的响应者会注意到两个结果查询之间没有功能差异。我仔细检查了Accounts.type 确实是varchar(50)(即使它被不幸命名了)。

Sam Hill 中发生了什么?

【问题讨论】:

    标签: mysql stored-procedures parameter-passing mysql-5.1


    【解决方案1】:

    您需要在WHERE 条件中使用COLLATE 来解决此问题,如下所示

    delimiter $$
    CREATE PROCEDURE get_admins2(
        IN  p_type  varchar(50)
    )
        BEGIN
                SELECT *
                FROM Accounts
                    INNER JOIN LINK_Account_Status ON
    Accounts.account_id=LINK_Account_Status.account_id
                        AND LINK_Account_Status.active_ind=1
                WHERE Accounts.active_ind=1
                    AND Accounts.`type`=p_type COLLATE utf8_general_ci; /* <-- Here */
        END $$
    delimiter ; 
    

    您也可以在参数声明本身 ("As of [MySQL] 5.5.3, COLLATE can be used...") 中添加 COLLATION,例如:

    delimiter $$
    CREATE PROCEDURE get_admins2(
        IN  p_type  varchar(50) COLLATE utf8_general_ci <-- Here
    
    .....<rest of the code here>.....
    

    编辑:

    在进行了一些搜索后,我发现,如果您的列具有不同的排序规则,即使表具有相同的排序规则,也可能会出现此问题。请参阅下面的 MySQL 论坛帖子

    http://forums.mysql.com/read.php?103,265345,265579

    【讨论】:

    • "参数类型和函数返回类型可以声明为使用任何有效的数据类型,但不能使用 COLLATE 属性。" dev.mysql.com/doc/refman/5.1/en/create-procedure.html
    • @JeromyFrench,是的;我错过了您使用的是 5.1.*。然后您可以在WHERE 条件下使用它,但在 MySQL 5.6 或更高版本中,您也可以在参数声明中使用collate;正如您已经编辑过的那样。是的,谢谢。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-10-13
    • 1970-01-01
    • 1970-01-01
    • 2017-06-24
    • 2013-11-18
    • 1970-01-01
    相关资源
    最近更新 更多