spring security基本知识(二) 自定义认证
配置自定义的用户存储
我们在 SecurityConfig 的配置类中 重写了 configure(AuthenticationManagerBuilder auth) 方法,我们可以通过 AuthenticationManagerBuilder 这个构造器类使用不同的用户存储,如 inMemoryAuthentication()基于内存的,jdbcAuthentication()基于关系型数据库的.
通过查看AuthenticationManagerBuilder的源码可以发现里面还有一个方法 userDetailsService(),允许我们自定义用户存储的实现.如下:
userDetailsService()方法 需要传入参数 “UserDetailsService”。而UserDetailsService是一个接口所以我们需要实现接口的loadUserByUsername(String s)方法。根据给定的用户名来查找用户。
loadUserByUsername()方法会返回代表给定用户的UserDetails对象 。而这个UserDetail 又是个什么呢?我们再次产看其源码,发现这也是一个接口,也就是说我们还要实现这个 UserDetail接口.这个结构
封装了用户的登陆信息
好了,了解了 userDetailsService 方法的构造,我们就可以着手写代码了。首先定义一个 MyUserService 实现 UserDetailsService 接口.并在重写的 loadUserByUsername 方法中返回 UserDetail类型的对象即可。
/**
* @author cuiqq
* @description: TODO
* @date 2019-06-2115:36
*/
public class MyUserService implements UserDetailsService { @Override
public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException { //自定义用户存储数据来源,可以是从关系型数据库,非关系性数据库,或者其他地方获取用户数据。
User userEntity = new User("cuiqq", "123456");
//还可以在此设置账号的锁定,过期,凭据失效 等参数
//... // 设置 权限,可以是从数据库中查找出来的
ArrayList<GrantedAuthority> authorities = new ArrayList<>();
authorities.add(new SimpleGrantedAuthority("ROLE_USER"));
authorities.add(new SimpleGrantedAuthority("ROLE_ADMIN")); userEntity.setAuthorities(authorities);
return userEntity;
}
}
@Data
public class UserEntity implements UserDetails {
/**
* 用户名
*/
private String username; /**
* 密码
*/
private String password; /**
* 是否可用
*/
private Boolean enabled; /**
* 用户所拥有的权限
*/
private List<? extends GrantedAuthority> authorities; /**
* 用户的账号是否过期,过期的账号无法通过授权验证. true 账号未过期
*/
private Boolean accountNonExpired = true; /**
* 用户的账户是否被锁定,被锁定的账户无法通过授权验证. true 账号未锁定
*/
private Boolean accountNonLocked = true; /**
* 用户的凭据(pasword) 是否过期,过期的凭据不能通过验证. true 没有过期,false 已过期
*/
private Boolean credentialsNonExpired = true; public UserEntity(String username, String password, Boolean enabled) {
this.username = username;
this.password = password;
this.enabled = enabled;
} @Override
public Collection<? extends GrantedAuthority> getAuthorities() {
return authorities;
} @Override
public String getPassword() {
return password;
} @Override
public String getUsername() {
return username;
} @Override
public boolean isAccountNonExpired() {
return accountNonExpired;
} @Override
public boolean isAccountNonLocked() {
return accountNonLocked;
} @Override
public boolean isCredentialsNonExpired() {
return credentialsNonExpired;
} @Override
public boolean isEnabled() {
return enabled;
}
}
除了我们自定义的UserEntity外,还有一个 User,其实这就是Spring Security为我们实现好的 UserDetails 类.我们可以看到它的源码如下:
public class User implements UserDetails, CredentialsContainer { private static final long serialVersionUID = SpringSecurityCoreVersion.SERIAL_VERSION_UID; // ~ Instance fields
// ================================================================================================
private String password;
private final String username;
private final Set<GrantedAuthority> authorities;
private final boolean accountNonExpired;
private final boolean accountNonLocked;
private final boolean credentialsNonExpired;
private final boolean enabled; //...
}
由于源码太长,这里只贴出一部分,可以看到这里面也有我们在UserEntity定义的字段.其实也不奇怪了,本来我们的 UserEntity 就是按着User进行改造的嘛.
之所以自定义UserEntity,这里是为了方面初学者进行快速入门,相比于User我们的UserEntity还是很简单的.
现在 我们的 UserDetailsService 已经完成了,接下来就是在 SecurityConfig 的configure方法中使用了,如下:
/**
* 自定义用户存储
**/
@Configuration
@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter { @Override
public void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.userDetailsService(new MyUserService());
}
}
spring security基本知识(二) 自定义认证的更多相关文章
- 【Spring Security】六、自定义认证处理的过滤器
这里接着上一章的自定义过滤器,这里主要的是配置自定义认证处理的过滤器,并加入到FilterChain的过程.在我们自己不在xml做特殊的配置情况下,security默认的做认证处理的过滤器为Usern ...
- Spring Boot+Spring Security+JWT 实现 RESTful Api 认证(二)
Spring Boot+Spring Security+JWT 实现 RESTful Api 认证(二) 摘要 上一篇https://javaymw.com/post/59我们已经实现了基本的登录和t ...
- [转]Spring Security学习总结二
原文链接: http://www.blogjava.net/redhatlinux/archive/2008/08/20/223148.html http://www.blogjava.net/red ...
- Spring Security教程(五):自定义过滤器从数据库从获取资源信息
在之前的几篇security教程中,资源和所对应的权限都是在xml中进行配置的,也就在http标签中配置intercept-url,试想要是配置的对象不多,那还好,但是平常实际开发中都往往是非常多的资 ...
- Spring Security教程(八):用户认证流程源码详解
本篇文章主要围绕下面几个问题来深入源码: 用户认证流程 认证结果如何在多个请求之间共享 获取认证用户信息 一.用户认证流程 上节中提到Spring Security核心就是一系列的过滤器链,当一个请求 ...
- spring security基本知识(一)
spring security基本知识(一) Spring Security是为基于Spring的应用程序提供声明式安全保护的安全 性框架.Spring Security提供了完整的安全性解决方案,它 ...
- Spring Security技术栈开发企业级认证与授权(一)环境搭建
本项目是基于慕课网的Spring Security技术栈开发企业级认证与授权,采用IDEA开发,本文章用来记录该项目的学习过程. 慕课网视频:https://coding.imooc.com/clas ...
- Spring Security使用数据库数据完成认证--练气后期2
写在前面 没错,这篇文章还是练气后期!但作者我相信筑基指日可待! 在前一篇文章当中,我们简单地分析了一下Spring Security的认证流程,知道了如果想要实现对自己用户数据(账户.角色.权限)的 ...
- Spring Boot+Spring Security+JWT 实现 RESTful Api 认证(一)
标题 Spring Boot+Spring Security+JWT 实现 RESTful Api 认证(一) 技术 Spring Boot 2.Spring Security 5.JWT 运行环境 ...
随机推荐
- Flask中的request模板渲染Jinja以及Session
Flask中的request与django相似介绍几个常用的以后用的时候直接查询即可 1.request from flask import request(用之前先引用,与django稍有不同) r ...
- DNS 搜索 - dig 命令
dig 命令_互动百科 示例: # 全部 dig www.zjffun.com # 只显示 ANSWER SECTION dig www.zjffun.com +noall +answer
- ES6数值的拓展
二进制和八进制表示法 ES6 提供了二进制和八进制数值的新的写法,分别用前缀0b(或0B)和0o(或0O)表示. 如果要将0b和0o前缀的字符串数值转为十进制,要使用Number方法 Number(' ...
- dcef3 指出一个坑
dcef3 指出一个坑 http://ju.outofmemory.cn/entry/80119 BccSafe's Blog 2014-06-11 2388 阅读 dcef3提供了TChromi ...
- 《Using Databases with Python》 Week2 Basic Structured Query Language 课堂笔记
Coursera课程<Using Databases with Python> 密歇根大学 Week2 Basic Structured Query Language 15.1 Relat ...
- 第十一周总结 继承、this和super的区别和用法、方法的重写和重载
一.继承 1.子类继承父类,通过一个关键字 extends 2.子类的对象可以调用父类中的(public protected)属性和方法 当作自己的来使用 3.子类可以添加自己独有的属性和方法 4.子 ...
- XSS注入常用语句(整理)
<script>alert('hello,gaga!');</script> //经典语句,哈哈! >"'><img src="javas ...
- 多线程16-SpinWait
); isCompleted = )); isCompleted = ); isCompleted = true; ...
- [转帖]NetSuite 进入中国市场满一年,甲骨文公布首份成绩单
NetSuite 进入中国市场满一年,甲骨文公布首份成绩单 https://baijiahao.baidu.com/s?id=1617073148682281883&wfr=spider&am ...
- RocketMQ事务性消息及持久化
TransactionProducer(事务消息): 在分布式系统中,我们时常会遇到分布式事务的问题,除了常规的解决方案之外,我们还可以利用RocketMQ的事务性消息来解决分布式事务的问题.Rock ...