Java解决高并发秒杀商品

在看本文章之前,需要了解Spring boot搭建和使用 ,本篇文章核心问题是如何解决高并发问题。

开发环境:redis缓存4.0.1,Rabbitmq消息队列,Erlang(这个跟MQ环境有关,先安装Erlang,再安装MQ),mysql5.7,JDK1.8(Spring boot要用1.8以上的版本)

开发框架:Spring boot 2.0.4 , mybatis,前端页面:thymeleaf展示信息

一:问题

首先我们要考虑的是为什么要解决高并发,高并发瓶颈出现在哪里,有了解过的朋友肯定知道是在数据库,因为在大量请求去操作数据库时会出现数据的错乱,超卖,系统崩溃,mysql死锁等现象。

二:思路

既然知道问题出现在哪之后,就要对症下药,减少对数据的访问。在这里提供一下解决思路:

1. 页面静态化:就是将整个页面存储到redis中,下次访问时去读取redis中的页面值

2. cdn:主要对整个网站的静态资源文件进行加速,如图片,css,js等(去阿里看教程)

3.数学验证码:用户在计算验证码结果时可以减少大量请求同时进入,减少redis, mysql,服务器的压力。

4:库存标识:这是一个巨大优化,通过标识来判断redis的库存是否足够,如不足就中断去读取redis库存。例:boolean over = map.get(goodsId);当我们map通过key读取到value值为true的时候,就返回错误提示给用户, if(over) { return Result.error(‘库存不足’); }.....这样不管以后有多个请求进入都只运行两行代码,以下的操作无法进入。

5.生成动态url:主要是防止恶意用户通过固定url进行提前秒杀商品(安全方面问题这个不可掉以轻心,你连安全措施都没做好以下的那些操作都是白搭的)

6. redis预减库存::在用户秒杀商品前去redis获取当前的库存数量,然后在秒杀时候直接减去redis存储的库存(大家放心这里Redis和MySQL数据是同步的,只要进入MQ队列操作完成下单,MySQL数据库会-1数量),从而避开去MySQL读取库存数据。

7. MQ消息队列:它是一个中间消息键,通过生产者发送消息给消费者,进行业务操作,而生产者无需知道执行结果,也就是用户点击秒杀之后等待处理结果,之后再去轮询查询处理结果(异步操作),这样就避开了不断请求去操作数据库。(这里的轮询查询也是直接从redis里面去查询,因为秒杀成功之后会将秒杀的结果放到redis中,轮询时候通过key去查询)

8. Nginx: 解决高并发的好方法,也就是我们多增加几个tomcat服务器。当用户访问的时候,请求可以提交到空闲的tomcat服务器上。

三:实现

1. 页面的静态化:很多人说怎么页面静态化,其实页面静态化就是将整个页面储到redis中,我们访问这个接口的时候就直接去获取redis的中页面,这样大大提高了访问页面的速度。如下图:

2. 预先获取秒杀商品信息,库存存储到redis中,怎么个预先法?在启动项目时在MiaoshaController调用InitializingBean接口,这个主要是在启动项目时去查询数据库中所有的秒杀商品的信息,库存等。大家别小看那一行标识代码,这可是一个巨大转折点的优化。为什么呢?接着看下去。如下图:

3. 数学公式验证码,这个也是减少大量请求的方法,因为你要去计算结果,想想几秒钟时间我可以减少多少访问请求,这个数学公司验证码自己去百度找下,同样把生成的验证码结果存储到redis中,判断时在去redis中获取结果对比验证码结果。

4.生成动态url,防止恶意用户提前秒杀商品! 我们应该先在访问秒杀业务时去生成一个动态的url,这样做可以防止恶意用户去通过固定url去提前秒杀商品。方法如下图:

html:

5.当我们生成动态Url之后,我们进行秒杀业务的操作,将我们的url传递到后台进行验证是否与之前所生存的一致,并且进行MQ消息队列处理请求 如下图:

我们执行完秒杀业务层之后,将结果0返回到js中,其实这时候mq已经异步进行操作去下订单操作了,js去轮询查询数据库中是否已经下订单成功,相当是说下订单操作和js去查询下订单信息是互不相关的,这也就说不管有没有秒杀是否成功都先返回一个0结果消息。当然这里还有个问题,就是我们如何区分秒杀的操作是在排队中呢还是库存已经秒杀完毕了呢?请接着继续看下去!

(异步操作,js查询和下订单各自执行)下面来重点将下MQ这个过程,在我们平时的超市中购物也是一样,当我们在结算的时候,并不会一窝蜂一样涌入收银台,而是排队结算。这也是队列机制。我们在使用MQ前先要去配置信息如下图:

然后我们在启动MQ时要自动加载定义通信消息,用于生产者发送消息给消费者的信息

e

当我们在执行秒杀业务验证都通过的话,生产者会发送一条"miaosha.queue"消息给消费者

当然消费者收到信息之后,进行秒杀下订单操作,不过为了数据正确性,这时候需要去数据库查询下当前的库存是否足够,而不是前面判断就可以了,前面redis判断只是为了减少mysql的访问。如下图:

这里我详细说下在下订单时,会出现向上面说怎么区分卖完了和排队中,假如秒杀商品被卖完了我们记录下,将商品Id当作K,true为V存储在redis中,在redis轮询查询的时候就可以判断是在排队还是商品卖完了。(没看明白的去看下轮询查询的代码)

在减库存的时候需要注意下sql语句 ,需要库存数量-1 并且库存数量必须>0才能操作下订单 ,至于添加订单详情数据我就不贴出来了,一般就是平常增加数据操作就行了,如下图:

还没有写完 。。。。。。。。还在更新完善中

我先给下源代码 :https://pan.baidu.com/s/1gpdFvcalAC53mq1L2BV3uw

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 204,053评论 6 478
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 85,527评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 150,779评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,685评论 1 276
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,699评论 5 366
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,609评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,989评论 3 396
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,654评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,890评论 1 298
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,634评论 2 321
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,716评论 1 330
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,394评论 4 319
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,976评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,950评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,191评论 1 260
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 44,849评论 2 349
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,458评论 2 342