【问题标题】:GenericDAO with Guice, playing with Generics and ParameterizedTypeGenericDAO 与 Guice,玩泛型和 ParameterizedType
【发布时间】:2012-01-24 01:04:43
【问题描述】:

大多数人应该熟悉为 Spring + hibernate 制作通用 DAO。参考来自这里http://www.ibm.com/developerworks/java/library/j-genericdao/index.html,但在Single DAO & generic CRUD methods (JPA/Hibernate + Spring)上有一个改进

这种改进是检测类型,因为它是超类的一部分,而不是使用构造函数来判断它是哪个类

public GenericDaoJpaImpl() {
    ParameterizedType genericSuperclass = (ParameterizedType) getClass()
         .getGenericSuperclass();
    this.entityClass = (Class<T>) genericSuperclass
         .getActualTypeArguments()[0];
}

但是,这个施法会因 Guice 而失败。要注入,接口和类需要像这样绑定在一个模块中

bind(TestDao.class).to(TestDaoImpl.class);

通过这样做,我们的 GenericDAO 的构造函数将无法工作,原因如下:

getClass().getGenericSuperclass() = java.lang.Class
getClass().getName() = com.gwtplatform.samples.basic.server.dao.TestDaoImpl$$EnhancerByGuice$$5fe0d6fd

与 Spring + Hibernate 返回的相反

getClass().getGenericSuperclass() = sun.reflect.generics.reflectiveObjects.ParameterizedTypeImpl
getClass().getName() =  com.gwtplatform.samples.basic.server.dao.TestDaoImpl

我现在只是在我的扩展 DAO 中使用超级构造函数,但仍然想获取类型而不是提供它,有什么想法吗?

【问题讨论】:

    标签: java hibernate generics guice


    【解决方案1】:

    “guicy”的方式是让 Guice 将 TypeLiteral 注入到您的代码中。

    bind(new TypeLiteral<Dao<Foo>>(){}).to(GenericDAO.class);
    

    然后……。

    class GenericDao implements Dao<T>
      @Inject
      GenericDao(TypeLiteral<T> type) {
        this.whatever = type;
      }
    }
    

    Guice 知道 T 的类型,很乐意告诉您。 TypeLiteral 具有获取原始基础类型的访问器。

    guice 文档中关于这项技术的信息很少,但这篇博文很有帮助:http://blog.publicobject.com/2008/11/guice-punches-erasure-in-face.html

    【讨论】:

    • 我将其标记为答案,因为这是获取类型的一种方式,但对我来说,与自己提供类型相比,最后这只是很多代码
    【解决方案2】:

    这些通用技巧让我头疼,如果我在那里,我经常质疑我是否应该这样做,也许有更好的解决方案,但我认为你可以通过在 Guice 中使用 Provider 来做到这一点,所以你是传递实际的类,而不是让 Guice 创建它。所以

    public class DAOProvider implements Provider<TestDaoImpl> {/*etc*/}
    
    bind(TestDao.class).toProvider(new DAOProvider());
    

    【讨论】:

      【解决方案3】:

      您可以使用以下代码从 Guice 代理获取底层类:

      Class<?> clazz = getClass();
      
      if (clazz.getName().contains("EnhancerByGuice")) {
        clazz = clazz.getSuperclass();
      }
      

      【讨论】:

        猜你喜欢
        • 2012-07-24
        • 2014-04-16
        • 2014-08-22
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2013-09-24
        • 1970-01-01
        相关资源
        最近更新 更多