Spring 使用方面的引导角色验证控制器
Spring Boot role validation controller using aspect
我有几个按角色分隔的控制器函数,我发现它似乎可以通过使用 Aspect 来完成,而不是在每个控制器方法中进行角色验证,但是我的实现中有些地方不对Aspect 中的代码永远不会运行
注解:
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface ForMerchantOnly {}
看点:
@Aspect
@Configuration
public class ForMerchantOnlyAspect {
private static final Logger logger = LogManager.getLogger(ForMerchantOnlyAspect.class);
@Before("@annotation(com.example.api.annotation.ForMerchantOnly) && args(request)")
public void before(HttpServletRequest request) throws ServiceException {
if (!(request instanceof HttpServletRequest)) {
throw new RuntimeException("request should be HttpServletRequesttype");
}
String domain = request.getServerName();
System.out.println("Aspect showing domain " + domain);
// -- other code
}
}
控制器
@ForMerchantOnly
@GetMapping("/list")
public ResponseEntity<ApiResp> list() {
System.out.println("Show something");
return ResponseEntity.ok().body();
}
我假设当我通过 chrome 浏览器调用控制器 /list 方法时,它会命中 ForMerchantOnlyAspect
中的代码,但它只是直接进入控制器方法。我错过了什么吗?
方面没有工作,因为它找不到匹配的连接点。没有具有注解 @ForMerchantOnly
且参数类型为 HttpServletRequest
的控制器方法
来自 documentation :
args: Limits matching to join points (the execution of methods when
using Spring AOP) where the arguments are instances of the given
types.
以下方面可用于需求。范围指示符 within
将范围设置为建议。
@Before("@annotation(com.example.api.annotation.ForMerchantOnly) && within(com.example.api..*)")
public void before() {
HttpServletRequest request = ((ServletRequestAttributes) RequestContextHolder.currentRequestAttributes())
.getRequest();
System.out.println("Aspect showing domain " + request.getServerName());
}
另请注意,使用 @Component
和 @Configuration
注释更好地用于配置。
您还可以查看 Spring 安全框架的 Method Security,它可以使用注释保护方法。
来自文档
From version 2.0 onwards Spring Security has improved support
substantially for adding security to your service layer methods. It
provides support for JSR-250 annotation security as well as the
framework’s original @Secured annotation. From 3.0 you can also make
use of new expression-based annotations. You can apply security to a
single bean, using the intercept-methods element to decorate the bean
declaration, or you can secure multiple beans across the entire
service layer using the AspectJ style pointcuts.
我有几个按角色分隔的控制器函数,我发现它似乎可以通过使用 Aspect 来完成,而不是在每个控制器方法中进行角色验证,但是我的实现中有些地方不对Aspect 中的代码永远不会运行
注解:
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public @interface ForMerchantOnly {}
看点:
@Aspect
@Configuration
public class ForMerchantOnlyAspect {
private static final Logger logger = LogManager.getLogger(ForMerchantOnlyAspect.class);
@Before("@annotation(com.example.api.annotation.ForMerchantOnly) && args(request)")
public void before(HttpServletRequest request) throws ServiceException {
if (!(request instanceof HttpServletRequest)) {
throw new RuntimeException("request should be HttpServletRequesttype");
}
String domain = request.getServerName();
System.out.println("Aspect showing domain " + domain);
// -- other code
}
}
控制器
@ForMerchantOnly
@GetMapping("/list")
public ResponseEntity<ApiResp> list() {
System.out.println("Show something");
return ResponseEntity.ok().body();
}
我假设当我通过 chrome 浏览器调用控制器 /list 方法时,它会命中 ForMerchantOnlyAspect
中的代码,但它只是直接进入控制器方法。我错过了什么吗?
方面没有工作,因为它找不到匹配的连接点。没有具有注解 @ForMerchantOnly
且参数类型为 HttpServletRequest
来自 documentation :
args: Limits matching to join points (the execution of methods when using Spring AOP) where the arguments are instances of the given types.
以下方面可用于需求。范围指示符 within
将范围设置为建议。
@Before("@annotation(com.example.api.annotation.ForMerchantOnly) && within(com.example.api..*)")
public void before() {
HttpServletRequest request = ((ServletRequestAttributes) RequestContextHolder.currentRequestAttributes())
.getRequest();
System.out.println("Aspect showing domain " + request.getServerName());
}
另请注意,使用 @Component
和 @Configuration
注释更好地用于配置。
您还可以查看 Spring 安全框架的 Method Security,它可以使用注释保护方法。
来自文档
From version 2.0 onwards Spring Security has improved support substantially for adding security to your service layer methods. It provides support for JSR-250 annotation security as well as the framework’s original @Secured annotation. From 3.0 you can also make use of new expression-based annotations. You can apply security to a single bean, using the intercept-methods element to decorate the bean declaration, or you can secure multiple beans across the entire service layer using the AspectJ style pointcuts.