Spring 是非常流行和成功的 Java 应用开发框架,Spring Security 正是 Spring 家族中的成员。Spring Security 基于 Spring 框架,提供了一套 Web 应用安全性的完整解决方案。
SpringSecurity的核心功能:
用户认证(Authentication):系统判断用户是否能登录
用户授权(Authorization):系统判断用户是否有权限去做某些事情
SpringSecurity 特点:
Spring 技术栈的组成部分,与Spring 无缝整合。
全面的权限控制,能提供完整可扩展的认证和授权支持保护
专门为 Web 开发而设计。
重量级,需要引入各种家族组件与依赖
org.springframework.boot
spring-boot-starter-security
看控制台
去浏览器输入地址
验证成功后是这样的,出先404不要担心
权限概念
名称 |
英文名称 |
概念 |
主体 |
principal |
使用系统的用户或设备或从其他系统远程登录的用户等等 |
认证 |
authentication |
权限管理系统(通过登录操作)确认一个主体的身份,允许主体进入系统。简单说就是“主体”证明自己是谁。 |
授权 |
authorization |
给用户分配权限:将操作系统的“权力”“授予”“主体”,这样主体就具备了操作系统中特定功能的能力。 |
提交用户名和密码后,将对用户名和密码进行身份验证。 扩展了 AbstractAuthenticationProcessingFilter,因此下图应该看起来非常相似:
该图基于我们的 SecurityFilterChain 图。
UsernamePasswordAuthenticationToken HttpServletRequest
SecurityContextHolder 被清除。
RememberMeServices.loginFail被调用。 如果未配置“记住我”,则这是无操作。 请参阅 Javadoc 中的 RememberMeServices 接口。
AuthenticationFailureHandler被调用。 请参阅 Javadoc 中的 AuthenticationFailureHandler 类
SessionAuthenticationStrategy收到新登录的通知。 请参阅 Javadoc 中的 SessionAuthenticationStrategy 接口。
身份验证在 SecurityContextHolder 上设置。 请参阅 Javadoc 中的 SecurityContextPersistenceFilter 类。
RememberMeServices.loginSuccess被调用。 如果未配置“记住我”,则这是无操作。 请参阅 Javadoc 中的 RememberMeServices 接口。
ApplicationEventPublisher发布 .InteractiveAuthenticationSuccessEvent
被调用。通常,这是一个 ,当我们重定向到登录页面时,它会重定向到 ExceptionTranslationFilter 保存的请求。AuthenticationSuccessHandlerSimpleUrlAuthenticationSuccessHandler
UsernamePasswordAuthenticationFilter : 对/login 的 POST 请求做拦截,校验表单中用户名,密码。
发出post
name=username
name=password
在application.properties文件中配置用户名和密码
spring.security.user.name=admin
spring.security.user.password=admin
package com.aaa.config;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.core.authority.SimpleGrantedAuthority;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import java.util.ArrayList;
import java.util.List;
@Configuration
public class SecurityConfig extends WebSecurityConfigurerAdapter {
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
//创建 BCryptPasswordEncoder 的新实例
BCryptPasswordEncoder bCryptPasswordEncoder = new BCryptPasswordEncoder();
//使用编码器对密码进行编码
String password = bCryptPasswordEncoder.encode("123456");
//配置身份验证管理器
//用户1
auth.inMemoryAuthentication()
//设置密码编码器
.passwordEncoder(bCryptPasswordEncoder)
//创建新用户
.withUser("admin")
//Set the password
.password(password);
}
}
Title
package com.aaa.config;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.core.authority.SimpleGrantedAuthority;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import java.util.ArrayList;
import java.util.List;
@Configuration
public class SecurityConfig extends WebSecurityConfigurerAdapter {
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
/*------------------------------------------------------------------------*/
//资源
List authorities = new ArrayList<>();
//添加资源
authorities.add(new SimpleGrantedAuthority("resource"));
authorities.add(new SimpleGrantedAuthority("ROLE_CE"));
/*------------------------------------------------------------------------*/
//创建 BCryptPasswordEncoder 的新实例
BCryptPasswordEncoder bCryptPasswordEncoder = new BCryptPasswordEncoder();
//使用编码器对密码进行编码
String password = bCryptPasswordEncoder.encode("123456");
/*------------------------------------------------------------------------*/
/*------------------------------------------------------------------------*/
//配置身份验证管理器
//用户1
auth.inMemoryAuthentication()
//设置密码编码器
.passwordEncoder(bCryptPasswordEncoder)
//创建新用户
.withUser("admin")
//设置密码
.password(password)
//设置资源
.roles("user");
/*------------------------------------------------------------------------*/
//用户2
auth.inMemoryAuthentication()
//设置密码编码器
.passwordEncoder(bCryptPasswordEncoder)
//创建新用户
.withUser("root")
//设置密码
.password(password)
//设置权限
.roles("role")
//设置资源
.authorities(authorities);
/*------------------------------------------------------------------------*/
}
@Override
protected void configure(HttpSecurity http) throws Exception {
/*------------------------------------------------------------------------*/
// 开始 配置自定义的信息
http.formLogin().loginPage("/login.html")//路径前面必须加 /
.loginProcessingUrl("/login")//跟提交的路径一样
.usernameParameter("username")//登陆账号
.passwordParameter("userpassword")//登陆密码
.defaultSuccessUrl("/test");//登陆成功的跳转路径
/*------------------------------------------------------------------------*/
/*------------------------------------------------------------------------*/
http.authorizeRequests().antMatchers("/login.html", "login").permitAll();//不用验证
http.authorizeRequests().antMatchers("/test").hasRole("test");//必须有哪个权限才能访问
http.authorizeRequests().antMatchers("/test").hasAnyAuthority("resource");//必须有哪个资源才能访问
//其他路径进行验证
http.authorizeRequests().anyRequest().authenticated();
//关闭csrf保护
http.csrf().disable();
/*------------------------------------------------------------------------*/
}
}
相关方法: 角色和权限都可以设置多个,以逗号分开
方法名称 |
说明 |
hasAuthority |
如果当前的主体具有指定的权限,则可以访问 |
hasAnyAuthority |
如果当前的主体有任何提供的角色的话,就可以访问 |
hasRole |
如果用户具备给定角色就允许访问 |
hasAnyRole |
用户具备任何一个角色都可以访问 |
当User对象没有对应权限时会返回403错误
@EnableGlobalMethodSecurity(securedEnabled=true,prePostEnabled = true,jsr250Enabled=true)
注意:使用这个这个注解的时候对应的角色信息必须是以ROLE_**的形式出现,否则无法识别
@Secured({"ROLE_CE"})
@GetMapping
public String test(){
return "Hello World!";
}
注意配置文件中,必须添加ROLE_
注意:此注解不需要特别添加前缀ROLE_
controller
@RolesAllowed({"CE"})
@GetMapping
public String test(){
return "Hello World!";
}
注意:此注解不需要特别添加前缀ROLE_
controller
@PreAuthorize("hasRole('user')")
@GetMapping
public String test(){
return "Hello World!";
}
package com.aaa.servie;
import com.aaa.entiy.User;
import org.springframework.security.core.authority.SimpleGrantedAuthority;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.stereotype.Service;
import java.util.ArrayList;
import java.util.List;
@Service
public class TestService implements UserDetailsService {
@Override
public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {
BCryptPasswordEncoder bCryptPasswordEncoder = new BCryptPasswordEncoder();
String encode = bCryptPasswordEncoder.encode("111");
User user = new User("root",encode);
if (username.equals(user.getUserName())){
List authorities = new ArrayList<>();
authorities.add(new SimpleGrantedAuthority("ROLE_CE"));
return new org.springframework.security.core.userdetails.User(username,encode,authorities);
}
return null;
}
}
package com.aaa.config;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.core.authority.SimpleGrantedAuthority;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.security.crypto.password.PasswordEncoder;
import javax.annotation.Resource;
import java.util.ArrayList;
import java.util.List;
@Configuration
public class SecurityConfig extends WebSecurityConfigurerAdapter {
@Resource
protected UserDetailsService userDetailsService;
@Bean
public PasswordEncoder passwordEncoder(){
return new BCryptPasswordEncoder();
}
@Override
protected void configure(HttpSecurity http) throws Exception {
/*------------------------------------------------------------------------*/
// 开始 配置自定义的信息
http.formLogin().loginPage("/login.html")//路径前面必须加 /
.loginProcessingUrl("/login")//跟提交的路径一样
.usernameParameter("username")//登陆账号
.passwordParameter("userpassword")//登陆密码
.defaultSuccessUrl("/test");//登陆成功的跳转路径
/*------------------------------------------------------------------------*/
/*------------------------------------------------------------------------*/
http.authorizeRequests().antMatchers("/login.html", "login").permitAll();//不用验证
http.authorizeRequests().antMatchers("/test").hasRole("test");//必须有哪个权限才能访问
http.authorizeRequests().antMatchers("/test").hasAnyAuthority("resource");//必须有哪个资源才能访问
//其他路径进行验证
http.authorizeRequests().anyRequest().authenticated();
//关闭csrf保护
http.csrf().disable();
/*------------------------------------------------------------------------*/
}
@Override
protected void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.userDetailsService(userDetailsService).passwordEncoder(passwordEncoder());
}
}