当前位置: 首页 > news >正文

从用户角度网站应该具备的条件网站建设哪家好 需要多少钱

从用户角度网站应该具备的条件,网站建设哪家好 需要多少钱,官方网站在家做兼职,查看网站空间1. 为什么要引入令牌大闸#xff1f; 场景1#xff1a;分布式锁和限流都不能解决机器人刷票的问题#xff0c;1000个请求抢票#xff0c;900个限流快速失败#xff0c;另外100个有可能是同一个在刷库。 引入令牌#xff0c;令牌中记录用户信息#xff0c;会进行校验用户…1. 为什么要引入令牌大闸 场景1分布式锁和限流都不能解决机器人刷票的问题1000个请求抢票900个限流快速失败另外100个有可能是同一个在刷库。 引入令牌令牌中记录用户信息会进行校验用户是否拿过令牌如果拿过令牌那么几秒内不允许再获得令牌 场景2没有余票时需要查库存才能知道没票会影响性能不如查询令牌余票来的快 令牌的数量是和票数是相关的令牌可以和票数相等那么通过查询令牌就可以知道是否还有余票会减少查询数据库减少IO压力 2. 增加秒杀令牌表来维护令牌信息 增加一张表表的创建SQL代码如下所示 drop table if exists sk_token; create table sk_token ( id bigint not null comment id, date date not null comment 日期, train_code varchar(20) not null comment 车次编号, count int not null comment 令牌余量, create_time datetime(3) comment 新增时间, update_time datetime(3) comment 修改时间, primary key (id), unique key date_train_code_unique (date, train_code) ) engineinnodb default charsetutf8mb4 comment秒杀令牌;利用代码生成器生成相应的文件 3. 初始化车次信息时初始化令牌信息 在SkTokenService中实现genDaily方法 /** * 初始化 */ public void genDaily(Date date, String trainCode) { LOG.info(删除日期【{}】车次【{}】的令牌记录, DateUtil.formatDate(date), trainCode); SkTokenExample skTokenExample new SkTokenExample(); skTokenExample.createCriteria().andDateEqualTo(date).andTrainCodeEqualTo(trainCode); skTokenMapper.deleteByExample(skTokenExample); DateTime now DateTime.now(); SkToken skToken new SkToken(); skToken.setDate(date); skToken.setTrainCode(trainCode); skToken.setId(SnowUtil.getSnowflakeNextId()); skToken.setCreateTime(now); skToken.setUpdateTime(now); //计算该车次共有多少个座位int seatCount dailyTrainSeatService.countSeat(date, trainCode); LOG.info(车次【{}】座位数{}, trainCode, seatCount); //查询该车次共有多少个车站long stationCount dailyTrainStationService.countByTrainCode(date, trainCode); LOG.info(车次【{}】到站数{}, trainCode, stationCount); // 3/4需要根据实际卖票比例来定一趟火车最多可以卖seatCount * stationCount张火车票 int count (int) (seatCount * stationCount); // * 3/4); LOG.info(车次【{}】初始生成令牌数{}, trainCode, count); skToken.setCount(count); skTokenMapper.insert(skToken); }然后在生成每日数据时加入该方法即可 //生成该车次的车站数据 dailyTrainStationService.genDaily(date,train.getCode()); //生成该车次的车厢数据 dailyTrainCarriageService.genDaily(date,train.getCode()); //生成该车次的座位数据 dailyTrainSeatService.genDaily(date,train.getCode()); //生成该车次的余票数据 dailyTrainTicketService.genDaily(dailyTrain,date,train.getCode()); LOG.info(生成日期【{}】车次【{}】的信息结束, DateUtil.formatDate(date), train.getCode()); //生成令牌余量数据 skTokenService.genDaily(date,train.getCode());4. 增加校验秒杀令牌功能 在执行核心业务之前加上下面代码 //校验令牌容量 boolean validSkTokenskTokenService.validSkToken(req.getDate(),req.getTrainCode(), req.getMemberId()); if(validSkToken){ LOG.info(令牌校验通过); }else{ LOG.info(令牌校验不通过); throw new BusinessException(BusinessExceptionEnum.CONFIRM_ORDER_SK_TOKEN_FAIL); }其对应逻辑先从redis缓存中查询令牌余量如果存在缓存60s过期则直接从缓存中查询令牌余量 如果余量大于0则获取令牌同时更新缓存中令牌余量 如果不存在缓存则从数据库中查询 /** * 校验令牌 */ public boolean validSkToken(Date date, String trainCode, Long memberId) { LOG.info(会员【{}】获取日期【{}】车次【{}】的令牌开始, memberId, DateUtil.formatDate(date), trainCode); // 需要去掉这段否则发布生产后体验多人排队功能时会因拿不到锁而返回等待5秒加入20人时只有第1次循环能拿到锁 // if (!env.equals(dev)) { // // 先获取令牌锁再校验令牌余量防止机器人抢票lockKey就是令牌用来表示【谁能做什么】的一个凭证 // String lockKey RedisKeyPreEnum.SK_TOKEN - DateUtil.formatDate(date) - trainCode - memberId; // Boolean setIfAbsent redisTemplate.opsForValue().setIfAbsent(lockKey, lockKey, 5, TimeUnit.SECONDS); // if (Boolean.TRUE.equals(setIfAbsent)) { // LOG.info(恭喜抢到令牌锁了lockKey{}, lockKey); // } else { // LOG.info(很遗憾没抢到令牌锁lockKey{}, lockKey); // return false; // } // } String skTokenCountKey RedisKeyPreEnum.SK_TOKEN_COUNT - DateUtil.formatDate(date) - trainCode; Object skTokenCount redisTemplate.opsForValue().get(skTokenCountKey); if (skTokenCount ! null) { LOG.info(缓存中有该车次令牌大闸的key{}, skTokenCountKey); Long count redisTemplate.opsForValue().decrement(skTokenCountKey, 1); if (count 0L) { LOG.error(获取令牌失败{}, skTokenCountKey); return false; } else { LOG.info(获取令牌后令牌余数{}, count); redisTemplate.expire(skTokenCountKey, 60, TimeUnit.SECONDS); // 每获取5个令牌更新一次数据库 if (count % 5 0) { skTokenMapperCust.decrease(date, trainCode, 5); } return true; } } else { LOG.info(缓存中没有该车次令牌大闸的key{}, skTokenCountKey); // 检查是否还有令牌 SkTokenExample skTokenExample new SkTokenExample(); skTokenExample.createCriteria().andDateEqualTo(date).andTrainCodeEqualTo(trainCode); ListSkToken tokenCountList skTokenMapper.selectByExample(skTokenExample); if (CollUtil.isEmpty(tokenCountList)) { LOG.info(找不到日期【{}】车次【{}】的令牌记录, DateUtil.formatDate(date), trainCode); return false; } SkToken skToken tokenCountList.get(0); if (skToken.getCount() 0) { LOG.info(日期【{}】车次【{}】的令牌余量为0, DateUtil.formatDate(date), trainCode); return false; } // 令牌还有余量 // 令牌余数-1 Integer count skToken.getCount() - 1; skToken.setCount(count); LOG.info(将该车次令牌大闸放入缓存中key: {} count: {}, skTokenCountKey, count); // 不需要更新数据库只要放缓存即可 redisTemplate.opsForValue().set(skTokenCountKey, String.valueOf(count), 60, TimeUnit.SECONDS); skTokenMapper.updateByPrimaryKey(skToken); return true; } // 令牌约等于库存令牌没有了就不再卖票不需要再进入购票主流程去判断库存判断令牌肯定比判断库存效率高 // int updateCount skTokenMapperCust.decrease(date, trainCode, 1); // if (updateCount 0) { // return true; // } else { // return false; // }}
http://www.pierceye.com/news/937277/

相关文章:

  • 口碑好的秦皇岛网站建设哪里有沙漠网站建设
  • 推荐外贸网站建设的公司聊城做网站费用价格
  • 在线设计的网站android 网站开发
  • 河北省建设厅网站官网织梦手机网站制作
  • 网站建设管理物联网的发展前景
  • 广州网站建设外贸做vip视频网站赚钱吗
  • 模板网建站山西 网站制作
  • 网站建设捌金手指花总二七网页制作与设计的内容
  • 阿凡达网站建设网网络营销包括什么内容
  • 网站设计师是什么做的好的国外网站
  • 19年做网站织梦cms源码
  • 做定制网站怎么样原创网站设计
  • 淮安网站建设 淮安网站制作反向代理wordpress
  • 七台河北京网站建设深圳营销策划
  • 陕西西乡网站建设如何做网站效果图
  • 三门峡高端网站建设临安建设规划局网站
  • 可信网站认证哪里有网站建设分金手指排名一
  • 十大品牌网站建设专业网站的利弊
  • 如何查看网站域名360seo
  • 苏州网站设计kgwl手机网站全屏代码
  • 网站开发工程师就业前景免费企业网站模板
  • 网站建设额企业建设网站对客户的好处
  • 济南网站制作设计公司WordPress文章相册修改
  • 购物网站建设思维导构图电商平台建设方案
  • 一个网站一年的费用多少惠州网站制作哪里好
  • 网站界面设计材料收集国内外包网站
  • 自如网站做的好 服务网站开发实训
  • 档案网站建设的意义网页制作工具可以分为
  • 网站建设价格是哪些方面决定的wordpress32m
  • 建设公司网站哪家好网站建设 中企动力洛阳分公司