Upgrade to Hibernate 4
This change upgrades Spring Web Flow to Hibernate 4 but remains compatible with Hibernate 3. Issue: SWF-1534
This commit is contained in:
18
build.gradle
18
build.gradle
@@ -56,7 +56,7 @@ configure(subprojects.findAll {it.name != "spring-js-resources"}) { subproject -
|
||||
}
|
||||
|
||||
subproject.ext {
|
||||
springVersion = "4.0.0.RELEASE"
|
||||
springVersion = "4.0.1.RELEASE"
|
||||
springSecurityVersion = "3.2.0.RELEASE"
|
||||
slf4jVersion = "1.6.1"
|
||||
log4jVersion = "1.2.15"
|
||||
@@ -132,10 +132,10 @@ project("spring-js") {
|
||||
compile("org.springframework:spring-web:$springVersion")
|
||||
compile("org.springframework:spring-webmvc:$springVersion")
|
||||
provided("javax.servlet:javax.servlet-api:3.0.1")
|
||||
optional("org.apache.tiles:tiles-api:2.1.2")
|
||||
optional("org.apache.tiles:tiles-core:2.1.2")
|
||||
optional("org.apache.tiles:tiles-jsp:2.1.2")
|
||||
optional("org.apache.tiles:tiles-servlet:2.1.2")
|
||||
optional("org.apache.tiles:tiles-api:2.2.2")
|
||||
optional("org.apache.tiles:tiles-core:2.2.2")
|
||||
optional("org.apache.tiles:tiles-jsp:2.2.2")
|
||||
optional("org.apache.tiles:tiles-servlet:2.2.2")
|
||||
testCompile("javax.servlet:jstl:1.2")
|
||||
testCompile("log4j:log4j:$log4jVersion") {
|
||||
exclude group: "javax.mail", module: "mail"
|
||||
@@ -143,6 +143,8 @@ project("spring-js") {
|
||||
exclude group: "com.sun.jdmk", module: "jmxtools"
|
||||
exclude group: "com.sun.jmx", module: "jmxri"
|
||||
}
|
||||
testCompile("org.slf4j:jcl-over-slf4j:$slf4jVersion")
|
||||
testCompile("org.slf4j:slf4j-api:$slf4jVersion")
|
||||
testCompile("org.springframework:spring-test:$springVersion")
|
||||
}
|
||||
}
|
||||
@@ -166,7 +168,7 @@ project("spring-webflow") {
|
||||
provided("javax.portlet:portlet-api:2.0")
|
||||
provided("junit:junit:3.8.2")
|
||||
provided("org.eclipse.persistence:javax.persistence:2.0.0")
|
||||
optional("org.hibernate:hibernate-core:3.6.9.Final") {
|
||||
optional("org.hibernate:hibernate-core:4.2.8.Final") {
|
||||
exclude group: "org.slf4j", module: "slf4j-api"
|
||||
}
|
||||
optional("org.slf4j:slf4j-api:$slf4jVersion")
|
||||
@@ -175,8 +177,8 @@ project("spring-webflow") {
|
||||
optional("org.springframework:spring-tx:$springVersion")
|
||||
optional("org.springframework:spring-webmvc-portlet:$springVersion")
|
||||
testCompile("javax.validation:validation-api:1.0.0.GA")
|
||||
testCompile("org.hibernate:hibernate-core:3.6.9.Final")
|
||||
testCompile("org.hibernate:hibernate-entitymanager:3.6.9.Final")
|
||||
testCompile("org.hibernate:hibernate-core:4.2.8.Final")
|
||||
testCompile("org.hibernate:hibernate-entitymanager:4.2.8.Final")
|
||||
testCompile("org.hibernate:hibernate-validator:4.3.0.Final")
|
||||
testCompile("org.apache.tomcat:tomcat-jasper-el:7.0.27")
|
||||
testCompile("org.hsqldb:hsqldb:2.2.8")
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2004-2012 the original author or authors.
|
||||
* Copyright 2004-2014 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -15,16 +15,21 @@
|
||||
*/
|
||||
package org.springframework.webflow.persistence;
|
||||
|
||||
import java.lang.reflect.InvocationTargetException;
|
||||
import java.lang.reflect.Method;
|
||||
|
||||
import org.hibernate.FlushMode;
|
||||
import org.hibernate.Interceptor;
|
||||
import org.hibernate.Session;
|
||||
import org.hibernate.SessionFactory;
|
||||
import org.springframework.orm.hibernate3.SessionHolder;
|
||||
import org.springframework.orm.hibernate4.SessionHolder;
|
||||
import org.springframework.transaction.PlatformTransactionManager;
|
||||
import org.springframework.transaction.TransactionStatus;
|
||||
import org.springframework.transaction.support.TransactionCallbackWithoutResult;
|
||||
import org.springframework.transaction.support.TransactionSynchronizationManager;
|
||||
import org.springframework.transaction.support.TransactionTemplate;
|
||||
import org.springframework.util.ClassUtils;
|
||||
import org.springframework.util.ReflectionUtils;
|
||||
import org.springframework.webflow.core.collection.AttributeMap;
|
||||
import org.springframework.webflow.core.collection.MutableAttributeMap;
|
||||
import org.springframework.webflow.definition.FlowDefinition;
|
||||
@@ -48,7 +53,7 @@ import org.springframework.webflow.execution.RequestContext;
|
||||
* <li>When an existing flow ends, commit the changes made to the session in a transaction if the ending state is a
|
||||
* commit state. Then, unbind the context and close it.
|
||||
* </ul>
|
||||
*
|
||||
*
|
||||
* The general data access pattern implemented here is:
|
||||
* <ul>
|
||||
* <li>Create a new persistence context when a new flow execution with the 'persistenceContext' attribute starts
|
||||
@@ -57,7 +62,7 @@ import org.springframework.webflow.execution.RequestContext;
|
||||
* <li>On successful flow completion, commit and flush those edits to the database, applying a version check if
|
||||
* necessary.
|
||||
* </ul>
|
||||
*
|
||||
*
|
||||
* <p>
|
||||
* Note: All data access except for the final commit will, by default, be non-transactional. However, a flow may call
|
||||
* into a transactional service layer to fetch objects during the conversation in the context of a read-only system
|
||||
@@ -68,13 +73,23 @@ import org.springframework.webflow.execution.RequestContext;
|
||||
* want intermediate flushing to happen, as the nature of a flow implies a transient, isolated resource that can be
|
||||
* canceled before it ends. Generally, the only time a read-write transaction should be started is upon successful
|
||||
* completion of the conversation, triggered by reaching a 'commit' end state.
|
||||
*
|
||||
*
|
||||
* @author Keith Donald
|
||||
* @author Juergen Hoeller
|
||||
* @author Ben Hale
|
||||
*/
|
||||
public class HibernateFlowExecutionListener extends FlowExecutionListenerAdapter {
|
||||
|
||||
private static final boolean hibernate3Present = ClassUtils.isPresent("org.hibernate.connection.ConnectionProvider",
|
||||
HibernateFlowExecutionListener.class.getClassLoader());
|
||||
|
||||
private static final Method openSessionMethod =
|
||||
ReflectionUtils.findMethod(SessionFactory.class, "openSession");
|
||||
|
||||
private static final Method openSessionWithInterceptorMethod =
|
||||
ReflectionUtils.findMethod(SessionFactory.class, "openSession", Interceptor.class);
|
||||
|
||||
|
||||
/**
|
||||
* The name of the attribute the flow {@link Session persistence context} is indexed under.
|
||||
*/
|
||||
@@ -183,8 +198,33 @@ public class HibernateFlowExecutionListener extends FlowExecutionListenerAdapter
|
||||
}
|
||||
|
||||
private Session createSession(RequestContext context) {
|
||||
Session session = (entityInterceptor != null ? sessionFactory.openSession(entityInterceptor) : sessionFactory
|
||||
.openSession());
|
||||
Session session;
|
||||
if (entityInterceptor != null) {
|
||||
if (hibernate3Present) {
|
||||
try {
|
||||
session = (Session) openSessionWithInterceptorMethod.invoke(sessionFactory, entityInterceptor);
|
||||
} catch (IllegalAccessException ex) {
|
||||
throw new IllegalStateException("Unable to open Hibernate 3 session", ex);
|
||||
} catch (InvocationTargetException ex) {
|
||||
throw new IllegalStateException("Unable to open Hibernate 3 session", ex);
|
||||
}
|
||||
} else {
|
||||
session = sessionFactory.withOptions().interceptor(entityInterceptor).openSession();
|
||||
}
|
||||
} else {
|
||||
if (hibernate3Present) {
|
||||
try {
|
||||
session = (Session) openSessionMethod.invoke(sessionFactory);
|
||||
} catch (IllegalAccessException ex) {
|
||||
throw new IllegalStateException("Unable to open Hibernate 3 session", ex);
|
||||
} catch (InvocationTargetException ex) {
|
||||
throw new IllegalStateException("Unable to open Hibernate 3 session", ex);
|
||||
}
|
||||
}
|
||||
else {
|
||||
session = sessionFactory.openSession();
|
||||
}
|
||||
}
|
||||
session.setFlushMode(FlushMode.MANUAL);
|
||||
return session;
|
||||
}
|
||||
@@ -198,7 +238,9 @@ public class HibernateFlowExecutionListener extends FlowExecutionListenerAdapter
|
||||
}
|
||||
|
||||
private void bind(Session session) {
|
||||
TransactionSynchronizationManager.bindResource(sessionFactory, new SessionHolder(session));
|
||||
Object sessionHolder = (hibernate3Present ?
|
||||
new org.springframework.orm.hibernate3.SessionHolder(session) : new SessionHolder(session));
|
||||
TransactionSynchronizationManager.bindResource(sessionFactory, sessionHolder);
|
||||
}
|
||||
|
||||
private void unbind(Session session) {
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright 2004-2012 the original author or authors.
|
||||
* Copyright 2004-2014 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
@@ -15,14 +15,11 @@
|
||||
*/
|
||||
package org.springframework.webflow.persistence;
|
||||
|
||||
import java.sql.SQLException;
|
||||
|
||||
import javax.sql.DataSource;
|
||||
|
||||
import junit.framework.TestCase;
|
||||
|
||||
import org.hibernate.Hibernate;
|
||||
import org.hibernate.HibernateException;
|
||||
import org.hibernate.Session;
|
||||
import org.hibernate.SessionFactory;
|
||||
import org.springframework.core.io.ClassPathResource;
|
||||
@@ -31,10 +28,10 @@ import org.springframework.jdbc.core.JdbcTemplate;
|
||||
import org.springframework.jdbc.datasource.DriverManagerDataSource;
|
||||
import org.springframework.jdbc.datasource.init.DataSourceInitializer;
|
||||
import org.springframework.jdbc.datasource.init.ResourceDatabasePopulator;
|
||||
import org.springframework.orm.hibernate3.HibernateCallback;
|
||||
import org.springframework.orm.hibernate3.HibernateTemplate;
|
||||
import org.springframework.orm.hibernate3.HibernateTransactionManager;
|
||||
import org.springframework.orm.hibernate3.LocalSessionFactoryBean;
|
||||
import org.springframework.orm.hibernate4.HibernateCallback;
|
||||
import org.springframework.orm.hibernate4.HibernateTemplate;
|
||||
import org.springframework.orm.hibernate4.HibernateTransactionManager;
|
||||
import org.springframework.orm.hibernate4.LocalSessionFactoryBean;
|
||||
import org.springframework.transaction.support.TransactionSynchronizationManager;
|
||||
import org.springframework.webflow.engine.EndState;
|
||||
import org.springframework.webflow.execution.FlowExecutionException;
|
||||
@@ -43,7 +40,7 @@ import org.springframework.webflow.test.MockRequestContext;
|
||||
|
||||
/**
|
||||
* Tests for {@link HibernateFlowExecutionListener}
|
||||
*
|
||||
*
|
||||
* @author Ben Hale
|
||||
*/
|
||||
public class HibernateFlowExecutionListenerTests extends TestCase {
|
||||
@@ -86,7 +83,7 @@ public class HibernateFlowExecutionListenerTests extends TestCase {
|
||||
assertSessionBound();
|
||||
|
||||
hibernateTemplate.executeWithNativeSession(new HibernateCallback<Object>() {
|
||||
public Object doInHibernate(Session session) throws HibernateException, SQLException {
|
||||
public Object doInHibernate(Session session) {
|
||||
assertSame("Should have been original instance", hibSession, session);
|
||||
return null;
|
||||
}
|
||||
|
||||
@@ -6,8 +6,8 @@ import org.hibernate.Session;
|
||||
import org.hibernate.SessionFactory;
|
||||
import org.springframework.core.io.ClassPathResource;
|
||||
import org.springframework.core.io.Resource;
|
||||
import org.springframework.orm.hibernate3.HibernateTransactionManager;
|
||||
import org.springframework.orm.hibernate3.LocalSessionFactoryBean;
|
||||
import org.springframework.orm.hibernate4.HibernateTransactionManager;
|
||||
import org.springframework.orm.hibernate4.LocalSessionFactoryBean;
|
||||
import org.springframework.transaction.support.TransactionSynchronizationManager;
|
||||
import org.springframework.webflow.execution.Action;
|
||||
import org.springframework.webflow.execution.Event;
|
||||
|
||||
@@ -5,9 +5,9 @@ import javax.sql.DataSource;
|
||||
import org.hibernate.SessionFactory;
|
||||
import org.springframework.core.io.ClassPathResource;
|
||||
import org.springframework.core.io.Resource;
|
||||
import org.springframework.orm.hibernate3.HibernateTemplate;
|
||||
import org.springframework.orm.hibernate3.HibernateTransactionManager;
|
||||
import org.springframework.orm.hibernate3.LocalSessionFactoryBean;
|
||||
import org.springframework.orm.hibernate4.HibernateTemplate;
|
||||
import org.springframework.orm.hibernate4.HibernateTransactionManager;
|
||||
import org.springframework.orm.hibernate4.LocalSessionFactoryBean;
|
||||
import org.springframework.transaction.support.TransactionSynchronizationManager;
|
||||
import org.springframework.webflow.execution.FlowExecutionListener;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user