V2~V3的变化【秒杀项目】

V2-V3的变化【秒杀项目】

  • 前言
  • 版权
  • 推荐
  • V2~V3的变化
  • 总结流程
    • 配置
      • pom.xml
      • application-dev.properties
    • comment
      • ErrorCode
    • configuration
      • WebMvcConfiguration
    • emtity
      • ItemStockLog
    • mapper
      • ItemStockLogMapper
      • ItemStockLogMapper.xml
    • controller
      • OrderController
    • service
      • ItemService
      • PromotionService
      • OrderService
    • rocket
      • DecreaseStockConsumer
      • LocalTransactionListenerImpl
  • 最后

前言

2023-8-17 13:03:47

以下内容源自《【秒杀项目】》
仅供学习交流使用

版权

禁止其他平台发布时删除以下此话
本文首次发布于CSDN平台
作者是CSDN@日星月云
博客主页是https://blog.csdn.net/qq_51625007
禁止其他平台发布时删除以上此话

推荐

V2~V3的变化

总结流程

OrderController//获取验证码order/captcha//验证码正确后//获取秒杀凭证//底层调用promotionService.generateToken()order/token//下单操作//限制单击流量//获取活动凭证//加入队列等待//调用底层的orderService.createOrderAsync()order/createOrderService
createOrderAsync()//异步创建订单//执行本地事务rocket//执行本地事务executeLocalTransaction()//创建订单//调用orderService.createOrder()    createOrder()//检查本地事务checkLocalTransaction//检查流水//调用itemService.findItemStorkLogById()checkStockStatus()//执行Mysql中的扣减库存//调用itemService.decreaseStock()onMessage()
PromotionService//判断售罄标识//获取秒杀令牌//v.decrement("promotion:gate:" + promotionId, 1) < 0//设置秒杀凭证//v.set(key, token, 10, TimeUnit.MINUTES);generateToken()OrderService//订单的创建//异步扣减库存//调用itemService.decreaseStockInCache()//生成订单//更新销量createOrder()itemService
/*//预扣库存//redisTemplate.opsForValue().decrement(key, amount);//售罄标识//redisTemplate.opsForValue().set("item:stock:over:" + itemId, 1);decreaseStockInCache()
*///使用Lua脚本//得到stock//判断stock>amount//DECRBY stockKey, amount//SET stockOverKey, 1decreaseStockInCache()//itemStockLogMapper.selectByPrimaryKey(id);findItemStorkLogById()//itemStockMapper.decreaseStock(itemId, amount);decreaseStock()

配置

pom.xml

        <dependency><groupId>org.apache.rocketmq</groupId><artifactId>rocketmq-spring-boot-starter</artifactId><version>2.2.0</version></dependency><dependency><groupId>com.github.whvcse</groupId><artifactId>easy-captcha</artifactId><version>1.6.2</version></dependency>

application-dev.properties

# rocketmq
rocketmq.name-server=192.168.253.160:9876
rocketmq.producer.group=seckill_producer# ThreadPool
spring.task.execution.pool.core-size=5
spring.task.execution.pool.queue-capacity=10
spring.task.execution.pool.max-size=30

comment

ErrorCode

	int CREATE_ORDER_FAILURE = 202;int OUT_OF_LIMIT = 203;

configuration

WebMvcConfiguration

//  registry.addInterceptor(loginCheckInterceptor).addPathPatterns("/order/create");registry.addInterceptor(loginCheckInterceptor).addPathPatterns("/order/captcha","/order/token", "/order/create");

emtity

ItemStockLog

mapper

ItemStockLogMapper

ItemStockLogMapper.xml

controller

OrderController

package com.nowcoder.seckill.controller;@Controller
@RequestMapping("/order")
@CrossOrigin(origins = "${nowcoder.web.path}", allowedHeaders = "*", allowCredentials = "true")
public class OrderController implements ErrorCode {private Logger logger = LoggerFactory.getLogger(OrderController.class);private RateLimiter rateLimiter = RateLimiter.create(1000);@Autowiredprivate OrderService orderService;@Autowiredprivate PromotionService promotionService;@Autowiredprivate RedisTemplate redisTemplate;@Autowiredprivate ThreadPoolTaskExecutor taskExecutor;//获取验证码@RequestMapping(path = "/captcha", method = RequestMethod.GET)public void getCaptcha(String token, HttpServletResponse response) {SpecCaptcha specCaptcha = new SpecCaptcha(130, 48, 4);if (token != null) {User user = (User) redisTemplate.opsForValue().get(token);if (user != null) {String key = "captcha:" + user.getId();redisTemplate.opsForValue().set(key, specCaptcha.text(), 1, TimeUnit.MINUTES);}}response.setContentType("image/png");try {OutputStream os = response.getOutputStream();specCaptcha.out(os);} catch (IOException e) {logger.error("发送验证码失败:" + e.getMessage());}}//获取秒杀凭证//底层调用promotionService.generateToken()@RequestMapping(path = "/token", method = RequestMethod.POST)@ResponseBodypublic ResponseModel generateToken(int itemId, int promotionId, String token, String captcha) {User user = (User) redisTemplate.opsForValue().get(token);if (StringUtils.isEmpty(captcha)) {throw new BusinessException(PARAMETER_ERROR, "请输入正确的验证码!");}String key = "captcha:" + user.getId();String realCaptcha = (String) redisTemplate.opsForValue().get(key);if (!captcha.equalsIgnoreCase(realCaptcha)) {throw new BusinessException(PARAMETER_ERROR, "请输入正确的验证码!");}String promotionToken = promotionService.generateToken(user.getId(), itemId, promotionId);//底层存入promotionToken到redis中if (StringUtils.isEmpty(promotionToken)) {throw new BusinessException(CREATE_ORDER_FAILURE, "下单失败!");}return new ResponseModel(promotionToken);}//    @RequestMapping(path = "/create", method = RequestMethod.POST)
//    @ResponseBody
//    public ResponseModel create(/*HttpSession session, */
//            int itemId, int amount, Integer promotionId, String token) {
        User user = (User) session.getAttribute("loginUser");
//        User user = (User) redisTemplate.opsForValue().get(token);
//        orderService.createOrder(user.getId(), itemId, amount, promotionId);
//        return new ResponseModel();
//    }//下单操作//调用底层的orderService.createOrderAsync()@RequestMapping(path = "/create", method = RequestMethod.POST)@ResponseBodypublic ResponseModel create(/*HttpSession session, */int itemId, int amount, Integer promotionId, String promotionToken, String token) {//限制单机流量if (!rateLimiter.tryAcquire(1,TimeUnit.SECONDS)) {throw new BusinessException(OUT_OF_LIMIT, "服务器繁忙,请稍后再试!");}//        User user = (User) session.getAttribute("loginUser");User user = (User) redisTemplate.opsForValue().get(token);logger.debug("登录用户 [" + token + ": " + user + "]");//验证活动凭证if (promotionId != null) {String key = "promotion:token:" + user.getId() + ":" + itemId + ":" + promotionId;String realPromotionToken = (String) redisTemplate.opsForValue().get(key);if (StringUtils.isEmpty(promotionToken) || !promotionToken.equals(realPromotionToken)) {throw new BusinessException(CREATE_ORDER_FAILURE, "下单失败!");}}//加入队列等待Future future = taskExecutor.submit(new Callable() {@Overridepublic Object call() throws Exception {
//              orderService.createOrder(user.getId(), itemId, amount, promotionId);orderService.createOrderAsync(user.getId(), itemId, amount, promotionId);return null;}});//验证处理结果try {future.get();} catch (Exception e) {throw new BusinessException(UNDEFINED_ERROR, "下单失败!");}return new ResponseModel();}
}

service

ItemService

   ItemStockLog createItemStockLog(int itemId, int amount);void updateItemStockLogStatus(String id, int status);ItemStockLog findItemStorkLogById(String id);

PromotionService

package com.nowcoder.seckill.service.impl;@Service
public class PromotionServiceImpl implements PromotionService, ErrorCode {@Autowiredprivate RedisTemplate redisTemplate;@Autowiredprivate UserService userService;@Autowiredprivate ItemService itemService;@Overridepublic String generateToken(int userId, int itemId, int promotionId) {if (userId < 0 || itemId < 0 || promotionId < 0) {return null;}// 售罄标识if (redisTemplate.hasKey("item:stock:over:" + itemId)) {return null;}// 校验用户User user = userService.findUserFromCache(userId);if (user == null) {return null;}// 校验商品Item item = itemService.findItemInCache(itemId);if (item == null) {return null;}// 校验活动if (item.getPromotion() == null|| !item.getPromotion().getId().equals(promotionId)|| item.getPromotion().getStatus() != 0) {return null;}// 秒杀大闸ValueOperations v = redisTemplate.opsForValue();if (v.decrement("promotion:gate:" + promotionId, 1) < 0) {return null;}String key = "promotion:token:" + userId + ":" + itemId + ":" + promotionId;String token = UUID.randomUUID().toString().replace("-", "");v.set(key, token, 10, TimeUnit.MINUTES);return token;}}

OrderService

package com.nowcoder.seckill.service.impl;@Service
public class OrderServiceImpl implements OrderService, ErrorCode {private Logger logger = LoggerFactory.getLogger(OrderServiceImpl.class);@Autowiredprivate OrderMapper orderMapper;@Autowiredprivate SerialNumberMapper serialNumberMapper;@Autowiredprivate UserService userService;@Autowiredprivate ItemService itemService;@Autowiredprivate RedisTemplate redisTemplate;@Autowiredprivate RocketMQTemplate rocketMQTemplate;/*** 格式:日期 + 流水* 示例:20210123000000000001** @return*///订单号的创建@Transactional(propagation = Propagation.REQUIRES_NEW)public String generateOrderID() {StringBuilder sb = new StringBuilder();// 拼入日期sb.append(Toolbox.format(new Date(), "yyyyMMdd"));// 获取流水号SerialNumber serial = serialNumberMapper.selectByPrimaryKey("order_serial");Integer value = serial.getValue();// 更新流水号serial.setValue(value + serial.getStep());serialNumberMapper.updateByPrimaryKey(serial);// 拼入流水号String prefix = "000000000000".substring(value.toString().length());sb.append(prefix).append(value);return sb.toString();}//订单的创建//调用itemService.decreaseStockInCache()@Transactionalpublic Order createOrder(int userId, int itemId, int amount, Integer promotionId, String itemStockLogId) {// 校验参数if (amount < 1 || (promotionId != null && promotionId.intValue() <= 0)) {throw new BusinessException(PARAMETER_ERROR, "指定的参数不合法!");}// 校验用户
//        User user = userService.findUserById(userId);User user = userService.findUserFromCache(userId);if (user == null) {throw new BusinessException(PARAMETER_ERROR, "指定的用户不存在!");}// 校验商品
//        Item item = itemService.findItemById(itemId);Item item = itemService.findItemInCache(itemId);if (item == null) {throw new BusinessException(PARAMETER_ERROR, "指定的商品不存在!");}// 校验库存int stock = item.getItemStock().getStock();if (amount > stock) {throw new BusinessException(STOCK_NOT_ENOUGH, "库存不足!");}// 校验活动if (promotionId != null) {if (item.getPromotion() == null) {throw new BusinessException(PARAMETER_ERROR, "指定的商品无活动!");} else if (!item.getPromotion().getId().equals(promotionId)) {throw new BusinessException(PARAMETER_ERROR, "指定的活动不存在!");} else if (item.getPromotion().getStatus() != 0) {throw new BusinessException(PARAMETER_ERROR, "指定的活动未开始!");}}// 扣减库存// 增加行锁:前提是商品主键字段上必须有索引。// 缓存库存:异步同步数据库并保证最终一致性。
//        boolean successful = itemService.decreaseStock(itemId, amount);boolean successful = itemService.decreaseStockInCache(itemId, amount);//在redis缓存中扣减logger.debug("预扣减库存完成 [" + successful + "]");if (!successful) {throw new BusinessException(STOCK_NOT_ENOUGH, "库存不足!");}// 生成订单Order order = new Order();order.setId(this.generateOrderID());order.setUserId(userId);order.setItemId(itemId);order.setPromotionId(promotionId);order.setOrderPrice(promotionId != null ? item.getPromotion().getPromotionPrice() : item.getPrice());order.setOrderAmount(amount);order.setOrderTotal(order.getOrderPrice().multiply(new BigDecimal(amount)));order.setOrderTime(new Timestamp(System.currentTimeMillis()));orderMapper.insert(order);logger.debug("生成订单完成 [" + order.getId() + "]");// 更新销量
//        itemService.increaseSales(itemId, amount);
//        logger.debug("更新销量完成 [" + itemId + "]");JSONObject body = new JSONObject();body.put("itemId", itemId);body.put("amount", amount);Message msg = MessageBuilder.withPayload(body.toString()).build();rocketMQTemplate.asyncSend("seckill:increase_sales", msg, new SendCallback() {@Overridepublic void onSuccess(SendResult sendResult) {logger.debug("投递增加商品销量消息成功");}@Overridepublic void onException(Throwable e) {logger.error("投递增加商品销量消息失败", e);}}, 60 * 1000);// 更新库存流水状态itemService.updateItemStockLogStatus(itemStockLogId, 1);logger.debug("更新流水完成 [" + itemStockLogId + "]");return order;}//异步创建订单//执行本地事务 @Overridepublic void createOrderAsync(int userId, int itemId, int amount, Integer promotionId) {// 售罄标识if (redisTemplate.hasKey("item:stock:over:" + itemId)) {throw new BusinessException(STOCK_NOT_ENOUGH, "已经售罄!");}// 生成库存流水ItemStockLog itemStockLog = itemService.createItemStockLog(itemId, amount);//初始状态是0logger.debug("生成库存流水完成 [" + itemStockLog.getId() + "]");// 消息体JSONObject body = new JSONObject();body.put("itemId", itemId);body.put("amount", amount);body.put("itemStockLogId", itemStockLog.getId());// 本地事务参数JSONObject arg = new JSONObject();arg.put("userId", userId);arg.put("itemId", itemId);arg.put("amount", amount);arg.put("promotionId", promotionId);arg.put("itemStockLogId", itemStockLog.getId());String dest = "seckill:decrease_stock";Message msg = MessageBuilder.withPayload(body.toString()).build();try {logger.debug("尝试投递扣减库存消息 [" + body.toString() + "]");TransactionSendResult sendResult = rocketMQTemplate.sendMessageInTransaction(dest, msg, arg);if (sendResult.getLocalTransactionState() == LocalTransactionState.UNKNOW) {throw new BusinessException(UNDEFINED_ERROR, "创建订单失败!");} else if (sendResult.getLocalTransactionState() == LocalTransactionState.ROLLBACK_MESSAGE) {throw new BusinessException(CREATE_ORDER_FAILURE, "创建订单失败!");}} catch (MessagingException e) {throw new BusinessException(CREATE_ORDER_FAILURE, "创建订单失败!");}}
}

rocket

DecreaseStockConsumer

package com.nowcoder.seckill.rocket.consumer;@Service
@RocketMQMessageListener(topic = "seckill",consumerGroup = "seckill_stock", selectorExpression = "decrease_stock")
public class DecreaseStockConsumer implements RocketMQListener<String> {private Logger logger = LoggerFactory.getLogger(DecreaseStockConsumer.class);@Autowiredprivate ItemService itemService;@Overridepublic void onMessage(String message) {JSONObject param = JSONObject.parseObject(message);int itemId = (int) param.get("itemId");int amount = (int) param.get("amount");try {itemService.decreaseStock(itemId, amount);logger.debug("最终扣减库存完成 [" + param.get("itemStockLogId") + "]");} catch (Exception e) {logger.error("从DB扣减库存失败", e);}}}

LocalTransactionListenerImpl

package com.nowcoder.seckill.rocket.producer;@Service
@RocketMQTransactionListener
public class LocalTransactionListenerImpl implements RocketMQLocalTransactionListener {private Logger logger = LoggerFactory.getLogger(LocalTransactionListenerImpl.class);@Autowiredprivate OrderService orderService;@Autowiredprivate ItemService itemService;//执行本地事务@Overridepublic RocketMQLocalTransactionState executeLocalTransaction(Message msg, Object arg) {try {String tag = msg.getHeaders().get("rocketmq_TAGS").toString();if ("decrease_stock".equals(tag)) {return this.createOrder(msg, arg);//调用方法} else {return RocketMQLocalTransactionState.UNKNOWN;}} catch (Exception e) {logger.error("执行MQ本地事务时发生错误", e);return RocketMQLocalTransactionState.ROLLBACK;}}//检查本地事务@Overridepublic RocketMQLocalTransactionState checkLocalTransaction(Message msg) {try {String tag = (String) msg.getHeaders().get("rocketmq_TAGS");if ("decrease_stock".equals(tag)) {return this.checkStockStatus(msg);//调用方法} else {return RocketMQLocalTransactionState.UNKNOWN;}} catch (Exception e) {logger.error("检查MQ本地事务时发生错误", e);return RocketMQLocalTransactionState.ROLLBACK;}}//创建订单private RocketMQLocalTransactionState createOrder(Message msg, Object arg) {JSONObject param = (JSONObject) arg;int userId = (int) param.get("userId");int itemId = (int) param.get("itemId");int amount = (int) param.get("amount");int promotionId = (int) param.get("promotionId");String itemStockLogId = (String) param.get("itemStockLogId");try {Order order = orderService.createOrder(userId, itemId, amount, promotionId, itemStockLogId);//调用service创建logger.debug("本地事务提交完成 [" + order.getId() + "]");return RocketMQLocalTransactionState.COMMIT;} catch (Exception e) {logger.error("创建订单失败", e);itemService.updateItemStockLogStatus(itemStockLogId, 3);logger.debug("更新流水完成 [" + itemStockLogId + "]");return RocketMQLocalTransactionState.ROLLBACK;}}//检查流水private RocketMQLocalTransactionState checkStockStatus(Message msg) {JSONObject body = JSONObject.parseObject(new String((byte[]) msg.getPayload()));String itemStockLogId = (String) body.get("itemStockLogId");ItemStockLog itemStockLog = itemService.findItemStorkLogById(itemStockLogId);logger.debug("检查事务状态完成 [" + itemStockLog + "]");if (itemStockLog == null) {return RocketMQLocalTransactionState.ROLLBACK;} else if (itemStockLog.getStatus() == 0) {return RocketMQLocalTransactionState.UNKNOWN;} else if (itemStockLog.getStatus() == 1) {return RocketMQLocalTransactionState.COMMIT;} else {return RocketMQLocalTransactionState.ROLLBACK;}}}

最后

我们都有光明的未来

祝大家考研上岸
祝大家工作顺利
祝大家得偿所愿
祝大家如愿以偿
点赞收藏关注哦

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.xdnf.cn/news/1425299.html

如若内容造成侵权/违法违规/事实不符,请联系一条长河网进行投诉反馈,一经查实,立即删除!

相关文章

Java JDK下载安装教程(2024年)

博主介绍&#xff1a;✌Java老徐、7年大厂程序员经历。全网粉丝12w、csdn博客专家、掘金/华为云/阿里云/InfoQ等平台优质作者、专注于Java技术领域和毕业项目实战✌ &#x1f345;文末获取源码联系&#x1f345; &#x1f447;&#x1f3fb; 精彩专栏推荐订阅&#x1f447;&…

这10款安卓APP,简直好用到爆!

AI视频生成&#xff1a;小说文案智能分镜智能识别角色和场景批量Ai绘图自动配音添加音乐一键合成视频http://AI视频生成&#xff1a;小说文案智能分镜智能识别角色和场景批量Ai绘图自动配音添加音乐一键合成视频 1.追书——追书神器 追书神器是小说追新大神&#xff0c;全网实…

520告白好物有哪些?收下这份清单不迷茫!

在这个充满爱意的日子里&#xff0c;你是否正在为如何向心仪的人表达深情而犯愁&#xff1f;别担心&#xff0c;我们为你精心准备了一份520告白好物清单都是一些实用的礼品&#xff0c;为你提供多样化的选择&#xff0c;助你轻松传达爱意&#xff0c;让告白不再迷茫。快来看看吧…

软考电商考前冲刺20问!看看你能答上多少?

距离软考考试的时间越来越近了&#xff0c;趁着最后的时间赶紧冲刺起来&#xff0c;今天给大家整理了——电子商务设计师考前20问 一、考前20问是什么&#xff1f; 考前几页纸是各科目考点的高度精华总结。也是我们今年考前冲刺蕞后一份资料 二、考前20问好在哪里&#xff1f;…

面对《消费者告知法》严查与技术BUG频发,亚马逊卖家如何巧妙应对挑战?

五一假期期间&#xff0c;亚马逊大量发送《美国消费者告知法案》验证邮件通知&#xff0c;在这个本该是卖家们忙碌而喜悦的时刻&#xff0c;亚马逊平台上的卖家们却遭遇了一场前所未有的“灾难”——《消费者告知法》验证问题的爆发&#xff0c;以及随之而来的一系列技术BUG&am…

JL-杰理芯片-认识TA的SDK的第四天

无蓝牙连接关机时间 关机时间&#xff1a;3分钟 60 * 5 300 低功耗 进入低功耗前&#xff0c;要关闭打印 内存D2、D4、D8 芯片&#xff08;主控&#xff09;的内存不能超过一定的数值&#xff0c;超过后就不能烧录 jl_isd.bin这个文件不能超过内存大小 而杰理的内存是…

剑指Offer打卡day34——AcWing 66. 两个链表的第一个公共结点

AcWing 66. 两个链表的第一个公共结点 暴力做法&#xff0c;两层for循环 /*** Definition for singly-linked list.* public class ListNode {* int val;* ListNode next;* ListNode(int x) {* val x;* next null;* }* }*/ class Solutio…

IEEE(电气电子工程师学会)数据库文献去哪里查询下载

IEEE数据库简介&#xff1a; IEEE&#xff08;电气电子工程师学会&#xff09;是目前全球科学技术领域领先的专业机构。其期刊在电气电子工程、计算机科学、人工智能、机器人、自动化控制、遥感和核工程领域的期刊影响因子和被引用量都名列前茅。而其学术会议涉及领域广&#…

package-lock.json导致npm install安装nyc出现超时错误

一、背景 前端项目在npm install安装依赖&#xff0c;无法下载组件nyc&#xff0c;详细报错信息&#xff1a; npm ERR! code CERT_HAS_EXPIRED npm ERR! errno CERT_HAS_EXPIRED npm ERR! request to https://registry.npm.taobao.org/nyc/download/nyc-13.3.0.tgz?cache0&a…

Windows下配置TortoiseGit 访问Ubuntu虚拟机下Samba共享目录

前言&#xff1a; 本文记录学习使用 Git 版本管理工具的学习笔记&#xff0c;通过阅读参考链接中的博文和实际操作&#xff0c;快速的上手使用 Git 工具。 本文参考了引用链接博文里的内容。 引用: 【TortoiseGit】TortoiseGit安装和配置详细说明-CSDN博客 Git版本管理可视…

Spring框架学习笔记(三):AOP编程

1 动态代理 1.1 通过案例理解动态代理 &#xff08;1&#xff09;需求说明&#xff1a; 1. 有 Vehicle接口(交通工具接口, 有一个 run 方法), 下面有两个实现类 Car 和 Ship 2. 当运行 Car 对象 的 run 方法和 Ship 对象的 run 方法时&#xff0c;输入如下内容, 注意观察前后…

了解RFID技术如何改善危化品仓储管理效率

随着科学的发展&#xff0c;我国化工行业也迎来飞速进步的黄金时期&#xff0c;而生产加工快速化的同时也导致一些危险化学品的使用量与存储量不断增加。由于危险化学品种类较多&#xff0c;使用和存储的方法都不一样&#xff0c;还具有易燃、易爆、腐蚀、毒害等特性&#xff0…

系统架构师考试(二)

敏捷方法 CMMI代表Capability Maturity Model Integration&#xff0c;是一种用于评估和改进组织软件工程和系统工程的模型。CMMI提供一个框架&#xff0c;帮助组织评估其软件和系统工程的成熟度&#xff0c;该模型基于过程成熟度模型&#xff08;CMM&#xff09;和集成项目管理…

数据中台管理系统原型

数据中台是一个通用性的基础平台&#xff0c;适用于各类行业场景&#xff0c;数据中台包含多元数据汇聚、数据标准化、数据开发、数据共享、数据智能、数据资产管理等功能&#xff0c;助力企业数字化转型。 数据汇聚 数据汇聚是将不同系统、不同类型的多元源数据汇聚至目标数据…

Flink 高可用之StandAlone-HA模式(一)

Flink 高可用之StandAlone-HA模式 压缩包: tar -xvzf flink-1.9.1-bin-scala_2.11.tgz -C /opt && cd /opt/flink-1.9.1 集群规划: 1.集群规划 - 服务器: node1(Master Slave): JobManager TaskManager- 服务器: node2(Master Slave): JobManager TaskManager- …

【WEB前端2024】开源智体世界:乔布斯3D纪念馆-第23课-烟花插件的售卖效果优化

【WEB前端2024】开源智体世界&#xff1a;乔布斯3D纪念馆-第23课-烟花插件的售卖效果优化 使用dtns.network德塔世界&#xff08;开源的智体世界引擎&#xff09;&#xff0c;策划和设计《乔布斯超大型的开源3D纪念馆》的系列教程。dtns.network是一款主要由JavaScript编写的智…

盘点2024年自动猫砂盆品牌,哪个牌子自动猫砂盆比较好?

养猫之路漫漫&#xff0c;无论是新手还是老手&#xff0c;都需要细心照料猫咪的每一个需求。特别是在选择自动猫砂盆这个问题上&#xff0c;更是让人头疼不已。因为每只猫咪的喜好和习惯都不同&#xff0c;如果猫砂盆选得不对&#xff0c;猫咪可能会拒绝使用&#xff0c;导致家…

摸鱼大数据——Linux搭建大数据环境(Hadoop高可用环境搭建)六

Hadoop高可用环境搭建 确定提前安装好了hadoop和zookeeper 1.删除原有数据文件 三台机器都要进行删除 可以使用CRT发送交互到所有会话 rm -rf /export/data/hadoop-3.3.0 2.安装软件 三台机器都要进行安装 注意: 如果网络较慢安装失败,那就重复安装即可 # 实现多个服务的通讯 …

springboot引入第三方jar包本地lib并打包

1&#xff1a;在项目根目录创建lib目录并放入第三方lib包 -- project ----lib &#xff08;放在这儿&#xff09; ----src ----target2&#xff1a;pom中引入第三方lib <!-- 引入magus模块 --><dependency><groupId>org.jeecg.msgus</groupId><art…

人才测评:计划管理能力与岗位胜任力素质测评

计划管理能力指的是什么&#xff1f; 计划管理能力&#xff0c;可以体现为从业者在精准制定好任务&#xff0c;或是根据任务的时间长&#xff0c;困难的程度来设定好完成的目标&#xff0c;一步一个脚印将工作完成好&#xff0c;并且能预估出可能出现的突发事件&#xff0c;将…