3. SpringSecurity与JWT整合

依赖:

<dependencies><dependency><groupId>org.mybatis.spring.boot</groupId><artifactId>mybatis-spring-boot-starter</artifactId><version>2.1.4</version></dependency><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-web</artifactId></dependency><dependency><groupId>io.jsonwebtoken</groupId><artifactId>jjwt</artifactId><version>0.9.1</version></dependency><dependency><groupId>com.alibaba</groupId><artifactId>druid-spring-boot-starter</artifactId><version>1.1.21</version></dependency><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-security</artifactId></dependency><dependency><groupId>mysql</groupId><artifactId>mysql-connector-java</artifactId><scope>runtime</scope></dependency><dependency><groupId>org.projectlombok</groupId><artifactId>lombok</artifactId><optional>true</optional></dependency><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-test</artifactId><scope>test</scope><exclusions><exclusion><groupId>org.junit.vintage</groupId><artifactId>junit-vintage-engine</artifactId></exclusion></exclusions></dependency>
</dependencies>

application.properties:

spring.thymeleaf.cache=false
spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver
spring.datasource.url=jdbc:mysql://localhost:3306/springsecurity001?useUnicode=true&characterEncoding=UTF-8&serverTimezone=GMT%2B8
spring.datasource.username=root
spring.datasource.password=123456
spring.datasource.type=com.alibaba.druid.pool.DruidDataSource
mybatis.mapper-locations=classpath:mapper/*.xml

启动类SecurityJwtApplication:

@SpringBootApplication
@MapperScan("com.blu.mapper")
public class SecurityJwtApplication {public static void main(String[] args) {SpringApplication.run(SecurityJwtApplication.class, args);}@Beanpublic BCryptPasswordEncoder bcryptPasswordEncoder(){return new BCryptPasswordEncoder();}}

MyUser:

@Data
public class MyUser implements UserDetails {private Integer id;private String name;private String password;private List<MyRole> roles;@JsonIgnore@Overridepublic Collection<? extends GrantedAuthority> getAuthorities() {return roles;}@JsonIgnore@Overridepublic String getUsername() {return name;}@JsonIgnore@Overridepublic boolean isAccountNonExpired() {return true;}@JsonIgnore@Overridepublic boolean isAccountNonLocked() {return true;}@JsonIgnore@Overridepublic boolean isCredentialsNonExpired() {return true;}@JsonIgnore@Overridepublic boolean isEnabled() {return true;}}

MyRole:

@Data
public class MyRole implements GrantedAuthority {private Integer id;private String name;@JsonIgnore@Overridepublic String getAuthority() {return name;}}

MyUserMapper:

public interface MyUserMapper {MyUser findByName(String name);
}
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd"><mapper namespace="com.blu.mapper.MyUserMapper"><resultMap type="com.blu.entity.MyUser" id="myUserMap"><id column="uid" property="id"></id><result column="uname" property="name"></result><result column="password" property="password"></result><collection property="roles" ofType="com.blu.entity.MyRole"><id column="rid" property="id" /><result column="rname" property="name" /></collection></resultMap><select id="findByName" parameterType="String"resultMap="myUserMap">select u.id uid,u.name uname,u.password,r.id rid,r.name rnamefrom user u,role r,role_user ur where u.name = #{name} and ur.user_id = u.id and ur.role_id = r.id</select>
</mapper>

UserService:

public interface UserService extends UserDetailsService {}

UserServiceImpl:

@Service
public class UserServiceImpl implements UserService {@Autowiredprivate MyUserMapper myUserMapper;@Overridepublic UserDetails loadUserByUsername(String username) throws UsernameNotFoundException {MyUser myUser = myUserMapper.findByName(username);return myUser;}}

JwtLoginFilter:

public class JwtLoginFilter extends AbstractAuthenticationProcessingFilter {public JwtLoginFilter(String defaultFilterProcessesUrl, AuthenticationManager authenticationManager) {super(new AntPathRequestMatcher(defaultFilterProcessesUrl));setAuthenticationManager(authenticationManager);}/*** 从登录参数json数据中获取用户名密码,然后调用AuthenticationManager.authenticate()方法进行校验。*/@Overridepublic Authentication attemptAuthentication(HttpServletRequest req, HttpServletResponse resp) throws AuthenticationException, IOException, ServletException {//将用户传的json数据转为user对象MyUser user = new ObjectMapper().readValue(req.getInputStream(),MyUser.class);return getAuthenticationManager().authenticate(new UsernamePasswordAuthenticationToken(user.getUsername(),user.getPassword()));}/*** 校验成功*/@Overrideprotected void successfulAuthentication(HttpServletRequest request, HttpServletResponse response, FilterChain chain, Authentication authResult) throws IOException, ServletException {Collection<? extends GrantedAuthority> authorities = authResult.getAuthorities();StringBuffer sb = new StringBuffer();for (GrantedAuthority authority : authorities) {sb.append(authority.getAuthority()).append(",");}String jwt = Jwts.builder().claim("authorities", sb).setSubject(authResult.getName()).setExpiration(new Date(System.currentTimeMillis() + 60 * 60 * 1000))//设置过期时间.signWith(SignatureAlgorithm.HS512, "root@123")//设置加密方式,以及key.compact();//设置登录成功后返回的信息Map<String,String> map = new HashMap<>();map.put("token",jwt);map.put("msg","登录成功");response.setContentType("application/json;charset=utf-8");PrintWriter writer = response.getWriter();writer.write(new ObjectMapper().writeValueAsString(map));writer.flush();writer.close();}/*** 校验失败*/@Overrideprotected void unsuccessfulAuthentication(HttpServletRequest request, HttpServletResponse response, AuthenticationException failed) throws IOException, ServletException {Map<String,String> map = new HashMap<>();map.put("msg","登录失败");response.setContentType("application/json;charset=utf-8");PrintWriter writer = response.getWriter();writer.write(new ObjectMapper().writeValueAsString(map));writer.flush();writer.close();}
}

JwtFilter:

public class JwtFilter extends GenericFilterBean {@Overridepublic void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {HttpServletRequest req =  (HttpServletRequest) servletRequest;//从请求头中获取tokenString jwtToken = req.getHeader("authorization");Jws<Claims> jws = Jwts.parser().setSigningKey("root@123").parseClaimsJws(jwtToken.replace("Bearer", ""));Claims claims = jws.getBody();String username = claims.getSubject();//获取角色List<GrantedAuthority> authorities = AuthorityUtils.commaSeparatedStringToAuthorityList((String) claims.get("authorities"));UsernamePasswordAuthenticationToken token = new UsernamePasswordAuthenticationToken(username,"",authorities);SecurityContextHolder.getContext().setAuthentication(token);filterChain.doFilter(servletRequest,servletResponse);}
}

测试接口:

@RestController
public class StringController {@GetMapping("hello")public String hello() {return "hello BLU!";}@GetMapping("hi")public String hi() {return "hi everyone!";}@GetMapping("admin")public String admin() {return "hello admin!";}}

Security配置类:

@EnableWebSecurity
public class SecurityConfig extends WebSecurityConfigurerAdapter{@Autowiredprivate UserServiceImpl userServiceImpl;@Autowiredprivate BCryptPasswordEncoder bcryptPasswordEncoder;@Overrideprotected void configure(HttpSecurity http) throws Exception {http.authorizeRequests().antMatchers(HttpMethod.GET,"/hi").permitAll().antMatchers("/hello").hasRole("vip1").antMatchers("/admin").hasRole("admin");http.formLogin().loginPage("/tologin").usernameParameter("name").passwordParameter("password").loginProcessingUrl("/login");http.csrf().disable();http.addFilterBefore(new JwtLoginFilter("/login",authenticationManager()),UsernamePasswordAuthenticationFilter.class).addFilterBefore(new JwtFilter(),UsernamePasswordAuthenticationFilter.class);}@Overrideprotected void configure(AuthenticationManagerBuilder auth) throws Exception {auth.userDetailsService(userServiceImpl).passwordEncoder(bcryptPasswordEncoder);}}

测试错误密码登录:

测试正确密码登录:

测试访问(有权限):

测试访问(无权限):

测试访问(错误token):

JWT教程_2 SpringSecurity与JWT整合相关推荐

  1. JWT 教程_1 SpringBoot与JWT整合

    https://gitee.com/fakerlove/spring-security 文章目录 1. 介绍 2. SpringBoot与JWT整合 2.1 JWT的结构: 2.2 JWT的使用测试: ...

  2. JWT教程_3 oauth和JWT 整合

    https://gitee.com/fakerlove/spring-security 4. oauth和JWT 整合 编写jwt 类 package com.example.demo3.config ...

  3. SpringSecurity与JWT认证

    SpringSecurity 教程 1. 简介 1.1 概念 1.2 入门案例 1.3 自定义登录逻辑 1.4 自定义登录页面 1.5 自定用户名参数 1.5 自定义成功处理器 1.6 登录失败处理器 ...

  4. GitHub开源项目学习 电商系统Mall (五) mall整合SpringSecurity和JWT实现认证和授权(二)

    mall整合SpringSecurity和JWT实现认证和授权(二) https://github.com/macrozheng/mall 登录注册功能实现 UmsAdminController类 实 ...

  5. GitHub开源项目学习 电商系统Mall (四) mall整合SpringSecurity和JWT实现认证和授权(一)

    mall整合SpringSecurity和JWT实现认证和授权(一) https://github.com/macrozheng/mall 跳过了官方Learning中较简单的Swagger-UI的实 ...

  6. 商城项目(三)整合SpringSecurity和JWT实现认证和授权

    整合SpringSecurity和JWT实现认证和授权 环境搭建 SpringSecurity JWT Hutool 项目使用表说明 ums_admin:后台用户表 ums_role:后台用户角色表 ...

  7. jwt判断token是否过期_4spring-security5整合jwt做登录、权限验证,全网最全!!!可用...

    github源码: https://github.com/gyb123456/spring-security5-jwt,最烦那些写文档只截图一半还不给源码的人,要不你就截全图,要不就给源码! 前言: ...

  8. SpringSecurity,jwt oathu sso,YeZiJie

    Spring Security 中文文档 参考手册 中文版 (springcloud.cc) 一 springsecurity 1 SpringSecurity框架简介 安全框架:解决系统安全问题的框 ...

  9. SpringBoot + SpringSecurity + Mybatis-Plus + JWT + Redis 实现分布式系统认证和授权(刷新Token和Token黑名单)

    1. 前提   本文在基于SpringBoot整合SpringSecurity实现JWT的前提中添加刷新Token以及添加Token黑名单.在浏览之前,请查看博客:   SpringBoot + Sp ...

最新文章

  1. C# Task的使用
  2. 【Java面试题】3 Java中使用final关键字修饰一个变量时,是引用不能变,还是引用的对象不能变?超详细解析...
  3. jacoco入门_代码覆盖度工具jacoco的入门
  4. php如何按降序,PHP数组如何按键名实现降序排列
  5. Altera的几个常用的Synthesis attributes(转载)
  6. 装饰器3--装饰器作用原理
  7. 我的第一个Python程序(简单的用户名密码登录程序)
  8. vue向ifarm传值_vue组件间传值
  9. 阿里云服务器ECS云盾提醒网站被WebShell木马后门分析与对策
  10. oracle 导入性能,EXP,EXPDP数据导入本地性能测试的一点心得
  11. SSRF libcurl protocol wrappers利用分析
  12. 小米笔记安装双系统linux,小米笔记本电脑怎么安装双系统?-小米win7
  13. Google 2018 更新内容
  14. Yapi 配置 pm2服务
  15. 搭建Web服务器建网站的步骤
  16. 用Python分析了30000+《独行月球》影评数据,看看观众们怎么说~
  17. Python毕业设计选题推荐
  18. 对8086的存储器扩展
  19. python生成6位数验证码_Python随机生成一个6位的验证码代码分享
  20. SystemUI架构分析学习

热门文章

  1. Android中的USB中的UsbAccessory和UsbDevice的区别
  2. Android 循环缓冲区
  3. postgis之获取二进制的长度
  4. Tensorflow2.0实战之GAN
  5. python 科学计算设计_Python程序设计与科学计算
  6. java placeholder_java swing JTextField设置PlaceHolder
  7. python string转date类型_java string类型怎么转化成date类型
  8. 计算机地址如何表达,计算机中的地址是表示
  9. rstudio server docker 部署_Docker环境运行Spring Cloud项目
  10. js数组获取index_想自学JS吗?想提升JS底层原理吗?76张脑图带你彻底搞懂原生JS...