2

我们有一个具有以下 Spring bean 的 Hibernate/Spring 应用程序:

<bean id="transactionManager" class="org.springframework.orm.hibernate3.HibernateTransactionManager" />
<bean id="sessionFactory" class="org.springframework.orm.hibernate3.annotation.AnnotationSessionFactoryBean" />

在将应用程序连接在一起时,在我们的休眠实体中使用私有构造函数时会出现以下错误:

Invocation of init method failed; nested exception is java.lang.IllegalArgumentException: No visible constructors in class 'ourclass'

实体是典型的领域对象,例如员工等。

当将构造函数的可见性修饰符更改为包(或公共)时,应用程序运行良好,实体被存储/加载到数据库中。我们/我们如何使用私有构造函数/静态工厂方法和 Spring/Hibernate 事务管理?

我们使用 Hibernate 注释来映射实体/关系。在 applicationContext.xml 中没有为与问题相关的域类声明任何 bean 定义。它是一个 pojo,应该有一个静态工厂方法和一个私有构造函数。

我们如何让 Hibernate(我猜是 org.springframework.spring-orm.hibernate3 类)使用静态工厂方法而不是构造函数?或者如果必要的话可能让它调用一个私有构造函数?

使用 spring factory-method 配置是有意义的,但实体没有映射为我们的 applicationContext.xml 中的 bean。它们仅使用 @Entity 注释进行注释以实现 Hibernate 持久性。

希望这个编辑能澄清(而不是神秘化)这个问题。:)

4

4 回答 4

5

虽然我没有使用 Spring,但我在一个项目中使用了 Hibernate,该项目具有必须通过工厂方法或通过多个参数构造函数实例化的类。

您可以通过 Interceptor 来做到这一点,它是一个侦听几个关键休眠事件的类,例如何时需要实例化对象或何时加载对象。

要让 Hibernate 使用您自己的方法来实例化对象,请执行以下操作:

public class MyInterceptor extends EmptyInterceptor {

    public Object instantiate(String entityName, EntityMode entityMode, Serializable id) {
        if(entityName.equals(Foo.class.getName())
             return Foo.create();
        return null;
    }
}

考虑到它可以通过反射解决并且我在我的项目中没有遇到这个问题(实际上所有类都没有可见的构造函数)。这可能与Spring有关。检查您正在使用的休眠版本。

于 2008-12-07T19:32:02.897 回答
1

你知道属性“工厂方法”吗?您可以让 spring 调用该方法而不是构造函数来实例化 bean。

于 2008-12-03T09:22:39.027 回答
0

我不认为你可以让 Hibernate(或任何外部框架)在你的对象上调用私有构造函数,除非它是通过一些 javassist 或 cglib 运行时创建的子类。

如果你想让 Hibernate 调用你的构造函数,你为什么不直接做呢public,或者package?Hibernate 通过调用默认的无参数构造函数来实例化您的对象。文档说明您的类必须具有默认的无参数构造函数,该构造函数具有包或公共可见性。您的类不能final因为 Hibernate 在使用关联时为它们创建代理。

于 2008-12-03T15:00:02.480 回答
0

Spring Reference 的第 3.2.3.2 节讨论了在 Spring 中实例化 bean 的几种不同方法。

您要么对静态工厂或实例工厂方法感兴趣。所有子部分都很短。看看你是否还有其他问题。

于 2008-12-03T16:48:43.900 回答