浅谈spring security入门
作者:知识追寻者 发布时间:2023-02-20 04:48:58
一 介绍
本节给知识追寻者给大家带来的是springSecurity入门篇,主要是简述下springSecrurity的启动原理和简单的入门搭建;
二 核心模块介绍
spring-security-core ; 包含核心身份验证和access-contol类和接口,远程支持和基本配置AP;
spring-security-web: web , url登陆验证和访问控制;
spring-security-config: 支持xml 或者java注解配置;
当然其模块远不止这些,比如CAS,ALC,Aspects,OpenI等等,对于入门我们了解核心即可;
三 入门搭建
3.1 依赖
springboot 2.3.0
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-security</artifactId>
</dependency>
3.2 控制层
控制层定义一个接口,用于浏览器请求,请求成功后会返回 hello zszxz
;
@GetMapping("hello")
public String hello() {
return "hello zszxz";
}
3.3 访问登陆页
启动项目
访问 localhost:8080/hello 会自动跳转至localhost:8080/login
可以看到 接口就被保护起来了,访问接口需要进行账号密码登陆;那么账号密码在哪里?看tiao控制台打印的日志
如下所示,一串uuid就是登陆密码;账号是 user;账号,密码输入后就会跳转至 localhost:8080/hello ;
.UserDetailsServiceAutoConfiguration :
Using generated security password: 8f5b8238-9b35-482f-b2a5-bf440af5271b
3.4 登陆原理解析
由日志打印可以看出 是在 UserDetailsServiceAutoConfiguration
类中发现的密码;我们点击该类发现有个
inMemoryUserDetailsManager
方法 里面有 properties.getUser(); 即获取用户,说明用户信息来自 SecurityProperties
;
@Lazy
public InMemoryUserDetailsManager inMemoryUserDetailsManager(SecurityProperties properties, ObjectProvider<PasswordEncoder> passwordEncoder) {
User user = properties.getUser();
List<String> roles = user.getRoles();
return new InMemoryUserDetailsManager(new UserDetails[]{org.springframework.security.core.userdetails.User.withUsername(user.getName()).password(this.getOrDeducePassword(user, (PasswordEncoder)passwordEncoder.getIfAvailable())).roles(StringUtils.toStringArray(roles)).build()});
}
点击 SecurityProperties
类其有个内部静态类User, 如下所示,账号就是user, 密码就是UUID; roles是个ArrayList;配置文件的前缀 “spring.security”
@ConfigurationProperties(
prefix = "spring.security"
)
public class SecurityProperties {
// 此处省略.........
public static class User {
private String name = "user";
private String password = UUID.randomUUID().toString();
private List<String> roles = new ArrayList();
private boolean passwordGenerated = true;
// 此处省略.........
现在我们通过配置文件的方式改变账号密码,在application.yml配置账号密码如下
spring:
security:
user:
password: zszxz
name: zszxz
重启服务,访问http://localhost:8080/login 此时 的填入的表单账号密码就是zszxz
; 而且发现 控制台不再打印出uuid ;
3.5 springSecurity基本原理
仔细检测日志信息, 可以发现springSecurity模块的日志打印信息如下,其实现原理就是通过一串的Servlet过滤器进行基本实现,最后一个是FilterSecurityInterceptor
* ;
[org.springframework.security.web.context.request.async.WebAsyncManagerIntegrationFilter@248deced, org.springframework.security.web.context.SecurityContextPersistenceFilter@677b8e13, org.springframework.security.web.header.HeaderWriterFilter@30331109, org.springframework.security.web.csrf.CsrfFilter@1bbae752, org.springframework.security.web.authentication.logout.LogoutFilter@64030b91, org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter@78faea5f,
...............
.intercept.FilterSecurityInterceptor@2b4c3c29
来自官网的图片如下;FilterChain 中包含了 Filter 和 Servlet , 其能够很快速的处理所有的URL请求; 当然每个具体的Filter 功能都不同,以后可能提到,有兴趣的读者也可以参照官网学习;
比较重要的Filter
UsernamePasswordAuthenticationFilter
DigestAuthenticationFilter
BasicAuthenticationFilter
ExceptionTranslationFilter
FilterSecurityInterceptor
四 加密方式
官网有列出 基于 withDefaultPasswordEncoder 方式 创建 用户,这样并不是很推荐,原因是其账号密码会暴露在内存和编译的源码中,并不是很安全,如果要用于生产环境还需要对密码进行一次hash或者加密;
UserBuilder users = User.withDefaultPasswordEncoder();
User user = users
.username("user")
.password("password")
.roles("USER")
.build();
User admin = users
.username("admin")
.password("password")
.roles("USER","ADMIN")
.build();
官方提供了好多种其它方式进行加密:
DelegatingPasswordEncoder
BCryptPasswordEncoder
Argon2PasswordEncoder
Pbkdf2PasswordEncoder
SCryptPasswordEncoder
它们的使用方式都差不多,示例如下,在使用时替换对应的加密对象即可;
SCryptPasswordEncoder encoder = new SCryptPasswordEncoder();
String result = encoder.encode("myPassword");
assertTrue(encoder.matches("myPassword", result));
五 参考文档
https://docs.spring.io/spring-security/site/docs/5.3.3.BUILD-SNAPSHOT/reference/html5/
来源:https://blog.csdn.net/youku1327/article/details/106560125


猜你喜欢
- 本文实例讲述了Android基于ListView实现类似Market分页加载效果。分享给大家供大家参考,具体如下:最近几天研究ListVie
- 本文实例讲述了Android编程实现全局获取Context及使用Intent传递对象的方法。分享给大家供大家参考,具体如下:一、全局获取 C
- Java for循环几种写法整理概要:J2SE 1.5提供了另一种形式的for循环。借助这种形式的for循环,可以用更简单地方式来遍历数组和
- 基于Java语言实现Socket通信由于近日项目需求,需要在服务器中增加Socket通信的功能,接收硬件设备发送的心跳包和相关数据,因此又重
- springboot的最强大的就是那些xxxAutoconfiguration,但是这些xxxAutoConfiguration又依赖那些s
- JetBrains 系列产品(IDEA、Pycharm 等)使用本站破解教程 (opens new window),在输入激活码时,部分小伙
- 具体代码如下所示:public class Parent { public static int a = parentStati
- 前言这篇博客介绍Java环境的配置,主要是安装JDK,以及path、JAVA_hOME、CLASSPAT的配置,还会介绍配置这些的原因。一.
- 访问静态资源的配置及顺序今天在玩SpringBoot的demo的时候,放了张图片在resources目录下,启动区访问的时候,突然好奇是识别
- 学习时,接触使用到IDEA这个开发工具。在用IDEA开发的时候,需要创建工程。以下介绍各类型项目的新建。一、 springboot工程简介:
- Java 中HttpURLConnection附件上传的实例详解整合了一个自己写的采用Http做附件上传的工具,分享一下!示例代码:/**
- 任何一个类都是Class类的实例对象,这个实例对象有三种表示方式第一种表示方式(任何一个类都有一个隐含的静态成员变量class):Class
- 前言作为一个新手,最近在学习C#,自己折腾弄了个简单的小说爬虫,实现了把小说内容爬下来写入txt,还只能爬指定网站。第一次搞爬虫,涉及到了网
- MojoUnityJson 是使用C#实现的JSON解析器 ,算法思路来自于游戏引擎Mojoc的C语言实现 Json.h 。借助C#的类库,
- W3C制定了XML DOM标准。很多编程语言中多提供了支持W3C XML DOM标准的API。我在之前的文章中介绍过如何使用Javascri
- 本文示例实现了Android退出时关闭所有Activity的功能,分享给大家供大家参考之用。具体方法如下:一般来说,在Android退出时,
- 本文章使用C#编程,制作一个端口扫描器,能够扫描本机有哪些端口开放了,并显示出来,分别使用单线程和多线程进行了比较。编译软件:Visual
- 一个简单的网格布局activity_main.xml<?xml version="1.0" encoding=&q
- 本文实例讲述了Android编程设计模式之抽象工厂模式。分享给大家供大家参考,具体如下:一、介绍抽象工厂模式(Abstract Factor
- 本文实例讲述了JAVA线程池原理。分享给大家供大家参考,具体如下:线程池的优点1、线程是稀缺资源,使用线程池可以减少创建和销毁线程的次数,每