SpringSecurity--基本使用--1

tech2022-11-22  94

1、简介

应用程序的安全性通常体现在两个方面:认证和授权。 认证是确认某主体在某系统中是否合法、可用的过程。这里的主体既可以是登录系统的用户,也 可以是接入的设备或者其他系统。 授权是指当主体通过认证之后,是否允许其执行某项操作的过程。 这些概念并非Spring Security独有,而是应用安全的基本关注点。Spring Security可以帮助我们更便 捷地完成认证和授权。

2、基本使用

1、依赖引入

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> <modelVersion>4.0.0</modelVersion> <groupId>com.my.test.security</groupId> <artifactId>SpringSecurityTest</artifactId> <version>0.0.1-SNAPSHOT</version> <parent> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-parent</artifactId> <version>2.1.4.RELEASE</version> </parent> <dependencies> <!-- SpringBoot依赖 --> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> <!-- SpringSecurity --> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-security</artifactId> </dependency> <!-- jdbc --> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-jdbc</artifactId> </dependency> <!-- mysql --> <dependency> <groupId>mysql</groupId> <artifactId>mysql-connector-java</artifactId> </dependency> <!-- lombok依赖 --> <dependency> <groupId>org.projectlombok</groupId> <artifactId>lombok</artifactId> </dependency> <!-- --> <dependency> <groupId>org.springframework</groupId> <artifactId>spring-context</artifactId> </dependency> </dependencies> </project>

2、controller及启动类

@SpringBootApplication @RestController public class SecurityApp { @GetMapping("/") public String hello() { return "Welcome to hello page"; } public static void main(String[] args) { SpringApplication.run(SecurityApp.class, args); } }

3、配置文件配置

server: port: 8888 spring: security: user: name: root password: Admin123 datasource: driver-class-name: com.mysql.cj.jdbc.Driver url: jdbc:mysql://localhost:3306/my_test?useUnicode=true&characterEncoding=utf8&useSSL=false&serverTimezone=GMT%2B8 username: root password: 666666

4、测试 访问:localhost:8888时,会进行验证,输入配置好的用户名密码便可进入访问的controller

3、WebSecurityConfigurerAdapter实现路由及身份权限验证

1、依赖 同2中依赖

2、配置类-继承WebSecurityConfigurerAdapter并进行设置

@EnableWebSecurity public class WebSecurityConfig extends WebSecurityConfigurerAdapter { @Override protected void configure(HttpSecurity http) throws Exception { /** * session管理策略 * ALWAYS---总是创建HttpSession IF_REQUIRED---Spring Security只会在需要时创建一个HttpSession NEVER---Spring Security不会创建HttpSession,但如果它已经存在,将可以使用HttpSession STATELESS---Spring Security永远不会创建HttpSession,它不会使用HttpSession来获取SecurityContext */ http.sessionManagement().sessionCreationPolicy(SessionCreationPolicy.NEVER); http.authorizeRequests() /** * 设置用户及角色认证,控制controller的访问权限 */ .antMatchers("/user/**").hasRole("USER") .antMatchers("/manager").hasRole("MANAGER") //登出跳转 .antMatchers("/logoutSuccess").permitAll() .antMatchers("/").permitAll() .and() .formLogin() //基于表单登录 .permitAll() //允许访问登录 /* 指定登录页 */ //.loginPage("/login") /* 指定登录时访问的URL */ //.loginProcessingUrl("/security/login") .and() .logout() /*退出时访问的url*/ .logoutUrl("/logout") /** * 注意logoutSuccessUrl不要与logoutSuccessHandler一起使用,否则logoutSuccessHandler将失效。 */ /*退出成功后要做的操作(如记录日志),和logoutSuccessUrl互斥*/ //.logoutSuccessHandler(new CoreqiLogoutSuccessHandler()) /*退出成功后跳转的页面--需配置权限,否则会转向登录页*/ .logoutSuccessUrl("/logoutSuccess") /*退出时要删除的Cookies的名字*/ //.deleteCookies("JSESSIONID") .and() //csrf是Spring Security提供的跨站请求伪造防护功能 .csrf().disable(); super.configure(http); } @Override protected void configure(AuthenticationManagerBuilder auth) throws Exception { /** * 普通用户权限设置 */ auth.inMemoryAuthentication() .passwordEncoder(new BCryptPasswordEncoder()) .withUser("user") /*密码需进行编码存储,否则匹配时,会自动进行解码操作*/ .password(new BCryptPasswordEncoder().encode("user123")).roles("USER"); /** * 管理员权限设置 */ auth.inMemoryAuthentication() .passwordEncoder(new BCryptPasswordEncoder()).withUser("manager") .password(new BCryptPasswordEncoder().encode("manager123")).roles("MANAGER"); } }

3、controller层代码

@SpringBootApplication @RestController public class SecurityApp { @GetMapping("/") public String hello() { return "Welcome to hello page"; } @GetMapping("/user") public String userPage() { return "user page"; } @GetMapping("/manager") public String managerPage() { return "manager page"; } @GetMapping("/logoutSuccess") public String logoutPage() { return "logout success!"; } public static void main(String[] args) { SpringApplication.run(SecurityApp.class, args); } }

4、使用SpringSecurity结合SpringDataJpa实现RBAC模式权限管理

1、使用登录成功/失败后置处理–Handler 成功Handler

@Component public class LoginSuccessHandler implements AuthenticationSuccessHandler{ @Override public void onAuthenticationSuccess(HttpServletRequest request, HttpServletResponse response, Authentication authentication) throws IOException, ServletException { response.setContentType("application/json; charset=utf-8"); response.sendRedirect("/user"); } }

失败Handler

@Component public class LoginFailureHandler implements AuthenticationFailureHandler { @Override public void onAuthenticationFailure(HttpServletRequest request, HttpServletResponse response, AuthenticationException exception) throws IOException, ServletException { System.out.println("登录失败!"); response.sendRedirect("/logoutFailure"); } }

2、实体类继承UserDetails并实现authorities的list以及dao接口 实体类

@Entity @Table(name = "security_user") @Data public class SecurityUser implements UserDetails{ private static final long serialVersionUID = 1L; @Id @GeneratedValue(strategy = GenerationType.IDENTITY) @Column(name = "id") private Integer id; @Column(name = "username") private String username; @Column(name = "password") private String password; /*GrantedAuthority接口的默认实现SimpleGrantedAuthority*/ @ElementCollection(targetClass = GrantedAuthority.class) private List<GrantedAuthority> authorities; @Override public Collection<? extends GrantedAuthority> getAuthorities() { return this.authorities; } @Override public boolean isAccountNonExpired() { // TODO Auto-generated method stub return true; } @Override public boolean isAccountNonLocked() { // TODO Auto-generated method stub return true; } @Override public boolean isCredentialsNonExpired() { // TODO Auto-generated method stub return true; } @Override public boolean isEnabled() { // TODO Auto-generated method stub return true; } }

dao接口

public interface UserDao extends JpaRepository<SecurityUser, Integer>, JpaSpecificationExecutor<SecurityUser> { @Query(value = "select * from security_user as u where u.username = ?1",nativeQuery = true) SecurityUser getUserByUsername(String username); }

3、实现UserDetailsService并配置user

@Service public class UserDetailServiceImp implements UserDetailsService { @Autowired private UserDao userDao; @Override public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException { PasswordEncoder encoder = PasswordEncoderFactories.createDelegatingPasswordEncoder(); SecurityUser user = userDao.getUserByUsername(username); user.setUsername(username); user.setPassword(encoder.encode(user.getPassword())); //user.setPassword(user.getPassword()); List<GrantedAuthority> authorities = new ArrayList<GrantedAuthority>(); GrantedAuthority authority = new SimpleGrantedAuthority("ROLE_USER"); authorities.add(authority); user.setAuthorities(authorities); return user; } }

4、WebSecurityConfig注入UserDetailsService实现类及其他配置

@EnableWebSecurity public class WebSecurityConfig extends WebSecurityConfigurerAdapter { @Autowired private LoginSuccessHandler successHandler; @Autowired private LoginFailureHandler failureHandler; @Autowired private UserDetailsService userDetailServiceImp; @Override protected void configure(HttpSecurity http) throws Exception { /** * session管理策略 ALWAYS---总是创建HttpSession IF_REQUIRED---Spring * Security只会在需要时创建一个HttpSession NEVER---Spring * Security不会创建HttpSession,但如果它已经存在,将可以使用HttpSession STATELESS---Spring * Security永远不会创建HttpSession,它不会使用HttpSession来获取SecurityContext */ http.sessionManagement().sessionCreationPolicy(SessionCreationPolicy.NEVER); http.authorizeRequests() /** * 设置用户及角色认证,控制controller的访问权限 */ .antMatchers("/user/**").hasRole("USER") .antMatchers("/manager").hasRole("MANAGER") // 登出跳转 .antMatchers("/logoutSuccess").permitAll() .antMatchers("/").permitAll().and().formLogin() // 基于表单登录 .permitAll() // 允许访问登录 .successHandler(successHandler).failureHandler(failureHandler) /* 指定登录页 */ // .loginPage("/login") /* 指定登录时访问的URL */ // .loginProcessingUrl("/security/login") .and().logout() /* 退出时访问的url */ .logoutUrl("/logout") /** * 注意logoutSuccessUrl不要与logoutSuccessHandler一起使用,否则logoutSuccessHandler将失效。 */ /* 退出成功后要做的操作(如记录日志),和logoutSuccessUrl互斥 */ // .logoutSuccessHandler(new CoreqiLogoutSuccessHandler()) /* 退出成功后跳转的页面--需配置权限,否则会转向登录页 */ .logoutSuccessUrl("/logoutSuccess") /* 退出时要删除的Cookies的名字 */ // .deleteCookies("JSESSIONID") .and() // csrf是Spring Security提供的跨站请求伪造防护功能 .csrf().disable(); super.configure(http); } @Override protected void configure(AuthenticationManagerBuilder auth) throws Exception { auth.userDetailsService(userDetailServiceImp); } }
最新回复(0)