java - 如何使用 Spring Integration 动态创建多个 TcpOutboundGateways?

标签 java spring spring-boot tcp spring-integration

我有一个场景,我需要一个客户端应用程序能够在应用程序启动时动态创建到可变数量的唯一主机/端口组合的 TCP 连接。我正在尝试使用 Spring Integration TcpOutboundGateway 来完成此操作,但一直找不到解决方案。我希望每个主机/端口组合都有自己专用的 TcpOutboundGateway。到目前为止,我对 TcpOutboundGateway 的研究使我得出以下单一网关解决方案……

@MessageGateway(defaultRequestChannel=“sendMessage”)
public interface myMessageGateway {
    byte[] sendMessage(String message);
}

@Bean
@ServiceActivator(inputChannel=“sendMessage”)
public MessageHandler tcpOutboundGateway(AbstractClientConnectionFactory factory) {
    TcpOutboundGateway gateway = new TcpOutboundGateway();
    gateway.setConnectionFactory(factory);
    return gateway;
}

@Bean
public AbstractClientConnectionFactory clientConnectionFactory() {
    return new TcpNetClientConnectionFactory(“123.456.789.0”, 5555);
}

我的理解是调用 sendMessage 函数会将请求消息放在“sendMessage” channel 上。然后该 channel 会将其传递给 tcpOutboundGateway 服务激活器,后者将处理消息的发送并最终返回服务器的响应作为 sendMessage 函数的返回值。在单一的预定义服务器连接的情况下,此解决方案对我来说效果很好。

我的问题是如何以支持一组可变的唯一主机/端口的方式动态创建新的消息网关和服务激活器?更具体地说,@MessageGateway 和@ServiceActivator 注释在后台为我们做了什么,我需要做什么才能复制该功能?

编辑:

因此,经过一些试验后,我找到了这个似乎可以解决问题的解决方案......

// Define the Message Gateway without any annotations
public interface MyMessageGateway {
    byte[] sendMessage(String message);
}

...

// Use the GatewayProxyFactoryBean to replicate the functionality of the @MessageGateway annotation
// context is my instance of a ConfigurableApplicationContext
GatewayProxyFactoryBean gpfb = new GatewayProxyFactoryBean(SenderGateway.class);
gpfb.setDefaultRequestChannel(“sendMessage”);
context.getBeanFactory().registerSingleton(“MyMessageGateway”, gpfb);
context.getBeanFactory().initializeBean(gpfb, “MyMessageGateway”);

// Create and register the ClientConnectionFactory Bean within the Application Context
AbstractClientConnectionFactory clientConnectionFactory = new TcpNetClientConnectionFactory(“123.456.789.0”, 5000);
context.getBeanFactory().registerSingleton(“ClientConnectionFactory”, clientConnectionFactory);
context.getBeanFactory().initializeBean(clientConnectionFactory, “ClientConnectionFactory”);

// Create and register the TcpOutboundGateway Bean within the Application Context
TcpOutboundGateway gateway = new TcpOutboundGateway();
gateway.setConnectionFactory(clientConnectionFactory);
context.getBeanFactory().registerSingleton(“TcpOutboundGateway”, tcpOutboundGateway);
context.getBeanFactory().initializeBean(tcpOutboundGateway, “TcpOutboundGateway”);

// Create and register the Request Channel to connect the Message Gateway and the TCP Outbound Gateway
// This should replicate the functionality of the @ServiceActivator annotation
DirectChannel sendMessage = new DirectChannel();
sendMessage.setBeanName(“sendMessage”);
context.getBeanFactory().registerSingleton(“sendMessage”, sendMessage);
context.getBeanFactory().initializeBean(sendMessage, “sendMessage”);

// Subscribe the TCP Outbound Gateway to the new Message Channel (sendMessage)
// This should replicate the functionality of the @ServiceActivator annotation
sendMessage.subscribe(tcpOutboundGateway);

// Start the ClientConnectionFactory
// This seems to be getting done automatically in the non-dynamic implementation above
clientConnectionFactory.start();

此实现允许以与上述注释实现相同的方式通过消息网关和 TCP 出站网关发送消息(使用为 MyMessageGateway 接口(interface)定义的 sendMessage 函数)。我发现,为了将这种方法用于多个主机/端口组合,您需要通过 context.getBeanFactory.getBean() 获取所需的消息网关。

我很好奇这种方法/实现是否存在任何缺陷?

最佳答案

做到这一点的唯一简单方法是考虑将动态 IntegrationFlow 与 Spring Integration 提供的 Java DSL 一起使用:https://docs.spring.io/spring-integration/docs/current/reference/html/#java-dsl-runtime-flows

我们还有一个完全适用于类似动态 TCP 客户端用例的综合示例:https://github.com/spring-projects/spring-integration-samples/tree/master/advanced/dynamic-tcp-client

关于java - 如何使用 Spring Integration 动态创建多个 TcpOutboundGateways?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56602415/

相关文章:

java - Stateless Apache Wicket 无状态页面/请求

java - Kontakt.io SDK : Is there a way to hard code in a list of beacons so that I can pull from them randomly whenever I need to search for a beacon?

java - 如何使用 Java 从 blob 中插入和检索 pdf

java - 无法 Autowiring MongoOperations bean

java - spring - 从 application.properties 文件中读取环境变量

java - 如何将响应从 Web 服务器发送到 iphone?

java - 如何在单个 Controller 中制作多个@PatchMapping?

java - gwt + Spring 安全

spring - 仅在第一次调用时调查 HTTP 406 错误代码

java - Spring Boot GCP Data Spanner 延迟问题