JAVA高并发秒杀系统构建之——业务分析与Dao层搭建

JAVA高并发秒杀系统构建之——业务分析与Dao层搭建

前言:最近在学习Java高并发,俗话说学以致用,现在准备搭建一个基于springMvc+spring+mybatis的手机秒杀系统,下面先从业务分析开始。

秒杀系统的业务流程

这里写图片描述
这里写图片描述


这里写图片描述


这里写图片描述

对于mysql来说,秒杀系统最主要的难点问题就是”竞争问题”,竞争问题即为多个用户对同一资源发起争夺
这里写图片描述

在mysql中,主要通过事务和行级锁来解决”竞争问题”。对于mysql的事务来说,在本系统中有以下几个步骤 1、事务开启 2、更新库存信息 3、插入购买明细 4、提交事务, 而竞争问题,主要出现在步骤2中,即发生在更新库存信息中。

行级锁,在本系统作用即为,当一条update语句执行时,其他update语句将处于等待状态
这里写图片描述
综合以上内容,可以看出,秒杀系统的难点在于如何高效地处理竞争问题


下面我们来开始设计数据库的表。

第一个表是秒杀商品表,其表创建sql语句如下图,其中新建3个索引,分别是秒杀商品秒杀开始时间,秒杀结束时间,商品创建时间,建这3个索引的目的是为了提高查询的速率。
这里写图片描述

第二个表是秒杀成功明细表,主键采用联合主键的方式,即seckill_id和user_phone做为联合主键,原因是这两个信息可以唯一标识一个秒杀成功明细,建立1个索引,索引栏为创建时间
这里写图片描述

表设计完之后,我们来设计dao实体和接口编码

这里写图片描述

之所以在SuccessKilled类中放一个Seckill类,是因为这两个实体存在多对一的关系,即为,多个SuccessKilled对应一个Seckill,在SuccessKilled中存放Seckill,是方便后续操作中获取数据和更新数据

这里写图片描述



接下来是Dao接口编码

SeckillDao
这里写图片描述

SuccessKilledDao
这里写图片描述
说明一下,因为SuccessKilled是以seckillId和userPhone作为联合主键,因此可以将此作为过滤重复的门槛,即保证不会出现用户多抢同一种seckill(秒杀抢购商品)的情况


基于Mybatis实现Dao

这里通过mybatis中的mapper方式来实现Dao层,基本的mybatis-config配置文件和spring整合mybatis的配置文件就不再详细给出,我想大家都应该会配置。因为有些人用hibernate可能方式不同,但整体系统实现思想是一样的。

SeckillDao.xml
这里写图片描述


SuccessKilledDao.xml
这里写图片描述

在insertSuccessKilledDao这里,利用sql中的ignore属性,当出现主键冲突时,可以将这一错误的提示转化为返回值0给系统。这样,方便了编码人员过滤重复,对于系统的业务处理是非常有帮助的。


mybatis更能发挥出sql大牛们的功底能力,因为相对于hibernate框架,mybatis更能突显程序员们对于sql语句的灵活编写能力,更能自由控制sql, 更能体现程序员的sql编写技巧,进而可以编写出更高效的sql语句,去适应系统的业务逻辑。


以上即为该系统的业务分析和Dao层的编写设计,下面的文章开始讲解Service层。

java实现秒杀系统@Controller @RequestMapping("seckill")//url:/模块/资源/{id}/细分 /seckill/list public class SeckillController { private final Logger logger = LoggerFactory.getLogger(this.getClass()); @Autowired private SeckillService seckillService; @RequestMapping(value="/list",method = RequestMethod.GET) public String list(Model model){ //获取列表页 List list=seckillService.getSeckillList(); model.addAttribute("list",list); //list.jsp+model = ModelAndView return "list";//WEB-INF/jsp/"list".jsp } @RequestMapping(value = "/{seckillId}/detail",method = RequestMethod.GET) public String detail(@PathVariable("seckillId") Long seckillId, Model model){ if (seckillId == null){ return "redirect:/seckill/list"; } Seckill seckill = seckillService.getById(seckillId); if (seckill == null){ return "forward:/seckill/list"; } model.addAttribute("seckill",seckill); return "detail"; } //ajax json @RequestMapping(value = "/{seckillId}/exposer", method = RequestMethod.POST, produces = {"application/json;charset=UTF-8"}) @ResponseBody public SeckillResult exposer(@PathVariable("seckillId") Long seckillId){ SeckillResult result; try { Exposer exposer =seckillService.exportSeckillUrl(seckillId); result = new SeckillResult(true,exposer); } catch (Exception e) { logger.error(e.getMessage(),e); result = new SeckillResult(false,e.getMessage()); } return result; } @RequestMapping(value = "/{seckillId}/{md5}/execution", method = RequestMethod.POST, produces = {"application/json;charset=UTF-8"} ) @ResponseBody public SeckillResult execute(@PathVariable("seckillId")Long seckillId,
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值