Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Exceptions should be handled correctly even if user info endpoint is misconfigured #13778

Closed
wapkch opened this issue Sep 6, 2023 · 4 comments
Assignees
Labels
type: enhancement A general enhancement

Comments

@wapkch
Copy link

wapkch commented Sep 6, 2023

Expected Behavior

When using Spring Security OAuth2 Client, even if we misconfigured the user info endpoint which result in an OAuth2AuthenticationException, the exception should be processed instead of an internal error which result in HTTP status 500.

Current Behavior

When using Spring Security OAuth2 Client, if a wrong user info endpoint which response contains invalid content type 'text/html' is configured, an OAuth2AuthenticationException will be thrown in the process of oauth callback request, if we use Spring Data session redis at the same time, an SerializationException will be thrown:

2023-09-06 15:20:07,322 [http-nio-8081-exec-4] WARN  [org.springframework.web.servlet.mvc.method.annotation.ExceptionHandlerExceptionResolver] [ExceptionHandlerExceptionResolver.java:434] [trace=9ac654b769f4296f,span=9ac654b769f4296f][tenant=javaapptest,region=] [TID: N/A] - Failure in @ExceptionHandler com.zatech.octopus.component.exception.resolver.MessageSourceExceptionHandler#handler(Throwable, HttpServletRequest, HttpServletResponse)
org.springframework.data.redis.serializer.SerializationException: Cannot serialize; nested exception is org.springframework.core.serializer.support.SerializationFailedException: Failed to serialize object using DefaultSerializer; nested exception is java.io.NotSerializableException: sun.reflect.generics.reflectiveObjects.ParameterizedTypeImpl
	at org.springframework.data.redis.serializer.JdkSerializationRedisSerializer.serialize(JdkSerializationRedisSerializer.java:96)
	at org.springframework.data.redis.core.AbstractOperations.rawHashValue(AbstractOperations.java:186)
	at org.springframework.data.redis.core.DefaultHashOperations.putAll(DefaultHashOperations.java:209)
	at org.springframework.data.redis.core.DefaultBoundHashOperations.putAll(DefaultBoundHashOperations.java:187)
	at org.springframework.session.data.redis.RedisIndexedSessionRepository$RedisSession.saveDelta(RedisIndexedSessionRepository.java:811)
	at org.springframework.session.data.redis.RedisIndexedSessionRepository$RedisSession.save(RedisIndexedSessionRepository.java:799)
	at org.springframework.session.data.redis.RedisIndexedSessionRepository$RedisSession.access$000(RedisIndexedSessionRepository.java:686)
	at org.springframework.session.data.redis.RedisIndexedSessionRepository.save(RedisIndexedSessionRepository.java:415)
	at org.springframework.session.data.redis.RedisIndexedSessionRepository.save(RedisIndexedSessionRepository.java:251)
	at org.springframework.cloud.sleuth.instrument.session.TraceSessionRepository.lambda$save$1(TraceSessionRepository.java:74)
	at org.springframework.cloud.sleuth.instrument.session.TraceSessionRepository.lambda$wrap$0(TraceSessionRepository.java:63)

I'm not sure what cause the OAuth2AuthenticationException cannot be serialized, the OAuth2AuthenticationException looks like this:

image

Context

A sample to reproduce the issue can be found here: https://github.com/wapkch/spring-security-oauth2-client-demo

spring:
  security:
    oauth2:
      client:
        registration:
          azure:
            client-id:
            client-secret:
            authorization-grant-type: authorization_code
            scope: openid,profile
            redirect-uri: http://localhost:8080/login/oauth2/code/callback
        provider:
          azure:
            authorization-uri:
            token-uri:
            user-info-uri: https://www.google.com # Intentionally configured incorrectly 
            user-name-attribute: preferred_username
            jwk-set-uri:
  1. Fill in the blank configs,
  2. Start the application
  3. Access http://localhost:8081/

Then we can reproduce:
image

And the log:

2023-09-06 15:20:07,322 [http-nio-8081-exec-4] WARN  [org.springframework.web.servlet.mvc.method.annotation.ExceptionHandlerExceptionResolver] [ExceptionHandlerExceptionResolver.java:434] [trace=9ac654b769f4296f,span=9ac654b769f4296f][tenant=javaapptest,region=] [TID: N/A] - Failure in @ExceptionHandler com.zatech.octopus.component.exception.resolver.MessageSourceExceptionHandler#handler(Throwable, HttpServletRequest, HttpServletResponse)
org.springframework.data.redis.serializer.SerializationException: Cannot serialize; nested exception is org.springframework.core.serializer.support.SerializationFailedException: Failed to serialize object using DefaultSerializer; nested exception is java.io.NotSerializableException: sun.reflect.generics.reflectiveObjects.ParameterizedTypeImpl
	at org.springframework.data.redis.serializer.JdkSerializationRedisSerializer.serialize(JdkSerializationRedisSerializer.java:96)
	at org.springframework.data.redis.core.AbstractOperations.rawHashValue(AbstractOperations.java:186)
	at org.springframework.data.redis.core.DefaultHashOperations.putAll(DefaultHashOperations.java:209)
	at org.springframework.data.redis.core.DefaultBoundHashOperations.putAll(DefaultBoundHashOperations.java:187)
	at org.springframework.session.data.redis.RedisIndexedSessionRepository$RedisSession.saveDelta(RedisIndexedSessionRepository.java:811)
	at org.springframework.session.data.redis.RedisIndexedSessionRepository$RedisSession.save(RedisIndexedSessionRepository.java:799)
	at org.springframework.session.data.redis.RedisIndexedSessionRepository$RedisSession.access$000(RedisIndexedSessionRepository.java:686)
	at org.springframework.session.data.redis.RedisIndexedSessionRepository.save(RedisIndexedSessionRepository.java:415)
@wapkch wapkch added status: waiting-for-triage An issue we've not yet triaged type: enhancement A general enhancement labels Sep 6, 2023
@marcusdacoregio marcusdacoregio self-assigned this Sep 11, 2023
@marcusdacoregio marcusdacoregio removed the status: waiting-for-triage An issue we've not yet triaged label Sep 11, 2023
@marcusdacoregio
Copy link
Contributor

Hi, @wapkch. Unfortunately, I have not been able to reproduce the error. Can you provide a minimal, reproducible sample that has everything that we need to reproduce it? You can use the Spring Authorization Server and the Testcontainers support in Spring Boot to make it easier to run.

@marcusdacoregio marcusdacoregio added the status: waiting-for-feedback We need additional information before we can continue label Sep 12, 2023
@wapkch
Copy link
Author

wapkch commented Sep 18, 2023

Hi, @marcusdacoregio Thanks for reply. I have updated the demo. The issue can be reproduced by the following steps:

  1. Start the application using com.example.springsecurityoauth2clientdemo.SpringSecurityOauth2ClientDemoApplicationTests#main
  2. Access http://127.0.0.1:8080/sso using a web browser
  3. login with username/password (user1/password)
  4. The issues can be produced.

@spring-projects-issues spring-projects-issues added status: feedback-provided Feedback has been provided and removed status: waiting-for-feedback We need additional information before we can continue labels Sep 18, 2023
@marcusdacoregio
Copy link
Contributor

@marcusdacoregio
Copy link
Contributor

Hi, @wapkch. This has been resolved as part of spring-projects/spring-framework#31283, available in Spring Framework 6.0.13. Thank you.

@marcusdacoregio marcusdacoregio removed the status: feedback-provided Feedback has been provided label Oct 2, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
type: enhancement A general enhancement
Projects
Status: No status
Development

No branches or pull requests

3 participants