3

我有一个导致死锁的表更新,并且当该方法获得某种锁定异常时,我试图让 Spring Retry 重试。我试过去掉 maxAttempts、value 和 backoff,但它似乎没有捕捉到任何异常。我错过了什么吗?我需要在 Application 文件中声明一个 bean 吗?任何帮助将非常感激!

应用程序.Java

@SpringBootApplication
@EnableRetry
public class Application extends SpringBootServletInitializer {

详细服务

@Service
public class DetailService {

    @Retryable(maxAttempts = 5, value = { LockAcquisitionException.class, ConcurrencyFailureException.class }, backoff = @Backoff(delay = 500, multiplier = 2) )
    public void delete(final String detailCode) {
        try {
            this.delete(this.dao.findByDetailCode(detailCode));
        } catch (LockAcquisitionException | ConcurrencyFailureException e) {
            LOG.warn("Locking error! Going to retry", e.getMessage());
            throw e;
        }
    }

    public void delete(Details detail) {
           this.dao.delete(detail);            
    }

    @Retryable(maxAttempts = 5, value = { LockAcquisitionException.class, ConcurrencyFailureException.class }, backoff = @Backoff(delay = 500, multiplier = 2) )
    public void delete(final Integer id) {
        if (id != null) {
            try {
                this.delete(this.dao.findOne(id));
            } catch (LockAcquisitionException | ConcurrencyFailureException e) { 
                 LOG.warn("Locking error! Going to retry", e.getMessage());
                 throw e;
            }
        }
    }

编辑

重写了我上面的 DetailService 以提供更多细节并添加缺少的方法

4

1 回答 1

11

如果您从同一个类中调用该delete()方法(在 中DetailService),那么您正在短路 Spring 包装 bean 的代理。

具有注解的类必须是 Spring 管理的 bean,并且delete()必须从其他 Spring 管理的 bean 调用该方法,这些 bean 可以通过自动装配、注入等方式访问可重试 bean。

编辑

如果您需要delete()从此类中的另一个方法调用该方法,则不能使用注释 - 改用适当配置的注释RetryTemplate

于 2016-08-03T23:40:47.933 回答