Qing 1 жил өмнө
parent
commit
40ac6a9671

+ 48 - 12
redis-demo/src/main/java/com/sf/service/RedisServiceImpl.java

@@ -1,5 +1,6 @@
 package com.sf.service;
 
+import com.sf.utils.DateUtils;
 import com.sf.utils.RedisUtils;
 import lombok.extern.slf4j.Slf4j;
 import org.springframework.beans.factory.annotation.Autowired;
@@ -11,6 +12,8 @@ import org.springframework.data.redis.core.script.DefaultRedisScript;
 import org.springframework.scripting.support.ResourceScriptSource;
 import org.springframework.stereotype.Service;
 
+import java.text.SimpleDateFormat;
+import java.time.LocalDateTime;
 import java.util.ArrayList;
 import java.util.List;
 
@@ -26,17 +29,41 @@ public class RedisServiceImpl implements RedisService {
         // 先判断 是否在秒杀有效时间内
         //  也就是当前时间  是否 >= startTime  <= endTime
 
+        String keyStart = "1_startTime";
+        String keyEnd = "1_endTime";
+        String startStr = (String) redisUtils.get(keyStart);
+        String endStr = (String) redisUtils.get(keyEnd);
+
+        LocalDateTime startTime = DateUtils.getDateTime(startStr);
+        LocalDateTime endTime = DateUtils.getDateTime(endStr);
+        LocalDateTime nowTime = LocalDateTime.now();
+
+        if (nowTime.isBefore(startTime)) {
+            log.info("还未到秒杀开始时间");
+            return;
+        }
+        if (nowTime.isAfter(endTime)) {
+            log.info("秒杀已结束");
+            return;
+        }
+        log.info("正在进行秒杀");
+
         // goodsId = 1
         // 1_stock_num
-//        String key = goodsId + "_stock_num";
-//        Integer num = (Integer) redisUtils.get(key);
-//        // 出现超卖的原因
-//        // 当10个线程同时获取num的值  此时num=5 会同时进行自减操作
-//        if (num > 0) {
-//            Long decr = redisUtils.decr(key);
-//            System.out.println(decr);
-//        }
 //        handleByTran(userId, goodsId);
+
+
+        // 双重校验的机制
+        // 先验证是否有库存
+        String key = goodsId + "_stock_num";
+        Integer num = (Integer) redisUtils.get(key);
+        // 出现超卖的原因
+        // 当10个线程同时获取num的值  此时num=5 会同时进行自减操作
+        if (num == 0) {
+            log.info("已经秒杀光了");
+            return;
+        }
+        // 在执行脚本之后 再一次验证有库存
         handleByLua(userId, goodsId);
 
         // 加锁  乐观锁和悲观锁
@@ -107,6 +134,19 @@ public class RedisServiceImpl implements RedisService {
 
     @Override
     public void init() {
+        // 初始化时增加秒杀开始和结束时间
+        // <1_startTime,"20220224">
+        // <1_endTime,"20220227">
+
+        String startTime = DateUtils.getDateTimeStr(2024, 2, 22);
+        String endTime = DateUtils.getDateTimeStr(2024, 2, 24);
+
+        String keyStart = "1_startTime";
+        String keyEnd = "1_endTime";
+
+        redisUtils.set(keyStart, startTime);
+        redisUtils.set(keyEnd, endTime);
+
         // 初始化秒杀商品的库存数量
         // stockNum
         // <1,10>    <1,9>
@@ -124,9 +164,5 @@ public class RedisServiceImpl implements RedisService {
 //        map.put("2", 10L);
 //        redisUtils.setAllMap("stock_num", map);
 
-
-        // <1_startTime,"20220224">
-        // <1_endTime,"20220227">
-
     }
 }

+ 33 - 0
redis-demo/src/main/java/com/sf/utils/DateUtils.java

@@ -0,0 +1,33 @@
+package com.sf.utils;
+
+import java.text.SimpleDateFormat;
+import java.time.LocalDateTime;
+import java.time.format.DateTimeFormatter;
+
+public class DateUtils {
+
+    public static String getDateTimeStr(int year, int month, int day) {
+//        SimpleDateFormat format = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
+//        LocalDateTime.now();
+//        LocalDateTime dateTime = LocalDateTime.of(2024,2,22,0,0,0);
+        LocalDateTime dateTime = LocalDateTime.of(year, month, day, 0, 0, 0);
+        DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
+        return dateTime.format(formatter);
+    }
+
+    public static LocalDateTime getDateTime(String str) {
+        DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
+        return LocalDateTime.parse(str, formatter);
+    }
+
+    public static void main(String[] args) {
+        DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss");
+        String str = "2024-02-24 00:00:00";
+        LocalDateTime dateTime = getDateTime(str);
+        LocalDateTime nowTime = LocalDateTime.now();
+        System.out.println(nowTime.format(formatter));
+        System.out.println(nowTime.isBefore(dateTime));
+        System.out.println(nowTime.isAfter(dateTime));
+    }
+
+}

+ 2 - 1
redis-demo/src/main/java/com/sf/utils/HttpUtils.java

@@ -31,7 +31,8 @@ public class HttpUtils {
     }
 
     public static void main(String[] args) throws Exception {
-        String url = "http://localhost:8080/init";
+//        String url = "http://localhost:8080/init";
+        String url = "http://localhost:8080/seckill?userId=111&goodsId=1";
         seckill(url);
     }
 }