mirror of
https://github.com/Alfresco/alfresco-community-repo.git
synced 2025-06-02 17:35:18 +00:00
Hibernate parts of AVM now based on Spring PlatformTransactionManager
abstraction. Configurations to match. git-svn-id: https://svn.alfresco.com/repos/alfresco-enterprise/alfresco/BRANCHES/WCM-DEV2/root@3286 c4b6b30b-aa2e-2d43-bbcb-ca4b014f7261
This commit is contained in:
parent
c54b07f607
commit
cdef918e07
@ -14,7 +14,7 @@
|
|||||||
</bean>
|
</bean>
|
||||||
|
|
||||||
<!-- A read only DefaultTransactionDefinition -->
|
<!-- A read only DefaultTransactionDefinition -->
|
||||||
<bean id="readOnlyTransactionDefinition"
|
<bean id="readTransactionDefinition"
|
||||||
class="org.springframework.transaction.support.DefaultTransactionDefinition">
|
class="org.springframework.transaction.support.DefaultTransactionDefinition">
|
||||||
<property name="propagationBehaviorName">
|
<property name="propagationBehaviorName">
|
||||||
<value>PROPAGATION_REQUIRES_NEW</value>
|
<value>PROPAGATION_REQUIRES_NEW</value>
|
||||||
@ -92,11 +92,31 @@
|
|||||||
</property>
|
</property>
|
||||||
</bean>
|
</bean>
|
||||||
|
|
||||||
|
<!-- The HibernateTransactionManager -->
|
||||||
|
<bean id="transactionManager"
|
||||||
|
class="org.springframework.orm.hibernate3.HibernateTransactionManager">
|
||||||
|
<property name="dataSource">
|
||||||
|
<ref bean="dataSource"/>
|
||||||
|
</property>
|
||||||
|
<property name="sessionFactory">
|
||||||
|
<ref bean="sessionFactory"/>
|
||||||
|
</property>
|
||||||
|
</bean>
|
||||||
|
|
||||||
<!-- The Hibernate Transaction wrapper. -->
|
<!-- The Hibernate Transaction wrapper. -->
|
||||||
<bean id="hibernateTxn" class="org.alfresco.repo.avm.hibernate.HibernateTxn">
|
<bean id="hibernateTxn" class="org.alfresco.repo.avm.hibernate.HibernateTxn">
|
||||||
<property name="sessionFactory">
|
<property name="sessionFactory">
|
||||||
<ref bean="sessionFactory"/>
|
<ref bean="sessionFactory"/>
|
||||||
</property>
|
</property>
|
||||||
|
<property name="transactionManager">
|
||||||
|
<ref bean="transactionManager"/>
|
||||||
|
</property>
|
||||||
|
<property name="readTransactionDefinition">
|
||||||
|
<ref bean="readTransactionDefinition"/>
|
||||||
|
</property>
|
||||||
|
<property name="writeTransactionDefinition">
|
||||||
|
<ref bean="writeTransactionDefinition"/>
|
||||||
|
</property>
|
||||||
</bean>
|
</bean>
|
||||||
|
|
||||||
<bean id="orphanReaper" class="org.alfresco.repo.avm.OrphanReaper"
|
<bean id="orphanReaper" class="org.alfresco.repo.avm.OrphanReaper"
|
||||||
|
@ -12,6 +12,6 @@ hibernate.connection.isolation=2
|
|||||||
hibernate.default_batch_fetch_size=16
|
hibernate.default_batch_fetch_size=16
|
||||||
hibernate.jdbc.batch_versioned_data=true
|
hibernate.jdbc.batch_versioned_data=true
|
||||||
hibernate.cache.use_second_level_cache=true
|
hibernate.cache.use_second_level_cache=true
|
||||||
hibernate.hbm2ddl.auto=create
|
hibernate.hbm2ddl.auto=update
|
||||||
# AVM specific properties.
|
# AVM specific properties.
|
||||||
avm.initialize=true
|
avm.initialize=false
|
||||||
|
@ -64,11 +64,59 @@
|
|||||||
</property>
|
</property>
|
||||||
</bean>
|
</bean>
|
||||||
|
|
||||||
|
<!-- The HibernateTransactionManager -->
|
||||||
|
<bean id="transactionManager"
|
||||||
|
class="org.springframework.orm.hibernate3.HibernateTransactionManager">
|
||||||
|
<property name="dataSource">
|
||||||
|
<ref bean="dataSource"/>
|
||||||
|
</property>
|
||||||
|
<property name="sessionFactory">
|
||||||
|
<ref bean="sessionFactory"/>
|
||||||
|
</property>
|
||||||
|
</bean>
|
||||||
|
|
||||||
|
<!-- A read only DefaultTransactionDefinition -->
|
||||||
|
<bean id="readTransactionDefinition"
|
||||||
|
class="org.springframework.transaction.support.DefaultTransactionDefinition">
|
||||||
|
<property name="propagationBehaviorName">
|
||||||
|
<value>PROPAGATION_REQUIRES_NEW</value>
|
||||||
|
</property>
|
||||||
|
<property name="isolationLevelName">
|
||||||
|
<value>ISOLATION_READ_COMMITTED</value>
|
||||||
|
</property>
|
||||||
|
<property name="readOnly">
|
||||||
|
<value>true</value>
|
||||||
|
</property>
|
||||||
|
</bean>
|
||||||
|
|
||||||
|
<!-- A write DefaultTransactionDefinition -->
|
||||||
|
<bean id="writeTransactionDefinition"
|
||||||
|
class="org.springframework.transaction.support.DefaultTransactionDefinition">
|
||||||
|
<property name="propagationBehaviorName">
|
||||||
|
<value>PROPAGATION_REQUIRES_NEW</value>
|
||||||
|
</property>
|
||||||
|
<property name="isolationLevelName">
|
||||||
|
<value>ISOLATION_READ_COMMITTED</value>
|
||||||
|
</property>
|
||||||
|
<property name="readOnly">
|
||||||
|
<value>false</value>
|
||||||
|
</property>
|
||||||
|
</bean>
|
||||||
|
|
||||||
<!-- The Hibernate Transaction wrapper. -->
|
<!-- The Hibernate Transaction wrapper. -->
|
||||||
<bean id="hibernateTxn" class="org.alfresco.repo.avm.hibernate.HibernateTxn">
|
<bean id="hibernateTxn" class="org.alfresco.repo.avm.hibernate.HibernateTxn">
|
||||||
<property name="sessionFactory">
|
<property name="sessionFactory">
|
||||||
<ref bean="sessionFactory"/>
|
<ref bean="sessionFactory"/>
|
||||||
</property>
|
</property>
|
||||||
|
<property name="transactionManager">
|
||||||
|
<ref bean="transactionManager"/>
|
||||||
|
</property>
|
||||||
|
<property name="readTransactionDefinition">
|
||||||
|
<ref bean="readTransactionDefinition"/>
|
||||||
|
</property>
|
||||||
|
<property name="writeTransactionDefinition">
|
||||||
|
<ref bean="writeTransactionDefinition"/>
|
||||||
|
</property>
|
||||||
</bean>
|
</bean>
|
||||||
|
|
||||||
<bean id="orphanReaper" class="org.alfresco.repo.avm.OrphanReaper"
|
<bean id="orphanReaper" class="org.alfresco.repo.avm.OrphanReaper"
|
||||||
|
@ -8,7 +8,7 @@ db.pool.max=32
|
|||||||
# Hibernate properties
|
# Hibernate properties
|
||||||
hibernate.dialect=org.hibernate.dialect.MySQLInnoDBDialect
|
hibernate.dialect=org.hibernate.dialect.MySQLInnoDBDialect
|
||||||
hibernate.current_session_context_class=thread
|
hibernate.current_session_context_class=thread
|
||||||
hibernate.connection.isolation=2
|
hibernate.connection.isolation=4
|
||||||
hibernate.default_batch_fetch_size=16
|
hibernate.default_batch_fetch_size=16
|
||||||
hibernate.jdbc.batch_versioned_data=true
|
hibernate.jdbc.batch_versioned_data=true
|
||||||
hibernate.cache.use_second_level_cache=true
|
hibernate.cache.use_second_level_cache=true
|
||||||
|
@ -956,7 +956,7 @@ public class AVMServiceImpl implements AVMService
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
HTxnCallback doit = new HTxnCallback();
|
HTxnCallback doit = new HTxnCallback();
|
||||||
fTransaction.perform(doit, false);
|
fTransaction.perform(doit, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -261,9 +261,11 @@ public class OrphanReaper implements Runnable
|
|||||||
delete.setEntity("parent", node);
|
delete.setEntity("parent", node);
|
||||||
delete.executeUpdate();
|
delete.executeUpdate();
|
||||||
}
|
}
|
||||||
|
session.delete(node);
|
||||||
}
|
}
|
||||||
else if (node instanceof PlainFileNode)
|
else if (node instanceof PlainFileNode)
|
||||||
{
|
{
|
||||||
|
session.delete(node);
|
||||||
// FileContent should be purged if nobody else references it.
|
// FileContent should be purged if nobody else references it.
|
||||||
FileContent content = ((PlainFileNode)node).getContent();
|
FileContent content = ((PlainFileNode)node).getContent();
|
||||||
if (content.getRefCount() == 1)
|
if (content.getRefCount() == 1)
|
||||||
@ -272,10 +274,13 @@ public class OrphanReaper implements Runnable
|
|||||||
session.delete(content);
|
session.delete(content);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
session.delete(node);
|
session.delete(node);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
HTxnCallback doit = new HTxnCallback();
|
HTxnCallback doit = new HTxnCallback();
|
||||||
|
@ -0,0 +1,42 @@
|
|||||||
|
/**
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
package org.alfresco.repo.avm.hibernate;
|
||||||
|
|
||||||
|
import java.sql.SQLException;
|
||||||
|
|
||||||
|
import org.hibernate.HibernateException;
|
||||||
|
import org.hibernate.Session;
|
||||||
|
import org.springframework.orm.hibernate3.HibernateCallback;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This is a wrapper around HibernateTxnCallback implementation.
|
||||||
|
* @author britt
|
||||||
|
*/
|
||||||
|
public class HibernateCallbackWrapper implements HibernateCallback
|
||||||
|
{
|
||||||
|
/**
|
||||||
|
* The HibernateTxnCallback to execute.
|
||||||
|
*/
|
||||||
|
private HibernateTxnCallback fCallback;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Make one up.
|
||||||
|
* @param callback
|
||||||
|
*/
|
||||||
|
public HibernateCallbackWrapper(HibernateTxnCallback callback)
|
||||||
|
{
|
||||||
|
fCallback = callback;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Call the HibernateTxnCallback internally.
|
||||||
|
* @param session The Hibernate Session.
|
||||||
|
*/
|
||||||
|
public Object doInHibernate(Session session) throws HibernateException,
|
||||||
|
SQLException
|
||||||
|
{
|
||||||
|
fCallback.perform(session);
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
@ -21,15 +21,14 @@ import java.util.Random;
|
|||||||
|
|
||||||
import org.alfresco.repo.avm.AVMException;
|
import org.alfresco.repo.avm.AVMException;
|
||||||
import org.alfresco.repo.avm.AVMNotFoundException;
|
import org.alfresco.repo.avm.AVMNotFoundException;
|
||||||
import org.hibernate.HibernateException;
|
|
||||||
import org.hibernate.JDBCException;
|
|
||||||
import org.hibernate.Session;
|
|
||||||
import org.hibernate.SessionFactory;
|
|
||||||
import org.hibernate.Transaction;
|
|
||||||
import org.springframework.dao.DataRetrievalFailureException;
|
import org.springframework.dao.DataRetrievalFailureException;
|
||||||
import org.springframework.dao.DeadlockLoserDataAccessException;
|
import org.springframework.dao.DeadlockLoserDataAccessException;
|
||||||
import org.springframework.dao.OptimisticLockingFailureException;
|
import org.springframework.dao.OptimisticLockingFailureException;
|
||||||
import org.springframework.orm.hibernate3.HibernateTemplate;
|
import org.springframework.orm.hibernate3.HibernateTemplate;
|
||||||
|
import org.springframework.transaction.PlatformTransactionManager;
|
||||||
|
import org.springframework.transaction.TransactionDefinition;
|
||||||
|
import org.springframework.transaction.TransactionException;
|
||||||
|
import org.springframework.transaction.TransactionStatus;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Helper for DAOs.
|
* Helper for DAOs.
|
||||||
@ -38,9 +37,19 @@ import org.springframework.orm.hibernate3.HibernateTemplate;
|
|||||||
public class HibernateTxn extends HibernateTemplate
|
public class HibernateTxn extends HibernateTemplate
|
||||||
{
|
{
|
||||||
/**
|
/**
|
||||||
* The SessionFactory.
|
* The transaction manager.
|
||||||
*/
|
*/
|
||||||
private SessionFactory fSessionFactory;
|
private PlatformTransactionManager fTransactionManager;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The read transaction definition.
|
||||||
|
*/
|
||||||
|
private TransactionDefinition fReadDefinition;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The write transaction definition.
|
||||||
|
*/
|
||||||
|
private TransactionDefinition fWriteDefinition;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The random number generator for inter-retry sleep.
|
* The random number generator for inter-retry sleep.
|
||||||
@ -56,16 +65,6 @@ public class HibernateTxn extends HibernateTemplate
|
|||||||
fRandom = new Random();
|
fRandom = new Random();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Set the Hibernate Session factory.
|
|
||||||
* @param factory
|
|
||||||
*/
|
|
||||||
public void setSessionFactory(SessionFactory factory)
|
|
||||||
{
|
|
||||||
super.setSessionFactory(factory);
|
|
||||||
fSessionFactory = factory;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Perform a set of operations under a single Hibernate transaction.
|
* Perform a set of operations under a single Hibernate transaction.
|
||||||
* Keep trying if the operation fails because of a concurrency issue.
|
* Keep trying if the operation fails because of a concurrency issue.
|
||||||
@ -74,44 +73,34 @@ public class HibernateTxn extends HibernateTemplate
|
|||||||
*/
|
*/
|
||||||
public void perform(HibernateTxnCallback callback, boolean write)
|
public void perform(HibernateTxnCallback callback, boolean write)
|
||||||
{
|
{
|
||||||
Session sess = null;
|
|
||||||
Transaction txn = null;
|
|
||||||
while (true)
|
while (true)
|
||||||
{
|
{
|
||||||
|
TransactionStatus status = null;
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
sess = fSessionFactory.openSession();
|
status =
|
||||||
txn = sess.beginTransaction();
|
fTransactionManager.getTransaction(write ? fWriteDefinition : fReadDefinition);
|
||||||
callback.perform(sess);
|
execute(new HibernateCallbackWrapper(callback));
|
||||||
txn.commit();
|
try
|
||||||
|
{
|
||||||
|
fTransactionManager.commit(status);
|
||||||
|
}
|
||||||
|
catch (TransactionException te)
|
||||||
|
{
|
||||||
|
throw new AVMException("Transaction Exception.", te);
|
||||||
|
}
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
catch (Throwable t)
|
catch (Throwable t)
|
||||||
{
|
{
|
||||||
// TODO Add appropriate logging.
|
if (!status.isCompleted())
|
||||||
if (txn != null)
|
|
||||||
{
|
{
|
||||||
try
|
fTransactionManager.rollback(status);
|
||||||
{
|
|
||||||
txn.rollback();
|
|
||||||
}
|
|
||||||
catch (HibernateException he)
|
|
||||||
{
|
|
||||||
// Do nothing.
|
|
||||||
}
|
|
||||||
}
|
|
||||||
// Translate the exception.
|
|
||||||
if (t instanceof JDBCException)
|
|
||||||
{
|
|
||||||
t = convertJdbcAccessException((JDBCException)t);
|
|
||||||
}
|
|
||||||
else if (t instanceof HibernateException)
|
|
||||||
{
|
|
||||||
t = convertHibernateAccessException((HibernateException)t);
|
|
||||||
}
|
}
|
||||||
// If we've lost a race or we've deadlocked, retry.
|
// If we've lost a race or we've deadlocked, retry.
|
||||||
if (t instanceof DeadlockLoserDataAccessException)
|
if (t instanceof DeadlockLoserDataAccessException)
|
||||||
{
|
{
|
||||||
|
System.err.println("Deadlock.");
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
long interval;
|
long interval;
|
||||||
@ -120,7 +109,6 @@ public class HibernateTxn extends HibernateTemplate
|
|||||||
interval = fRandom.nextInt(1000);
|
interval = fRandom.nextInt(1000);
|
||||||
}
|
}
|
||||||
Thread.sleep(interval);
|
Thread.sleep(interval);
|
||||||
continue;
|
|
||||||
}
|
}
|
||||||
catch (InterruptedException ie)
|
catch (InterruptedException ie)
|
||||||
{
|
{
|
||||||
@ -130,6 +118,7 @@ public class HibernateTxn extends HibernateTemplate
|
|||||||
}
|
}
|
||||||
if (t instanceof OptimisticLockingFailureException)
|
if (t instanceof OptimisticLockingFailureException)
|
||||||
{
|
{
|
||||||
|
System.err.println("Lost Race.");
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
if (t instanceof AVMException)
|
if (t instanceof AVMException)
|
||||||
@ -138,24 +127,38 @@ public class HibernateTxn extends HibernateTemplate
|
|||||||
}
|
}
|
||||||
if (t instanceof DataRetrievalFailureException)
|
if (t instanceof DataRetrievalFailureException)
|
||||||
{
|
{
|
||||||
|
System.err.println("Data Retrieval Error.");
|
||||||
throw new AVMNotFoundException("Object not found.", t);
|
throw new AVMNotFoundException("Object not found.", t);
|
||||||
}
|
}
|
||||||
throw new AVMException("Unrecoverable error.", t);
|
throw new AVMException("Unrecoverable error.", t);
|
||||||
}
|
}
|
||||||
finally
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set the transaction manager we are operating under.
|
||||||
|
* @param manager
|
||||||
|
*/
|
||||||
|
public void setTransactionManager(PlatformTransactionManager manager)
|
||||||
{
|
{
|
||||||
if (sess != null)
|
fTransactionManager = manager;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set the read Transaction Definition.
|
||||||
|
* @param def
|
||||||
|
*/
|
||||||
|
public void setReadTransactionDefinition(TransactionDefinition def)
|
||||||
{
|
{
|
||||||
try
|
fReadDefinition = def;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Set the write Transaction Definition.
|
||||||
|
* @param def
|
||||||
|
*/
|
||||||
|
public void setWriteTransactionDefinition(TransactionDefinition def)
|
||||||
{
|
{
|
||||||
sess.close();
|
fWriteDefinition = def;
|
||||||
}
|
|
||||||
catch (HibernateException he)
|
|
||||||
{
|
|
||||||
// Do nothing.
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user