如何在Spring AOP类

时间:2017-11-22 13:28:14

标签: java spring spring-boot spring-aop hystrix

在我当前的项目中,我需要使用Hystrix进行请求回退处理(主要是请求超时回退)。我测试了一个简单的案例,它将@HystrixCommand注释放在一个spring rest controller方法之上,如下所示:

@RestController
public class xxxxxx {

    @RequestMapping(value = "xxxxxxx")
        @HystrixCommand(fallbackMethod="fallback", commandProperties = {
            @HystrixProperty(name = "circuitBreaker.sleepWindowInMilliseconds", value = "2000"),
            @HystrixProperty(name = "execution.isolation.thread.timeoutInMilliseconds", value = "2000")
    })
    public String xxxxxx(@RequestParam(value = "xxxx", required = true) String xxxx) {
        ....
        return json.toString();
    }

}

这非常有效。超时在2秒后触发,并进入我预定义的后退方法。现在问题出现了:控制器上有太多方法,项目中有很多控制器。通过方法复制和粘贴@HystrixCommand方法不是一个好主意,我需要通过spring aop实现它。 然后我写了如下内容:

@Aspect
@Configuration
public class TimeoutMonitor {

    @Pointcut("execution(xxxxxxxx)")
    public void excuteService() {}

    @Around("excuteService()")
    @HystrixCommand(fallbackMethod="fallback", commandProperties = {
        @HystrixProperty(name = "circuitBreaker.sleepWindowInMilliseconds", value = "2000"),
        @HystrixProperty(name = "execution.isolation.thread.timeoutInMilliseconds", value = "2000")
    })
    public Object monitor(ProceedingJoinPoint pjp){
        try {
            Object output = pjp.proceed();
            return output;
        }catch(Throwable e) {
            return null;
        }
    }

    @HystrixCommand
    public String fallback(ProceedingJoinPoint pjp) {
        JSONObject json = new JSONObject();
        json.put("message", "request timeout");
        return json.toString();
    }
}

它不起作用......永远不会达到回退方法

在调试过程中,我确保逻辑流程通过excuteService() - > monitor() - >匹配方法的流程,并且它已经过了2秒,但是从未达到回退方法。我已经研究过这个问题,发现@HystrixCommand也是由AOP实现的。我想将一个aop放在另一个是导致这个问题的原因,但遗憾的是我无法想出解决它的方法。

如果有人能提供解决方案,我将不胜感激。也不允许使用aop实现的解决方案,但不允许在每种方法上复制和粘贴@HystrixCommand。

1 个答案:

答案 0 :(得分:1)

由于对此问题仍无回应,我将在此处提出自己的临时解决方案。

首先,在spring aop中使用hystrix仍然不可行,所以唯一的努力就是减少对控制器端的影响。 Hystrix允许springboot application.properties文件中的默认超时设置如下:

hystrix.command.default.execution.isolation.thread.timeoutInMilliseconds=3000
hystrix.command.default.circuitBreaker.sleepWindowInMilliseconds=3000

通过这种方式,将每个方法放在上面的注释只减少到一行:

@HystrixCommand(fallbackMethod="fallback")

在这些方面仍然不够简洁:

  • 需要为每个方法复制/粘贴此注释

  • 需要在使用hystrix的每个地方复制/粘贴后备方法

  • 对于hystrix回退方法本身,参数类型和数量需要与hystrix标记方法完全相同。目前我在每个控制器中使用了几个称为'fallback'的重载方法

虽然仍然不如我所说的那么简洁,但这是我目前所能想到的。一旦找到更好的解决方案,就会执行更新。