user1089362
user1089362

Reputation: 566

Spring boot 2 connection to rabbitmq via Apache Camel

I have problem with connection to rabbitmq via Apache Camel on Spring Boot 2.

I did following steps:

My dependencies:

implementation "org.apache.camel:camel-spring-boot-starter:${camelVersion}"
implementation "org.apache.camel:camel-jackson-starter:${camelVersion}"
implementation "org.apache.camel:camel-core:${camelVersion}"
implementation "org.apache.camel:camel-rabbitmq-starter:${camelVersion}"
implementation "org.springframework.boot:spring-boot-starter-amqp"

Application.yaml

spring:
      rabbitmq:
      dynamic: true
      host: 192.168.1.1
      port: 5672
      username: X
      password: Y

And I have following route:

@Component
public class BasicRoute extends RouteBuilder {

@Override
public void configure() throws Exception {

    from("direct:loggerQueue")
            .id("loggerQueue")
            .to("rabbitmq://TEST-QUEUE.exchange?queue=TEST-QUEUE.queue&autoDelete=false&connectionFactory=#rabbitConnectionFactory")
            .end();
}

}

Finnaly I have still following issue:

2019-03-06 12:46:05.766 WARN 19464 --- [ restartedMain] o.a.c.c.rabbitmq.RabbitMQProducer : Failed to create connection. It will attempt to connect again when publishing a message. java.net.ConnectException: Connection refused: connect

Connection seems ok, I tested it. Something is bad with rabbitConnectionFactory.

I don't know what I have bad.

Upvotes: 2

Views: 2802

Answers (1)

sweetfa
sweetfa

Reputation: 5845

The problem appears to be that RabbitMQComponent is expecting to find a connection factory of type com.rabbitmq.client.ConnectionFactory.

However, the springboot auto-configure is creating a connection factory of type org.springframework.amqp.rabbit.connection.CachingConnectionFactory.

So, whenever the RabbitMQComponent attempts to find the appropriate connection factory, because it is looking for the specific type, and because it does not subclass the rabbitmq ConnectionFactory, it returns a null value, and fails to use the appropriate host name and configuration parameters specified in your application.yml.

You should also see the following in your log if you have debug level set:
2019-12-15 17:58:53.631 DEBUG 48710 --- [           main] o.a.c.c.rabbitmq.RabbitMQComponent       : Creating RabbitMQEndpoint with host null:0 and exchangeName: asterix
2019-12-15 17:58:55.927 DEBUG 48710 --- [           main] o.a.c.c.rabbitmq.RabbitMQComponent       : Creating RabbitMQEndpoint with host null:0 and exchangeName: asterix-sink

EDIT: The CachingConnectionFactory is configured with the required Rabbit connection factory as part of the autoconfiguration. However, you need to provide a link to the correct factory.

Therefore, you need to add a @Bean to disambiguate.

@Configuration
@RequiredArgsConstructor
public class CamelConfig {

  private final CachingConnectionFactory rabbitConnectionFactory;

  @Bean
  com.rabbitmq.client.ConnectionFactory rabbitSourceConnectionFactory() {
    return rabbitConnectionFactory.getRabbitConnectionFactory();
  }
}

and in your endpoint configuration:

rabbitmq:asterix?connectionFactory=#rabbitSourceConnectionFactory

Note that the # is optional, as it gets stripped out within the code when it is trying to find the rabbit connection factory bean.

In your application.yml, configure the connection parameters (the url is no longer included in the endpoint URI).

spring:
  rabbitmq:
    host: localhost
    port: 5672
    username: guest
    password: guest

Upvotes: 4

Related Questions