2014-06-15 1 views
1

Ces deux procédures stockées compilez dans mon serveur MySQL 5.1.73:pourquoi un paramètre passé dans une procédure stockée provoque l'erreur MySQL 1267?

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 ; 

exécution CALL get_admins(); renvoie les résultats je pense.

CALL get_admins2('admin'); erreurs d'exécution:

Code d'erreur: 1267. mélange illégal de collations (utf8_general_ci, IMPLICIT) et (utf8_unicode_ci, IMPLICIT) pour l'opération '='

Le répondeur observatrice sera Notez qu'il n'y a pas de différence fonctionnelle entre les deux requêtes résultantes. J'ai vérifié que Accounts.type est, en effet, un varchar(50) (même s'il est malheureusement nommé).

Que se passe-t-il dans le Sam Hill ici?

Répondre

2

Vous devez utiliser COLLATE dans votre WHERE état pour résoudre cela comme ci-dessous

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 ; 

Vous pouvez ainsi ajouter la COLLATIONNEMENT dans la déclaration de paramètre lui-même ("As of [MySQL] 5.5.3, COLLATE can be used...") comme:

delimiter $$ 
CREATE PROCEDURE get_admins2(
    IN p_type varchar(50) COLLATE utf8_general_ci <-- Here 

.....<rest of the code here>..... 

EDIT :

Après avoir fait une recherche, j'ai trouvé que, cela problème peut se produire si vos colonnes ont un classement différent même si les tables ont le même classement. Voir ci-dessous le MySQL Forum post

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

+1

« Types de paramètres et types de retour de la fonction peut être déclarée d'utiliser tout type de données valides, sauf que l'attribut COLLATE ne peut pas être utilisé. » http://dev.mysql.com/doc/refman/5.1/fr/create-procedure.html –

+2

@JeromyFrench, Oui; J'ai raté que vous utilisez 5.1. *. Vous pouvez ensuite l'utiliser dans la condition 'WHERE' mais en MySQL 5.6 ou plus, vous pouvez aussi utiliser 'collate' dans la déclaration des paramètres; comme vous l'avez déjà édité. Ouais merci pour ça. – Rahul

+0

Merci de m'avoir indiqué la bonne direction. –

Questions connexes