12
votes

I have a class similar to the following:

@Configuration
public class ApplicationConfiguration {

    private <T> T createService(Class<T> serviceInterface) {
        // implementation omitted
    }

    @Bean
    public FooService fooService() {
        return createService(FooService.class);
    }

    @Bean
    public BarService barService() {
        return createService(BarService.class);
    }

    ...

}

The problem is that there are too many @Bean-annotated methods which differ only in their names, return types and arguments for the crateService method call. I would like to make this class similar to the following:

@Configuration
public class ApplicationConfiguration {

    private static final Class<?>[] SERVICE_INTERFACES = {
            FooSerivce.class, BarService.class, ...};


    private <T> T createService(Class<T> serviceInterface) {
        // implementation omitted
    }

    @Beans // whatever
    public Map<String, Object> serviceBeans() {
        Map<String, Object> result = ...
        for (Class<?> serviceInterface : SERVICE_INTERFACES) {
            result.put(/* calculated bean name */,
                    createService(serviceInterface));
        }
        return result;
    }

}

Is it possible in Spring?

1
Of course yes. But you will have only one injectable bean in the application context : the map. - Serge Ballesta
Can you please explain in detail what you're trying to achieve? I don't see how having many @ Bean annotated methods with different return types and names is a problem. Ideally you will group those @ Bean methods in separate @ Configuration classes, so you won't have one God class holding the whole configuration. You can @ Import different configuration classes to reuse defined @ Bean methods. - hovanessyan
I also have exact same requirement. In my case, I am first reading the config data from a file and for each entry in the config, I need to create a bean (all of same java type with different data). Hence I cannot use @Bean annotation, as it has to be read from a config - Harish
@hovanessyan Harish explained the problem. I don't know how much beans will be registered, so I can't hardcode them as separate @Bean-annotated methods. - Victor
@Victor if the problem is what Harish described, you can try a different approach. If all the "beans" are the same java type, you can do use a single @ Bean which has a field - collection of the java type of each entry from the file, or you may consider not using Spring Beans at all. - hovanessyan

1 Answers

5
votes
@Configuration
public class ApplicationConfiguration {

    @Autowired
    private ConfigurableBeanFactory beanFactory;

    @PostConstruct
    public void registerServices() {
        beanFactory.registerSingleton("service...", new NNNService());
        ... 
    }
}