相信很多做技术的朋友都做过前后端分离项目,项目分离后认证就靠JWT,费话不多说,直接上干活(写的不好还请多多见谅,大牛请绕行)

直接上代码,项目为Maven项目,结构如图:

包分类如下:

com.api.config  相关配置类

com.api.ctrl  controller层

com.api.entity  相关实体类

com.api.repo   jpa仓库相关

com.api.serice  service层相关

ApiApplication 为启动类

主要配置核心类如下:

JWTAuthenticationFilter

package com.api.config;

import com.api.entity.User;
import com.api.repo.UserRepo;
import io.jsonwebtoken.Jwts;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.web.authentication.www.BasicAuthenticationFilter; import javax.servlet.FilterChain;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.ArrayList; public class JWTAuthenticationFilter extends BasicAuthenticationFilter { private UserRepo userRepo; public JWTAuthenticationFilter(AuthenticationManager authenticationManager,UserRepo userRepo) {
super(authenticationManager);
this.userRepo = userRepo;
} @Override
protected void doFilterInternal(HttpServletRequest request, HttpServletResponse response, FilterChain chain) throws IOException, ServletException { String header = request.getHeader("Authorization");
//如果不包含Bearer则退出
if(header != null && !header.startsWith("Bearer")){
chain.doFilter(request,response);
return;
} UsernamePasswordAuthenticationToken authenticationToken = getAuthentication(request);
SecurityContextHolder.getContext().setAuthentication(authenticationToken);
chain.doFilter(request,response);
} private UsernamePasswordAuthenticationToken getAuthentication(HttpServletRequest request) {
String token = request.getHeader("Authorization");
if (token != null) {
// parse the token.
String user = Jwts.parser()
.setSigningKey("HSMyJwtSecret".getBytes())
.parseClaimsJws(token.replace("Bearer ", ""))
.getBody()
.getSubject();
if (user != null) {
Integer userId = Integer.valueOf(user.split(":")[0]);
User currUser = userRepo.findById(userId).orElse(null);
if(currUser != null){
return new UsernamePasswordAuthenticationToken(currUser, null, new ArrayList<>());
}
return new UsernamePasswordAuthenticationToken(new User(), null, new ArrayList<>());
}
}
return null;
}
}
JWTLoginFilter
package com.api.config;

import com.api.entity.User;
import com.fasterxml.jackson.databind.ObjectMapper;
import io.jsonwebtoken.Jwts;
import io.jsonwebtoken.SignatureAlgorithm;
import org.springframework.security.authentication.AuthenticationManager;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.web.authentication.UsernamePasswordAuthenticationFilter; import javax.servlet.FilterChain;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Date; public class JWTLoginFilter extends UsernamePasswordAuthenticationFilter { private AuthenticationManager authenticationManager; public JWTLoginFilter(AuthenticationManager authenticationManager){
this.authenticationManager = authenticationManager;
} @Override
public Authentication attemptAuthentication(HttpServletRequest request, HttpServletResponse response) throws AuthenticationException {
try {
User user = new ObjectMapper().readValue(request.getInputStream(), User.class);
return authenticationManager.authenticate(
new UsernamePasswordAuthenticationToken(
user.getUsername(),
user.getPassword(),
new ArrayList<>()
)
); }catch (Exception e){
throw new RuntimeException(e);
}
} @Override
protected void successfulAuthentication(HttpServletRequest request, HttpServletResponse response, FilterChain chain, Authentication authResult) throws IOException, ServletException {
String token = Jwts.builder()
.setSubject(((JwtUser) authResult.getPrincipal()).getUsername())
.setExpiration(new Date(System.currentTimeMillis() + 60 * 60 * 24 * 1000))
.signWith(SignatureAlgorithm.HS256,"HSMyJwtSecret".getBytes())
.compact();
response.addHeader("Authorization", "Bearer " + token);
response.getOutputStream().println(token);
}
}
MyUserDetailService
package com.api.config;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.authentication.AuthenticationProvider;
import org.springframework.security.authentication.UsernamePasswordAuthenticationToken;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.AuthenticationException;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.stereotype.Component; import java.util.Collection; @Component
public class MyAuthencationProvider implements AuthenticationProvider { @Autowired
private MyUserDetailService myUserDetailService; @Override
public Authentication authenticate(Authentication authentication) throws AuthenticationException {
String username = authentication.getPrincipal().toString();
JwtUser jwtUser = (JwtUser) myUserDetailService.loadUserByUsername(username);
Collection<? extends GrantedAuthority> authorities = jwtUser.getAuthorities();
return new UsernamePasswordAuthenticationToken(jwtUser, jwtUser.getPassword(), authorities);
} @Override
public boolean supports(Class<?> aClass) {
return true;
}
}
MyUserDetailService
package com.api.config;

import com.api.entity.User;
import com.api.repo.UserRepo;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UserDetailsService;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.stereotype.Component; @Component
public class MyUserDetailService implements UserDetailsService { @Autowired
private UserRepo userRepo; @Override
public UserDetails loadUserByUsername(String s) throws UsernameNotFoundException {
User user = userRepo.findFirstByUsername(s);
if(user != null){
JwtUser jwtUser = new JwtUser(String.format("%s:%s",String.valueOf(user.getId()),user.getUsername()),user.getPassword());
return jwtUser;
}
throw new UsernameNotFoundException("用户名未找到");
}
}
WebSecurityConfig
package com.api.config;

import com.api.repo.UserRepo;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Configuration;
import org.springframework.core.annotation.Order;
import org.springframework.http.HttpMethod;
import org.springframework.security.config.annotation.authentication.builders.AuthenticationManagerBuilder;
import org.springframework.security.config.annotation.method.configuration.EnableGlobalMethodSecurity;
import org.springframework.security.config.annotation.web.builders.HttpSecurity;
import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder; @Configuration
@EnableWebSecurity
@EnableGlobalMethodSecurity(prePostEnabled = true)
@Order(-1)
public class WebSecurityConfig extends WebSecurityConfigurerAdapter { @Autowired
private MyAuthencationProvider myAuthencationProvider;
@Autowired
private UserRepo userRepo; @Override
protected void configure(HttpSecurity http) throws Exception {
http.cors().and().csrf().disable().authorizeRequests()
.antMatchers(HttpMethod.POST, "/register").permitAll()
.anyRequest().authenticated()
.and()
.addFilter(new JWTLoginFilter(authenticationManager()))
.addFilter(new JWTAuthenticationFilter(authenticationManager(),userRepo));
} @Override
public void configure(AuthenticationManagerBuilder auth) throws Exception {
auth.authenticationProvider(myAuthencationProvider);
} }
JwtUser
package com.api.config;

import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.userdetails.UserDetails; import java.util.Collection; public class JwtUser implements UserDetails { private String username;
private String password; public JwtUser(String username,String password){
this.username = username;
this.password = password;
} @Override
public Collection<? extends GrantedAuthority> getAuthorities() {
return null;
} @Override
public String getPassword() {
return password;
} @Override
public String getUsername() {
return username;
} @Override
public boolean isAccountNonExpired() {
return false;
} @Override
public boolean isAccountNonLocked() {
return false;
} @Override
public boolean isCredentialsNonExpired() {
return false;
} @Override
public boolean isEnabled() {
return false;
} }
MyMvcConfigurer
package com.api.config;

import org.springframework.boot.autoconfigure.AutoConfigureBefore;
import org.springframework.context.annotation.Configuration;
import org.springframework.security.access.SecurityConfig;
import org.springframework.web.servlet.config.annotation.CorsRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; @Configuration
@AutoConfigureBefore(SecurityConfig.class)
public class MyMvcConfigurer implements WebMvcConfigurer { @Override
public void addCorsMappings(CorsRegistry registry) {
registry.addMapping("/**")
.allowedOrigins("*")
.allowedMethods("*")
.allowedHeaders("*")
.allowCredentials(true)
.maxAge(3600);
}
}

以上为config包下全部内容

项目POM.xml配置如下

<?xml version="1.0" encoding="UTF-8"?>
<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>
<parent>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-parent</artifactId>
<version>2.1.0.RELEASE</version>
<relativePath/> <!-- lookup parent from repository -->
</parent>
<groupId>com.api</groupId>
<artifactId>api</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>api</name>
<description>Demo project for Spring Boot</description> <properties>
<java.version>1.8</java.version>
</properties> <dependencies>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-jdbc</artifactId>
</dependency> <dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-data-jpa</artifactId>
</dependency> <dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-security</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</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>
</dependency> <dependency>
<groupId>com.github.wenhao</groupId>
<artifactId>jpa-spec</artifactId>
<version>3.2.3</version>
</dependency> <dependency>
<groupId>cn.hutool</groupId>
<artifactId>hutool-all</artifactId>
<version>4.3.1</version>
</dependency> <dependency>
<groupId>io.jsonwebtoken</groupId>
<artifactId>jjwt</artifactId>
<version>0.7.0</version>
</dependency> </dependencies> <build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.5.1</version>
<configuration>
<compilerArgs>
<arg>-verbose</arg>
<arg>-Xlint:all,-options,-path</arg>
</compilerArgs>
<source>1.8</source>
<target>1.8</target>
</configuration>
</plugin> <plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
</plugin>
<plugin>
<artifactId>maven-jar-plugin</artifactId>
<configuration>
<archive>
<manifest>
<addClasspath>true</addClasspath>
<classpathPrefix>lib/</classpathPrefix>
<mainClass>com.api.ApiApplication</mainClass>
</manifest>
</archive>
</configuration> </plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-resources-plugin</artifactId>
<configuration>
<delimiters>
<delimiter>@</delimiter>
<delimiter>#{*}</delimiter>
<delimiter>#</delimiter>
</delimiters>
</configuration>
</plugin>
</plugins>
</build> <repositories>
<repository>
<id>spring-snapshots</id>
<name>Spring Snapshots</name>
<url>https://repo.spring.io/snapshot</url>
<snapshots>
<enabled>true</enabled>
</snapshots>
</repository>
<repository>
<id>spring-milestones</id>
<name>Spring Milestones</name>
<url>https://repo.spring.io/milestone</url>
</repository>
</repositories>
<pluginRepositories>
<pluginRepository>
<id>spring-snapshots</id>
<name>Spring Snapshots</name>
<url>https://repo.spring.io/snapshot</url>
<snapshots>
<enabled>true</enabled>
</snapshots>
</pluginRepository>
<pluginRepository>
<id>spring-milestones</id>
<name>Spring Milestones</name>
<url>https://repo.spring.io/milestone</url>
</pluginRepository>
</pluginRepositories> </project>

以下为其他包结构以及类文件

以上配置成功后即可以POST方式访问

http://localhost:8080/login?username=xxx&password=xx 认证成功后会在返回jwt,下次请求认证的资源在header里边带上Authorization Bearer xxxxxx

即可。

SpringBoot2.0整合SpringSecurity实现WEB JWT认证的更多相关文章

  1. SpringBoot2.0 整合 SpringSecurity 框架,实现用户权限安全管理

    本文源码:GitHub·点这里 || GitEE·点这里 一.Security简介 1.基础概念 Spring Security是一个能够为基于Spring的企业应用系统提供声明式的安全访问控制解决方 ...

  2. SpringBoot2.0整合SpringSecurity实现自定义表单登录

    我们知道企业级权限框架一般有Shiro,Shiro虽然强大,但是却不属于Spring成员之一,接下来我们说说SpringSecurity这款强大的安全框架.费话不多说,直接上干货. pom文件引入以下 ...

  3. springboot2.0整合springsecurity前后端分离进行自定义权限控制

    在阅读本文之前可以先看看springsecurity的基本执行流程,下面我展示一些核心配置文件,后面给出完整的整合代码到git上面,有兴趣的小伙伴可以下载进行研究 使用maven工程构建项目,首先需要 ...

  4. SpringBoot2.0 整合 Swagger2 ,构建接口管理界面

    一.Swagger2简介 1.Swagger2优点 整合到Spring Boot中,构建强大RESTful API文档.省去接口文档管理工作,修改代码,自动更新,Swagger2也提供了强大的页面测试 ...

  5. springboot2.0整合logback日志(详细)

    <div class="post"> <h1 class="postTitle"> springboot2.0整合logback日志(详 ...

  6. 第二篇:SpringBoot2.0整合ActiveMQ

    本篇开始将具体介绍SpringBoot如何整合其它项目. 如何创建SpringBoot项目 访问https://start.spring.io/. 依次选择构建工具Maven Project.语言ja ...

  7. SpringBoot2.0 整合 QuartJob ,实现定时器实时管理

    一.QuartJob简介 1.一句话描述 Quartz是一个完全由java编写的开源作业调度框架,形式简易,功能强大. 2.核心API (1).Scheduler 代表一个 Quartz 的独立运行容 ...

  8. SpringBoot2.0 整合 Dubbo框架 ,实现RPC服务远程调用

    一.Dubbo框架简介 1.框架依赖 图例说明: 1)图中小方块 Protocol, Cluster, Proxy, Service, Container, Registry, Monitor 代表层 ...

  9. SpringBoot2.0 整合 Redis集群 ,实现消息队列场景

    本文源码:GitHub·点这里 || GitEE·点这里 一.Redis集群简介 1.RedisCluster概念 Redis的分布式解决方案,在3.0版本后推出的方案,有效地解决了Redis分布式的 ...

随机推荐

  1. Sturts2中Action的搜索顺序

    http://localhost:8080/ProjectName/path1/path2/path3/XX.action 首先会判断以/path1/paht2/path3为namespace的pac ...

  2. Volume 6. Mathematical Concepts and Methods

    138 - Street Numbers #include <stdio.h> //(2n+1)^2 - 8m^2 = 1,佩尔函数,或者打表 int main() { ; , xi = ...

  3. EF中避免查询重复执行的手段

    由于ef有lazyload机制,编写的查询语句往往都没有立即执行,当你轮训结果集的时候才会将查询翻译成database端的sql语句,执行sql将结果返回到方法中.但是,下次再使用前面的结果集的时候, ...

  4. Codeforces 158B (数学)

    B. Mushroom Scientists time limit per test 2 seconds memory limit per test 256 megabytes input stand ...

  5. Docker website

    https://github.com/docker/labs/  (nguo123gmail  Cooooos123!) Docker Tutorials and Labs At this time ...

  6. html缓存机制,http头部控制

    1.缓存分类:服务器缓存(协商缓存),第三方缓存,浏览器缓存(强制缓存) 2.浏览器缓存(添加 meta),设置请求指定的http头部信息.(状态码200,from cache , from dist ...

  7. 常见的各品牌路由器默认IP地址汇总清单

    常见的各品牌路由器默认IP地址汇总清单 下面是各常见品牌路由器的默认IP清单: 如果您使用的设备品牌不在上述列表中,也可以试着访问下RouterIPAddress.com或SetupRouter.co ...

  8. ssh2项目整合 struts2.1+hibernate3.3+spring3 基于hibernate注解和struts2注解

    项目文件夹结构例如以下: watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQveW9uZ3poaWFu/font/5a6L5L2T/fontsize/400/fi ...

  9. Tomcat手工搭建Jsp和Servlet程序

    要执行J2EE的程序,就必须安装相关的容器.而怎样选择JSP+Servlet模式.Tomcat是非常重要的选择之中的一个,是世界上最为广泛的Servlet和JSP容器. 下载: 1. URL: htt ...

  10. 传智播客JDBC视频教程

    视频介绍: 一些视频教程通过浅显案例来让刚開始学习的人感到轻松,可是课程中编写的代码不能直接应用于项目中:而本套视频教程正好相反,视频解说者李勇老师以技术见长.性格朴实无华.不善于幽默搞笑.李勇老师编 ...