我创建了一个基本的Spring MVC / JPA / Hibernate应用程序。我试图保存一个UserProfile实体来测试我是否可以实际持久化它,但没有任何东西得到保存,也没有抛出异常。
在控制器方法中,我创建了一个简单的UserProfile(它是一个@Entity),我将它发送给服务方法。 UserProfileServiceImpl类使用@Service注释,addUserProfile(UserProfile profile)方法使用@Transactional注释。
在服务方法中,我所做的只是调用DAO方法(使用@Repository注释的类)。在DAO方法中,我所做的只是调用entityManager.persist(object),object是用户配置文件对象。
我希望你能告诉我什么是错的。我将在下面发布一些代码和配置文件。
服务方法:
// The service method gets called from the controller.
// Its class is annotated with @Service
@Transactional(readOnly = false)
public void addUserProfile(UserProfile userProfile) {
userProfileDao.save(userProfile);
}
道法:
// The save(T object) method is in the GenericDaoJpa class, which is the superclass
// of the UserProfileDaoJPA class that is referenced from the service.
// I have established that the entityManager is there and the object is a
// UserProfile. The @Repository annotation is on the child class UserProfileDaoJpa.
public void save(T object) {
entityManager.persist(object);
}
主要application-context.xml
<context:property-placeholder location="classpath*:**/*.properties"/>
<import resource="spring-jpa.xml"/>
application-context-web.xml文件
<mvc:annotation-driven />
<context:component-scan base-package="nl.codebasesoftware.produx" />
<bean id="viewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<property name="prefix" value="/WEB-INF/views/"/>
<property name="suffix" value=".jsp"/>
</bean>
弹簧jpa.xml
<bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource" destroy-method="close" p:driverClassName="${db.driverClassName}"
p:url="${db.url}" p:username="${db.username}" p:password="${db.password}"/>
<bean id="entityManagerFactory" class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean"
p:dataSource-ref="dataSource"/>
<bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager"
p:entityManagerFactory-ref="entityManagerFactory"/>
<tx:annotation-driven mode="aspectj" transaction-manager="transactionManager"/>
<bean id="defaultLobHandler" class="org.springframework.jdbc.support.lob.DefaultLobHandler"/>
的persistence.xml
<persistence-unit name="mysqlPersistenceUnit" transaction-type="RESOURCE_LOCAL">
<provider>org.hibernate.ejb.HibernatePersistence</provider>
<properties>
<property name="hibernate.dialect" value="org.hibernate.dialect.MySQL5InnoDBDialect"/>
<property name="hibernate.hbm2ddl.auto" value="create-drop"/>
</properties>
</persistence-unit>
<!-- Needed to properly process @PersistenceContext -->
<bean class="org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor"/>
不知何故没有SQL通过此设置发送到Mysql,但也没有抛出任何异常,因此我不知道发生了什么。希望你能帮忙:)。
答案 0 :(得分:2)
我认为您缺少服务中的事务传播。标记readonly = false只是将会话设置为自动刷新。但是设置正确的事务传播将确保启动trnasaction和commit / rollback。
删除mode =“aspectj”后,它已经开始工作,因为我认为因为按照春季文档
默认模式“proxy”将处理要注释的带注释的bean 使用Spring的AOP框架(遵循代理语义,如上所述) 上面,仅适用于通过代理进入的方法调用)。该 替代模式“aspectj”将编织受影响的类 使用Spring的AspectJ事务方面(修改目标类) 字节码,以便应用于任何类型的方法调用)。 AspectJ的 编织需要类路径上的spring-aspects.jar以及 加载时编织(或编译时编织)已启用。 (见章节 题为“如何配置”的第6.8.4.5节“弹簧配置” 设置加载时编织。)
可能您尚未配置load time weaving
答案 1 :(得分:0)
好的,我明白了。首先,我以为我找到了答案
Declarative transactions (@Transactional) doesn't work with @Repository in Spring
但经过一些测试后,我发现它不是
的位置 <tx:annotation-driven mode="aspectj" transaction-manager="transactionManager"/>
但其内容。
删除mode="aspectj"
属性后,它开始工作了!如果有人想评论为什么会这样,请做。
让我与您分享我的完整设置。这适用于带有Hibernate 4的Spring 3.1。注意:对于'简洁',我只发布了配置文件的内容,并省略了外部标记<beans>
和<persistence>
以及命名空间声明。我完全删除了spring-jpa.xml,并将其内容移动到application-context.xml。
web.xml的内容
<?xml version="1.0" encoding="ISO-8859-1" ?>
<web-app xmlns="http://java.sun.com/xml/ns/j2ee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd" version="2.4">
<display-name>My Spring MVC web application</display-name>
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath*:**/application-context.xml</param-value>
</context-param>
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
<servlet>
<servlet-name>produxDispatcherServlet</servlet-name>
<servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>classpath*:**/application-context-web.xml</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>produxDispatcherServlet</servlet-name>
<url-pattern>/</url-pattern>
</servlet-mapping>
</web-app>
application-context.xml的内容:
<!-- main setup -->
<context:property-placeholder location="classpath*:**/*.properties"/>
<context:annotation-config/>
<context:component-scan base-package="nl.codebasesoftware.produx.domain" />
<context:component-scan base-package="nl.codebasesoftware.produx.service" />
<context:component-scan base-package="nl.codebasesoftware.produx.dao" />
<!-- Data and JPA setup -->
<bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource" destroy-method="close" p:driverClassName="${db.driverClassName}"
p:url="${db.url}" p:username="${db.username}" p:password="${db.password}"/>
<bean id="entityManagerFactory" class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean" p:dataSource-ref="dataSource"/>
<bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager" p:entityManagerFactory-ref="entityManagerFactory"/>
<tx:annotation-driven transaction-manager="transactionManager"/>
<bean id="defaultLobHandler" class="org.springframework.jdbc.support.lob.DefaultLobHandler"/>
application-context-web.xml的内容:
<mvc:annotation-driven />
<context:component-scan base-package="nl.codebasesoftware.produx.controller" />
<bean id="viewResolver" class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<property name="prefix" value="/WEB-INF/views/"/>
<property name="suffix" value=".jsp"/>
</bean>
webapps / META-INF / persistence.xml的内容
<persistence-unit name="mysqlPersistenceUnit" transaction-type="RESOURCE_LOCAL">
<provider>org.hibernate.ejb.HibernatePersistence</provider>
<properties>
<property name="hibernate.dialect" value="org.hibernate.dialect.MySQL5InnoDBDialect"/>
<!-- <property name="hibernate.hbm2ddl.auto" value="create-drop"/> -->
</properties>
</persistence-unit>
<!-- Needed to properly process @PersistenceContext which injects the entity manager -->
<bean class="org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor"/>
environment.properties的内容:
db.url=jdbc:mysql://localhost:3306/yourDatabaseName
db.driverClassName=com.mysql.jdbc.Driver
db.username=yourUsername
db.password=yourPassword