使用Solace时sendRequest同时返回成功与失败的异常排查
问题原因与解决方案
核心原因
你遇到的问题是两种消息处理机制冲突+Correlation ID匹配异常导致的:
- 全局回调抢收响应:你给Session设置了全局的
messageRxCb,这个回调会接收所有发到当前Session的消息,包括sendRequest对应的响应。但sendRequest的成功回调是靠消息的Correlation ID来匹配请求的,全局回调收了响应却没告诉客户端“这是某个请求的回复”,导致客户端以为响应没到,超时触发失败回调。 - Correlation ID未正确回传:你的
sendRequest手动指定了Correlation ID为'correlation test',如果服务端返回响应时没把这个ID复制到响应的Correlation ID字段里,sendRequest的回调根本认不出这是自己的响应,自然会一直等超时,而全局回调会无差别接收所有消息,所以能打出正确结果。
解决办法
1. 移除全局会话回调(最省心)
如果你的场景只有请求-响应交互,不需要监听所有Session消息,直接删掉创建Session时的全局回调参数:
session = solace.SolclientFactory.createSession({ "url": "ws://localhost:8008", "userName": "tech_core", "vpnName": "testing", "password": pass }); // 去掉第二个参数的全局messageRxCb配置
这样sendRequest的成功回调会专门处理对应Correlation ID的响应,不会再出现抢消息的问题。
2. 保留全局回调但处理Correlation ID
如果必须留全局回调,就得在回调里判断消息是否属于某个sendRequest的响应:
async function messageRxCb(session: any, message: any) { const correlationId = message.getCorrelationId(); // 匹配你手动设置的Correlation ID if (correlationId === 'correlation test') { // 告诉客户端这个响应已经被处理,避免sendRequest超时 session.sendReplyAcknowledgement(message); return; // 不要往下处理,留给sendRequest的回调 } // 处理其他非请求响应的消息 message = Parser.decodeBinaryAttachmentToPb(message, pnlPb.RespPnl); console.log('result from RxCb', message); }
重点提醒:必须让服务端把请求里的Correlation ID原样复制到响应的Correlation ID字段,否则sendRequest永远匹配不到响应。
3. 让客户端自动生成Correlation ID
如果不需要自定义Correlation ID,删掉sendRequest的最后一个参数,让Solace自动生成唯一ID,同时确保服务端正确回传这个ID:
session.sendRequest(request, timeout, (ses: any, message: any) => { console.log('SUCCESS', message); subscriber.next(message); }, (ses: any, event: any) => { console.error('FAIL', event); subscriber.error(event); } // 移除最后一个自定义Correlation ID参数 )
内容的提问来源于stack exchange,提问作者Lê Quang Bảo
相关产品推荐
相关产品推荐

