项目-苍穹外卖(十五) WebSocket+语音播报功能实现(来订单+催单)

一、介绍

二、入门案例

配置类:

package com.sky.config;

import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.socket.server.standard.ServerEndpointExporter;

/**
 * WebSocket配置类,用于注册WebSocket的Bean
 */
@Configuration
public class WebSocketConfiguration {

    @Bean
    public ServerEndpointExporter serverEndpointExporter() {
        return new ServerEndpointExporter();
    }

}

websocket:

package com.sky.websocket;

import org.springframework.stereotype.Component;
import javax.websocket.OnClose;
import javax.websocket.OnMessage;
import javax.websocket.OnOpen;
import javax.websocket.Session;
import javax.websocket.server.PathParam;
import javax.websocket.server.ServerEndpoint;
import java.util.Collection;
import java.util.HashMap;
import java.util.Map;

/**
 * WebSocket服务
 */
@Component
@ServerEndpoint("/ws/{sid}")
public class WebSocketServer {

    //存放会话对象
    private static Map<String, Session> sessionMap = new HashMap();

    /**
     * 连接建立成功调用的方法
     */
    @OnOpen
    public void onOpen(Session session, @PathParam("sid") String sid) {
        System.out.println("客户端:" + sid + "建立连接");
        sessionMap.put(sid, session);
    }

    /**
     * 收到客户端消息后调用的方法
     *
     * @param message 客户端发送过来的消息
     */
    @OnMessage
    public void onMessage(String message, @PathParam("sid") String sid) {
        System.out.println("收到来自客户端:" + sid + "的信息:" + message);
    }

    /**
     * 连接关闭调用的方法
     *
     * @param sid
     */
    @OnClose
    public void onClose(@PathParam("sid") String sid) {
        System.out.println("连接断开:" + sid);
        sessionMap.remove(sid);
    }

    /**
     * 群发
     *
     * @param message
     */
    public void sendToAllClient(String message) {
        Collection<Session> sessions = sessionMap.values();
        for (Session session : sessions) {
            try {
                //服务器向客户端发送消息
                session.getBasicRemote().sendText(message);
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    }

}

定时任务: 

package com.sky.task;

import com.sky.websocket.WebSocketServer;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;

@Component
public class WebSocketTask {
    @Autowired
    private WebSocketServer webSocketServer;

    /**
     * 通过WebSocket每隔5秒向客户端发送消息
     */
    @Scheduled(cron = "0/5 * * * * ?")
    public void sendMessageToClient() {
        webSocketServer.sendToAllClient("这是来自服务端的消息:" + DateTimeFormatter.ofPattern("HH:mm:ss").format(LocalDateTime.now()));
    }
}

三、语音播报

来订单:

    /**
     * 订单支付
     *
     * @param ordersPaymentDTO
     * @return
     */
    public OrderPaymentVO payment(OrdersPaymentDTO ordersPaymentDTO) throws Exception {
        // 当前登录用户id
        Long userId = BaseContext.getCurrentId();
        User user = userMapper.getById(userId);

/*        //调用微信支付接口,生成预支付交易单
        JSONObject jsonObject = weChatPayUtil.pay(
                ordersPaymentDTO.getOrderNumber(), //商户订单号
                new BigDecimal(0.01), //支付金额,单位 元
                "苍穹外卖订单", //商品描述
                user.getOpenid() //微信用户的openid
        );

        if (jsonObject.getString("code") != null && jsonObject.getString("code").equals("ORDERPAID")) {
            throw new OrderBusinessException("该订单已支付");
        }*/

        JSONObject jsonObject = new JSONObject();
        jsonObject.put("code", "ORDERPAID");
        OrderPaymentVO vo = jsonObject.toJavaObject(OrderPaymentVO.class);
        vo.setPackageStr(jsonObject.getString("package"));

        //为替代微信支付成功后的数据库订单状态更新,多定义一个方法进行修改
        Integer OrderPaidStatus = Orders.PAID; //支付状态,已支付
        Integer OrderStatus = Orders.TO_BE_CONFIRMED;  //订单状态,待接单
        //发现没有将支付时间 check_out属性赋值,所以在这里更新
        LocalDateTime check_out_time = LocalDateTime.now();

        orderMapper.updateStatus(OrderStatus, OrderPaidStatus, check_out_time, orderId);

        //通过websocket向客户端浏览器推送消息  type orderId content
        Map map= new HashMap();
        map.put("type",1); //1表示来单提醒 2表示客户催单
        map.put("orderId",orderId);
        map.put("content","订单号:"+orderMapper.getById(orderId).getNumber());

        String s = JSON.toJSONString(map);
        webSocketServer.sendToAllClient(s);

        return vo;
    }

催单:

 

### 苍穹外卖平台订单提醒功能实现 #### 商家端通知机制 当用户下并支付成功之后,系统需立即向商家发出通知。此过程涉及多个组件间的协作: - **微信服务器回调**:一旦用户的支付请求被确认完成,微信服务器会主动调用Java服务器上的特定接口以传递支付成功的消息[^3]。 ```java // 假设这是接收来自微信服务器的通知的方法签名 @PostMapping("/payNotify") public ResponseEntity<String> payNotify(@RequestBody Map<String, String> notifyData){ // 处理逻辑... } ``` - **WebSocket推送至商家客户端**:接收到支付成功的信号后,服务端利用WebSocket协议实时更新商家应用内的界面状态,确保及时显示新订单信息。 ```javascript // WebSocket连接建立后的监听函数 (JavaScript) socket.onmessage = function(event) { const data = JSON.parse(event.data); if(data.type === 'new_order'){ alert('您有一个新的订单!'); } }; ``` #### 来提醒的具体形式 为了提高用户体验以及保证商家不会错过任何一笔生意,在设计上提供了两种主要的方式来传达这一重要事件给商家: 1. **语音播报**:对于忙碌中的店铺而言尤其有用,即使不直视屏幕也能获知最新动态; 2. **弹窗提示**:直观地展示于屏幕上,附带必要详情以便快速响应顾客需求[^2]。 #### 定期检查未处理订单的状态 除了即时性的提醒外,还应考虑设置周期性任务去扫描那些长时间处于待处理阶段的订单,并触发相应的预警措施。这通常是在`OrderService`的服务层中定义相应的行为,例如提供了一个名为`reminder`的方法用于执行此类操作[^4]。 ```java @Service public class OrderServiceImpl implements OrderService { @Override public void reminder(Long id) { // 查找对应ID的订单记录,并根据情况决定下一步动作 } // ...其他方法省略 } ``` 通过上述手段相结合的方式,可以有效地构建起一套完整的、高效的订单提醒体系,从而保障整个交易流程顺畅无阻。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值