TransactionManager通过TransactionSynchronizationManager进行事务控制,TransactionTemplate就使用transactionManager运行sql。
TransactionTemplate -> PlatformTransactionManager -> TransactionSynchronizationManager
1 2 3 4 5 6 7
| TransactionTemplate transactionTemplate = new TransactionTemplate(transactionManager); transactionTemplate.execute(new TransactionCallbackWithoutResult() { @Override protected void doInTransactionWithoutResult(TransactionStatus arg0) { int count = em.createNativeQuery("delete XX").executeUpdate(); } });
|
可以利用TransactionAspectSupport.currentTransactionStatus()控制事务状态,利用setRollbackOnly
要知道是否一个活动事务可以用TransactionSynchronizationManager.isActualTransactionActive()
写了一个Audit,目的在事务结束前调用一个oracle的package,记录所有变化的数据。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79
| import java.lang.reflect.Field; import java.sql.CallableStatement; import java.sql.Connection; import java.sql.SQLException; import java.util.Map;
import javax.persistence.EntityManager;
import oracle.jdbc.driver.OracleTypes;
import org.apache.log4j.Logger; import org.aspectj.lang.JoinPoint; import org.aspectj.lang.annotation.After; import org.aspectj.lang.annotation.Aspect; import org.aspectj.lang.annotation.Before; import org.aspectj.lang.annotation.Pointcut; import org.hibernate.Session; import org.hibernate.jdbc.Work; import org.springframework.orm.jpa.EntityManagerFactoryInfo; import org.springframework.orm.jpa.EntityManagerHolder; import org.springframework.orm.jpa.LocalEntityManagerFactoryBean; import org.springframework.stereotype.Component; import org.springframework.transaction.interceptor.TransactionAspectSupport; import org.springframework.transaction.support.TransactionSynchronizationManager;
@Component @Aspect public class AuditRecorder { private static final Logger log = Logger.getLogger(AuditRecorder.class);
@After("execution(public * xx.yy..*Service.*(..)) && @annotation(auditable)") public void recordUsage(JoinPoint jp) { audit(); }
private void audit() { if (TransactionSynchronizationManager.isActualTransactionActive()) { Map map = TransactionSynchronizationManager.getResourceMap(); log.info("mapsize " + map.size()); for (Object key : map.keySet()) { log.debug("key " + key + " , " + map.get(key));
if (key instanceof EntityManagerFactoryInfo) { EntityManagerFactoryInfo info = (EntityManagerFactoryInfo) key;
String unitName = info.getPersistenceUnitName(); if (!unitName.contains("srs") && !unitName.contains("cas")) { log.debug("call audit procedure."); if (map.get(key) instanceof EntityManagerHolder) { EntityManagerHolder emHolder = (EntityManagerHolder) map .get(key); EntityManager em = emHolder.getEntityManager(); Session s = (Session) em.getDelegate(); s.doWork(new Work() { public void execute(Connection conn) throws SQLException { String sql = "{call SP_COMMON.setloginuser(?)}"; CallableStatement call = conn .prepareCall(sql); call.setString(1, "test"); call.executeUpdate();
CallableStatement call2 = conn .prepareCall("{? = call SP_COMMON.getloginuser}"); call2.registerOutParameter(1, OracleTypes.VARCHAR); call2.executeQuery();
System.out.println("<< " + call2.getString(1)); } }); } } } } } } }
|