当授权服务器也是资源服务器时如何配置oAuth2 [英] How to configure oAuth2 when Authorization Server is also the Resource server
问题描述
我正在尝试使用授权代码授权或隐式授权在 spring boot 2.xx 中设置一个非常基本的 oAuth2 身份验证,但我似乎无法访问获取令牌后的资源服务器(与授权服务器驻留在同一个spring boot应用程序中).
以下是WebSecurityConfigurerAdapter
的配置
@EnableWebSecurity@配置公共类 WebSecurityConfiguration 扩展了 WebSecurityConfigurerAdapter {private static final String[] IGNORE_URIS = {"/swagger-resources/**","/swagger-ui.html","/v2/api-docs","/webjars/**","/资源/**","/h2-console/**","/common/**","/配置/用户界面","/配置/安全",/错误"};@豆public PasswordEncoder passwordEncoder() {返回新的 BCryptPasswordEncoder();}@覆盖公共无效配置(WebSecurity web){web.ignoring().antMatchers(IGNORE_URIS);}@覆盖protected void configure(HttpSecurity http) 抛出异常 {http.authorizeRequests().antMatchers("/product/**").hasAnyRole("管理员").and().httpBasic().and().formLogin().and().authorizeRequests().anyRequest().authenticated();}@覆盖protected void configure(AuthenticationManagerBuilder auth) 抛出异常 {auth.inMemoryAuthentication().withUser("admin").password("{noop}admin").roles("ADMIN");}@豆公共密码编码器 bCrypt() {返回新的 BCryptPasswordEncoder();}
和 AuthorizationServerConfigurerAdapter
@Configuration@EnableAuthorizationServer公共类 AuthorizationServerConfiguration 扩展 AuthorizationServerConfigurerAdapter {私人最终 AuthenticationManager authenticationManager;@自动连线公共 AuthorizationServerConfiguration(AuthenticationConfiguration authenticationConfiguration) 抛出异常 {this.authenticationManager = authenticationConfiguration.getAuthenticationManager();}@覆盖公共无效配置(ClientDetailsServiceConfigurer 客户端)抛出异常 {客户.inMemory().withClient("my-client-id").authorizedGrantTypes("authorization_code", "隐式").authorities("管理员").scopes("所有").resourceIds("product_api").secret("{noop}secret").redirectUris("https://google.com").accessTokenValiditySeconds(0);}@覆盖public void configure(AuthorizationServerSecurityConfigurer oauthServer) 抛出异常 {oauthServer.tokenKeyAccess("permitAll()").checkTokenAccess("permitAll()");}@覆盖public void configure(AuthorizationServerEndpointsConfigurer endpoints) 抛出异常 {endpoints.authenticationManager(authenticationManager);}}
到目前为止一切顺利.我可以通过在浏览器中输入以下 URL 来访问默认的 Spring 登录页面.
登录后,我可以授予对 my-client-id" 应用的访问权限.
最终在我批准应用程序后,我可以在浏览器的 URL 栏中看到新生成的访问令牌,就像这样.
https://www.google.com/#access_token=f2153498-6a26-42c6-93f0-80825ef03b16&token_type=bearer&scope=all
我的问题是,当我还配置了资源服务器时,所有这些流程都将不起作用.
@EnableResourceServer@配置公共类 ResourceServerConfiguration 扩展 ResourceServerConfigurerAdapter {@覆盖公共无效配置(ResourceServerSecurityConfigurer 资源){resources.resourceId("product_api");}@覆盖公共无效配置(HttpSecurity http)抛出异常{http.requestMatchers().antMatchers("/**").and().authorizeRequests().antMatchers("/**").permitAll();}}
我做错了什么?当我尝试访问 oauth/authorize
url 之前,我得到以下内容:
为什么?如何访问登录页面并检索令牌?我错过了什么?
需要使用
@Order
注解指定 WebMvc 和 ResourceServer 类的顺序
@EnableWebSecurity@配置@订单(1)公共类 WebSecurityConfiguration 扩展了 WebSecurityConfigurerAdapter {...}
和资源服务器
@EnableResourceServer@配置@订单(2)公共类 ResourceServerConfiguration 扩展 ResourceServerConfigurerAdapter {...}
如果你想看到可行的例子,你可以在这里查看 https://github.com/alex-petrov81/stackoverflow-answers/tree/master/auth-server-also-resource我已经从您的代码示例中创建了它.
I'm trying to setup a very basic oAuth2 authentication in spring boot 2.x.x using either authorization code grant or implicit grant but I can't seem to access the Resource server (which resides in the same spring boot app as the Authorization server) after the token is obtained.
Following is the configuration of WebSecurityConfigurerAdapter
@EnableWebSecurity
@Configuration
public class WebSecurityConfiguration extends WebSecurityConfigurerAdapter {
private static final String[] IGNORE_URIS = {
"/swagger-resources/**",
"/swagger-ui.html",
"/v2/api-docs",
"/webjars/**",
"/resources/**",
"/h2-console/**",
"/common/**",
"/configuration/ui",
"/configuration/security",
"/error"
};
@Bean
public PasswordEncoder passwordEncoder() {
return new BCryptPasswordEncoder();
}
@Override
public void configure(WebSecurity web) {
web.ignoring().antMatchers(IGNORE_URIS);
}
@Override
protected void configure(HttpSecurity http) throws Exception {
http.authorizeRequests()
.antMatchers("/product/**")
.hasAnyRole("ADMIN").and()
.httpBasic().and().formLogin().and().authorizeRequests().anyRequest().authenticated();
}
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.inMemoryAuthentication().withUser("admin").password("{noop}admin").roles("ADMIN");
}
@Bean
public PasswordEncoder bCrypt() {
return new BCryptPasswordEncoder();
}
And the AuthorizationServerConfigurerAdapter
@Configuration
@EnableAuthorizationServer
public class AuthorizationServerConfiguration extends AuthorizationServerConfigurerAdapter {
private final AuthenticationManager authenticationManager;
@Autowired
public AuthorizationServerConfiguration(AuthenticationConfiguration authenticationConfiguration) throws Exception {
this.authenticationManager = authenticationConfiguration.getAuthenticationManager();
}
@Override
public void configure(ClientDetailsServiceConfigurer clients) throws Exception {
clients
.inMemory()
.withClient("my-client-id")
.authorizedGrantTypes("authorization_code", "implicit")
.authorities("ADMIN")
.scopes("all")
.resourceIds("product_api")
.secret("{noop}secret").redirectUris("https://google.com").accessTokenValiditySeconds(0);
}
@Override
public void configure(AuthorizationServerSecurityConfigurer oauthServer) throws Exception {
oauthServer.tokenKeyAccess("permitAll()")
.checkTokenAccess("permitAll()");
}
@Override
public void configure(AuthorizationServerEndpointsConfigurer endpoints) throws Exception {
endpoints.authenticationManager(authenticationManager);
}
}
So far so good. I am able to reach the default Spring login page by typing the following Url in the browser.
Then The login page shows up and I enter my credentials.
After I log in I can then grant access to "my-client-id" app.
Eventually after I approve the app I can see the newly generated access token in the URL bar of the browser which is something like this.
https://www.google.com/#access_token=f2153498-6a26-42c6-93f0-80825ef03b16&token_type=bearer&scope=all
My question is that All of this flow won't work when I also configure a Resource Server.
@EnableResourceServer
@Configuration
public class ResourceServerConfiguration extends ResourceServerConfigurerAdapter {
@Override
public void configure(ResourceServerSecurityConfigurer resources) {
resources.resourceId("product_api");
}
@Override
public void configure(HttpSecurity http) throws Exception {
http
.requestMatchers()
.antMatchers("/**")
.and().authorizeRequests()
.antMatchers("/**").permitAll();
}
}
What am I doing wrong? When I try to access the oauth/authorize
url as before I get the following:
Why? How can one access the login page and retrieve the token? What Am I missing?
You need to use
@Order
Annotation to specify order for WebMvc and ResourceServer classes
@EnableWebSecurity
@Configuration
@Order(1)
public class WebSecurityConfiguration extends WebSecurityConfigurerAdapter {
...
}
and for Resource Server
@EnableResourceServer
@Configuration
@Order(2)
public class ResourceServerConfiguration extends ResourceServerConfigurerAdapter {
...
}
If you want to see workable example, you can check it here https://github.com/alex-petrov81/stackoverflow-answers/tree/master/auth-server-also-resource I've created it from your code example.
这篇关于当授权服务器也是资源服务器时如何配置oAuth2的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!