In my application I need to acquire a different implementation depending on some user input.
As I want to take full advantage of HK2 I want to solve this with the methods Jersey/HK2 provide.
So far, all I ever did was inject services via interfaces that were bound to implementations on the startup using ApplicationConfig
and ApplicationBinder
:
@javax.ws.rs.ApplicationPath("api")
public class ApplicationConfig extends ResourceConfig
{
public ApplicationConfig()
{
super();
packages(true, "my.package");
register(new ApplicationBinder());
register(....);
....
}
}
public class ApplicationBinder extends AbstractBinder
{
@Override
protected void configure()
{
bind(ServletTemplateLoader.class).to(TemplateLoader.class);
bindAsContract(JobsImpl.class);
bindAsContract(JobInputAppender.class);
bindAsContract(ParamNameMapper.class);
bind(RedisJobRepository.class).to(JobRepositoryInterface.class);
....
}
Now however, I need to acquire an implementation dynamically depending on user input. There are 25 different implementations all using the same interface.
This means, I can no longer simply use the bind.to
approach. Instead I reckon I need to register them all individually with bindAsContract
.
But then, how do I write a method/class that for any given input (from the user) will provide me with the correct implementation?
Essentially, I need a method that looks like this:
public interface MyInterface {}
public class Type1Impl implements MyInterface {} // registered with `bindAsContract`
public MyInterface getImplementation(final String type_)
{
switch (type_) {
case "type1":
return // what to do here to get "my.package.Type1Impl" instance?
case "type":
....
}
}
I need the instance to come from HK2 because the Impl also uses injected services, so I can't simply create a new instance on the fly.
I think there is a better answer using IterableProvider. Basically you can do this in one of your services:
public class ImplementationGetter {
@Inject
private IterableProvider<MyInterface> interfaceProvider;
public MyInterface getImplementation(final String type_) {
return interfaceProvider.named(type_).get();
}
}
Hope this helps!