如何在Spring Security上缓存自检请求?

lx0bsm1f  于 2022-11-23  发布在  Spring
关注(0)|答案(1)|浏览(98)

我正在使用Spring Boot对我的资源服务器进行OAuth2认证。但是认证服务器(不是我们的)变得不稳定,有时无法解析。
我已经读了很多文章,但找不到如何缓存这些请求,以减少应用程序上的401数量。
我的安全配置运行如下:

.oauth2ResourceServer()
                .opaqueToken()
                .introspectionClientCredentials(this.clientId, this.clientSecret) 
                .introspectionUri(this.introspectionUri);

谁能帮帮我?
PS:我试着使用@Cacheable,但我不认为我尝试了正确的方法。

rta7y2nd

rta7y2nd1#

对于那些运行相同的问题。这里是我如何解决:
已在我的安全配置上公开Bean:

@Bean 
public OpaqueTokenIntrospector introspector() {
    return new CustomOpaqueTokenIntrospector(this.introspectionUri,this.clientId, this.clientSecret);
  }

并创建了一个自定义类来缓存找到的值:

public class CustomOpaqueTokenIntrospector implements OpaqueTokenIntrospector {
  private final OpaqueTokenIntrospector introspector;

  private CacheManager cacheManager;
  private Cache<String, OAuth2AuthenticatedPrincipal> accessTokens;
CacheManager.createCache("iamCache",CacheManager.getRuntimeConfiguration);
  public CustomOpaqueTokenIntrospector(String uri, String clientId, String clientSecret) {

    cacheManager = CacheManagerBuilder.newCacheManagerBuilder().build();
    cacheManager.init();

    accessTokens = cacheManager.createCache("iamCache",
        CacheConfigurationBuilder
            .newCacheConfigurationBuilder(String.class, OAuth2AuthenticatedPrincipal.class,
                ResourcePoolsBuilder.heap(1000))
            .withExpiry(ExpiryPolicyBuilder.timeToLiveExpiration(Duration.ofSeconds(1800))));

    this.introspector = new NimbusOpaqueTokenIntrospector(uri, clientId, clientSecret);
  }

  public @Override OAuth2AuthenticatedPrincipal introspect(String token) {
    if (this.accessTokens.containsKey(token)) {
      if (this.getAccessTokensCacheFromCacheManager().get(token).getAttribute("exp") != null
          && ((Instant) this.getAccessTokensCacheFromCacheManager().get(token).getAttribute("exp"))
              .isAfter(Instant.now())) {
        return this.getAccessTokensCacheFromCacheManager().get(token);
      }
      
      this.getAccessTokensCacheFromCacheManager().remove(token);
    }
    OAuth2AuthenticatedPrincipal principal = introspector.introspect(token);
    this.getAccessTokensCacheFromCacheManager().put(token, principal);

    return principal;
  }

  public Cache<String, OAuth2AuthenticatedPrincipal> getAccessTokensCacheFromCacheManager() {
    return cacheManager.getCache("iamCache", String.class, OAuth2AuthenticatedPrincipal.class);
  }
}

相关问题