主鍵自增,Insert為0的記錄導致資料混亂

壹頁書發表於2017-02-04
牙疼不是病,疼起來真要命.

環境.MySQL 5.6.14
SQL_Mode:STRICT_TRANS_TABLES,NO_ENGINE_SUBSTITUTION

生產環境 配置表,設定主鍵為自增.
一天某同學讓我幫忙從測試導一批資料到生產.
雖然我對這種方式深惡痛絕,但是沒有辦法..也只能照做.
匯入之後的第二天,業務發現很多生產資料錯亂了。
這個禮物的配置表,主鍵原本設計成自增主鍵.
但是後來他們用0表示一種特殊禮物...坑就在這裡了。

過程模擬

  1. drop table if exists config_gift;
  2. create table config_gift(
  3.     GiftID int not null primary key auto_increment,
  4.     GiftName varchar(32) not null
  5. ) auto_increment=50000;

  6. insert into config_gift(GiftName) select '鮮花';
  7. insert into config_gift(GiftName) select '鞭炮';
  8. insert into config_gift(GiftName) select '福袋';


  9. select * from config_gift;
當時的SQL_Mode是:STRICT_TRANS_TABLES,NO_ENGINE_SUBSTITUTION

如果這時執行如下的語句,
insert into config_gift select 0,'蛋糕';
insert into config_gift select null,'香水';

檢視結果竟然如下:


MySQL 如果已經設定了主鍵自動增長,但是後來卻 插入 0 或者 null 作為主鍵值的話, MySQL會用自增長的值,取代原本的 0 或者 null 。

業務程式碼中寫死了 0 這個禮物ID的判斷,所以導致了大量資料錯亂,花了很長時間修正.

這種事情猝不及防
業務方定的這個特殊禮物就用0表示,而且也沒有人來通知資料庫...
資料上線的時候,都是一批資料,人力甄別資料似乎也不現實.

改SQL_mode保平安吧.

在自增主鍵下,處理主鍵為0的資料
set @@session.sql_mode='STRICT_TRANS_TABLES,NO_ENGINE_SUBSTITUTION,no_auto_value_on_zero'

修改Global和Session級別的SQL_mode之後,主鍵為0的禮物可以正確插入了。


主要注意的是,即使在這個SQL_mode下(STRICT_TRANS_TABLES,NO_ENGINE_SUBSTITUTION,no_auto_value_on_zero)
自增主鍵,Insert主鍵為null的資料,還是會使用自增主鍵的值作為主鍵,而不是報錯.

來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/29254281/viewspace-2133054/,如需轉載,請註明出處,否則將追究法律責任。

相關文章