Résolution de l'erreur de mélange illégal de classements dans MySQL
Lors de l'exécution d'opérations de base de données impliquant la comparaison ou la manipulation de données textuelles, il est crucial d'assurer la cohérence dans les classements de caractères. Dans MySQL, le message d'erreur « Mélange illégal de classements » indique généralement une incompatibilité entre les classements utilisés pour les opérandes dans une opération.
Dans le code fourni, le problème provient d'un conflit entre les classements utilisés dans le tables et procédures stockées suivantes :
CREATE TABLE users ( ... ) ENGINE = INNODB CHARACTER SET utf8 COLLATE utf8_unicode_ci; CREATE TABLE products ( ... ) ENGINE = INNODB CHARACTER SET utf8 COLLATE utf8_unicode_ci; CREATE TABLE productUsers ( ... ) ENGINE = INNODB CHARACTER SET utf8 COLLATE utf8_unicode_ci; CREATE PROCEDURE updateProductUsers (IN rUsername VARCHAR(24),IN rProductID INT UNSIGNED,IN rPerm VARCHAR(16)) BEGIN UPDATE productUsers INNER JOIN users ON productUsers.userID = users.userID SET productUsers.permission = rPerm WHERE users.username = rUsername AND productUsers.productID = rProductID; END
Les paramètres d'entrée de la procédure stockée et la colonne de nom d'utilisateur de la table des utilisateurs sont déclarés avec le classement par défaut utf8_general_ci, tandis que la colonne d'autorisation de la table productUsers et le paramètre rPerm sont déclarés avec le classement utf8_unicode_ci.
Pour résoudre ce problème, vous disposez de plusieurs options :
Option 1 : Ajouter COLLATE à Variables d'entrée
Ajoutez la clause COLLATE aux variables d'entrée dans l'appel de procédure stockée pour spécifier explicitement le classement utf8_unicode_ci.
$rUsername = 'aname' COLLATE utf8_unicode_ci; $call = "CALL updateProductUsers(@rUsername, @rProductID, @rPerm);";
Option 2 : ajouter COLLATE à la clause WHERE
Ajouter la clause COLLATE à la clause WHERE dans le définition de procédure stockée pour spécifier le classement utf8_unicode_ci pour le user.username column.
CREATE PROCEDURE updateProductUsers( IN rUsername VARCHAR(24), IN rProductID INT UNSIGNED, IN rPerm VARCHAR(16)) BEGIN UPDATE productUsers INNER JOIN users ON productUsers.userID = users.userID SET productUsers.permission = rPerm WHERE users.username = rUsername COLLATE utf8_unicode_ci AND productUsers.productID = rProductID; END
Option 3 : Ajouter COLLATE à la définition du paramètre IN
Pour les versions MySQL antérieures à 5.7, vous pouvez ajouter la clause COLLATE à la définition du paramètre IN dans la procédure stockée elle-même.
CREATE PROCEDURE updateProductUsers( IN rUsername VARCHAR(24) COLLATE utf8_unicode_ci, IN rProductID INT UNSIGNED, IN rPerm VARCHAR(16)) BEGIN UPDATE productUsers INNER JOIN users ON productUsers.userID = users.userID SET productUsers.permission = rPerm WHERE users.username = rUsername AND productUsers.productID = rProductID; END
Option 4 : Modifier la table Champ
Modifiez la colonne du nom d'utilisateur dans la table des utilisateurs pour utiliser le classement utf8_unicode_ci.
ALTER TABLE users CHARACTER SET utf8 COLLATE utf8_unicode_ci;
Bien que utf8_general_ci soit généralement plus rapide pour le tri des données, il est recommandé d'utiliser utf8mb4/utf8mb4_unicode_ci car il prend en charge une plus large gamme de caractères Unicode.
Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!