秒杀系统个人总结
2018-03-30 11:07
176 查看
对于高并发的项目,处理原则是尽量在上游处理,优先级:客户端-》后端内存-》redis-》数据库;如果能在客户端处理的,尽量不交给tomcat,能在tomcat处理的,尽量不要交给redis,毕竟tomcat-redis也存在网络交互,能在redis处理的,尽量不交给数据库,一般高并发的瓶颈都是在数据库。
另外可以使用nignx做负载均衡,横向扩展处理服务器,这时session一般就要保存在redis,这个也是分布式session;可以使用rabbitMQ作为订单的的处理,rabbitMQ是分布式消息队列系统,需要安装,个人感觉什么分布式开源系统,原理都是统一处理多个来源信息,支持集群;
在高并发环境下,可以限制用户某时间段内的访问次数,加验证码等手段减轻服务器压力;另外在高并发下也很容易出现数据错误的情况,例如这里的多个用户同时获得剩余商品都是1,然后就出现订单多于总商品的情况,对于这种情况,可以:1,在数据库表中合适的添加唯一值索引,2,利用rabbitMQ来延迟处理订单,rabbitMQ是通过队列的处理消息,成功进入队列的订单给用户返回排队中的提示信息,后面用户方面可以通过轮询的方式去查找数据库,如果数据库存在该用户的订单信息,即提示秒杀成功,如果数据库的商品为0且订单表不存在该用户信息,提示秒杀失败,否则提示排队中
1、页面静态化,页面缓存:
将页面的写成html,所有的数据都通过js异步获取,并且在页面中加入缓存功能,设置缓存时间,springboot提供缓存统一设置:
#static
spring.resources.add-mappings=true
spring.resources.cache-period= 3600
spring.resources.chain.cache=true
spring.resources.chain.enabled=true
spring.resources.chain.gzipped=true
spring.resources.chain.html-application-cache=true
spring.resources.static-locations=classpath:/static/2、nignx负载均衡
upstream server_pool_miaosha{
server 127.0.0.1:8080 weight=1;
server 127.0.0.1:8081 weight=1;
}
server {
listen 81;
server_name localhost;
location / {
proxy_pass http://server_pool_miaosha;
}
3、分布式session
,随机生成一个token作为key,当前用户user作为value保存在redis中,并且将该token保存在客户端的cookie中,对于客户端每次请求都会自动的将cookie信息传递到服务器,这时我们就可以通过CooKi_NAME-TOKEN获取token,进而去redis获取用户信息
redisService.set(MiaoshaUserKey.token, token, user);
Cookie cookie = new Cookie(COOKI_NAME_TOKEN, token);
cookie.setMaxAge(MiaoshaUserKey.token.expireSeconds());
cookie.setPath("/");
response.addCookie(cookie);
@RequestMapping(value="/{path}/do_miaosha", method= RequestMethod.POST)
@ResponseBody
public Result<Integer> miaosha(Model model, MiaoshaUser user,
@RequestParam("goodsId")long goodsId,
@PathVariable("path") String path) {客户端调用秒杀接口前:
$.ajax({
url:"/miaosha/path",
type:"GET",
data:{
goodsId:goodsId,
verifyCode:$("#verifyCode").val()
},
success:function(data){
if(data.code == 0){
var path = data.data;
console.info("path:"+path);
doMiaosha(path);
}else{
layer.msg(data.msg);
}
},客户端调用秒杀接口:
$.ajax({
url:"/miaosha/"+path+"/do_miaosha",
type:"POST",
data:{
goodsId:$("#goodsId").val(),
},
success:function(data){
if(data.code == 0){
getMiaoshaResult($("#goodsId").val());
//window.location.href="/order_detail.htm?orderId="+data.data.id;
}else{
layer.msg(data.msg);
}
},
这个即能达到隐藏接口的功能
5、接口限流:
public class AccessInterceptor extends HandlerInterceptorAdapter{
@Autowired
MiaoshaUserService userService;
@Autowired
RedisService redisService;
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler)
throws Exception {
if(handler instanceof HandlerMethod) {
MiaoshaUser user = getUser(request, response);
UserContext.setUser(user);
HandlerMethod hm = (HandlerMethod)handler;
AccessLimit accessLimit = hm.getMethodAnnotation(AccessLimit.class);
if(accessLimit == null) {
return true;
}
int seconds = accessLimit.seconds();
int maxCount = accessLimit.maxCount();
boolean needLogin = accessLimit.needLogin();
String key = request.getRequestURI();通过自定义注解,添加拦截器,redis记录通过设置超时时间来限制该用户的某时间段内的访问次数
6、jmeter工具压测
一个完整的jmeter压测包括线程组,HTTP请求默认值,HTTP请求,CSV Data Set Config ,聚合报告
另外可以使用nignx做负载均衡,横向扩展处理服务器,这时session一般就要保存在redis,这个也是分布式session;可以使用rabbitMQ作为订单的的处理,rabbitMQ是分布式消息队列系统,需要安装,个人感觉什么分布式开源系统,原理都是统一处理多个来源信息,支持集群;
在高并发环境下,可以限制用户某时间段内的访问次数,加验证码等手段减轻服务器压力;另外在高并发下也很容易出现数据错误的情况,例如这里的多个用户同时获得剩余商品都是1,然后就出现订单多于总商品的情况,对于这种情况,可以:1,在数据库表中合适的添加唯一值索引,2,利用rabbitMQ来延迟处理订单,rabbitMQ是通过队列的处理消息,成功进入队列的订单给用户返回排队中的提示信息,后面用户方面可以通过轮询的方式去查找数据库,如果数据库存在该用户的订单信息,即提示秒杀成功,如果数据库的商品为0且订单表不存在该用户信息,提示秒杀失败,否则提示排队中
1、页面静态化,页面缓存:
将页面的写成html,所有的数据都通过js异步获取,并且在页面中加入缓存功能,设置缓存时间,springboot提供缓存统一设置:
#static
spring.resources.add-mappings=true
spring.resources.cache-period= 3600
spring.resources.chain.cache=true
spring.resources.chain.enabled=true
spring.resources.chain.gzipped=true
spring.resources.chain.html-application-cache=true
spring.resources.static-locations=classpath:/static/2、nignx负载均衡
upstream server_pool_miaosha{
server 127.0.0.1:8080 weight=1;
server 127.0.0.1:8081 weight=1;
}
server {
listen 81;
server_name localhost;
location / {
proxy_pass http://server_pool_miaosha;
}
3、分布式session
,随机生成一个token作为key,当前用户user作为value保存在redis中,并且将该token保存在客户端的cookie中,对于客户端每次请求都会自动的将cookie信息传递到服务器,这时我们就可以通过CooKi_NAME-TOKEN获取token,进而去redis获取用户信息
redisService.set(MiaoshaUserKey.token, token, user);
Cookie cookie = new Cookie(COOKI_NAME_TOKEN, token);
cookie.setMaxAge(MiaoshaUserKey.token.expireSeconds());
cookie.setPath("/");
response.addCookie(cookie);
@Override public Object resolveArgument(MethodParameter methodParameter, ModelAndViewContainer modelAndViewContainer, NativeWebRequest nativeWebRequest, WebDataBinderFactory webDataBinderFactory) throws Exception { HttpServletRequest request = nativeWebRequest.getNativeRequest(HttpServletRequest.class); HttpServletResponse response = nativeWebRequest.getNativeResponse(HttpServletResponse.class); String paramToken = request.getParameter(MiaoshaUserService.COOKI_NAME_TOKEN); String cookieToken = getCookieValue(request, MiaoshaUserService.COOKI_NAME_TOKEN); if(StringUtils.isEmpty(cookieToken) && StringUtils.isEmpty(paramToken)) { return null; } String token = StringUtils.isEmpty(paramToken)?cookieToken:paramToken; return userService.getByToken(response, token); } private String getCookieValue(HttpServletRequest request, String cookiName) { Cookie[] cookies = request.getCookies(); if(cookies == null || cookies.length <=0){ return null; } for(Cookie cookie : cookies) { if(cookie.getName().equals(cookiName)) { return cookie.getValue(); } } return null; }4、隐藏秒杀地址主要是通过客户端在调用秒杀接口前要先到服务器获取一个随机数,这个随机数会保存在redis中,然后在访问地址中带上这个随机数
@RequestMapping(value="/{path}/do_miaosha", method= RequestMethod.POST)
@ResponseBody
public Result<Integer> miaosha(Model model, MiaoshaUser user,
@RequestParam("goodsId")long goodsId,
@PathVariable("path") String path) {客户端调用秒杀接口前:
$.ajax({
url:"/miaosha/path",
type:"GET",
data:{
goodsId:goodsId,
verifyCode:$("#verifyCode").val()
},
success:function(data){
if(data.code == 0){
var path = data.data;
console.info("path:"+path);
doMiaosha(path);
}else{
layer.msg(data.msg);
}
},客户端调用秒杀接口:
$.ajax({
url:"/miaosha/"+path+"/do_miaosha",
type:"POST",
data:{
goodsId:$("#goodsId").val(),
},
success:function(data){
if(data.code == 0){
getMiaoshaResult($("#goodsId").val());
//window.location.href="/order_detail.htm?orderId="+data.data.id;
}else{
layer.msg(data.msg);
}
},
这个即能达到隐藏接口的功能
5、接口限流:
public class AccessInterceptor extends HandlerInterceptorAdapter{
@Autowired
MiaoshaUserService userService;
@Autowired
RedisService redisService;
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler)
throws Exception {
if(handler instanceof HandlerMethod) {
MiaoshaUser user = getUser(request, response);
UserContext.setUser(user);
HandlerMethod hm = (HandlerMethod)handler;
AccessLimit accessLimit = hm.getMethodAnnotation(AccessLimit.class);
if(accessLimit == null) {
return true;
}
int seconds = accessLimit.seconds();
int maxCount = accessLimit.maxCount();
boolean needLogin = accessLimit.needLogin();
String key = request.getRequestURI();通过自定义注解,添加拦截器,redis记录通过设置超时时间来限制该用户的某时间段内的访问次数
6、jmeter工具压测
一个完整的jmeter压测包括线程组,HTTP请求默认值,HTTP请求,CSV Data Set Config ,聚合报告
相关文章推荐
- 秒杀系统的技术挑战、应对策略以及架构设计总结一二!
- 个人版机房收费系统总结
- 个人版机房收费系统总结
- 数据库基础---数据库系统概论个人总结版
- Linux系统下的ssh使用(依据个人经验总结)
- 个人版机房收费系统总结
- shell(3):个人总结的Linux系统基础和全局导读
- (慕课 ssm与高并发)秒杀系统总结
- 系统分析中写 需求说明书 的方法--个人经验总结
- 作业提交系统Torque个人安装总结(PBS)
- 个人版机房收费系统总结
- ubuntu文件系统的个人总结
- 个人项目总结------珠宝管理系统
- UCOSIII-OSTaskQPend 由于任务内建消息队列形参类型错误导致系统卡死现象个人总结
- 关于完成广告系统后的个人总结
- 《大型网站技术架构:核心原理与案例分析》拜读总结,第十二章——秒杀系统架构设计案例分析
- 自己用springboot+mybatis+easyui写的个人管理系统遇到的问题总结
- 对Linux系统进行配置应该养成做备份的习惯--个人总结
- 秒杀系统的技术挑战、应对策略以及架构设计总结一二!
- BootStrap框架个人总结(bootstrap框架、导航条、下拉菜单、轮播广告carousel、栅格系统布局、标签页tabs、模态框、菜单定位)