根据某些对象的运行时泛型类型获取CDI bean

时间:2015-04-09 16:28:09

标签: java generics cdi

我有时会遇到一种情况,我想根据某个对象的运行时类型选择一些通用接口的合适实现。我想用CDI做到这一点。我想做的例子:

public interface Id {}

public interface AId extends Id {
    String getAValue();
}

public interface BId extends Id {
    Integer getBValue();
}

public interface Loader<I extends Id> {
    Object load(I id);
}

public class ALoader implements Loader<AId> {
    public Object load(AId id) {
        return id.getAValue();
    }
}

public class BLoader implements Loader<BId> {
    public Object load(BId id) {
        return id.getBValue();
    }
}

public class MyCdiBean {
    @Inject
    private Instance<Loader> loaders;

    public <I extends Id> Object loadSomething(I id) {
        return loaders.select(new TypeLiteral<Loader<I>>() {}).get().load(id);
    }
}

当然,new TypeLiteral<Loader<I>>() {}不起作用,因为CDI无法通过反射API确定I的类型(或者我认为),但我希望它能说清楚我是什么我想这样做:我想使用我的变量的运行时类型基于其泛型类型参数选择CDI bean。

我知道我能做到

public class MyCdiBean {
    @Inject
    private Loader<AId> aLoader;
    @Inject
    private Loader<BId> bLoader;

    public Object loadSomething(Id id) {
        if (id instanceof AId) {
            return aLoader.load((AId)id);
        }
        return bLoader.load((BId) id);
    }
}

但我希望避免instanceof次检查(基本上,我希望在没有MyCdiBean了解AIdBId的情况下工作。

我也知道它可以使用限定符注释,但不是完全类型安全的方式。

还有其他干净的方法吗?你认为什么是解决这个问题的好方法?

0 个答案:

没有答案