はじめに
MySQLの処理能力が限られているため、スパイク要求がキューに配置された後、スパイク要求の処理が完了するまでに時間がかかることがあります。この間、フロントエンドはスパイク要求の処理結果を常に尋ねます。
1.フロントエンドでポーリング機能を定義します。
50ミリ秒ごとに "/ miaosha / getresult"インターフェースを呼び出して、パラメーターgoodsIdを渡します。スパイクが成功すると、注文ページを表示するかどうかを尋ねます。スパイクが失敗すると、失敗情報が表示され、スパイクリクエストが表示されます。
まだ処理中の場合は、50ミリ秒待ってからもう一度クエリしてください。
1 // ポーリング関数: 50ミリ秒ごとにスパイクが成功するかどうかを確認します2 関数getResult(goodsId){ 3 g_showLoading(); 4 $ .ajax({ 5 url: "/ miaosha / getresult" 、 6 type: "GET" 、 7 データ:{ 8 goodsId:$( "#goodsId" ).val()、 9 }、 10 成功:function(data){ 11 var result = data.data; 12 if(result <0 ){ 13 レイヤー。 msg( "申し訳ありませんが、スパイクは失敗しました" ); 14 } else if(result == 0 ){ 15 setTimeout(function(){ 16 getResult(goodsId); 17 }、50 ) 18 } else { 19 layer.confirm( "おめでとう、スパイクは成功。注文を確認しますか?"、 {btn:["OK"、 "Cancel" ]}、 20 関数(){ 21 window.location.href = "/ order_detail.htm?orderId =" + result; 22 }、 23 function(){ 24 layer.closeAll(); 25 26 }); 27 } 28 29 }、 30 エラー:関数(){ 31 layer.msg(data.msg); 32 } 33 }); 34 35 }
2.バックエンドのgetResultメソッドは、スパイクの処理結果を返します
成功:注文IDを返します;失敗:在庫がないことを示す-1を返します;処理中:0を返します。
1 / * 2 *ポーリング関数:スパイク3 の結果を表示 3 * * / 4 @AccessLimit(秒= 5、maxCount = 5 ) 5 @RequestMapping(値= "/ getresult"、メソッド= RequestMethod.GET) 6 @ResponseBody 7 public Result <Long> getResult(Model model、MiaoshaUser user、@ RequestParam( "goodsId")long goodsId){ 8 // 現在のスパイクステータスを判断する 9 long result = miaoshaService.getMiaoshaResult(user.getId()、goodsId); 10 11 return Result.success(result); 12 }
3. miaoshaService.javaのgetMiaoshaResult()メソッドは、スパイクの結果を実際に取得するメソッドです
このメソッドには、goodsIdとuserIdの2つのパラメーターがあります。これらの2つのパラメーターはクエリに使用されます。
このメソッドでは、2つの判断が行われます。1回目はgoodsId + userIdに対応するスパイク注文が存在するかどうかであり、注文番号が返されます。それ以外の場合は2回目
2回目は在庫削減の状況を判断し、在庫削減に失敗した場合はスパイクを返却し、それ以外の場合は処理済とみなします。
1 // ポーリング中のスパイクのステータスを判別します 2 public long getMiaoshaResult(Long userId、long goodsId){ 3 // 1. スパイクが成功したかどうか判別します 4 OrderInfo orderInfo = orderInfoService.getByUserIdGoodsId(userId、goodsId); 5 if(orderInfo!= null ){ 6 return orderInfo.getId(); // 注文ID 7 } 8 // 成功した場合、失敗したか、進行中であるかを判断します 9 if(!getReduceResult(goodsId)){ 10 return -1; // 在庫なし、スパイクキル 11 } else return 0; // 在庫あり、スパイクキル 12 }
2番目の判断では、在庫削減結果を取得する関数であるgetResult()関数を使用する必要があり、在庫削減結果を保存するための対応するsetResult()関数があります。
1 プライベート ボイド setReduceResult(長い goodsId、ブールreduceResult){ 2 redisService.set(ReduceResultPrefix.getReduceResult、 "" + goodsId、reduceResult)。 3 } 4 5 private boolean getReduceResult(long goodsId){ 6 return redisService.exists(ReduceResultPrefix.getReduceResult、 "" + goodsId); 7 }
在庫削減操作の後にsetReduceResultメソッドを呼び出して、在庫削減の結果をredisにキャッシュします。
1 // 3つのステップ:在庫の削減、注文の 発行、スパイク注文の書き込み2 @Transactional 3 public OrderInfo miaoSha(long useId、long goodsId){ 4 // 在庫の 削減、および在庫削減 の結果の設定5 boolean reduceResult = miaoshaGoodsService。 reduceStock(goodsId); 6 miaoshaGoodsService.reduceFMStock(goodsId); 7 setReduceResult(goodsId、reduceResult); 8 if(!reduceResult){ 9 return null ; 10 }
その中で、miaoshaGoodsService.reduceStock(goodsId);は、ORMフレームワークの更新オペレーションを呼び出して在庫を削減します。
更新操作は影響を受ける行の数を返します。戻り値が1の場合、在庫削減は成功したことを意味し、戻り値は0であり、在庫削減が失敗したことを意味します。
miaoshaGoodsService.reduceStock()メソッドでは、0および1が戻り値としてfalseおよびtrueに変換され、reduceResult変数に割り当てられます。
次に、reduceResult変数をredisにキャッシュします。