Oauth2Login 仅用于特定的 url
Posted
技术标签:
【中文标题】Oauth2Login 仅用于特定的 url【英文标题】:Oauth2Login for only specific urls 【发布时间】:2020-10-16 11:08:20 【问题描述】:我正在尝试为通过 Spring Security 登录设置 oauth2 配置。但仅适用于特定的网址。
我的安全配置如下所示。
@Override
public void configure(HttpSecurity http) throws Exception
http
.antMatcher("/secured/**")
.authorizeRequests()
.anyRequest()
.authenticated()
.and()
.oauth2Login()
.clientRegistrationRepository(clientRegistrationRepository())
.authorizedClientService(authorizedClientService());
基本上,我只希望 oauth2Login 触发以 /secured 开头的 url。它似乎几乎可以工作,唯一的问题是每当 Spring 尝试将我的会话重定向到 google 进行身份验证时,它都会触发 404。
oauth 身份验证的标准重定向应该触发到 http://localhost:8080/oauth2/authorization/google,我的应用程序尝试这样做,但它是 404。
我假设 http://localhost:8080/oauth2/authorization/google url 被某种类型的安全配置阻止?但我终其一生都无法弄清楚原因。
我猜我需要为任何转到“/oauth2/authorization/**”的请求找到正确的 .permitAll() 组合
我已经在下面尝试过。
@Override
public void configure(HttpSecurity http) throws Exception
http
.antMatcher("/secured/**")
.authorizeRequests()
.antMatchers("/oauth2/authorization/**")
.permitAll()
.anyRequest()
.authenticated()
.and()
.oauth2Login()
.clientRegistrationRepository(clientRegistrationRepository())
.authorizedClientService(authorizedClientService());
但这不起作用.....有人看到我的问题吗?我没有其他与此冲突的安全配置,我有点茫然。
【问题讨论】:
【参考方案1】:根据之前的回答,没有 lambda-style 的版本应该是这个样子吧?
@Override
public void configure(HttpSecurity http) throws Exception
http
.authorizeRequests
.antMatchers("/secured/**").authenticated()
.anyRequest().authenticated()
.and()
.oauth2Login()
.clientRegistrationRepository(clientRegistrationRepository())
.authorizedClientService(authorizedClientService());
如果我们只希望 "/secured/**"
使用 oauth2Login,为什么我们要使用 authenticated()
来处理 antMatcher("/secured/**")
和 anyRequest()
(而不是 permitAll()
来处理 anyRequest()
)?
谢谢。
【讨论】:
感谢您指出这一点。我已按照您的建议使用permitAll()
使用正确的配置更新了我的回复。【参考方案2】:
了解这里问题的第一步是了解http.antMatcher()
和http.authorizeRequests()
之间的区别。
让我们看看下面的配置。 (我正在使用 Spring Security 5.2 中可用的 lambda 样式配置,以使其更具可读性)
@Override
public void configure(HttpSecurity http) throws Exception
http
.antMatcher("/secured/**")
.authorizeRequests(authorize -> authorize
.anyRequest().authenticated()
)
.oauth2Login(oauth2Login -> oauth2Login
.clientRegistrationRepository(clientRegistrationRepository())
.authorizedClientService(authorizedClientService())
);
在这里,我们指定只有在匹配 "/secured/**"
时才会调用 HTTP 安全性。
换句话说,只有SecurityFilterChain
匹配"/secured/**"
的请求才会被处理。
这是一个问题,因为SecurityFilterChain
是从"/oauth2/authorization/google"
发起授权请求的原因。
但是,SecurityFilterChain
没有被调用,因为"/oauth2/authorization/google"
与"/secured/**"
不匹配。
请考虑以下配置。
@Override
public void configure(HttpSecurity http) throws Exception
http
.authorizeRequests(authorize -> authorize
.antMatchers("/secured/**").authenticated()
.anyRequest().permitAll()
)
.oauth2Login(oauth2Login -> oauth2Login
.clientRegistrationRepository(clientRegistrationRepository())
.authorizedClientService(authorizedClientService())
);
在这里,将为所有请求调用 HTTP 安全性。
但是,只有匹配 "/secured/**"
的请求才会要求用户进行身份验证。
【讨论】:
【参考方案3】:@eleftheria-stein-kousathana 的回答让我想到了另一个可能的解决方案。
如上所述,重要的是要知道不会调用 OAuth 端点,因为它们的安全配置绑定到直接跟在 HttpSecurity
对象之后的 antMatcher()
调用。
但正如docs 中所述,您还可以更改redirectionEndpoint
和authorizationEndpoint
的baseUris
@Override
public void configure(HttpSecurity http) throws Exception
http
.antMatcher("/secured/**")
.authorizeRequests()
.anyRequest()
.authenticated()
.and()
.oauth2Login()
//New Code Starting here
.authorizationEndpoint()
.baseUri("/secured/oauth2/authorization")
.and()
.redirectionEndpoint()
.baseUri("/secured/oauth2/code/*")
.and()
//new code ending here
.clientRegistrationRepository(clientRegistrationRepository())
.authorizedClientService(authorizedClientService());
请务必更改 clientRegistration
的 redirectUriTemplate
以及在 AuthorizationServer 上配置的重定向 uri
并且一定要在redirectionEndpoint.baseUri
的末尾添加星号...这花了我几分钟来找出问题所在:-)
【讨论】:
以上是关于Oauth2Login 仅用于特定的 url的主要内容,如果未能解决你的问题,请参考以下文章
NVActivityIndicatorView 仅用于特定视图