Spring 启动和 Spring 云安全 OAUTH 2 SSO 最新版本失败
Spring Boot and Spring Cloud Security OAUTH 2 SSO Failing with latest releases
我正在尝试将示例 Spring Boot 和 Spring Cloud Security with OAuth 从 Spring Boot 1.4.1 + Brixton.RELEASE 升级到 Spring启动 1.5.3+ Dalston.RELEASE。然而,经过了漫长的努力,却一无所获。
似乎出于某种原因,资源服务器安全过滤器链没有被触发。因此,对“/me”或“/user”的调用由默认的安全过滤器链处理。我在想这是否是订单的问题。但试图明确设置安全过滤器链的顺序如下
- 授权服务器 6
- 网络默认 5
- 资源服务器 3(硬编码 ??)
由于默认过滤器链正在处理请求,它总是转到登录页面,生成 HTML 并且 SSO 客户端(服务器端 thymeleaf web UI)失败。
源代码如下
授权服务器
@SpringBootApplication
public class MyAuthServerApplication {
public static void main(String[] args) {
SpringApplication.run(MyAuthServerApplication.class, args);
}
}
然后是授权服务器配置
@Configuration
@EnableAuthorizationServer
@Order(6)
public class AuthorizationServerConfigurer extends A
uthorizationServerConfigurerAdapter {
@Override
public void configure(ClientDetailsServiceConfigurer clients) throws
Exception {
clients.inMemory()
.withClient("myauthserver")
.secret("verysecretpassword")
.redirectUris("http://localhost:8080/")
.authorizedGrantTypes("authorization_code", "refresh_token")
.scopes("myscope")
.autoApprove(true);
}
}
然后资源服务器class
@Configuration
@EnableResourceServer
public class ResourceServerConfigurer extends
ResourceServerConfigurerAdapter {
@Override
public void configure(HttpSecurity http) throws Exception {
http.antMatcher("/user")
.authorizeRequests()
.anyRequest()
.authenticated();
}
}
Web MVC 配置
@Configuration
public class WebMvcConfigurer extends WebMvcConfigurerAdapter {
@Override
public void addViewControllers(ViewControllerRegistry registry) {
registry.addViewController("login").setViewName("login");
}
}
默认spring安全配置
@Configuration
@EnableWebSecurity
@Order(9)
public class WebSecurityConfigurer extends WebSecurityConfigurerAdapter {
@Override
protected void configure(HttpSecurity http) throws Exception {
http
.authorizeRequests()
.antMatchers("/login").permitAll()
.anyRequest().authenticated()
.and().csrf()
.and().formLogin().loginPage("/login");
}
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception
{
auth
.inMemoryAuthentication()
.withUser("user").password("password").roles("USER")
.and()
.withUser("admin").password("admin").roles("USER", "ADMIN");
}
}
资源控制器
@RestController
public class ResourceController {
@RequestMapping(value = { "/user" }, produces = "application/json")
public Map<String, Object> user(OAuth2Authentication user) {
Map<String, Object> userDetails = new HashMap<>();
userDetails.put("user", user.getUserAuthentication().getPrincipal());
userDetails.put("authorities",
AuthorityUtils.
authorityListToSet(user.getUserAuthentication().getAuthorities()));
return userDetails;
}
}
最后配置 - application.yml 认证服务器
server:
port: 9090
contextPath: /auth
logging:
level:
org.springframework: INFO
org.springframework.security: DEBUG
此处未显示 login.html Thymeleaf 模板。
OAUTH 2 SSO 客户端 Web 应用程序
@SpringBootApplication
public class MyWebsiteApplication {
public static void main(String[] args) {
SpringApplication.run(MyWebsiteApplication.class, args);
}
}
网络安全配置
@Configuration
@EnableOAuth2Sso
public class WebSecurityConfigurer extends WebSecurityConfigurerAdapter {
@Override
protected void configure(HttpSecurity http) throws Exception {
http.authorizeRequests()
.antMatchers("/").permitAll() // Allow navigating to index
page,
.anyRequest().authenticated(); // but secure all the other URLs
}
}
网络控制器
@控制器
public class MyWebsiteController {
/**
* Default index page to verify that our application works.
*/
@RequestMapping("/")
@ResponseBody
public String helloWorld() {
return "Hello world!";
}
/**
* Return a ModelAndView which will cause the
'src/main/resources/templates/time.html' template to be rendered,
* with the current time.
*/
@RequestMapping("/time")
public ModelAndView time() {
ModelAndView mav = new ModelAndView("time");
mav.addObject("currentTime", getCurrentTime());
return mav;
}
private String getCurrentTime() {
return LocalTime.now().format(DateTimeFormatter.ISO_LOCAL_TIME);
}
}
客户端 Web 应用程序的应用程序配置 - application.yml
server:
port: 8080
contextPath: /
security:
oauth2:
client:
accessTokenUri: http://localhost:9090/auth/oauth/token
userAuthorizationUri: http://localhost:9090/auth/oauth/authorize
clientId: myauthserver
clientSecret: verysecretpassword
resource:
userInfoUri: http://localhost:9090/auth/user
此处未显示 time.html 页面的 Thymeleaf 模板。
一定有一些微妙的小配置错误或一些我不知道的错误。非常感谢任何帮助或想法。
解决方案
猜对了,获取的安全过滤器链的顺序已更改。这是 link 到
Spring 1.5.x release note
修改后的代码在这里,稍后会上传到Github。 auth 服务器配置的所有更改。
Spring 安全配置 - 删除 @Order 注释。
@Configuration
@EnableWebSecurity
public class WebSecurityConfigurer extends WebSecurityConfigurerAdapter {
@Override
protected void configure(HttpSecurity http) throws Exception {
http
.authorizeRequests()
.antMatchers("/login").permitAll()
.anyRequest().authenticated()
.and().csrf()
.and().formLogin().loginPage("/login");
}
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception
{
auth
.inMemoryAuthentication()
.withUser("user").password("password").roles("USER")
.and()
.withUser("admin").password("admin").roles("USER", "ADMIN");
}
}
然后将application.yml改成如下
server:
port: 9090
contextPath: /auth
logging:
level:
org.springframework: INFO
org.springframework.security: DEBUG
security:
oauth2:
resource:
filter-order : 3
就是这样,在 auth 服务器上进行身份验证后,时间显示在客户端应用程序 /time url 上。
我正在尝试将示例 Spring Boot 和 Spring Cloud Security with OAuth 从 Spring Boot 1.4.1 + Brixton.RELEASE 升级到 Spring启动 1.5.3+ Dalston.RELEASE。然而,经过了漫长的努力,却一无所获。
似乎出于某种原因,资源服务器安全过滤器链没有被触发。因此,对“/me”或“/user”的调用由默认的安全过滤器链处理。我在想这是否是订单的问题。但试图明确设置安全过滤器链的顺序如下
- 授权服务器 6
- 网络默认 5
- 资源服务器 3(硬编码 ??)
由于默认过滤器链正在处理请求,它总是转到登录页面,生成 HTML 并且 SSO 客户端(服务器端 thymeleaf web UI)失败。
源代码如下
授权服务器
@SpringBootApplication
public class MyAuthServerApplication {
public static void main(String[] args) {
SpringApplication.run(MyAuthServerApplication.class, args);
}
}
然后是授权服务器配置
@Configuration
@EnableAuthorizationServer
@Order(6)
public class AuthorizationServerConfigurer extends A
uthorizationServerConfigurerAdapter {
@Override
public void configure(ClientDetailsServiceConfigurer clients) throws
Exception {
clients.inMemory()
.withClient("myauthserver")
.secret("verysecretpassword")
.redirectUris("http://localhost:8080/")
.authorizedGrantTypes("authorization_code", "refresh_token")
.scopes("myscope")
.autoApprove(true);
}
}
然后资源服务器class
@Configuration
@EnableResourceServer
public class ResourceServerConfigurer extends
ResourceServerConfigurerAdapter {
@Override
public void configure(HttpSecurity http) throws Exception {
http.antMatcher("/user")
.authorizeRequests()
.anyRequest()
.authenticated();
}
}
Web MVC 配置
@Configuration
public class WebMvcConfigurer extends WebMvcConfigurerAdapter {
@Override
public void addViewControllers(ViewControllerRegistry registry) {
registry.addViewController("login").setViewName("login");
}
}
默认spring安全配置
@Configuration
@EnableWebSecurity
@Order(9)
public class WebSecurityConfigurer extends WebSecurityConfigurerAdapter {
@Override
protected void configure(HttpSecurity http) throws Exception {
http
.authorizeRequests()
.antMatchers("/login").permitAll()
.anyRequest().authenticated()
.and().csrf()
.and().formLogin().loginPage("/login");
}
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception
{
auth
.inMemoryAuthentication()
.withUser("user").password("password").roles("USER")
.and()
.withUser("admin").password("admin").roles("USER", "ADMIN");
}
}
资源控制器
@RestController
public class ResourceController {
@RequestMapping(value = { "/user" }, produces = "application/json")
public Map<String, Object> user(OAuth2Authentication user) {
Map<String, Object> userDetails = new HashMap<>();
userDetails.put("user", user.getUserAuthentication().getPrincipal());
userDetails.put("authorities",
AuthorityUtils.
authorityListToSet(user.getUserAuthentication().getAuthorities()));
return userDetails;
}
}
最后配置 - application.yml 认证服务器
server:
port: 9090
contextPath: /auth
logging:
level:
org.springframework: INFO
org.springframework.security: DEBUG
此处未显示 login.html Thymeleaf 模板。
OAUTH 2 SSO 客户端 Web 应用程序
@SpringBootApplication
public class MyWebsiteApplication {
public static void main(String[] args) {
SpringApplication.run(MyWebsiteApplication.class, args);
}
}
网络安全配置
@Configuration
@EnableOAuth2Sso
public class WebSecurityConfigurer extends WebSecurityConfigurerAdapter {
@Override
protected void configure(HttpSecurity http) throws Exception {
http.authorizeRequests()
.antMatchers("/").permitAll() // Allow navigating to index
page,
.anyRequest().authenticated(); // but secure all the other URLs
}
}
网络控制器
@控制器 public class MyWebsiteController {
/**
* Default index page to verify that our application works.
*/
@RequestMapping("/")
@ResponseBody
public String helloWorld() {
return "Hello world!";
}
/**
* Return a ModelAndView which will cause the
'src/main/resources/templates/time.html' template to be rendered,
* with the current time.
*/
@RequestMapping("/time")
public ModelAndView time() {
ModelAndView mav = new ModelAndView("time");
mav.addObject("currentTime", getCurrentTime());
return mav;
}
private String getCurrentTime() {
return LocalTime.now().format(DateTimeFormatter.ISO_LOCAL_TIME);
}
}
客户端 Web 应用程序的应用程序配置 - application.yml
server:
port: 8080
contextPath: /
security:
oauth2:
client:
accessTokenUri: http://localhost:9090/auth/oauth/token
userAuthorizationUri: http://localhost:9090/auth/oauth/authorize
clientId: myauthserver
clientSecret: verysecretpassword
resource:
userInfoUri: http://localhost:9090/auth/user
此处未显示 time.html 页面的 Thymeleaf 模板。
一定有一些微妙的小配置错误或一些我不知道的错误。非常感谢任何帮助或想法。
解决方案
猜对了,获取的安全过滤器链的顺序已更改。这是 link 到
Spring 1.5.x release note
修改后的代码在这里,稍后会上传到Github。 auth 服务器配置的所有更改。
Spring 安全配置 - 删除 @Order 注释。
@Configuration
@EnableWebSecurity
public class WebSecurityConfigurer extends WebSecurityConfigurerAdapter {
@Override
protected void configure(HttpSecurity http) throws Exception {
http
.authorizeRequests()
.antMatchers("/login").permitAll()
.anyRequest().authenticated()
.and().csrf()
.and().formLogin().loginPage("/login");
}
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception
{
auth
.inMemoryAuthentication()
.withUser("user").password("password").roles("USER")
.and()
.withUser("admin").password("admin").roles("USER", "ADMIN");
}
}
然后将application.yml改成如下
server:
port: 9090
contextPath: /auth
logging:
level:
org.springframework: INFO
org.springframework.security: DEBUG
security:
oauth2:
resource:
filter-order : 3
就是这样,在 auth 服务器上进行身份验证后,时间显示在客户端应用程序 /time url 上。