簡體   English   中英

mysql: 錯誤代碼 [1267]; 操作 '=' 的排序規則 (latin1_general_cs,IMPLICIT) 和 (latin1_swedish_ci,IMPLICIT) 的非法混合

[英]mysql: error code [1267]; Illegal mix of collations (latin1_general_cs,IMPLICIT) and (latin1_swedish_ci,IMPLICIT) for operation '='

我想讓我的用戶表的password列在 mysql 中case sensitive

以下是該表的說明:

/*Table: mst_user*/

   FIELD          TYPE          COLLATION        
-------------  ------------  -----------------
user_id        VARCHAR(100)  latin1_swedish_ci
first_name     VARCHAR(25)   latin1_swedish_ci
last_name      VARCHAR(25)   latin1_swedish_ci
USER_PASSWORD  VARCHAR(50)   latin1_swedish_ci
user_status    INT(11)       (NULL)           
version_id     INT(11)       (NULL)           
active_status  INT(11)       (NULL)           
user_type      INT(11)       (NULL)    

為了使USER_PASSWORD字段區分大小寫,我執行了以下查詢:

ALTER TABLE `mst_user` MODIFY `USER_PASSWORD` VARCHAR(50) COLLATE `latin1_general_cs`;

這有效並且該字段現在區分大小寫。

但是我有一個存儲過程,它在這個表上執行一個SELECT查詢來檢查用戶是否存在給定的憑據。

存儲過程::

CREATE PROCEDURE `usp_password_verify`(ip_login_id         VARCHAR(200),
                                 ip_user_password    VARCHAR(200),
                                INOUT success     INT(1),
INOUT tbl_usr_password          VARCHAR(100),
INOUT  pkg_user_password         VARCHAR(100))
BEGIN
  SELECT COUNT(*)
    INTO success
    FROM mst_user
   WHERE UPPER (user_id) = UPPER (ip_login_id)
   AND USER_PASSWORD=ip_user_password;

   SET tbl_usr_password = '';
   SET pkg_user_password= '';
END$$

當我從我的 java 代碼調用這個存儲過程時,我收到以下錯誤:

**error code [1267]; Illegal mix of collations (latin1_general_cs,IMPLICIT) and (latin1_swedish_ci,IMPLICIT) for operation '='**

任何人都可以幫助這有什么問題嗎? 在存儲過程中執行時,作為簡單查詢的東西會出錯!?

正如在 表達式排序規則下所記錄

MySQL 分配 coercibility 值如下:

[ deletia ]

  • 列或存儲的例程參數或局部變量的排序規則的可強制性為 2。

[ deletia ]

MySQL 使用 coercibility 值和以下規則來解決歧義:

[ deletia ]

  • 如果雙方具有相同的強制力,則:

    • 如果兩邊都是Unicode,或者兩邊都不是Unicode,那就是錯誤。

可以在表達式中添加顯式COLLATE子句以強制操作數之一具有具有較低強制值的顯式排序規則:

USER_PASSWORD=ip_user_password COLLATE 'latin1_general_cs'

在這種情況下,您甚至可能要考慮latin1_bin

在任何情況下,您都不應該以純文本形式存儲密碼 相反,存儲用戶密碼的加鹽散列,並簡單地驗證散列是否與存儲的相匹配。

因此,在與此錯誤斗爭之后:

ERROR 1267 (HY000): Illegal mix of collations (utf8mb4_unicode_ci,COERCIBLE) and (utf8mb4_general_ci,COERCIBLE) for operation '='

我設法通過從以下位置更改導入數據庫文件來解決此問題:

CHARSET utf8mb4 COLLATE utf8mb4_unicode_ci NO SQL

這是如果您要導入函數/過程/觸發器,我的數據庫具有大量所有這些功能......我將其更改為:

CHARSET=utf8mb4 COLLATE=utf8mb4_general_ci;

我真的希望這可以幫助某人。 我知道上述內容很有幫助,但我仍然花了幾個小時才將其轉化為解決方案。 謝謝

我在面臨同樣的錯誤后來到這里。 在通過提供的解決方案之后,很明顯 COLLATION 是我錯誤的觸發因素。 我的代碼與原始問題類似,但我的錯誤是MySQL said: #1267 - Illegal mix of collations (utf8mb4_0900_ai_ci,IMPLICIT) and (utf8mb4_general_ci,IMPLICIT) for operation '='

我也試圖收集密碼和用戶名(目前沒有散列),我通過為兩個參數顯式添加 COLLATION 來修復它。

第一個代碼(不穩定的代碼):

WHERE user.username = username
AND user.password = password

我當前的代碼(工作代碼):

WHERE user.username = username COLLATE utf8mb4_0900_ai_ci
AND user.password = password COLLATE utf8mb4_0900_ai_ci

僅向密碼添加排序規則以強制與用戶名進行排序規則匹配或僅添加到用戶名不起作用。 即使一個參數已經有正確的排序規則,它仍然有錯誤。 所以我向兩個參數添加了相同的排序規則並且它起作用了。

請記住在完成后對您的密碼進行加鹽/散列,我的代碼仍在進行中。

我知道這有點晚了,但如果這可以讓某人節省半天的時間,那么它仍然值得放下。

所以,我的設置是這樣的: 10.1.22-MariaDB, utf8mb4_general_ci 一切都很好,我恢復了我的數據庫的轉儲,一切順利。

數據庫最初在utf8_general_ci ,但由於某些原因恢復為utf8_unicode_ci 將其改回utf8_general_ci並檢查數據庫中沒有像列或表定義這樣的工件被整理為utf8_unicode_ci而不是utf8_general_ci

嘗試更新特定表會導致在沒有任何明顯原因的情況下非法混合整理。

它歸結為實際上不是表本身,而是相關的觸發器。

事實上,觸發器調用了一個在我的數據庫中沒有整理信息的過程,但是在information_schema.ROUTINES.DATABASE_COLLATION中有一個utf8_unicode_ci整理。

在新數據庫整理的上下文中重新創建過程解決了我的問題。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM