什么是 JJWT:


JJWT 是一个提供端到端的JWT创建和验证的Java库。永远免费和开源(Apache License,版本2.0),JJWT很容易使用和理解。


JJWT 快速入门

1. 在 mengxuegu-member-util/pom.xml 添加 jjwt 依赖( jdk8 以下)



<dependencies> <!--jwt令牌--> 
 <dependency> 
   <groupId>io.jsonwebtoken</groupId> 
   <artifactId>jjwt</artifactId> 
   <version>0.6.0</version> 
 </dependency> 
</dependencies>



如果使用 JDK9 还要添加以下依赖:



默认情况下,在 java SE 9.0 中 将不再包含 java EE 的 Jar 包,而 JAXB API 是 java EE 的 API ,因此我们要手动导



入这个 Jar 包 。



<dependencies> <!--jwt令牌--> 
 <dependency> 
   <groupId>io.jsonwebtoken</groupId> 
   <artifactId>jjwt</artifactId> 
   <version>0.6.0</version> 
 </dependency> 

 <dependency> 
   <groupId>javax.xml.bind</groupId> 
   <artifactId>jaxb-api</artifactId> 
   <version>2.3.0</version>  
 </dependency> 

 <dependency> 
   <groupId>com.sun.xml.bind</groupId> 
   <artifactId>jaxb-impl</artifactId> 
   <version>2.3.0</version> 
 </dependency> 

 <dependency> 
   <groupId>com.sun.xml.bind</groupId> 
   <artifactId>jaxb-core</artifactId> .
   <version>2.3.0</version> 
 </dependency> 

 <dependency> 
   <groupId>javax.activation</groupId> 
   <artifactId>activation</artifactId>  
   <version>1.1.1</version> 

 <dependencies> <!--jwt令牌--> 
  <dependency> 
   <groupId>io.jsonwebtoken</groupId> 
   <artifactId>jjwt</artifactId> 
   <version>0.6.0</version> 
   </dependency> 
 </dependencies>
 </dependency> 
</dependencies>



创建普通测试类 TestJwt ,用于生成 token :



import io.jsonwebtoken.JwtBuilder; 
import io.jsonwebtoken.Jwts; 
import io.jsonwebtoken.SignatureAlgorithm;
import java.util.Date;

public class TestJwt {
  public static void main(String[] args) { 
    String token = createJwt(); 
    System.out.println("生成的令牌:"+ token); 
}


// 生成令牌 
public static String createJwt () { 
  JwtBuilder builder= Jwts.builder().setId("11111") // 是字符串 
  .setSubject("admin") // 主题 如用户名 
  .setIssuedAt(new Date()) // 签发时间 
  .signWith(SignatureAlgorithm.HS256,"ceshiyuan"); // 签名密钥 
 return builder.compact(); 
}


//eyJhbGciOiJIUzI1NiJ9.eyJqdGkiOiIxMTExMSIsInN1YiI6ImFkbWluIiwiaWF0IjoxNTkwNDYyNDUyfQ.EbF6wKi KRzFrJVShGurQnfhK36mDp2_ykiYTj5J0uOc



再次运行,会发现每次运行的结果是不一样的,因为我们每次的签发时间是不一样的。



解析 jwt 令牌:



当服务端生成 token 后发给客户端,客户端在下次向服务端发送请求时需要携带这个 token ( 这就好像是拿着一张门票一 样) ,那服务端接到这个 token 应该解析出 token 中的信息 ( 例如用户名 ), 根据这些信息 查询数据库返回相应的结果。



在 TestCreateJwt 类添加一个方法 parserJwt 来解析 jwt 令牌中信息:



package com.ape.springboot.controller;

import com.sun.org.apache.xml.internal.security.algorithms.SignatureAlgorithm;
import io.jsonwebtoken.Claims;
import io.jsonwebtoken.JwtBuilder;
import io.jsonwebtoken.Jwts;

public class TestCreateJwt {
    public static void main(String[] args) {
        String token = createJwt();
        System.out.println("生成的令牌:" + token);
        parserJwt(token);
    }

    // 生成令牌
    public static String createJwt() {
        JwtBuilder builder = Jwts.builder().setId("11111") // 是字符串
                .setSubject("admin") // 主题 如用户名 .setIssuedAt(new Date()) // 签发时间
                .signWith(SignatureAlgorithm.HS256, "ceshiyuan"); // 签名密钥
        return builder.compact();
    }

    // 解析令牌
    public static void parserJwt(String token) {
        Claims claims = Jwts.parser().setSigningKey("ceshiyuan") // 签名密钥要一致
                .parseClaimsJws(token).getBody();
        System.out.println("id:" + claims.getId());
        System.out.println("subject:" + claims.getSubject());
        // System.out.println("IssuedAt:"+claims.getIssuedAt());
    }
}



如果将 token 或签名秘钥篡改一下,会发现运行时就会报错,所以解析 token 也就是验证 token




javaswing的库配置 java jwt库_java


校验 Jwt 令牌是否过期


一般我们并不希望签发的 token 是永久生效的,所以我们可以为 token 添加一个过期时间。


//           生成令牌 
         
public static           String  
         createJwt  
         () { 
         
  //           当前时间毫秒数 
         
  long           now  
         =  
         System 
         . 
         currentTimeMillis 
         (); 
         
  //          过期时间为 
         10 
         秒 
         
  long           exp  
         =  
         now  
         +  
         1000 
         * 
         10 
         ; 
         
  JwtBuilder builder          =  
         Jwts 
         . 
         builder 
         (). 
         setId 
         ( 
         "11111" 
         )  
         //  
         是字符串 
         
  .          setSubject 
         ( 
         "admin" 
         )  
         //  
         主题 如用户名 
         
  .          setIssuedAt 
         ( 
         new  
         Date 
         ())  
         //  
         签发时间 
         
  .          signWith 
         ( 
         SignatureAlgorithm 
         . 
         HS256 
         , 
         "ceshiyuan" 
         )  
         //  
         签名密钥 
         
  .          setExpiration 
         ( 
         new  
         Date 
         ( 
         exp 
         ));  
         //  
         过期时间  
         +++++++ 
         
  return           builder 
         . 
         compact 
         (); 
         
}

测试:先生成一个token ,然后等待10秒后再去解析它,发现报如下错


Exception in thread "main" io.jsonwebtoken.ExpiredJwtException: JWT expired at


javaswing的库配置 java jwt库_JJWT 实现 JWT_02


创建JWT工具类


JwtUtil 代码实现如下:


import       io      . 
     jsonwebtoken 
     . 
     Claims 
     ; 
     
import       io      . 
     jsonwebtoken 
     . 
     JwtBuilder 
     ; 
     
import       io      . 
     jsonwebtoken 
     . 
     Jwts 
     ; 
     
import       io      . 
     jsonwebtoken 
     . 
     SignatureAlgorithm 
     ; 
     
import       org      . 
     springframework 
     . 
     boot 
     . 
     context 
     . 
     properties 
     . 
     ConfigurationProperties 
     ; 
     
import       org      . 
     springframework 
     . 
     context 
     . 
     annotation 
     . 
     Configuration 
     ; 
     
import       org      . 
     springframework 
     . 
     stereotype 
     . 
     Component 
     ; 
     
import       java      . 
     util 
     . 
     Date 
     ; 
     
@Component 
     
@ConfigurationProperties      (      prefix  
     =  
     "mengxuegu.jwt.config" 
     ) 
     
public class       JwtUtil       { 
     
//       密钥 
     
private       String       secretKey 
     ; 
     
//      单位秒,默认      7 
     天 
     
private       long       expires  
     =  
     60 
     * 
     60 
     * 
     24 
     * 
     7 
     ; 
     
public       String       getSecretKey 
     () { 
     
return       secretKey      ; 
     
}
     
public       void       setSecretKey 
     ( 
     String  
     secretKey 
     ) { 
     
this      .      secretKey  
     =  
     secretKey 
     ; 
     
}
     
public       long       getExpires 
     () { 
     
return       expires      ; 
     
}
     
public       void       setExpires 
     ( 
     long  
     expires 
     ) { 
     
this      .      expires  
     =  
     expires 
     ; 
     
}
     
/**
     
*       生成      JWT 
     
* @param id 
     
*/ 
     
public       String       createJWT 
     ( 
     String  
     id 
     ,  
     String  
     subject 
     ,  
     Boolean  
     isLogin 
     ) { 
     
long       nowMillis       =  
     System 
     . 
     currentTimeMillis 
     (); 
     
Date now       =       new  
     Date 
     ( 
     nowMillis 
     ); 
     
JwtBuilder builder       =       Jwts 
     . 
     builder 
     (). 
     setId 
     ( 
     id 
     ) 
     
.      setSubject      ( 
     subject 
     ) 
     
.      setIssuedAt      ( 
     now 
     ) 
     
.      signWith      ( 
     SignatureAlgorithm 
     . 
     HS256 
     ,  
     secretKey 
     ) 
     
.      claim      ( 
     "isLogin" 
     ,  
     isLogin 
     ); 
     
if       (      expires  
     >  
     0 
     ) { 
     
// expires      乘以      1000 
     是毫秒转秒 
     
builder      .      setExpiration 
     ( 
     new  
     Date 
     ( 
     nowMillis  
     +  
     expires 
     * 
     1000 
     )); 
     3.  
     在 
      mengxuegu-member-api  
     模块的 
      application.yml  
     中添加配置 
     
业务层添加       login       方法 
     
校验登录用户名密码,登录成功后,生成       token       响应给客户端 
     
1.       在       com.mengxuegu.member.service.impl.IStaffffService  
     接口添加 
      login  
     抽象方法 
     
2.       在       com.mengxuegu.member.service.impl.StaffffServiceImpl  
     实现 
      login  
     方法 
     
}
     
return       builder      . 
     compact 
     (); 
     
}
     
/**
     
*       解析      JWT 
     
* @param jwtToken 
     
*/ 
     
public       Claims parseJWT      ( 
     String  
     jwtToken 
     ){ 
     
return       Jwts      . 
     parser 
     (). 
     setSigningKey 
     ( 
     secretKey 
     ) 
     
.      parseClaimsJws      ( 
     jwtToken 
     ). 
     getBody 
     (); 
     
} 
     
}

 
application.yml 中添加配置 
ceshiyuan   : 
  
 jwt   :
  
  config   : 
  
   secretKey   :    mengxuegu  
  # jwt 
  令牌密钥 
  
    expires   :    604800  
  #  
  单位秒, 
  7 
  天 
  

 
校验登录用户名密码,登录成功后,生成   token   响应给客户端
 

@Autowired 
   
JwtUtil jwtUtil    ; 
   
@Override 
   
public     Result     login 
   ( 
   String  
   username 
   ,  
   String  
   password 
   ) { 
   
Result error     =     Result 
   . 
   error 
   ( 
   " 
   用户名或密码错误 
   " 
   ); 
   
if    (    StringUtils 
   . 
   isBlank 
   ( 
   username 
   ) 
   
||     StringUtils    . 
   isBlank 
   ( 
   password 
   )) { 
   
return     error    ; 
   
}    控制层添加     login     方法 
   
在     com.mengxuegu.member.controller.AuthController     控制类中添加  
   login  
   方法 
   
测试登录 
   
登录请求,发送     POST     请求 
    localhost:6666/user/login 
   
// 1.     通过用户名查询 
   
Staff staff     =     getByUsername 
   ( 
   username 
   ); 
   
if    (    staff  
   ==  
   null 
   ) { 
   
return     error    ; 
   
}
   
// 2.     存在,判断密码是否正确    ( 
   输入的密码,数据库加密的密码 
   ) 
   
if    (     ! 
   new  
   BCryptPasswordEncoder 
   (). 
   matches 
   ( 
   password 
   ,  
   staff 
   . 
   getPassword 
   ())) { 
   
return     error    ; 
   
}
   
// 3.     生成    token  
   响应 
   
String     jwt     =  
   jwtUtil 
   . 
   createJWT 
   ( 
   staff 
   . 
   getId 
   ()  
   +  
   "" 
   ,  
   staff 
   . 
   getUsername 
   (),  
   true 
   ); 
   
//     手动封装个    json 
   对象  
   {token: jwt} 
   
Map    <    String 
   ,  
   String 
   >  
   map  
   =  
   new  
   HashMap 
   <> 
   (); 
   
map    .    put 
   ( 
   "token" 
   ,  
   jwt 
   ); 
   
return     Result    . 
   ok 
   ( 
   map 
   ); 
   
}


控制层添加 login 方法


/**
   
*     登录 
   
* @return 
   
*/ 
   
@PostMapping    (    "/login" 
   ) 
   
public     Result     login 
   ( 
   @RequestBody  
   Staff staff 
   ) { 
   
return     staffService    . 
   login 
   ( 
   staff 
   . 
   getUsername 
   (),  
   staff 
   . 
   getPassword 
   ()); 
   
}


测试登录


登录请求,发送     POST     请求 
    localhost:6666/user/login  
  
   

{ 
    
 "username"     :      "admin" 
    , 
    
 "password"     :      "123456" 
    
}

javaswing的库配置 java jwt库_JWT从初级到资深_03