java - 带有非可选参数的基于 Quarkus 注释的拦截器

标签 java interceptor quarkus

根据提问的数量,这似乎是一个热门话题,但我还没有找到我正在寻找的答案。我想在我的 Quarkus 应用程序中实现一个简单的授权服务,但我似乎一遍又一遍地重复代码。

基本上,我从 Authorization Http header 中获取 JWT,并检查其中提供的角色是否足以访问我的端点:

public void someApiCall(@Context HttpHeaders headers) {
    authService.validate(ApiToken.SOME_API_CALL, headers); // Throws an exception when unauthorized
    
    //…
}

现在,我认为这看起来很笨拙,而且我不喜欢每个 Http 端点都需要的附加参数。我已经对 AOP 进行了一些研究,并且知道如何添加一个拦截器,该拦截器可以通过将应用于我的方法的注释来验证 Http header :

@Authorize
public void someApiCall(/*…*/) { /*…*/ }

问题是,我不知道如何将参数传递到此注释中以指定所需的角色。我想要这样的东西:

@Authorize(UserRole.SYSADMIN)

这看起来很简单,但我想不通。您将在下面找到拦截器和注释类(当然缺少所需的角色):

授权.java

@Retention(value=RUNTIME)
@Target(value=METHOD)
public @interface Authorize {}

AuthorizeInterceptor.java

@Interceptor
@Priority(3000)
@Authorize
public class AuthorizeInterceptor {

    @Inject
    AuthorizationService authService;

    @AroundInvoke
    public void validateRole(InvokationContext ctx) {
        authService.validate(ApiToken.ALL, ((RestEndpoint)ctx.getTarget()).getHttpHeaders());
    }
}

RestEndpoint.java

public class RestEndpoint {

    @Context
    HttpHeaders headers;

    public HttpHeaders getHttpHeaders() { return headers; }
}

一些资源.java

public class SomeResource extends RestEndpoint {

    @GET
    @Authorize
    public Object someApiCall() {
        /* do code directly */
    }
}

因此,总而言之,在我编写 @Authorize 的地方,我想要有 @Authorize(UserRole.SOME_ROLE)

提前致谢!

最佳答案

所以,我设法搞清楚了。事实证明这并不难,我只是不知道去哪里找。

这里是修改后的类:

授权.java

@InterceptorBinding
@Retention(RUNTIME)
@Target({TYPE, METHOD})
public @interface Authorize {
    // Nonbinding is very important. It makes the interceptor fire regardless of the value
    @Nonbinding ApiToken value();
}

AuthorizeInterceptor.java

@Interceptor
@Priority(3000)
@Authorize(ApiToken.NULL)
public class AuthorizeInterceptor {
    /* fields */

    public Object validate(InvokationContext ctx) throws Exception {
        authService.validate(/* stays the same */);
        return ctx.proceed();
    }
}

一些资源.java

public class SomeResource {
    @GET
    @Authorize(ApiToken.SOME_API_CALL)
    public Object someApiCall() { /* implementation */ }
}

正如 Turing85 所指出的,JavaEE 中已经存在类似的 API,它以相同的方式实现授权功能。

关于java - 带有非可选参数的基于 Quarkus 注释的拦截器,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/63415713/

相关文章:

java - 如何使用 Spring RestTemplate 将 JSON 作为参数发送到 url 中?

linq - 拦截所有 EF6 Linq 查询

java - Quarkus 没有对 Panache 的严重依赖?

java - 使用 Heroku 的 Quarkus 数据源

java - JAXB。通过两个 xsd 验证 XML

Netbeans IDE 中的 Java 代码为 : Code executed is the older one!,即使我对代码进行了更改

java - 使用 servlet 3.0 的 JBoss 6 session 安全特性的问题

java - hibernate 拦截器 : How do I override onCollectionUpdate and onCollectionRecreate to not populate my entities with database values?

NHibernate 拦截器不要求更改多对多集合/列表

ignite - 如何在 Quarkus 中使用 Apache Ignite?