Java 拦截spring事务的最佳方法?
我想在Spring Boot中分析和跟踪事务 目前,我正在Java 拦截spring事务的最佳方法?,java,spring,spring-boot,spring-aop,spring-transactions,Java,Spring,Spring Boot,Spring Aop,Spring Transactions,我想在Spring Boot中分析和跟踪事务 目前,我正在@Transactional注释上使用@Before特性,然后使用TransactionSynchronizationAdapter注册提交挂钩。但这不包括使用编程api启动的任何事务(例如PlatformTransactionManager) 我尝试在(“execution(*org.springframework.transaction.PlatformTransactionManager.getTransaction(..)”)之前
@Transactional
注释上使用@Before
特性,然后使用TransactionSynchronizationAdapter
注册提交挂钩。但这不包括使用编程api启动的任何事务(例如PlatformTransactionManager
)
我尝试在(“execution(*org.springframework.transaction.PlatformTransactionManager.getTransaction(..)”)之前将方面切入点设置为,
在春天,推荐的方法是什么?理想情况下使用基于注释的配置
这就是我到目前为止所做的:
@Aspect
@Component
@ConditionalOnProperty("transaction.metrics.enabled")
public class TransactionProfilerAspect {
private static final Logger logger = LoggerFactory.getLogger(TransactionProfilerAspect.class);
private static final AtomicLong TX_ID_FACTORY = new AtomicLong();
@Autowired
@Qualifier("longRunningTransactionDetectorExecutor")
ScheduledExecutorService scheduledExecutorService;
@Value("${transaction.metrics.timeoutMillis:5000}")
Long transactionTimeoutMillis;
@Before("@annotation(org.springframework.transaction.annotation.Transactional) && execution(* *(..))")
public void beforeTransactional() {
long txId = TX_ID_FACTORY.incrementAndGet();
String txName = TransactionSynchronizationManager.getCurrentTransactionName();
logger.info("Starting transaction [txId={}], [txName={}]", txId, txName);
Stopwatch stopwatch = Stopwatch.createStarted();
ScheduledFuture<?> future = scheduleTransactionTimeout(txId, stopwatch);
TransactionSynchronizationManager.registerSynchronization(new TransactionSynchronizationAdapter() {
@Override
public void beforeCommit(boolean readOnly) {
logger.info("Attempting commit for [txId={}]", txId);
}
@Override
public void afterCommit() {
logger.info("Commit successful for [txId={}]", txId);
}
@Override
public void afterCompletion(int status) {
if (status == STATUS_ROLLED_BACK) {
logger.warn("Rolling back transaction [txId={}]", txId);
}
synchronized (stopwatch) {
if (!future.isDone()) {
future.cancel(true);
}
}
long elapsed = stopwatch.stop().elapsed(TimeUnit.MILLISECONDS);
logger.info("Completed transaction [txId={}], took {}ms", txId, elapsed);
}
});
}
private ScheduledFuture<?> scheduleTransactionTimeout(long txId, Stopwatch stopwatch) {
return scheduledExecutorService.schedule(() -> {
synchronized (stopwatch) {
logger.warn("Transaction [txId={}] exceeded the time limit of {}ms", txId, transactionTimeoutMillis);
}
}, transactionTimeoutMillis, TimeUnit.MILLISECONDS);
}
}
@方面
@组成部分
@ConditionalOnProperty(“transaction.metrics.enabled”)
公共类TransactionProfilerAspect{
私有静态最终记录器Logger=LoggerFactory.getLogger(TransactionProfilerSpect.class);
私有静态最终AtomicLong TX_ID_FACTORY=新AtomicLong();
@自动连线
@限定符(“longRunningTransactionDetectorExecutor”)
ScheduledExecutorService ScheduledExecutorService;
@值(${transaction.metrics.timeoutMillis:5000}”)
长事务超时毫秒;
@在(@annotation(org.springframework.transaction.annotation.Transactional)和&execution(**(..))之前
事务()之前的公共无效{
long txId=TX_ID_FACTORY.incrementAndGet();
字符串txName=TransactionSynchronizationManager.getCurrentTransactionName();
info(“启动事务[txId={}],[txName={}]”,txId,txName);
Stopwatch Stopwatch=Stopwatch.createStarted();
ScheduledFuture future=scheduleTransactionTimeout(txId,秒表);
TransactionSynchronizationManager.registerSynchronization(新TransactionSynchronizationAdapter()){
@凌驾
提交前公共无效(布尔只读){
info(“正在尝试提交[txId={}]”,txId);
}
@凌驾
public void afterCommit(){
info(“为[txId={}]提交成功”,txId);
}
@凌驾
完成后公共作废(int状态){
如果(状态==状态\u回滚){
warn(“回滚事务[txId={}]”,txId);
}
同步(秒表){
如果(!future.isDone()){
future.cancel(true);
}
}
长时间运行=秒表.stop().perseed(时间单位为毫秒);
info(“已完成的事务[txId={}],花费了{}毫秒”,txId,已过去);
}
});
}
专用ScheduledFuture scheduleTransactionTimeout(长txId,秒表秒表){
返回scheduledExecutorService.schedule(()->{
同步(秒表){
logger.warn(“事务[txId={}]超过了{}毫秒的时间限制”,txId,transactionTimeoutMillis);
}
},transactionTimeoutMillis,TimeUnit.ms);
}
}