【问题标题】:Spring Integration TCP. Get connection ID of the connected clients弹簧集成 TCP。获取已连接客户端的连接 ID
【发布时间】:2016-08-21 09:45:39
【问题描述】:

我在这里遇到了动态 TCP 连接方法 (Spring-IP Dynamic FTP Sample) 的问题。收到消息后,我想获取收到消息的 TCP 连接详细信息。这样我就可以在我的应用程序中跟踪发送该消息的发件人。但是在服务激活器中,我无法获得此详细信息。

当我的 TCP 客户端连接到服务器时,还需要连接详细信息。这样,如果服务器想要启动通信,它将具有连接详细信息。

关于信息,我的应用程序有多个 TCP 客户端和服务器。

【问题讨论】:

  • 想要 TCP 连接 ID,不管它是什么。您需要发件人详细信息。经典的 XY 问题。

标签: tcp spring-integration


【解决方案1】:

得到了 Gary Russell 先生在另一篇文章中的答复。

回答

对于正常的请求/回复处理,使用入站网关,框架将负责将服务激活器回复路由到正确的套接字。它通过使用连接 ID 标头来做到这一点。

如果您需要提供任意回复(例如,一条消息有多个回复,则必须使用入站和出站通道适配器,并且您的应用程序负责设置连接 ID 标头。

有两种方法可以访问服务激活器调用的 POJO 中所需的标头:

public void foo(byte[] payload, @Header(IpHeaders.CONNECTION_ID) String connectionId) {
    ...
}

public void foo(Message<byte[]> message) {
    String connectionId = message.getHeaders().get(...);
}

然后,当您发送回复时,您需要以某种方式设置该标题。

编辑

下面是我的实现

要获取所有连接的客户端,只需从上下文中获取 ServerConnectionFactory 并访问方法 .getConnectedClients()。它返回每个已连接客户端的列表 connectionIds。

AbstractServerConnectionFactory connFactory = (AbstractServerConnectionFactory) appContext.getBean("server");
List<String> openConns = connFactory.getOpenConnectionIds();

如上所述,在 Gary 的响应中,使用此 connectionId 并将其设置在 conneciton 标头中,同时将消息发送到客户端。示例代码如下。

MessageChannel serverOutAdapter = null;
try{
    serverOutAdapter = (MessageChannel) appContext.getBean("toObAdapter");
}catch(Exception ex){
    LOGGER.error(ex.getMessage());
    throw ex;
}

    if(null == serverOutAdapter){
        throw new Exception("output channel not available");
    }

    AbstractServerConnectionFactory connFactory = (AbstractServerConnectionFactory) appContext.getBean("serverConnFactoryBeanId");
    List<String> openConns = connFactory.getOpenConnectionIds();
    if(null == openConns || openConns.size() == 0){

        throw new Exception("No Client connection registered");
    }

    for (String connId: openConns) {
        MessageBuilder<String> mb = MessageBuilder.withPayload(message).setHeader(IpHeaders.CONNECTION_ID, connId);
        serverOutAdapter.send(mb.build());
    }

注意 1:如果您想从服务器发送消息,请谨慎配置服务器和客户端连接工厂,以免超时。即在客户端连接工厂中放置 so-keep-alive = true。

注意 2:如果服务器必须与客户端通信,请确保客户端在加载上下文后立即连接到服务器。因为 Spring-IP 客户端连接工厂仅在发送第一条消息时才连接。为了在上下文加载后连接客户端,请将 client-mode="true" 放入“tcp-outbound-channel-adapter”的 tcp 客户端上下文中。

【讨论】:

  • 在我的服务方法中添加这个 @Header(IpHeaders.CONNECTION_ID) String connectionId 作为参数对我有用。谢谢!
猜你喜欢
  • 1970-01-01
  • 2010-11-18
  • 1970-01-01
  • 2015-10-11
  • 1970-01-01
  • 2018-12-30
  • 2012-04-03
  • 2021-07-01
  • 2016-05-08
相关资源
最近更新 更多