Home > front end >  Injecting component method output into component constructor
Injecting component method output into component constructor

Time:12-10

I have a spring boot app with some repositories (i.e. InMemory, Database) that implement a common interface (IRepository), and a factory for accessing them as below.

public class SomeRepositoryFactory {
    
    public IRepository getRepository(String repoType) {
        if (repoType == "Database") {
            return new DatabaseRepository();
        } else if (repoType == "InMemory") {
            return new InMemoryRepository();
        }
        return null;
    }

}

There is also a service class that has a repository as a dependency

public class SomeService {

    private IRepository repository;

    public SomeService (IRepository repository) {
        this.repository = repository;
    }

}

I managed to wire them fine manually with the following configuration

@Configuration
public class MyConfig {

    @Bean
    public SomeRepositoryFactory someRepositoryFactory() {
        return new SomeRepositoryFactory();
    }

    @Bean
    public IRepository someRepository() {
        return someRepositoryFactory().getRepository("InMemory");
    }

    @Bean
    public SomeService someService() {
        return new SomeService(someRepository());
    }

}

However, I'd like to try use autowiring to accomplish this. In particular, I'm not sure how to inject the service class with a repository that is retrieved from the factory. Ideally I'd like to have some annotation like this

@Component
@inject with SomeRepositoryFactory.getRepository.("InMemory")
public class SomeService {

    private IRepository repository;

    public SomeService (IRepository repository) {
        this.repository = repository;
    }

}

CodePudding user response:

If you have only one bean with an implementation for an interface you simply have inject it like you would any other managed instance. You can use constructor injection, @Autowire, setter injection, etc.

This should simply work:

@Component
public class SomeService {

    private IRepository repository;

    // Constructor injection here, should find the bean from someRepository configuration method
    public SomeService (IRepository repository) {
        this.repository = repository;
    }

}

In case you have multiple implementation for the same interface, you could annotate it the injection with @Qualifier:

@Component
public class SomeService {

    private IRepository repository;

    public SomeService (@Qualifier("someRepository") IRepository repository) {
        this.repository = repository;
    }

}
  • Related