訂單30分鐘未支付,系統自動超時關閉有哪些實現方案?
1.基於任務排程實現,效率是非常低,耗伺服器效能
2.基於redis過期key實現.使用者下單的時候,生成乙個令牌(有效期)30分鐘,存放到我們redis;
redis.set(ordertoken ,orderid) 下單時候存放到redis,並儲存id入庫,30分鐘過期,
redis客戶端監聽,過期獲取到orderid,拿orderid去查訂單,沒有支付則,訂單關閉,庫存增加
缺點:非常冗餘 ,會在表中存放乙個冗餘字段
3.基於redis延遲佇列
4.基於mq的延遲佇列實現(最佳) 死信佇列(延遲佇列)
原理:當我們在下單的時候,往mq投遞乙個訊息設定有效期為30分鐘,但該訊息失效的時候(沒有被消費的情況下),
執行我們客戶端乙個方法告訴我們該訊息已經失效,這時候查詢這筆訂單是否有支付.
實現原理(訊息過期投遞到死信佇列)
原理:下單投放訊息到a交換機(過期時間30分鐘),訊息到aa佇列(繫結死信交換機),不設定aa佇列的消費者(故此訊息一直未消費).
30分鐘後,過期訊息投遞到死信交換機,死信佇列,由死信消費者消費,判斷訂單id是否支付,執行業務邏輯,支付->return
未支付->關閉訂單,返還庫存
demo演示:
1.宣告訂單和死信交換機、 訂單和死信佇列 、關鍵步驟訂單佇列繫結訂單交換機和死信交換機 、死信佇列繫結死信交換機
public class deadlettermqconfig ")
private string orderexchange;
/*** 訂單佇列
*/@value("$")
private string orderqueue;
/*** 訂單路由key
*/@value("$")
private string orderroutingkey;
/*** 死信交換機
*/@value("$")
private string dlxexchange;
/*** 死信佇列
*/@value("$")
private string dlxqueue;
/*** 死信路由
*/@value("$")
private string dlxroutingkey;
/*** 宣告死信交換機
*/@bean
public directexchange dlxexchange()
/*** 宣告死信佇列
*/@bean
public queue dlxqueue()
/*** 宣告訂單業務交換機
*/@bean
public directexchange orderexchange()
/*** 宣告訂單佇列 核心操作一
*/@bean
public queue orderqueue()
/*** 繫結訂單佇列到訂單交換機
*/@bean
public binding orderbinding()
/*** 繫結死信佇列到死信交換機
*/@bean
public binding binding()
}
server.port=8082
spring.datasource.url=jdbc:mysql://localhost:3306/test?useunicode=true&characterencoding=utf-8&servertimezone=gmt%2b8
spring.datasource.username=root
spring.datasource.password=root
spring.datasource.driver-class-name=com.mysql.cj.jdbc.driver
#開啟駝峰命名 譬如資料庫create_time 自動對映pojo屬性createtime
mybatis.configuration.map-underscore-to-camel-case=true
#配置virtual-host虛擬主機
spring.rabbitmq.virtual-host=/zhang_rabbit
#ip位址
spring.rabbitmq.host=127.0.0.1
#使用者名稱 密碼
spring.rabbitmq.username=zhang
spring.rabbitmq.password=zhang
#連線埠號
spring.rabbitmq.port=5672
#spring.rabbitmq.publisher-confirm-type=
#模擬演示死信佇列
mayikt.dlx.exchange=mayikt_order_dlx_exchange
mayikt.dlx.queue=mayikt_order_dlx_queue
mayikt.dlx.routingkey=dlx
##備胎交換機
mayikt.order.exchange=mayikt_order_exchange
mayikt.order.queue=mayikt_order_queue
mayikt.order.routingkey=mayikt.order
3.建立producer生產者.暫時設定訊息10秒過期,驗證訊息是否加入死信佇列
@restcontroller
public class ordercontroller ")
private string orderexchange; //訂單交換機
@value("$")
private string orderroutingkey; //訂單路由key
public string addorder()
//rabbit投遞訊息
rabbittemplate.convertandsend(orderexchange,orderroutingkey,orderid,messagepostprocessor());
return "success";
}//處理待傳送訊息
private messagepostprocessor messagepostprocessor()};}
}
4.死信消費者消費過期訊息
@component //死信佇列
public class orderdlxconsumer
//根據id查詢
if (null == orderentity)
//獲取狀態
integer orderstatus=orderentity.getorderstatus();
//判斷未支付 , 關閉訂單
if(0==orderstatus)}}
5.下單測試 http://localhost:8082/addorder.訂單入庫成功.狀態0未支付
10秒後,死信消費者處理 狀態0未支付 變為2 已關閉
RabbitMQ延時佇列實現訂單關閉
配置virtual host虛擬主機 spring.rabbitmq.virtual host test order close ip位址 spring.rabbitmq.host 127.0 0.1 使用者名稱 密碼 spring.rabbitmq.username guest spring.ra...
訂單管理系統 v3 0
執行平台 net framework 2.0 領域 訂單管理系統程式優點 1 遠端api方式儲存訂單,完美跨域,任何 加段 就可以提交到系統,與現有銷售專題無縫結合,訂單統一管理。2 完整的許可權分配,細到為每乙個人分配不同的許可權,操作日誌,訂單記錄一目了然。3 廣告碼跟蹤功能,輕鬆了解不同流量來...
原生rabbitMq實現
原生實現rabbitmq 為什麼要使用rabbitmq訊息佇列 我們模擬這樣乙個場景,假如你在網上購物 買了東西,你支付過程5s 傳送簡訊通知5s 郵件通知等時間就更長了,你整個支的過程我們模擬這樣乙個場景,假如你在網上購物 買了東西,你支付過程5s 傳送簡訊通知5s 郵件通知等時間就更長了,你整個...