micronaut-projects / micronaut-security

The official Micronaut security solution
Apache License 2.0
166 stars 123 forks source link

JwksSignature error when used from HttpServerFilter #1680

Open mrusinak opened 3 weeks ago

mrusinak commented 3 weeks ago

Expected Behavior

I should be able to use JwksSignature.verify() from within HttpServerFilter.doFilter

This worked in 4.3.7, and started failing on upgrade to 4.4.1

Actual Behaviour

An exception is thrown:

java.lang.IllegalStateException: blockOptional() is blocking, which is not supported in thread default-nioEventLoopGroup-1-3
    at reactor.core.publisher.BlockingOptionalMonoSubscriber.blockingGet(BlockingOptionalMonoSubscriber.java:108)
    at reactor.core.publisher.Mono.blockOptional(Mono.java:1831)
    at io.micronaut.security.token.jwt.signature.jwks.JwksSignature.loadJwkSet(JwksSignature.java:178)
    at io.micronaut.security.token.jwt.signature.jwks.JwksSignature.computeJWKSet(JwksSignature.java:78)
    at io.micronaut.security.token.jwt.signature.jwks.JwksSignature.verify(JwksSignature.java:149)

Steps To Reproduce

  1. Create a project with dependencies
    1. "io.micronaut:micronaut-http-server-netty"
    2. "io.micronaut.security:micronaut-security-jwt"
  2. Create an HttpServerFilter, and configure/autowire in a JwksSignature
  3. Within the doFilter method of the filter, attempt call the verify method of the signature
    1. Or really, any method that will cause fetching of the JWKS

Possible? (Kotlin) Workaround:

Environment Information

No response

Example Application

No response

Version

4.4.1

sdelamo commented 2 weeks ago

This is an intentional change in Micronaut Framework 4.4.0 to avoid performance degradation due to the blocking of the Netty event loop.

In addition, since Micronaut framework 4.4.0, any Project Reactor blocking operations throw an exception when they are done on an event loop thread. This new behaviour will help you identify the controller’s methods, which you must annotate with @ExecuteOn to avoid performance loss or dead locks in the event loop.

Please watch: https://www.youtube.com/watch?v=W6iztOuulVU

if you are using a ServerFilter annotate the filter method with @ExecuteOn.

mrusinak commented 2 weeks ago

Thanks, but I do think this is still a bit of a bug / unexpected problem - I believe it should be possible to call JwksSignature.verify() from within nonblocking threads without running into an error like this.

Whether that be a new method, new argument, or change to the existing verify() so it can be used without a hidden call to resolve JWKS in a blocking fashion

sdelamo commented 2 weeks ago

we are working on https://github.com/micronaut-projects/micronaut-security/pull/1693