TcpConnectionFactoryFactoryBean 不支持循环引用?

TcpConnectionFactoryFactoryBean does not support circular references?

我正在尝试使用 spring 创建一个简单的 TcpInboundGateway

但以下不起作用:

@EnableIntegration
@IntegrationComponentScan
public class MyEndpoint {
    @Bean
    public TcpInboundGateway gateway() throws Exception {
        TcpInboundGateway gate = new TcpInboundGateway();
        TcpConnectionFactoryFactoryBean fact = new TcpConnectionFactoryFactoryBean();
        fact.setType("server");
        fact.setPort(5555);
        gate.setConnectionFactory(fact.getObject());
        gate.setRequestChannel(new RendezvousChannel());
        return gate;
    }
}

结果:

Caused by: org.springframework.beans.factory.FactoryBeanNotInitializedException: org.springframework.integration.ip.config.TcpConnectionFactoryFactoryBean does not support circular references
    at org.springframework.beans.factory.config.AbstractFactoryBean.getEarlySingletonInstance(AbstractFactoryBean.java:164)
    at org.springframework.beans.factory.config.AbstractFactoryBean.getObject(AbstractFactoryBean.java:148)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:483)
    at org.springframework.beans.factory.support.SimpleInstantiationStrategy.instantiate(SimpleInstantiationStrategy.java:162)
    ... 31 more

这里可能遗漏了什么?

您对 JavaConfig 的概念有点误解。请阅读更多 Spring 框架 Manual Reference

针对您的特定情况的答案:任何 FactoryBean 都必须配置为单独的 @Beanmethod argument injection:

等引用
@Bean
public TcpConnectionFactoryFactoryBean connectionFactory() {
    TcpConnectionFactoryFactoryBean fact = new TcpConnectionFactoryFactoryBean();
    fact.setType("server");
    fact.setPort(5555);
    return fact;
}

@Bean
public TcpInboundGateway gateway(AbstractConnectionFactory connectionFactory) throws Exception {
   TcpInboundGateway gate = new TcpInboundGateway();
   gate.setConnectionFactory(connectionFactory);
   gate.setRequestChannel(new RendezvousChannel());
   return gate;
}

以及RendezvousChannel作为一个bean从你单独的问题:.

将您的代码更改为

@Bean
public TcpInboundGateway gateway(AbstractConnectionFactory connectionFactory) throws Exception {
    TcpInboundGateway gate = new TcpInboundGateway();
    gate.setConnectionFactory(connectionFactory);
    gate.setRequestChannel(new RendezvousChannel());
    return gate;
}

@Bean
public TcpConnectionFactoryFactoryBean connectionFactory() {
    TcpConnectionFactoryFactoryBean fact = new TcpConnectionFactoryFactoryBean();
    fact.setType("server");
    fact.setPort(5555);
    return fact;
}

Spring 有一种处理 FactoryBean 实例的特定方式,您的 gateway bean 通过在初始化 TcpConnectionFactoryFactoryBean 之前调用 getObject 来打破它(您也可以调用 afterPropertiesSet 来初始化内联)。使用上面的代码,您让 Spring 负责初始化。