How to Create Multiple Beans of the Same Class in Spring Boot 3

This article demonstrates several techniques—including @Bean methods, @Component inheritance, BeanFactoryPostProcessor, and custom FactoryBean implementations—to instantiate multiple beans of the same class in a Spring Boot 3 application, comparing their advantages and limitations.

Spring Full-Stack Practical Cases
Spring Full-Stack Practical Cases
Spring Full-Stack Practical Cases
How to Create Multiple Beans of the Same Class in Spring Boot 3

1. Introduction

In Spring Boot applications, you may need to create multiple instances (beans) of the same class with different configurations. While defining several @Bean methods in a @Configuration class works, it becomes redundant and hard to maintain when many instances are required.

2. Practical Examples

2.1 Using Java Configuration

The simplest way is to define multiple @Bean methods in a configuration class.

public class Person {
  private String name;
  private Integer age;
  public Person(String name, Integer age) {
    this.name = name;
    this.age = age;
  }
  // getters, setters
  @Override
  public String toString() {
    return "Person [name=" + name + ", age=" + age + "]";
  }
}
@Configuration
public class PersonConfig {
  @Bean
  public Person person1() {
    return new Person("Pack", 22);
  }

  @Bean
  public Person person2() {
    return new Person("xxgg", 24);
  }
}

The @Bean annotation registers both beans in the Spring container, allowing them to be autowired where needed.

2.2 Using @Component

By annotating subclasses with @Component, you can create beans that inherit from a common superclass.

@Component
public class PersonOne extends Person {
  public PersonOne() {
    super("Pack", 22);
  }
}

@Component
public class PersonTwo extends Person {
  public PersonTwo() {
    super("xxxooo", 24);
  }
}

This approach does not create multiple instances of the same class; it creates separate subclasses, which can increase code complexity.

2.3 Using BeanFactoryPostProcessor

A custom BeanFactoryPostProcessor can register multiple bean instances before any other beans are created.

public class PersonFactoryPostProcessor implements BeanFactoryPostProcessor {
  @Override
  public void postProcessBeanFactory(ConfigurableListableBeanFactory beanFactory) throws BeansException {
    Map<String, Object> map = beanFactory.getBeansWithAnnotation(Qualifier.class);
    for (Map.Entry<String, Object> entry : map.entrySet()) {
      createInstances(beanFactory, entry.getKey(), entry.getValue());
    }
  }

  private void createInstances(ConfigurableListableBeanFactory beanFactory, String beanName, Object bean) {
    Qualifier qualifier = bean.getClass().getAnnotation(Qualifier.class);
    for (String name : extractNames(qualifier)) {
      Object newBean = beanFactory.getBean(beanName);
      beanFactory.registerSingleton(name.trim(), newBean);
    }
  }

  private String[] extractNames(Qualifier qualifier) {
    return qualifier.value().split(",");
  }
}

The processor scans for @Qualifier annotations, extracts bean names, and registers singleton instances accordingly.

2.4 Custom FactoryBean Implementation

You can also implement FactoryBean to control bean creation.

@Qualifier(value = "personOne, personTwo")
public class Person implements FactoryBean<Object> {
  private String name;
  private Integer age;

  public Person() {}

  @Override
  public Class<Person> getObjectType() {
    return Person.class;
  }

  @Override
  public Object getObject() throws Exception {
    return new Person();
  }

  @Override
  public boolean isSingleton() {
    return true;
  }
}

Using @Qualifier on the class level allows multiple bean IDs to refer to the same type.

3. Putting It All Together

@Configuration
public class PersonConfig {
  @Bean
  public PersonFactoryPostProcessor personFactoryPostProcessor() {
    return new PersonFactoryPostProcessor();
  }

  @Bean
  public Person person() {
    return new Person();
  }

  @Bean
  public Human human() {
    return new Human();
  }
}

While the BeanFactoryPostProcessor approach is powerful, it adds complexity and is generally not recommended for simple scenarios. The @Bean method remains the most straightforward way to create multiple beans of the same class in Spring Boot 3.

Original Source

Signed-in readers can open the original source through BestHub's protected redirect.

Sign in to view source
Republication Notice

This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactadmin@besthub.devand we will review it promptly.

ConfigurationSpring Bootdependency-injectionbean
Spring Full-Stack Practical Cases
Written by

Spring Full-Stack Practical Cases

Full-stack Java development with Vue 2/3 front-end suite; hands-on examples and source code analysis for Spring, Spring Boot 2/3, and Spring Cloud.

0 followers
Reader feedback

How this landed with the community

Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.