一、前记
记得很久之前面试美的,当时吹水微服务,被人问到一个问题:微服务鉴权如何处理的?嗯,很简单一个问题,但是懵逼了(水平不行啊),自然就挂了,后面就想以后吹水微服务一定要做好鉴权这一块的内容。
二、准备知识
Spring Security、OAuth2.0、Jwt;网上有很多内容,这里不赘述。
OAuth2.0主要学几种模式,如密码模式、客户端模式等等,这里我们使用密码模式。
三、参考文章
本文参考了这几个大神的文章,1)https://www.jianshu.com/p/24764aba1012?utm_source=oschina-app;
2)https://www.jianshu.com/p/59dea41787c9
第一个文章是Spring Cloud相关内容,不是特别适合入门,所以我去除了SC的内容;第一篇改为内置InMemory数据库;第一篇文章请求Jwt token使用了SC的FeignClient,返回的Jwt对象还自己写pojo定义了,实际上Spring Security OAuth已经有请求相关对象(ResourceOwnerPasswordAccessTokenProvider,谢谢第二篇),所以我进行了替换;第一篇文章认证服务器、资源服务器分开部署,有两个bean同名容易困扰,本篇认证服务器、资源服务器是统一部署的,没有混杂的东西,新手容易入手;第一篇还有一个Jwt公钥Public.cert直接保存在服务器读取的,不是很安全啊,我没有用这种方式。
可以说两篇融(chao)合(xi)了这两篇以后,加上自己的思考,就有了我这第三篇。
四、微服务请求流程
盗第一篇的图:
我是这样设计的,开放三个rest api对外提供访问:login、user、admin;其中user需要user权限的用户可以访问、admin需要admin用户权限、login无限制访问,用户名密码认证成功后返回access token,后续访问user、admin携带该token,权限无误后可以访问。
五、程序设计
1)WebSecurityConfig
功能:提供内置用户名密码数据库、提供AuthenticationManager给OAuth使用、配置需要认证的路径
@Configuration
@EnableWebSecurity
public class WebSecurityConfig extends WebSecurityConfigurerAdapter
a.建立test、admin、dba账户,对应不同权限;passwordEncoder是BCryptPasswordEncoder
@Autowired
private PasswordEncoder passwordEncoder;
@Bean
PasswordEncoder passwordEncoder(){
return new BCryptPasswordEncoder();
}
@Bean
public UserDetailsService userDetailsService(){
InMemoryUserDetailsManager manager = new InMemoryUserDetailsManager();
manager.createUser(User.withUsername("test").password(passwordEncoder.encode("test")).roles("USER").build());
manager.createUser(User.withUsername("admin").password(passwordEncoder.encode("admin")).roles("USER","ADMIN").build());
manager.createUser(User.withUsername("dba").password(passwordEncoder.encode("dba")).roles("USER","DBA").build());
return manager;
}
b.配置认证路径(Spring Secur