Mysql處理Duplicate entry ‘6‘ for key ‘PRIMARY‘問題及解決
Mysql處理Duplicate entry ‘6‘ for key ‘PRIMARY‘
在業(yè)務中app和設備都需要調(diào)用ip查詢對應城市的天氣接口,出現(xiàn)了ip這個唯一索引引起的插入沖突。
以前單系統(tǒng)處理這種主鍵沖突或唯一索引沖突,都是先查詢后插入。
使用 if-else語句,判斷dp_city是否存在,若存在則更新,不存在則插入。
if not exists (select ip from dp_city where ip = adress) ? ? ? insert into dp_city (ip ,name,...) values(adress,name,...) else ? ? ? update dp_city set name= 'name',... where ip = adress
但這樣寫不僅效率太差,每次都需要執(zhí)行兩條SQL語句,一條語句用來判斷dp_city是否在表中已經(jīng)存在,另一條語句用來插入或更新表中數(shù)據(jù)。
而且在高并發(fā)的場景下,兩個請求同一時刻都查到數(shù)據(jù)不存在,一個請求先插入數(shù)據(jù),另一個請求再插入數(shù)據(jù)時就會出現(xiàn)主鍵或索引沖突的異常,也不能保證原子性。
解決這個問題最常規(guī)的做法是:加鎖
加數(shù)據(jù)庫悲觀鎖太影響性能;加數(shù)據(jù)庫樂觀鎖,基于版本號判斷,一般用于更新操作,像這種插入操作基本上不會用。
另一種辦法是使用redis加入基于redis的分布式鎖,鎖定已存在的ip。但也如果過度依賴redis,若是出現(xiàn)網(wǎng)絡超時,服務就悲劇了。
那么有沒有更優(yōu)雅高效的方法呢,通過查閱資料,發(fā)現(xiàn)MySQL一條語句很好的解決了這個問題:ON DUPLICATE KEY UPDATE
該語句的語法如下:
INSERT INTO tablename(field1,field2, field3, ...) VALUES(value1, value2, value3, ...) ON DUPLICATE KEY UPDATE field1=value1,field2=value2, field3=value3, ...;?
這個語法的目的是為了解決重復性,當數(shù)據(jù)庫中存在某個記錄時,執(zhí)行這條語句會更新它,而不存在這條記錄時,會插入它。
該語句規(guī)則如下:
如果你插入的記錄導致一個UNIQUE索引或者primary key(主鍵)出現(xiàn)重復,那么就會認為該條記錄存在,則執(zhí)行update語句而不是insert語句,反之,則執(zhí)行insert語句而不是更新語句。
mysql1062錯誤:Duplicate entry ‘...‘ for key ‘PRIMARY
問題解釋
Duplicate entry ‘…’ for key ‘PRIMARY,即插入數(shù)據(jù)時,要插入數(shù)據(jù)的主鍵數(shù)據(jù)(…)已經(jīng)存在,不能再重復添加了。
例:Duplicate entry ‘0’ for key ‘PRIMARY是指主鍵為0的數(shù)據(jù)已經(jīng)存在,不能再插入主鍵值為0的數(shù)據(jù)了。
問題解決
在執(zhí)行插入操作insert前,可以先執(zhí)行一遍該主鍵值的查找操作select
【簡單的來說,就是這個語句已經(jīng)執(zhí)行過了,無需重復執(zhí)行】
1062、1060報錯都是一樣的
以上為個人經(jīng)驗,希望能給大家一個參考,也希望大家多多支持腳本之家。
相關文章
MySQL如何查詢數(shù)據(jù)庫中所有表名及注釋等信息
這篇文章主要介紹了MySQL如何查詢數(shù)據(jù)庫中所有表名及注釋等信息問題,具有很好的參考價值,希望對大家有所幫助,如有錯誤或未考慮完全的地方,望不吝賜教2023-10-10Django連接本地mysql數(shù)據(jù)庫(pycharm)的步驟
這篇文章主要介紹了Django連接本地mysql數(shù)據(jù)庫(pycharm)的步驟,本文分步驟給大家介紹的非常詳細,對大家的學習或工作具有一定的參考借鑒價值,需要的朋友可以參考下2020-09-09mysql聚集索引、輔助索引、覆蓋索引、聯(lián)合索引的使用
本文主要介紹了mysql聚集索引、輔助索引、覆蓋索引、聯(lián)合索引的使用,文中通過示例代碼介紹的非常詳細,具有一定的參考價值,感興趣的小伙伴們可以參考一下2022-02-02