spring transaction timeout configurable

Deadly 提交于 2019-12-24 07:47:43

问题


I have a transactional method which has a fixed timeout. Is there a way to make a transaction timeout configurable through i.e. an application.yml?

@Transactional(propagation = Propagation.REQUIRED, timeout = TIMEOUT)
public String doStuff(String id) throws Exception {
    service.doSomeStuff
}

回答1:


As we cannot assign variable value to Java annotation attribute , to programmatically set @Transactional 's timeout , your best bet is to override AbstractPlatformTransactionManager#determineTimeout().

Suppose you are using JpaTransactionManager, the new manager looks like the code below. It allows to set timeout per transaction. We can use TransactionDefinition 's name to identify a transaction ,which in case of Spring declarative transaction ,the default name is in the format of FullyQualifiedClassName.MethodName.

public class FooTransactionManager extends JpaTransactionManager {

    private Map<String, Integer> txTimeout = new HashMap<String, Integer>();

    public <T> void configureTxTimeout(Class<T> clazz, String methodName, Integer timeoutSecond) {
        txTimeout.put(clazz.getName() + "." + methodName, timeoutSecond);
    }

    //The timeout set by `configureTxTimeout` will have higher priority than the one set in @Transactional
    @Override
    protected int determineTimeout(TransactionDefinition definition) {;
        if (txTimeout.containsKey(definition.getName())) {
            return txTimeout.get(definition.getName());
        } else {
            return super.determineTimeout(definition);
        }
    }   
}

Then configure the PlatformTransactionManager:

@Bean
public PlatformTransactionManager transactionManager(final EntityManagerFactory emf) {
    final FooTransactionManager transactionManager = new FooTransactionManager();
    transactionManager.setEntityManagerFactory(emf);

    transactionManager.configureTxTimeout(Foo.class, "doStuff", 10);
    transactionManager.configureTxTimeout(Bar.class, "doStuff", 20);
    transactionManager.configureTxTimeout(Bar.class, "doMoreStuff", 30);
    //blablabla

    return transactionManager;
}

The codes above is just for demonstration purpose . In reality , you can use @Value to read the value from an external properties (e.g application.yml) during the configuration.



来源:https://stackoverflow.com/questions/54151182/spring-transaction-timeout-configurable

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!