java Spring Security 6.0.0-具有WebClient OAuth2客户端配置的M6

jw5wzhpr  于 2022-11-20  发布在  Java
关注(0)|答案(1)|浏览(509)

在最新的spring-boot-starter-oauth2-client 3.0.0-M4类中,OAuth2ProtectedResourceDetailsClientCredentialsAccessTokenProvider都已被完全删除。
当我尝试将WebClient与非React类oAuth2客户端配置一起使用时,遇到以下问题:

java.lang.IllegalArgumentException: principalName cannot be empty
    at org.springframework.util.Assert.hasText(Assert.java:289) ~[spring-core-6.0.0-M5.jar:6.0.0-M5]
    Suppressed: reactor.core.publisher.FluxOnAssembly$OnAssemblyException: 
Error has been observed at the following site(s):
    *__checkpoint ⇢ Request to GET http://localhost:8080/v1/notifications/2245 [DefaultWebClient]
Original Stack Trace:
        at org.springframework.util.Assert.hasText(Assert.java:289) ~[spring-core-6.0.0-M5.jar:6.0.0-M5]
        at org.springframework.security.oauth2.client.InMemoryOAuth2AuthorizedClientService.loadAuthorizedClient(InMemoryOAuth2AuthorizedClientService.java:78) ~[spring-security-oauth2-client-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.oauth2.client.AuthorizedClientServiceOAuth2AuthorizedClientManager.authorize(AuthorizedClientServiceOAuth2AuthorizedClientManager.java:130) ~[spring-security-oauth2-client-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.oauth2.client.web.reactive.function.client.ServletOAuth2AuthorizedClientExchangeFilterFunction.lambda$authorizeClient$22(ServletOAuth2AuthorizedClientExchangeFilterFunction.java:470) ~[spring-security-oauth2-client-6.0.0-M6.jar:6.0.0-M6]
        at reactor.core.publisher.MonoSupplier.call(MonoSupplier.java:86) ~[reactor-core-3.5.0-M4.jar:3.5.0-M4]
        at reactor.core.publisher.FluxSubscribeOnCallable$CallableSubscribeOnSubscription.run(FluxSubscribeOnCallable.java:227) ~[reactor-core-3.5.0-M4.jar:3.5.0-M4]
        at reactor.core.scheduler.SchedulerTask.call(SchedulerTask.java:68) ~[reactor-core-3.5.0-M4.jar:3.5.0-M4]
        at reactor.core.scheduler.SchedulerTask.call(SchedulerTask.java:28) ~[reactor-core-3.5.0-M4.jar:3.5.0-M4]
        at java.base/java.util.concurrent.FutureTask.run(FutureTask.java:317) ~[na:na]
        at java.base/java.util.concurrent.ScheduledThreadPoolExecutor$ScheduledFutureTask.run(ScheduledThreadPoolExecutor.java:304) ~[na:na]
        at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1144) ~[na:na]
        at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:642) ~[na:na]
        at java.base/java.lang.Thread.run(Thread.java:1589) ~[na:na]
    Suppressed: java.lang.Exception: #block terminated with an error
        at reactor.core.publisher.BlockingSingleSubscriber.blockingGet(BlockingSingleSubscriber.java:99) ~[reactor-core-3.5.0-M4.jar:3.5.0-M4]
        at reactor.core.publisher.Mono.block(Mono.java:1675) ~[reactor-core-3.5.0-M4.jar:3.5.0-M4]
        at com.example.restservice.controller.GreetingController.jwtRestcallExample(GreetingController.java:79) ~[classes/:na]
        at com.example.restservice.controller.GreetingController.greeting(GreetingController.java:56) ~[classes/:na]
        at java.base/jdk.internal.reflect.DirectMethodHandleAccessor.invoke(DirectMethodHandleAccessor.java:104) ~[na:na]
        at java.base/java.lang.reflect.Method.invoke(Method.java:578) ~[na:na]
        at org.springframework.web.method.support.InvocableHandlerMethod.doInvoke(InvocableHandlerMethod.java:205) ~[spring-web-6.0.0-M5.jar:6.0.0-M5]
        at org.springframework.web.method.support.InvocableHandlerMethod.invokeForRequest(InvocableHandlerMethod.java:150) ~[spring-web-6.0.0-M5.jar:6.0.0-M5]
        at org.springframework.web.servlet.mvc.method.annotation.ServletInvocableHandlerMethod.invokeAndHandle(ServletInvocableHandlerMethod.java:117) ~[spring-webmvc-6.0.0-M5.jar:6.0.0-M5]
        at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.invokeHandlerMethod(RequestMappingHandlerAdapter.java:895) ~[spring-webmvc-6.0.0-M5.jar:6.0.0-M5]
        at org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter.handleInternal(RequestMappingHandlerAdapter.java:808) ~[spring-webmvc-6.0.0-M5.jar:6.0.0-M5]
        at org.springframework.web.servlet.mvc.method.AbstractHandlerMethodAdapter.handle(AbstractHandlerMethodAdapter.java:87) ~[spring-webmvc-6.0.0-M5.jar:6.0.0-M5]
        at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:1067) ~[spring-webmvc-6.0.0-M5.jar:6.0.0-M5]
        at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:960) ~[spring-webmvc-6.0.0-M5.jar:6.0.0-M5]
        at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:1003) ~[spring-webmvc-6.0.0-M5.jar:6.0.0-M5]
        at org.springframework.web.servlet.FrameworkServlet.doGet(FrameworkServlet.java:895) ~[spring-webmvc-6.0.0-M5.jar:6.0.0-M5]
        at jakarta.servlet.http.HttpServlet.service(HttpServlet.java:668) ~[tomcat-embed-core-10.0.22.jar:5.0.0]
        at org.springframework.web.servlet.FrameworkServlet.service(FrameworkServlet.java:880) ~[spring-webmvc-6.0.0-M5.jar:6.0.0-M5]
        at jakarta.servlet.http.HttpServlet.service(HttpServlet.java:777) ~[tomcat-embed-core-10.0.22.jar:5.0.0]
        at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:223) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:158) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:53) ~[tomcat-embed-websocket-10.0.22.jar:10.0.22]
        at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:185) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:158) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:341) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.access.intercept.AuthorizationFilter.doFilterInternal(AuthorizationFilter.java:77) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:116) ~[spring-web-6.0.0-M5.jar:6.0.0-M5]
        at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:350) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.access.ExceptionTranslationFilter.doFilter(ExceptionTranslationFilter.java:126) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.access.ExceptionTranslationFilter.doFilter(ExceptionTranslationFilter.java:120) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:350) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.session.SessionManagementFilter.doFilter(SessionManagementFilter.java:131) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.session.SessionManagementFilter.doFilter(SessionManagementFilter.java:85) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:350) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.authentication.AnonymousAuthenticationFilter.doFilter(AnonymousAuthenticationFilter.java:98) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:350) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.servletapi.SecurityContextHolderAwareRequestFilter.doFilter(SecurityContextHolderAwareRequestFilter.java:164) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:350) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.savedrequest.RequestCacheAwareFilter.doFilter(RequestCacheAwareFilter.java:63) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:350) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.oauth2.server.resource.web.BearerTokenAuthenticationFilter.doFilterInternal(BearerTokenAuthenticationFilter.java:142) ~[spring-security-oauth2-resource-server-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:116) ~[spring-web-6.0.0-M5.jar:6.0.0-M5]
        at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:350) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.authentication.logout.LogoutFilter.doFilter(LogoutFilter.java:107) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.authentication.logout.LogoutFilter.doFilter(LogoutFilter.java:93) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:350) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.csrf.CsrfFilter.doFilterInternal(CsrfFilter.java:116) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:116) ~[spring-web-6.0.0-M5.jar:6.0.0-M5]
        at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:350) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.header.HeaderWriterFilter.doHeadersAfter(HeaderWriterFilter.java:90) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.header.HeaderWriterFilter.doFilterInternal(HeaderWriterFilter.java:75) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:116) ~[spring-web-6.0.0-M5.jar:6.0.0-M5]
        at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:350) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.context.SecurityContextHolderFilter.doFilterInternal(SecurityContextHolderFilter.java:69) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:116) ~[spring-web-6.0.0-M5.jar:6.0.0-M5]
        at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:350) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.context.request.async.WebAsyncManagerIntegrationFilter.doFilterInternal(WebAsyncManagerIntegrationFilter.java:62) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:116) ~[spring-web-6.0.0-M5.jar:6.0.0-M5]
        at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:350) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.session.DisableEncodeUrlFilter.doFilterInternal(DisableEncodeUrlFilter.java:42) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:116) ~[spring-web-6.0.0-M5.jar:6.0.0-M5]
        at org.springframework.security.web.FilterChainProxy$VirtualFilterChain.doFilter(FilterChainProxy.java:350) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.FilterChainProxy.doFilterInternal(FilterChainProxy.java:214) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.security.web.FilterChainProxy.doFilter(FilterChainProxy.java:186) ~[spring-security-web-6.0.0-M6.jar:6.0.0-M6]
        at org.springframework.web.filter.DelegatingFilterProxy.invokeDelegate(DelegatingFilterProxy.java:351) ~[spring-web-6.0.0-M5.jar:6.0.0-M5]
        at org.springframework.web.filter.DelegatingFilterProxy.doFilter(DelegatingFilterProxy.java:267) ~[spring-web-6.0.0-M5.jar:6.0.0-M5]
        at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:185) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:158) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.springframework.web.filter.RequestContextFilter.doFilterInternal(RequestContextFilter.java:100) ~[spring-web-6.0.0-M5.jar:6.0.0-M5]
        at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:116) ~[spring-web-6.0.0-M5.jar:6.0.0-M5]
        at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:185) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:158) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.springframework.web.filter.FormContentFilter.doFilterInternal(FormContentFilter.java:93) ~[spring-web-6.0.0-M5.jar:6.0.0-M5]
        at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:116) ~[spring-web-6.0.0-M5.jar:6.0.0-M5]
        at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:185) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:158) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.springframework.boot.actuate.metrics.web.servlet.WebMvcMetricsFilter.doFilterInternal(WebMvcMetricsFilter.java:94) ~[spring-boot-actuator-3.0.0-M4.jar:3.0.0-M4]
        at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:116) ~[spring-web-6.0.0-M5.jar:6.0.0-M5]
        at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:185) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:158) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.springframework.web.filter.CharacterEncodingFilter.doFilterInternal(CharacterEncodingFilter.java:201) ~[spring-web-6.0.0-M5.jar:6.0.0-M5]
        at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:116) ~[spring-web-6.0.0-M5.jar:6.0.0-M5]
        at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:185) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:158) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:197) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:97) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:542) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:119) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:92) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:78) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:356) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.apache.coyote.http11.Http11Processor.service(Http11Processor.java:399) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.apache.coyote.AbstractProcessorLight.process(AbstractProcessorLight.java:65) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.apache.coyote.AbstractProtocol$ConnectionHandler.process(AbstractProtocol.java:867) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.apache.tomcat.util.net.NioEndpoint$SocketProcessor.doRun(NioEndpoint.java:1760) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.apache.tomcat.util.net.SocketProcessorBase.run(SocketProcessorBase.java:49) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.apache.tomcat.util.threads.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1191) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.apache.tomcat.util.threads.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:659) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at org.apache.tomcat.util.threads.TaskThread$WrappingRunnable.run(TaskThread.java:61) ~[tomcat-embed-core-10.0.22.jar:10.0.22]
        at java.base/java.lang.Thread.run(Thread.java:1589) ~[na:na]

我已经使用非React类配置了oauth2-client Security,如下所示:

@Bean
@Qualifier("clientRegistrations")
@Primary
public ClientRegistrationRepository getRegistration(
        @Value("${spring.security.oauth2.client.provider.custom.token-uri}") String tokenUri,
        @Value("${spring.security.oauth2.client.registration.custom.client-id}") String clientId,
        @Value("${spring.security.oauth2.client.registration.custom.client-secret}") String clientSecret) {
    ClientRegistration registration = ClientRegistration
            .withRegistrationId("custom")
            .tokenUri(tokenUri)
            .clientId(clientId)
            .clientSecret(clientSecret)
            .authorizationGrantType(AuthorizationGrantType.CLIENT_CREDENTIALS)
            .build();
    return new InMemoryClientRegistrationRepository(registration);
}

@Bean
public WebClient webClientTemplate(ClientRegistrationRepository clientRegistrations) {
    InMemoryOAuth2AuthorizedClientService clientService = new InMemoryOAuth2AuthorizedClientService(clientRegistrations);
    AuthorizedClientServiceOAuth2AuthorizedClientManager authorizedClientManager = new AuthorizedClientServiceOAuth2AuthorizedClientManager(clientRegistrations, clientService);
    ServletOAuth2AuthorizedClientExchangeFilterFunction oauth = new ServletOAuth2AuthorizedClientExchangeFilterFunction(authorizedClientManager);
    oauth.setDefaultClientRegistrationId("custom");
    return WebClient.builder()
            .filter(oauth)
            .filter(errorHandler())
            .build();
}

public static ExchangeFilterFunction errorHandler() {
    return ExchangeFilterFunction.ofResponseProcessor(clientResponse -> {

        if (clientResponse.statusCode().is5xxServerError() || clientResponse.statusCode().is4xxClientError()) {
            return clientResponse.bodyToMono(String.class)
                    .flatMap(errorBody -> Mono.error(new IllegalAccessException(errorBody)));
        } else {
            return Mono.just(clientResponse);
        }
    });
}

application.yml

spring:
  security:
    oauth2:
      client:
        registration:
          custom:
            client-id: <client id>
            client-secret: <client password>
            authorization-grant-type: client_credential
        provider:
          custom:
            token-uri: <url>

pom.xml

<parent>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-parent</artifactId>
    <version>3.0.0-M4</version>
    <relativePath/>
</parent>
<!-- Spring Boot security dependencies -->
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-security</artifactId>
</dependency>
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-oauth2-resource-server</artifactId>
</dependency>
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-oauth2-client</artifactId>
</dependency>
<dependency>
    <groupId>org.springframework.security</groupId>
    <artifactId>spring-security-oauth2-jose</artifactId>
</dependency>
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-webflux</artifactId>
</dependency>

根据Spring Security 5 Replacement for OAuth2RestTemplate提供的解决方案,建议使用WebClient而不是RestTemplate,我已经遵循了solution,但如果我仔细观察提到的解决方案,它使用spring-boot-starter-oauth2-client 3.0.0-M4中的React式类,但我的应用程序不是React式应用程序。所以我不想使用一些不应该在非且可能导致一些性能问题。
当我尝试使用oAuth2客户端React类时,WebClient可以按预期工作,但如果我将所有React类更改为非React类,则会面临上述问题。有人能提供帮助吗?是什么导致了这个问题?
工作样品配置:

@Bean
public ReactiveClientRegistrationRepository getRegistration(
        @Value("${spring.security.oauth2.client.provider.custom.token-uri}") String tokenUri,
        @Value("${spring.security.oauth2.client.registration.custom.client-id}") String clientId,
        @Value("${spring.security.oauth2.client.registration.custom.client-secret}") String clientSecret) {
    ClientRegistration registration = ClientRegistration
            .withRegistrationId("custom")
            .tokenUri(tokenUri)
            .clientId(clientId)
            .clientSecret(clientSecret)
            .authorizationGrantType(AuthorizationGrantType.CLIENT_CREDENTIALS)
            .build();
    return new InMemoryReactiveClientRegistrationRepository(registration);
}

@Bean
public WebClient webClient(ReactiveClientRegistrationRepository clientRegistrations) {
    InMemoryReactiveOAuth2AuthorizedClientService clientService = new InMemoryReactiveOAuth2AuthorizedClientService(clientRegistrations);
    AuthorizedClientServiceReactiveOAuth2AuthorizedClientManager authorizedClientManager = new AuthorizedClientServiceReactiveOAuth2AuthorizedClientManager(clientRegistrations, clientService);
    ServerOAuth2AuthorizedClientExchangeFilterFunction oauth = new ServerOAuth2AuthorizedClientExchangeFilterFunction(authorizedClientManager);
    oauth.setDefaultClientRegistrationId("custom");
    return WebClient.builder()
            .filter(oauth)
            .filter(errorHandler())
            .build();
}

public static ExchangeFilterFunction errorHandler() {
    return ExchangeFilterFunction.ofResponseProcessor(clientResponse -> {
        if (clientResponse.statusCode().is5xxServerError() || clientResponse.statusCode().is4xxClientError())
            return clientResponse.bodyToMono(String.class)
                    .flatMap(errorBody -> Mono.error(new IllegalAccessException(errorBody)));
        else
            return Mono.just(clientResponse);
    });
}
nzk0hqpo

nzk0hqpo1#

WebClient是被动的=〉它所需的被动客户端配置
P.S.你最好使用3.0.0-RC 2。Spring从M4开始删除了更多的类,你的原型可能会在月底之前迁移到3.0.0版本时失败。

相关问题