最近为了写socket补偿方案.(一旦消息发送失败,就要进行失败消息存储,并且对失败消息按照消息类型的不同补偿方案进行补偿)
补偿方式就是针对如下图不同的消息主键进行不同次数,不同等待时长进行消息补偿.
然后因为没考虑到线程一定要有开有关.在同一个线程中进行递归补偿.并且递归逻辑中增加了Thread.sleep(15*1000)的逻辑.造成线程池资源耗尽.消息堆积.并且因为过程中有查库操作,将数据库也给搞挂了...
下面是具体的代码:
package medicalshare.socketweb.helper;
import com.alibaba.dubbo.config.annotation.Reference;
import com.ctrip.framework.apollo.Config;
import com.ctrip.framework.apollo.spring.annotation.ApolloConfig;
import lombok.extern.slf4j.Slf4j;
import medicalshare.socketweb.vo.MessageConfigVo;
import medicalshare.socketweb.websocket.SocketContext;
import medicalshare.support.constant.SocketSendResultConstant;
import medicalshare.user.api.UserService;
import medicalshare.user.dto.UserMessageDto;
import org.apache.commons.lang3.StringUtils;
import org.apache.commons.lang3.time.FastDateFormat;
import org.springframework.scheduling.annotation.Async;
import org.springframework.stereotype.Component;
import org.springframework.web.socket.BinaryMessage;
import org.springframework.web.socket.TextMessage;
import org.springframework.web.socket.WebSocketSession;
import java.io.IOException;
import java.nio.ByteBuffer;
import java.util.*;
/**
* Created by sino on 2018/12/7.
*/
@Component
@Slf4j
public class AsyncSocketHelper {
FastDateFormat fdf = FastDateFormat.getInstance("yyyy-MM-dd HH:mm:ss:SSS");
@Reference
private UserService userService;
@ApolloConfig("Message.yml")
private Config messageConfig;
@Async("socketThreadPool")
protected void sendText(String message, String account, MessageConfigVo messageConfigVo) {
try {
WebSocketSession userSession = SocketContext.getUserSession(account);
if (userSession != null && userSession.isOpen()) {
log.info("向{}账户发送WebSocket消息成功:{}", account, message);
int status=0;
if (messageConfigVo.getTimes()>0){
status=updateUserMessage(message, account, messageConfigVo.getMessageType(), SocketSendResultConstant.SENDSUCCESS,"socketSuccessMessage");
}else{
status=addUserMessage(message, account, messageConfigVo.getMessageType(), SocketSendResultConstant.SENDSUCCESS, "socketSuccessMessage");
}
if (status!=0){
synchronized (userSession) {
TextMessage textMessage = new TextMessage(message);
userSession.sendMessage(textMessage);
}
}
}else {
log.error("向{}账户发送WebSocket消息失败{}!当前账号不在线,无法发送",account,message);
makeupMessage( message, account, messageConfigVo);
}
} catch (IOException e) {
log.error("向{}账户发送WebSocket消息异常:{}", account, e);
makeupMessage( message, account,messageConfigVo);
}
}
/**
* 更新失败消息为成功。
* @param message
* @param account
* @param messageType
*/
public int updateUserMessage(String message, String account, String messageType,String title,String socketFalg) {
String codeValue = messageConfig.getProperty("Message.Make_UP."+messageType