Java秒殺簡單設計二:數據庫表和Dao層設計

Java秒殺簡單設計二:數據庫表Dao層設計

上一篇中搭建springboot項目環境和設計數據庫表  https://www.cnblogs.com/taiguyiba/p/9791431.htmlhtml

在此基礎上設計數據庫表Dao層代碼java

1.數據庫表設計

項目涉及到兩張表,seckill:秒殺庫存表,success_killed:秒殺成功明細表spring

seckill:秒殺庫存表數據庫

CREATE TABLE `seckill`  (
  `seckill_id` bigint(20) NOT NULL AUTO_INCREMENT COMMENT '商品庫存ID',
  `name` varchar(120) CHARACTER SET utf8 COLLATE utf8_general_ci NOT NULL COMMENT '商品名稱',
  `number` int(11) NOT NULL COMMENT '庫存數量',
  `create_time` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP COMMENT '建立時間',
  `start_time` timestamp NOT NULL DEFAULT '0000-00-00 00:00:00' COMMENT '秒殺開始時間',
  `end_time` timestamp NOT NULL DEFAULT '0000-00-00 00:00:00' COMMENT '秒殺結束時間',
  PRIMARY KEY (`seckill_id`) USING BTREE,
  INDEX `idx_start_time`(`start_time`) USING BTREE,
  INDEX `idx_end_time`(`end_time`) USING BTREE,
  INDEX `idx_create_time`(`create_time`) USING BTREE
) ENGINE = InnoDB AUTO_INCREMENT = 1000 CHARACTER SET = utf8 COLLATE = utf8_general_ci COMMENT = '秒殺庫存表';

 

插入數據:apache

INSERT INTO `seckill` VALUES (1000, '1000元秒殺iphone6', 100, '2018-10-14 22:36:57', '2016-01-01 00:00:00', '2016-01-02 00:00:00');
INSERT INTO `seckill` VALUES (1001, '800元秒殺ipad', 200, '2018-10-14 22:36:57', '2016-01-01 00:00:00', '2016-01-02 00:00:00');
INSERT INTO `seckill` VALUES (1002, '6600元秒殺mac book pro', 300, '2018-10-14 22:36:57', '2016-01-01 00:00:00', '2016-01-02 00:00:00');
INSERT INTO `seckill` VALUES (1003, '7000元秒殺iMac', 400, '2018-10-14 22:36:57', '2016-01-01 00:00:00', '2016-01-02 00:00:00');

success_killed:秒殺成功明細表springboot

CREATE TABLE `success_killed`  (
  `seckill_id` bigint(20) NOT NULL COMMENT '秒殺商品ID',
  `user_phone` bigint(20) NOT NULL COMMENT '用戶手機號',
  `state` tinyint(4) NOT NULL DEFAULT -1 COMMENT '狀態標識:-1:無效 0:成功 1:已付款 2:已發貨',
  `create_time` timestamp NOT NULL DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '建立時間',
  PRIMARY KEY (`seckill_id`, `user_phone`) USING BTREE,
  INDEX `idx_create_time`(`create_time`) USING BTREE
) ENGINE = InnoDB CHARACTER SET = utf8 COLLATE = utf8_general_ci COMMENT = '秒殺成功明細表';

 

 

 

2.Dao設計

首先在 SeckillApplication.java文件中添加Mapper掃描註解@MapperScan("com.seckill.dao")mybatis

package com.seckill; import org.mybatis.spring.annotation.MapperScan; import org.springframework.boot.SpringApplication; import org.springframework.boot.autoconfigure.SpringBootApplication; @SpringBootApplication @MapperScan("com.seckill.dao") public class SeckillApplication { public static void main(String[] args) { SpringApplication.run(SeckillApplication.class, args); } }

 

 

建立SeckillDao.java文件:app

    包括減庫存、查詢、使用存儲過程秒殺等方法iphone

 

package com.seckill.dao; import java.util.Date; import java.util.List; import java.util.Map; import org.apache.ibatis.annotations.Param; import com.seckill.entity.Seckill; public interface SeckillDao { /** * 減庫存 * @param seckillId * @param killTime * @return 若是影響行數>1,表示更新庫存的記錄行數 */ int reduceNumber(@Param("seckillId") long seckillId,@Param("killTime") Date killTime); /** * 根據id查詢秒殺的商品信息 * @param seckillId * @return */ Seckill queryById(@Param("seckillId") long seckillId); /** * 根據偏移量查詢秒殺商品列表 * @param offset * @param limit * @return */ List<Seckill> queryAll(@Param("offset") int offset,@Param("limit")int limit); /** * 使用存儲過程執行秒殺 * @param paramMap */ void killByProcedure(Map<String,Object> paramMap); }

 

 注意:Java沒有保存形參的記錄,queryAll(int offset,int limit) ==> queryAll(arg0,arg1),因此在多個參數的時候,須要使用註解:@Paramspa

建立 SuccessKilledDao.java文件

package com.seckill.dao; import org.apache.ibatis.annotations.Param; import com.seckill.entity.SuccessKilled; public interface SuccessKilledDao { /** * 插入購買明細,可過濾重複 * @param seckillId * @param userPhone * @return 插入的行數 */
    int insertSuccessKilled(@Param("seckillId") long seckillId,@Param("userPhone") long userPhone); /** * 根據秒殺商品ID查詢明細SuccessKilled對象, 攜帶了Seckill秒殺產品對象 * @param seckillId * @param userPhone * @return */ SuccessKilled queryByIdWithSeckill(@Param("seckillId") long seckillId,@Param("userPhone") long userPhone); }

 建立SeckillDao.xml文件

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
        "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
 
<mapper namespace="com.seckill.dao.SeckillDao">
    <update id="reduceNumber"> UPDATE seckill SET number = number - 1 WHERE seckill_id = #{seckillId} AND start_time <![CDATA[ <= ]]> #{killTime} AND end_time >= #{killTime} AND number > 0
    </update>
 
    <select id="queryById" resultType="Seckill" parameterType="long"> SELECT * FROM seckill WHERE seckill_id = #{seckillId} </select>
 
    <select id="queryAll" resultType="Seckill"> SELECT * FROM seckill ORDER BY create_time DESC limit #{offset},#{limit} </select>
    <!-- 使用mybatis調用存儲過程 -->
    <select id="killByProcedure" statementType="CALLABLE"> call execute_seckill( #{seckillId,jdbcType=BIGINT,mode=IN}, #{phone,jdbcType=BIGINT,mode=IN}, #{killTime,jdbcType =TIMESTAMP,mode=IN}, #{result,jdbcType=INTEGER,mode=OUT} ) </select>
</mapper>

 SuccessKilledDao.xml文件

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
        "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
 
<mapper namespace="com.seckill.dao.SuccessKilledDao">
    <insert id="insertSuccessKilled">
        <!--當出現主鍵衝突時(即重複秒殺時),會報錯;不想讓程序報錯,加入ignore--> INSERT ignore INTO success_killed(seckill_id,user_phone,state) VALUES (#{seckillId},#{userPhone},0) </insert>
 
    <select id="queryByIdWithSeckill" resultType="SuccessKilled">
        <!--根據seckillId查詢SuccessKilled對象,並攜帶Seckill對象-->
        <!--如何告訴mybatis把結果映射到SuccessKill屬性同時映射到Seckill屬性-->
        <!--能夠自由控制SQL語句--> SELECT sk.seckill_id, sk.user_phone, sk.create_time, sk.state, s.seckill_id "seckill.seckill_id", s.name "seckill.name", s.number "seckill.number", s.start_time "seckill.start_time", s.end_time "seckill.end_time", s.create_time "seckill.create_time" FROM success_killed sk INNER JOIN seckill s ON sk.seckill_id = s.seckill_id WHERE sk.seckill_id=#{seckillId} and sk.user_phone=#{userPhone} </select>
</mapper>
相關文章
相關標籤/搜索