面試或者工作中經常能遇到類似於搶購或者是併發爭奪默寫限量資源的需求,有一些想法但是比較亂,這裏剛好整理一下。
一個搶購活動主要由這幾部分組成
1.頁面刷新-刷新時間/可購買數量
2.下單-爭奪購買資格
3.支付-更新訂單狀態
頁面刷新處理辦法:
1.頁面靜態化
2.反向代理緩存靜態頁面
3.所需動態參數通過接口獲得,不要經過框架渲染
4.提供參數的接口不要由查詢數據庫的操作,所有搶購參數全部放在內存或者緩存中
下單處理辦法:重點
1.過濾器過濾請求(可以視搶購是否真的很大的併發量選擇開啓):主要是考慮以某種假隨機的方式過濾掉一部分請求,例如獲取隨機數在某個範圍內才允許繼續搶購/IP尾號爲某幾個數才允許繼續搶購
2.過濾器過濾掉惡意請求:限制某一賬號頻繁請求/某一賬號第一次進入搶購後進行記錄,再次進入則在過濾器處攔截返回提示搶購中;限制某一IP頻繁請求對IP一秒內請求5-10次的拉入黑名單30秒/60秒,此情況可返回線路繁忙/搶購繁忙
3.佔用庫存:重點
單點系統用內存,分佈式可以用緩存,將此次搶購商品數量放入其中。或者採用佔用資格即增加的方式,維護庫存。
經過上面一系列的攔截過濾,假設有10件商品參與搶購,有1000個用戶參與到搶購活動中來,前面兩種過濾後期望剩餘用戶數爲100。
單點系統調用同步方法(沒測試過)對內存中的庫存進行操作。
分佈式方法可以對redis的key進行incr或decr維護緩存中的庫存。
佔用庫存成功的將繼續生成訂單即支付,未有機會執行佔用庫存的,需要對庫存進行判斷,如果大於等於搶購數量則返回搶購失敗。
4.下單:可異步生成訂單,直接返回搶購成功,請去訂單列表支付(體驗不太好)。或者就同步生成訂單,跳轉訂單頁面進行支付。
支付處理辦法:
1.與銀行支付通訊必須是同步的,如果有notify,則在notify結束後修改訂單狀態。
記錄一下,以後會補上一個簡單搶購系統的詳細代碼實現。