[英]Postgres: Optimising concurrent same row updates
我正在使用PostgreSQL v10 + golang,我認為這是一個非常常見的SQL問題:
current_value
和一個max_value
整數列。 current_value >= max_value
,我想刪除請求。 current_value
(在最壞的情況下)增加1(可以認為是從分布式主機對同一數據庫的並發更新)。 在我當前和幼稚的實現中,對同一行的多個UPDATE自然會彼此阻塞(如果重要,隔離級別為“讀取已提交”)。 在最壞的情況下,每秒大約有10個以上的請求會更新同一行。 這會造成瓶頸並損害性能,這是我買不起的。
我想到了一些解決方案,但它們都犧牲了完整性或性能。 保持兩者的唯一聽起來不是很干凈,因為這個看似常見的問題:
只要計數器current_value
與max_value
處於相對安全的距離內(delta> 100),就將更新請求發送到一個通道,該通道將由工作人員每秒刷新一次,以收集更新並立即請求更新。 否則(增量<= 100),請在事務的上下文中進行更新(並遇到瓶頸,但在少數情況下)。 這將加快更新請求的速度,直到幾乎達到極限為止,從而有效地解決了瓶頸。
這可能可以解決我的問題。 但是,我不禁想到有更好的方法來解決此問題。
我沒有在網上找到一個很好的解決方案,盡管我的啟發式方法行得通,但感覺並不干凈,而且缺乏完整性。
非常歡迎有創意的解決方案!
感謝@ laurenz-albe的建議,我試圖縮短UPDATE(將行鎖定到事務的COMMIT)之間的持續時間。 將所有UPDATES推送到事務的末尾似乎已經成功了。 現在,我每秒可以處理100多個請求並保持完整性!
每秒10個並發更新太少了。 只要確保交易盡可能短,就不會有問題。
您最大的問題將是VACUUM
,因為許多更新對於PostgreSQL來說可能是最糟糕的工作量。 確保使用70左右的fillfactor
創建表,並且未索引current_value
,以便獲得HOT更新。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.