Redis - Consider renaming one of the beans or enabling overriding by setting spring.main.allow-bean-definition-overriding=true

Viewed 31925

I am developing Spring Boot + Spring Data Redis example. In this example, I'm developing the code for the RedisMessageListenerContainer and define the corresponding bean here.

Now when I run the application I get the below error. Could someone guide me what is the issue ?

***************************
APPLICATION FAILED TO START
***************************

Description:

The bean 'redisMessageListenerContainer', defined in class path resource [org/springframework/boot/autoconfigure/session/RedisSessionConfiguration$SpringBootRedisHttpSessionConfiguration.class], could not be registered. A bean with that name has already been defined in com.example.RedisApplication and overriding is disabled.

Action:

Consider renaming one of the beans or enabling overriding by setting spring.main.allow-bean-definition-overriding=true

RedisApplication.java

@Log
@SpringBootApplication
public class RedisApplication {

    @Autowired
    private OrderRepository orderRepository;
    @Autowired
    private LineItemRepository lineItemRepository;

    private ApplicationRunner titleRunner(String title, ApplicationRunner rr) {
        return args -> {
            log.info(title.toUpperCase() + ":");
            rr.run(args);
        };
    }

    @Bean
    ApplicationRunner geography(RedisTemplate<String, String> rt) {
        return titleRunner("geography", args -> {
            GeoOperations<String, String> geo = rt.opsForGeo();
            geo.add("Sicily", new Point(13.361389, 38.155556), "Arigento");
            geo.add("Ramesh", new Point(15.087269, 37.502669), "Catania");
            geo.add("Anup", new Point(13.583333, 37.316667), "Palermo");

            Circle circle = new Circle(new Point(13.583333, 37.316667),
                    new Distance(100, RedisGeoCommands.DistanceUnit.KILOMETERS));

            GeoResults<GeoLocation<String>> radius = geo.radius("Sicily", circle);
            radius.getContent().forEach(c -> log.info(c.toString()));
        });
    }

    public static void main(String[] args) {
        SpringApplication.run(RedisApplication.class, args);
    }



    @Bean
    ApplicationRunner repositories() {
        return titleRunner("repositories", args -> {
            Long orderId = generateId();

            List<LineItem> itemsList = Arrays.asList(
                        new LineItem(orderId, generateId(), "plunger"),
                        new LineItem(orderId, generateId(), "soup"), 
                        new LineItem(orderId, generateId(), "cofee mug"));

            itemsList.stream().map(lineItemRepository::save).forEach(li -> log.info(li.toString()));

            Order order = new Order(orderId, new Date(), itemsList);
            orderRepository.save(order);

            Collection<Order> found = orderRepository.findByWhen(order.getWhen());
            found.forEach(o -> log.info("found : " + o.toString()));
        });
    }

    private Long generateId() {
        long tmp = new Random().nextLong();
        return Math.max(tmp, tmp * -1);
    }

    private final String TOPIC = "Chat";
    @Bean
    ApplicationRunner pubSub(RedisTemplate<String, String> rt) {
        return titleRunner("publish/subscribe", args ->{
            rt.convertAndSend(TOPIC, "Hello World @ "+Instant.now().toString());
        });
    }

    @Bean
    RedisMessageListenerContainer redisMessageListenerContainer(RedisConnectionFactory rcf) {
        MessageListener ml = (message, pattern) -> {
            String str = new String(message.getBody());
            log.info("message from ' " + TOPIC + "':'" + str);
        };

        RedisMessageListenerContainer mlc = new RedisMessageListenerContainer();
        mlc.setConnectionFactory(rcf);
        mlc.addMessageListener(ml, new PatternTopic(TOPIC));
        return mlc;
    }
}
5 Answers

You can implement the change the suggested in the error message by adding (at least in my example)

spring.main.allow-bean-definition-overriding=true to the "application.properties" file. In my case (a windows machine)

\gs-actuator-service\basewebcall\src\main\resources\application.properties

application.yml

spring:  
  main:
    allow-bean-definition-overriding: true

application.properties

spring.main.allow-bean-definition-overriding=true

I am not sure if it's a bug, but if you give any name other than redisMessageListenerContainer i.e Spring will consider bean name, then it works fine.

@Bean
    RedisMessageListenerContainer listener(RedisConnectionFactory rcf) {
        MessageListener ml = (message, pattern) -> {
            String str = new String(message.getBody());
            log.info("message from ' " + TOPIC + "':'" + str);
        };

        RedisMessageListenerContainer mlc = new RedisMessageListenerContainer();
        mlc.setConnectionFactory(rcf);
        mlc.addMessageListener(ml, new PatternTopic(TOPIC));
        return mlc;
    }

This happened to me when there are two java files annotated with @SpringBootApplication in the same project. As per the message in the logs, by default this is not allowed and asking us to include the property in the application.properties to enable the same. Hope this helps.

find in your modul: resources/application.properties and write:

spring.main.allow-bean-definition-overriding=true

it help you, you need to turn on the beans override mechanism.

Related