1.首先需要導入maven依賴
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-core</artifactId>
<version>2.9.4</version>
</dependency>
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>2.9.4</version>
</dependency>
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-annotations</artifactId>
<version>2.9.4</version>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>fastjson</artifactId>
<version>1.2.41</version>
</dependency>
<dependency>
<groupId>io.jsonwebtoken</groupId>
<artifactId>jjwt</artifactId>
<version>0.7.0</version>
</dependency>
<dependency>
<groupId>com.auth0</groupId>
<artifactId>java-jwt</artifactId>
<version>3.2.0</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context</artifactId>
<version>5.1.3.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-tx</artifactId>
<version>5.1.3.RELEASE</version>
</dependency>
<dependency>
<groupId>org.quartz-scheduler</groupId>
<artifactId>quartz</artifactId>
<version>2.3.0</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-context-support</artifactId>
<version>5.1.3.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-test</artifactId>
<version>5.1.3.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-web</artifactId>
<version>5.1.3.RELEASE</version>
</dependency>
<dependency>
<groupId>org.springframework</groupId>
<artifactId>spring-webmvc</artifactId>
<version>5.1.3.RELEASE</version>
</dependency>
<dependency>
<groupId>org.slf4j</groupId>
<artifactId>slf4j-log4j12</artifactId>
<version>1.7.16</version>
</dependency>
2.編寫jwt工具類
package com.dqw.util;
import java.security.Key;
import java.util.Date;
import javax.crypto.spec.SecretKeySpec;
import javax.xml.bind.DatatypeConverter;
import io.jsonwebtoken.Claims;
import io.jsonwebtoken.JwtBuilder;
import io.jsonwebtoken.Jwts;
import io.jsonwebtoken.SignatureAlgorithm;
public class JWTUtil {
public static String sercetKey = "InMySchoolOnline";
public final static long keeptime = 1800000;
public static String generToken(String id, String issuer, String subject) {
long ttlMillis = keeptime;
SignatureAlgorithm signatureAlgorithm = SignatureAlgorithm.HS256;
long nowMillis = System.currentTimeMillis();
Date now = new Date(nowMillis);
byte[] apiKeySecretBytes = DatatypeConverter.parseBase64Binary(sercetKey);
Key signingKey = new SecretKeySpec(apiKeySecretBytes, signatureAlgorithm.getJcaName());
JwtBuilder builder = Jwts.builder().setId(id).setIssuedAt(now);
if (subject != null) {
builder.setSubject(subject);
}
if (issuer != null) {
builder.setIssuer(issuer);
}
builder.signWith(signatureAlgorithm, signingKey);
if (ttlMillis >= 0) {
long expMillis = nowMillis + ttlMillis;
Date exp = new Date(expMillis);
builder.setExpiration(exp);
}
return builder.compact();
}
public static String updateToken(String token) {
Claims claims = verifyToken(token);
String id = claims.getId();
String subject = claims.getSubject();
String issuer = claims.getIssuer();
return generToken(id, issuer, subject);
}
private static Claims verifyToken(String token) {
Claims claims = Jwts.parser().setSigningKey(DatatypeConverter.parseBase64Binary(sercetKey))
.parseClaimsJws(token).getBody();
return claims;
}
}
3.編輯token鑑定spring攔截器
package com.dqw.interceptor;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.apache.log4j.Logger;
import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;
import com.alibaba.fastjson.JSON;
import com.dqw.util.JWTUtil;
import com.dqw.util.ResponseData;
public class HeaderTokenInterceptor implements HandlerInterceptor {
private static final Logger LOG = Logger.getLogger(HeaderTokenInterceptor.class);
public boolean preHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse,
Object handler) throws Exception {
ResponseData responseData = null;
String headerToken = httpServletRequest.getHeader("token");
if (!httpServletRequest.getRequestURI().contains("login")) {
if (headerToken == null) {
responseData=ResponseData.customerError();
}
try {
headerToken = JWTUtil.updateToken(headerToken);
LOG.debug("token驗證通過,並續期了");
} catch (Exception e) {
LOG.debug("token驗證出現異常!");
responseData=ResponseData.customerError();
}
}
if(responseData!=null) {
httpServletResponse.getWriter().write(JSON.toJSONString(responseData));
return false;
}else {
httpServletResponse.setHeader("token", headerToken);
return true;
}
}
public void postHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o,
ModelAndView modelAndView) throws Exception {
}
public void afterCompletion(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse,
Object o, Exception e) throws Exception {
}
}
4.項目中用到的其他類
package com.dqw.util;
import java.util.HashMap;
import java.util.Map;
public class ResponseData {
private final String message;
private final int code;
private final Map<String, Object> data = new HashMap<String, Object>();
public String getMessage() {
return message;
}
public int getCode() {
return code;
}
public Map<String, Object> getData() {
return data;
}
public ResponseData putDataValue(String key, Object value) {
data.put(key, value);
return this;
}
private ResponseData(int code, String message) {
this.code = code;
this.message = message;
}
public static ResponseData ok() {
return new ResponseData(200, "Ok");
}
public static ResponseData notFound() {
return new ResponseData(404, "Not Found");
}
public static ResponseData badRequest() {
return new ResponseData(400, "Bad Request");
}
public static ResponseData forbidden() {
return new ResponseData(403, "Forbidden");
}
public static ResponseData unauthorized() {
return new ResponseData(401, "unauthorized");
}
public static ResponseData serverInternalError() {
return new ResponseData(500, "Server Internal Error");
}
public static ResponseData customerError() {
return new ResponseData(1001, "customer Error");
}
}
package com.dqw.po;
public class User {
private Integer id;
private String email;
private String password;
public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
public String getPassword() {
return password;
}
public void setPassword(String password) {
this.password = password;
}
package com.dqw.interceptor;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;
public class HttpInterceptor implements HandlerInterceptor {
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
response.setHeader("Access-Control-Allow-Origin", "*");
response.setHeader("Access-Control-Allow-Headers", "token, Accept, Origin, X-Requested-With, Content-Type, Last-Modified");
return true;
}
@Override
public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView) throws Exception {
}
@Override
public void afterCompletion(HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex) throws Exception {
}
}
package com.dqw.controller;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import com.dqw.util.ResponseData;
@RestController
@RequestMapping("index")
public class IndexController {
@GetMapping("index")
public ResponseData toLogin() {
ResponseData responseData = ResponseData.ok();
return responseData;
}
}
package com.dqw.controller;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.bind.annotation.RestController;
import com.dqw.po.User;
import com.dqw.util.JWTUtil;
import com.dqw.util.ResponseData;
@RestController
@RequestMapping("login")
public class LoginController {
@PostMapping(value="login")
public @ResponseBody ResponseData login(User user) {
boolean login = toLogin(user);
ResponseData responseData = ResponseData.ok();
if(login) {
String token = JWTUtil.generToken("1", "Jersey-Security-Basic", user.getEmail());
responseData.putDataValue("token", token);
responseData.putDataValue("user", user);
}else {
responseData=ResponseData.customerError();
}
return responseData;
}
public boolean toLogin(User user) {
if(user.getEmail()!=null&&user.getEmail().trim().length()>0) {
if(user.getEmail().equals("root")) {
if(user.getPassword().equals("123456")) {
return true;
}
}
}
return false;
}
}
}
5.附springmvc配置文件
<context:component-scan base-package="com"></context:component-scan>
<mvc:annotation-driven/>
<context:annotation-config></context:annotation-config>
<mvc:interceptors>
<mvc:interceptor>
<mvc:mapping path="/**"/>
<bean class="com.dqw.interceptor.HttpInterceptor"></bean>
</mvc:interceptor>
<mvc:interceptor>
<mvc:mapping path="/**"/>
<bean class="com.dqw.interceptor.HeaderTokenInterceptor"></bean>
</mvc:interceptor>
</mvc:interceptors>
6.login.html
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
<script type="text/javascript" src="jquery.min.js"></script>
<script type="text/javascript" src="jquery.cookie.js"></script>
</head>
<body>
郵箱:<input type="text" name="email"><br>
密碼:<input type="text" name="password"><br>
<input type="submit" onclick="signIn()" value="登錄">
<script type="text/javascript">
function signIn() {
let email = $("input[name='email']").val();
let password = $("input[name='password']").val();
$.ajax({
url: "http://localhost:8080/jwt/login/login.action",
type: "POST",
dataType: "json",
data: {email: email, password: password},
success: function (result) {
if(result.code==200){
$.cookie('token', result.data.token);
location="index.html";
}else{
alert("用戶名或者密碼錯誤!");
}
}
})
}
</script>
</body>
</html>
7.index.html
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>歡迎</title>
<script type="text/javascript" src="jquery.min.js"></script>
<script type="text/javascript" src="jquery.cookie.js"></script>
</head>
<body>
歡迎你(可以從本地存取獲取cookie中獲取)
<br>
<button onclick="logout()">註銷</button>
<script type="text/javascript">
loadDeptTree();
function loadDeptTree() {
$.ajax({
headers: {
token: $.cookie('token')
},
url: "http://localhost:8080/jwt/index/index.action",
type: 'GET',
dataType: 'json',
success : function (result) {
if(result.code==200){
alert("加載到的數據:"+result+",並進行渲染頁面.....");
}else{
alert("異常,非法token,這裏不直接判斷是否token不對,實際開發需要各種判斷返回碼。");
}
}
})
}
function logout() {
var keys = document.cookie.match(/[^ =;]+(?=\=)/g);
if(keys) {
for(var i = keys.length; i--;)
document.cookie = keys[i] + '=0;expires=' + new Date(0).toUTCString()
}
window.location.href = "login.html";
}
</script>
</body>
</html>