7

我刚刚来自我小小的 JavaSE/Guice 世界,目前正在发现“由容器携带”-EE6 的路径。在 Glassfish3.1 遇到一些问题后,我刚刚切换到 JBoss,现在面临一个不应该出现的问题。

作为基础设施辅助类,我正在尝试为任何类型的实体创建通用存储库/DAO。以一种非常简单的方式,这可能看起来像这样。

public class Repository<E, K extends Serializable & Comparable<K>> {

    private final Instance<EntityManager> entityManagerInstance;

    protected final Class<E> getDomainObjectClass() {
        return domainObjectClass;
    }

    private final Class<E> domainObjectClass;

    protected final EntityManager getEntityManager() {
            return entityManagerInstance.get();
    }

    @Inject
    public Repository(Instance<EntityManager> entityManageryProvider, Provider<E> domainObjectProvider) {
            //This is a dirty hack, sadly :(
            domainObjectClass = (Class<E>)domainObjectProvider.get().getClass();
            this.entityManagerInstance = entityManageryProvider;
    }

    public final void persist(E domainObject) {
        final EntityManager em = getEntityManager();
        em.persist(domainObject);
    }

    public final Collection<E> getAllEntities() {
            final EntityManager em = getEntityManager();
            final CriteriaBuilder cb = em.getCriteriaBuilder();
            final CriteriaQuery<E> query = cb.createQuery(getDomainObjectClass());

            final List<E> result = em.createQuery(query).getResultList();
            return Collections.unmodifiableList(result);
    }

    public final E find(K id) {
            Preconditions.checkNotNull(id);
            final EntityManager em = getEntityManager();
            return em.find(getDomainObjectClass(), id);
    }

    // [...]
}

现在可能有一个 bean 不需要依赖于实体的查询功能,而只需要某种实体类型的存储库,例如(可能是一个测试用例):

public class DomainObjectARepositoryTest{

    @Inject
    Repository<DomainObjectA, PersistableUUID> domainObjectARepository;


    @Test
    public void testMitarbeitererstellung() {
        for (DomainObjectA a : domainObjectARepository.getAllEntities()) {
            // do cool stuff
        }       
    }
}

不幸的是,Weld 似乎不喜欢这种通用注入。在部署时,我收到以下错误:

state=Create: org.jboss.weld.exceptions.DeploymentException: WELD-001408 Unsatisfied dependencies for type [Repository<DomainObjectA , PersistableUUID>] with qualifiers [@Default] at injection point [[field] @Inject sompackage.DomainObjectARepositoryTest.domainObjectARepository]

我是否遗漏了什么或者他们只是忘记了实现通用注入?据我了解通用的东西,无论如何它都会在编译后被删除——即使到目前为止这在 guice3 中工作得很好。

亲切的问候,

avi

编辑:发现garvin king的评论说这种行为在规范中,但没有在焊接中实现,(状态是在 2009 年 6 月)

4

1 回答 1

1

这是一个相当长的评论,而不是对您问题的完整答案,但可能会为您指明正确的方向:

很长一段时间以来,我一直在关注 seam-dev 和weld-dev 中的讨论,并且不记得曾经出现过这样的事情。所以我的猜测是,自从 Gavin 发表评论以来,它就没有出现在议程上。

你可以做相对容易的事情来验证这个假设:

(a) 获取对 BeanManager 的引用并查询它以获取相关的 bean 类型(或者只是为了Object在保存端),当然您必须删除@InjectinDomainObjectARepositoryTest才能启动应用程序。

(b) 注册一个扩展并收听ProcessBean部署期间出现的情况。这将是我建议的方式,您将在此处找到更多信息。

有了这个结果,您绝对应该能够判断是否有任何 bean 类型Repository<E, K extends Serializable & Comparable<K>>在附近:-)

如果您在此处报告结果并考虑在负面情况下提交 Jira 问题,那就太酷了。

于 2011-06-23T05:17:40.953 回答