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

【技术实战】Spring Task与WebSocket在外卖系统中的高效应用

1. 为什么外卖系统需要定时任务和实时通信每次点外卖的时候你可能没注意过背后的技术细节。比如超时未支付的订单会自动取消商家接单后你的手机会立即收到通知这些看似简单的功能其实都藏着精妙的技术实现。我在开发外卖系统时发现最头疼的就是处理这两种场景一是异常订单的自动处理二是实时通知的及时送达。传统做法是靠人工刷新页面或者轮询服务器但这既浪费资源又影响用户体验。后来我尝试用Spring Task和WebSocket来解决这些问题效果出奇地好。Spring Task就像个尽职的管家能定时检查订单状态。比如设置每15分钟扫描一次数据库自动取消超时未支付的订单。这比让服务员不停查订单高效多了。而WebSocket则像条专用热线让服务器能主动给用户和商家推送消息不用等客户端反复询问。2. Spring Task处理异常订单的实战技巧2.1 快速搭建定时任务记得第一次用Spring Task时我惊讶于它的轻量。只需要在pom.xml里加个spring-context依赖其实大部分Spring项目已经包含它了dependency groupIdorg.springframework/groupId artifactIdspring-context/artifactId /dependency然后在启动类上加个EnableScheduling注解系统就具备定时任务能力了。这就像给系统装了个闹钟到点就会自动执行任务。2.2 编写订单检查任务处理异常订单的核心代码其实很简单。我通常会写个这样的服务类Service public class OrderCheckService { Scheduled(cron 0 */15 * * * ?) public void checkUnpaidOrders() { // 查询超时未支付订单 ListOrder unpaidOrders orderMapper.selectTimeoutOrders(15); // 批量更新订单状态为已取消 unpaidOrders.forEach(order - { order.setStatus(OrderStatus.CANCELLED); order.setCancelReason(超时未支付); orderMapper.update(order); }); } }这里有个实用技巧cron 0 */15 * * * ?表示每15分钟执行一次。刚开始我总是记不住cron表达式后来发现网上有很多生成工具比如常用的cronmaker.com。2.3 性能优化经验踩过几次坑后我总结出几个优化点执行频率要合理初期我设成每分钟检查结果数据库压力飙升。后来改成15分钟一次既保证时效性又减轻负担。批量处理代替单条操作用selectTimeoutOrders批量查询比循环查单条效率高10倍不止。添加分布式锁在集群环境下用Redis加锁避免多个节点重复执行。异常处理要完善记得有次任务抛异常导致后续都不执行了现在我会在方法里加try-catchScheduled(cron 0 */15 * * * ?) public void checkUnpaidOrders() { try { // 业务逻辑 } catch (Exception e) { log.error(定时任务异常, e); } }3. WebSocket实现实时通知的完整方案3.1 为什么不用HTTP轮询早期版本我用HTTP轮询实现通知功能结果发现三个问题客户端要不断发请求耗电耗流量通知延迟高达5-10秒服务器压力大QPS经常爆表改用WebSocket后连接建立后可以保持长时间通信服务器有新消息能立即推送给客户端。实测延迟降到100ms以内服务器负载降低70%。3.2 搭建WebSocket服务端配置WebSocket需要三个核心组件配置类建立WebSocket端点Configuration EnableWebSocket public class WebSocketConfig implements WebSocketConfigurer { Override public void registerWebSocketHandlers(WebSocketHandlerRegistry registry) { registry.addHandler(orderNoticeHandler(), /ws/order) .setAllowedOrigins(*); } Bean public WebSocketHandler orderNoticeHandler() { return new OrderNoticeHandler(); } }处理器处理连接和消息public class OrderNoticeHandler extends TextWebSocketHandler { private static final MapString, WebSocketSession sessions new ConcurrentHashMap(); Override public void afterConnectionEstablished(WebSocketSession session) { String shopId getShopIdFromSession(session); sessions.put(shopId, session); } Override protected void handleTextMessage(WebSocketSession session, TextMessage message) { // 处理客户端消息 } }消息发送工具其他服务调用这个类推送消息Component public class NoticeSender { public void sendToShop(String shopId, String message) { WebSocketSession session OrderNoticeHandler.getSession(shopId); if (session ! null session.isOpen()) { session.sendMessage(new TextMessage(message)); } } }3.3 前端对接关键代码前端实现也很重要这是Vue中的典型用法const socket new WebSocket(ws://yourdomain.com/ws/order); socket.onopen () { console.log(连接建立); }; socket.onmessage (event) { const notice JSON.parse(event.data); // 显示通知弹窗 showNotification(notice); // 播放提示音 if (notice.type NEW_ORDER) { playSound(/sounds/new-order.mp3); } };4. 实战中的典型问题与解决方案4.1 定时任务不执行的排查流程有次上线后发现定时任务没执行通过以下步骤解决了问题检查启动类是否有EnableScheduling确认任务方法所在的类被Spring管理有Component或Service查看cron表达式是否正确用在线工具验证检查日志是否有异常抛出最后发现是方法修饰符误写成private了4.2 WebSocket断线重连机制移动端网络不稳定我增加了这样的重连逻辑let reconnectAttempts 0; function connect() { const socket new WebSocket(ws://yourdomain.com/ws/order); socket.onclose () { const delay Math.min(1000 * Math.pow(2, reconnectAttempts), 30000); setTimeout(connect, delay); reconnectAttempts; }; socket.onopen () { reconnectAttempts 0; }; }4.3 消息可靠性保证为确保重要通知不丢失我实现了三级保障WebSocket实时推送失败后尝试HTTP补发最终持久化到数据库供客户端查询对应的消息表设计CREATE TABLE push_messages ( id bigint NOT NULL, user_id bigint DEFAULT NULL, content varchar(500) DEFAULT NULL, is_read tinyint(1) DEFAULT 0, created_at datetime DEFAULT CURRENT_TIMESTAMP, PRIMARY KEY (id) ) ENGINEInnoDB DEFAULT CHARSETutf8mb4;5. 进阶优化方案5.1 分布式定时任务方案当系统扩展到多节点时我用Redis实现了分布式锁Scheduled(cron 0 */15 * * * ?) public void distributedCheck() { String lockKey order:check:lock; String requestId UUID.randomUUID().toString(); try { boolean locked redisTemplate.opsForValue() .setIfAbsent(lockKey, requestId, 10, TimeUnit.MINUTES); if (locked) { checkUnpaidOrders(); } } finally { if (requestId.equals(redisTemplate.opsForValue().get(lockKey))) { redisTemplate.delete(lockKey); } } }5.2 WebSocket集群方案用Redis的Pub/Sub实现多节点间的消息转发Configuration public class RedisConfig { Bean public RedisMessageListenerContainer container( RedisConnectionFactory factory, MessageListenerAdapter listenerAdapter) { RedisMessageListenerContainer container new RedisMessageListenerContainer(); container.setConnectionFactory(factory); container.addMessageListener(listenerAdapter, new ChannelTopic(ws.notice)); return container; } Bean public MessageListenerAdapter listenerAdapter(NoticeForwarder forwarder) { return new MessageListenerAdapter(forwarder, forward); } }5.3 性能监控方案通过Spring Boot Actuator暴露指标management: endpoints: web: exposure: include: health,metrics,scheduledtasks metrics: tags: application: ${spring.application.name}然后可以监控定时任务执行次数执行耗时WebSocket连接数消息推送成功率6. 实际效果与业务价值上线这套方案后系统指标明显改善异常订单处理及时率从78%提升到99.9%服务器资源消耗降低40%用户投诉减少65%商家接单速度平均提升2分钟有个餐饮客户反馈说现在新订单提示音一响就能马上处理再也不用盯着电脑刷新页面了。这种提升用户体验的成就感正是技术价值的体现。

相关文章:

【技术实战】Spring Task与WebSocket在外卖系统中的高效应用

1. 为什么外卖系统需要定时任务和实时通信 每次点外卖的时候,你可能没注意过背后的技术细节。比如超时未支付的订单会自动取消,商家接单后你的手机会立即收到通知,这些看似简单的功能其实都藏着精妙的技术实现。 我在开发外卖系统时发现&…...

DFT测试点插入实战:如何用Synopsys DFT Compiler提升芯片测试覆盖率

DFT测试点插入实战:Synopsys DFT Compiler全流程优化指南 芯片测试覆盖率是衡量制造质量的核心指标之一。在实际工程中,我们常常遇到这样的困境:明明设计了完整的扫描链,但ATPG工具生成的测试向量覆盖率始终卡在85%-90%之间&#…...

2024 数据资产入表财务实操手册(发布稿)——解读分享

本文介绍了数据资产入表财务实操手册,包括背景、依据、流程、参与主体、表后管理等内容。手册详细阐述了数据资产入表的各个环节,包括合规确认、权属确认、经济利益确认、成本归集与分摊、列报与披露、摊销与减值等,并明确了参与主体和所需资料。 重点内容: 1. 介绍数据资…...

保姆级教学:Unsloth框架下从零开始完成DeepSeek-R1模型微调

保姆级教学:Unsloth框架下从零开始完成DeepSeek-R1模型微调 1. 环境准备与快速部署 1.1 安装Unsloth框架 Unsloth是一个开源的LLM微调和强化学习框架,能够显著提升训练速度并降低显存占用。首先安装必要的依赖: # 安装Unsloth&#xff08…...

如何用Neorg构建合成生物学数据共享平台:终极架构设计指南

如何用Neorg构建合成生物学数据共享平台:终极架构设计指南 【免费下载链接】neorg Modernity meets insane extensibility. The future of organizing your life in Neovim. 项目地址: https://gitcode.com/gh_mirrors/ne/neorg 在当今数据驱动的合成生物学研…...

GEO优化系统开发避坑指南:如何避免数据跨境传输的法律风险?

GEO优化系统开发避坑指南:如何避免数据跨境传输的法律风险? 在全球数字化浪潮中,地理位置数据已成为企业优化用户体验的核心资产。从精准营销到本地化服务,GEO优化系统正重塑商业运营模式。然而,随着各国数据保护法规日…...

CD32.【C++ Dev】类和对象(22) 内存管理(下)

目录 1.定位new表达式 作用 格式 代码示例 分析 2.malloc/free和new/delete的区别 记忆方法 Myclass* ptr (Myclass*)malloc(sizeof(Myclass)); if (ptr nullptr) {...} free(ptr) ptr nullptr; Myclass* ptr new Myclass; delete ptr 3.内存泄漏 内存泄漏分…...

62:AI多语言神谕生成:文本生成模型与TTS语音合成基础

作者: HOS(安全风信子) 日期: 2026-03-16 主要来源平台: GitHub 摘要: 在《死亡笔记》中,基拉需要以神谕的形式向世界传达正义的旨意。本文探讨如何利用AI技术实现多语言神谕生成,结合文本生成模型与TTS语音…...

ESP32以太网运行时配置库:支持W5500/ENC28J60与Web门户

1. 项目概述ESP32_SC_Ethernet_Manager 是一款专为 ESP32-S2、ESP32-S3 和 ESP32-C3 系列微控制器设计的以太网连接与凭证管理库。其核心目标是解决嵌入式设备在部署后,因网络环境变更(如 IP 地址段调整、DNS 服务器更换、网关迁移)或设备物理…...

libopencm3多平台支持解析:STM32、GD32、LPC和SAM系列微控制器的统一开发框架

libopencm3多平台支持解析:STM32、GD32、LPC和SAM系列微控制器的统一开发框架 【免费下载链接】libopencm3 Open source ARM Cortex-M microcontroller library 项目地址: https://gitcode.com/gh_mirrors/li/libopencm3 libopencm3是一个开源ARM Cortex-M微…...

weixin252基于微信小程序的网约巴士订票平台的设计与实现ssm(文档+源码)_kaic

系统的实现5.1用户信息管理如图5.1显示的就是用户信息管理页面,此页面提供给管理员的功能有:用户信息的查询管理,可以删除用户信息、修改用户信息、新增用户信息,还进行了对用户名称的模糊查询性别类型查询的条件图5.1 用户信息管…...

铁路关键部件缺陷检测数据集全览(涵盖吊弦病害、绝缘子缺陷、螺栓松动与轨道裂缝)

1. 铁路关键部件缺陷检测数据集概述 铁路作为国家重要的交通基础设施,其安全运行直接关系到乘客生命财产安全。近年来,随着计算机视觉技术的快速发展,基于深度学习的铁路关键部件缺陷检测方法逐渐成为研究热点。而要训练出高精度的检测模型&a…...

@Autowired 和 @Resource的区别

在 Spring 框架中, Autowired 和 Resource 都是⽤于依赖注⼊(DI)的注解,但它们的来源、注⼊逻辑和使⽤场景存在明显差异。以下是两者的核⼼区别:Autowired 属于 Spring 框架原⽣注解,位于 org.springfr…...

Qwen3.5-35B-A3B-AWQ-4bit图文理解能力展示:手写公式识别、表格数据提取、Logo溯源

Qwen3.5-35B-A3B-AWQ-4bit图文理解能力展示:手写公式识别、表格数据提取、Logo溯源 1. 模型能力概览 Qwen3.5-35B-A3B-AWQ-4bit是一款专为视觉多模态理解设计的量化模型,在保持高效推理的同时,展现出强大的图片内容理解能力。这个模型特别适…...

嵌入式低功耗唤醒定时器库WakeUp设计与实现

1. WakeUp 库概述:面向低功耗嵌入式系统的深度睡眠唤醒定时器实现WakeUp 是一个专为资源受限型 Cortex-M0/M0 微控制器设计的轻量级、可移植的唤醒定时器(Wake-up Timer)软件库,核心目标是在系统进入深度睡眠(DeepSlee…...

前后端交互实战:从零搭建登录系统

1. 登录系统基础架构设计 登录系统是每个Web应用的基石,就像小区门禁系统一样,既要保证合法用户顺利通行,又要拦截非法访问。我们先来看一个典型的登录流程:用户在表单输入账号密码 -> 前端校验数据格式 -> 后端验证凭证 -&…...

I型NPC三电平VSG控制:高输出波形质量与电压电流双闭环的SPWM调制

基于I型NPC三电平的VSG(虚拟同步机)控制,具有较高的输出波形质量,采用中点电位平衡控制,SPWM调制,电压电流双闭环控制。 1.I型NPC三电平VSG控制 2.电压电流双闭环,SPWM 3.提供相关参考文献 支持…...

从Spring_couplet_generation看AI内容生成的安全与伦理考量

从Spring_couplet_generation看AI内容生成的安全与伦理考量 最近在部署和试用一些AI内容生成模型,比如能写对联的Spring_couplet_generation,感觉挺有意思的。它能根据几个关键词,瞬间生成一副对仗工整、寓意吉祥的对联,省去了不…...

Express-GraphQL测试策略终极指南:单元测试与集成测试最佳实践

Express-GraphQL测试策略终极指南:单元测试与集成测试最佳实践 【免费下载链接】express-graphql Create a GraphQL HTTP server with Express. 项目地址: https://gitcode.com/gh_mirrors/ex/express-graphql Express-GraphQL是一款用于创建GraphQL HTTP服务…...

Comsol无量纲拓扑优化:探索结构优化新境界

comsol无量纲拓扑优化。在工程领域,拓扑优化就像是一把神奇的钥匙,能解锁材料分布的最优解,让结构在满足各种约束条件下发挥最大性能。而Comsol作为一款强大的多物理场仿真软件,在拓扑优化方面有着独特的魅力,尤其是无…...

FortuneSheet数据验证与条件格式化的终极教程

FortuneSheet数据验证与条件格式化的终极教程 【免费下载链接】fortune-sheet A drop-in javascript spreadsheet library that provides rich features like Excel and Google Sheets 项目地址: https://gitcode.com/gh_mirrors/fo/fortune-sheet FortuneSheet是一款功…...

Javashop商城系统深度评测:为何它能成为企业级电商的首选方案?

1. 为什么企业级电商需要Javashop? 第一次接触Javashop是在去年帮一家连锁超市做线上商城改造时。当时他们原有的系统在大促期间频繁崩溃,技术团队疲于应付各种突发问题。经过多方对比测试,最终选择了Javashop,结果上线后的第一个…...

GitHub仓库的创建与git的连接使用

补充上面git指令:如何撤销修改:git restore -- b.txt 注意空格一:首先注册github账号,登录页面显示如下:二:点击右上角加号,点击第一个创建仓库存储。新建文件点击public公共三:简单…...

突破9大兼容性限制:WarcraftHelper如何让魔兽争霸3重获新生

突破9大兼容性限制:WarcraftHelper如何让魔兽争霸3重获新生 【免费下载链接】WarcraftHelper Warcraft III Helper , support 1.20e, 1.24e, 1.26a, 1.27a, 1.27b 项目地址: https://gitcode.com/gh_mirrors/wa/WarcraftHelper WarcraftHelper是一款专注于解…...

Neorg性能优化终极指南:10个技巧让组织效率翻倍

Neorg性能优化终极指南:10个技巧让组织效率翻倍 【免费下载链接】neorg Modernity meets insane extensibility. The future of organizing your life in Neovim. 项目地址: https://gitcode.com/gh_mirrors/ne/neorg Neorg作为一款基于Neovim的现代化笔记管…...

OBS项目架构分析:理解大型C++多媒体应用的设计模式

OBS项目架构分析:理解大型C多媒体应用的设计模式 【免费下载链接】OBS Open Broadcaster Software (Deprecated: See OBS Studio repository instead) 项目地址: https://gitcode.com/gh_mirrors/ob/OBS Open Broadcaster Software(OBS&#xff0…...

Python数据分析新手必看:pandas一行代码计算平均值偏差的3种姿势

Python数据分析新手必看:pandas一行代码计算平均值偏差的3种姿势 当你第一次接触数据分析时,可能会被各种统计指标搞得晕头转向。平均值、中位数、标准差...这些术语听起来就让人头疼。但今天我们要聊的这个指标——平均值偏差(Mean Absolute…...

MCP采样接口调用流深度解构(金融级灰度发布场景实录)

第一章:MCP采样接口调用流的金融级灰度发布全景图在高可用、强一致性的金融级系统中,MCP(Metric-Control-Proxy)采样接口的灰度发布并非简单的流量切分,而是一套融合服务治理、链路染色、动态采样率调控与实时可观测性…...

为什么选择picoGPT:10个理由让你爱上这个极简AI模型实现

为什么选择picoGPT:10个理由让你爱上这个极简AI模型实现 【免费下载链接】picoGPT An unnecessarily tiny implementation of GPT-2 in NumPy. 项目地址: https://gitcode.com/gh_mirrors/pi/picoGPT 在当今AI模型日益复杂、框架庞大的时代,picoG…...

终极指南:Feast增量物化如何高效更新特征数据

终极指南:Feast增量物化如何高效更新特征数据 【免费下载链接】feast Feature Store for Machine Learning 项目地址: https://gitcode.com/GitHub_Trending/fe/feast Feast作为一款强大的机器学习特征存储工具,其增量物化功能能够帮助数据科学家…...