Java后端使用socketio,实现小程序答题pk功能

本文记录了使用Java后端通过socket.io实现小程序答题PK功能的过程。在功能需求部分,描述了用户如何在小程序中进行答题匹配。在实施过程中遇到了消息发送不一致和因nginx超时导致的连接断开问题,并给出了相应的解决方案。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

在使用socket.io跟前端通信过程中,出现了一系列问题,现做下记录。

一、功能需求

在小程序端,用户可相互邀请,进入房间后进行答题PK。实现方法是,用户点击邀请好友,建立连接,查询当前是否有房间,有房间发送消息给两人,匹配成功,开始pk。没有房间新建房间返回,等待20秒,等待别人匹配。

代码如下,先看配置,在application.yml配置文件中增加如下配置

Java后端使用socketio,实现小程序答题pk功能

配置类

package com.cwn.wethink.remy.handler;
 
import com.corundumstudio.socketio.SocketConfig;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
 
import com.corundumstudio.socketio.SocketIOServer;
 
/**
 * @description:
 * @author: m1575
 * @create: 2020-11-11
 **/
@Configuration
class SocketIOConfig {
 
@Value("${socketio.host}")
private String host;
 
@Value("${socketio.port}")
private Integer port;
 
@Value("${socketio.bossCount}")
private int bossCount;
 
@Value("${socketio.workCount}")
private int workCount;
 
@Value("${socketio.allowCustomRequests}")
private boolean allowCustomRequests;
 
@Value("${socketio.upgradeTimeout}")
private int upgradeTimeout;
 
@Value("${socketio.pingTimeout}")
private int pingTimeout;
 
@Value("${socketio.pingInterval}")
private int pingInterval;
 
/**
 * 以下配置在上面的application.properties中已经注明
 * @return
 */
@Bean
public SocketIOServer socketIOServer() {
SocketConfig socketConfig = new SocketConfig();
socketConfig.setTcpNoDelay(true);
socketConfig.setSoLinger(0);
com.corundumstudio.socketio.Configuration config = new com.corundumstudio.socketio.Configuration();
config.setSocketConfig(socketConfig);
config.setHostname(host);
config.setPort(port);
config.setBossThreads(bossCount);
config.setWorkerThreads(workCount);
config.setAllowCustomRequests(allowCustomRequests);
config.setUpgradeTimeout(upgradeTimeout);
config.setPingTimeout(pingTimeout);
config.setPingInterval(pingInterval);
return new SocketIOServer(config);
}
}

后台实现

package com.cwn.wethink.remy.handler;
 
import java.util.*;
import java.util.concurrent.ConcurrentHashMap;
import javax.annotation.PostConstruct;
import javax.annotation.PreDestroy;
import com.alibaba.fastjson.JSONObject;
import com.corundumstudio.socketio.*;
import com.cwn.wethink.pojo.entity.Question;
import com.cwn.wethink.remy.entity.PkAgainGame;
import com.cwn.wethink.remy.entity.PkAnswerTime;
import com.cwn.wethink.remy.entity.PkGroup;
import com.cwn.wethink.remy.entity.WxUserInfo;
import com.cwn.wethink.remy.mapper.PkMapper;
import com.cwn.wethink.remy.mapper.WxUserInfoMapper;
import com.cwn.wethink.remy.service.RemyCourseService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
 
@Service
@Slf4j
public class MessageEventHandler {
 
// 用来存已连接的客户端
private static Map<Long, SocketIOClient> clientMap = new ConcurrentHashMap<>();
 
@Autowired
private SocketIOServer socketIOServer;
 
@Autowired
private PkMapper pkMapper;
 
@Autowired
private WxUserInfoMapper wxUserInfoMapper;
 
@Autowired
private RemyCourseService remyCourseService;
 
/**
 * Spring IoC容器创建之后,在加载SocketIOServiceImpl Bean之后启动
 * @throws Exception
 */
@PostConstruct
private void autoStartup() throws Exception {
start();
}
 
/**
 * Spring IoC容器在销毁SocketIOServiceImpl Bean之前关闭,避免重启项目服务端口占用问题
 * @throws Exception
 */
@PreDestroy
private void autoStop() throws Exception {
stop();
}
 
public void start() {
// 监听客户端连接,同级挑战比拼
socketIOServer.addConnectListener(client -> {
Long uid = Long.valueOf(getParamsByClient(client));
log.info("connect come in,uid:{}",uid);
//0为同级挑战,1为邀请好友pk
int type = 0;
//房间号
int pkId = 0;
//从请求的连接中拿出参数
Map<String, List<String>> params = client.getHandshakeData().getUrlParams();
List<String> list = params.get("type");
if (list != null &&
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值