TCP实现同步响应

tcp是异步通信,如果想同步将响应信息返回给调用者tcp是做不到的。

解决方案:

第一步:新建消息管理器类。

package com.components.driver.netty;

/**
 * 消息管理器<br>
 * tcp通讯中实现同步返回
 **/
public class ResponseMsg {
    /** 应答超时时间 */
    private final static Long RES_TIMEOUT = 10*1000L;

    private Object data;

    public Object getResponse() {
        try {
            //不加锁 抛java.lang.IllegalMonitorStateException
            synchronized (this) {
                this.wait(RES_TIMEOUT);
            }
        } catch (InterruptedException ignore) {
            return null;
        }

        return getData();
    }

    public Object getData() {
        return data;
    }

    public void setData(Object data) {
        this.data = data;
    }
}

第二步:创建消息发送服务类,在tcp消息发送方法中添加如下代码。

package com.components.driver.netty;

import com.alibaba.fastjson.JSONObject;
import java.nio.charset.StandardCharsets;
import java.util.concurrent.ConcurrentHashMap;

/**
 * 消息同步发送服务
 */
public class CommManager {
    /**
     * TCP推送消息列表,记录消息超时
     */
    public static final ConcurrentHashMap<Long, ResponseMsg> PUSH_MSG_MAP_TCP = new ConcurrentHashMap<>();

    /**
     * 同步发送数据<br>
     * 发送成功后等待终端的应答数据
     * @param data json数据
     */
    public static String sendTcpMessageSync(String data){
        // tcp消息发送
        NettyClient.sendData(data);
        JSONObject jsonObject = JSONObject.parseObject(data);
        ResponseMsg responseMsg = new ResponseMsg();
        // 等待响应的key.
        PUSH_MSG_MAP_TCP.put((Long) jsonObject.get("seqNo"), responseMsg);
        //等待responseMsg设置的超时时间内获取响应数据
        return (String) responseMsg.getResponse();
    }
...
}

第三步:创建消息接收服务类。消息接收的地方处理响应数据,将响应数据放到缓存Map中。

...省略块...
            // 请求
            if (StringUtils.equals(RequestTypeEnum.request.toString(), requestType)){
                responsePacket.setType(RequestTypeEnum.response.toString());
                responsePacket.setTraceId(responsePacket.getSeqNo());
                issctBusinessAction(responsePacket, businessAction);
            }else
            // 响应
            {
                Long requestId = responsePacket.getTraceId() == null ? responsePacket.getSeqNo() : responsePacket.getTraceId();
                ResponseMsg responseMsg = CommManager.PUSH_MSG_MAP_TCP.get(requestId);
                if (responseMsg != null) {
                    responseMsg.setData(data);
                    responseMsg.notify();
                    CommManager.PUSH_MSG_MAP_TCP.remove(requestId);
                }
            }
...省略块...

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值