Token是密码学中的一个概念,可以用作身份验证凭证。在计算机领域中,token可以是一个字符串,用于标识用户的身份和权限。当用户进行身份验证时,他们通常会收到一个token,以便在将来的请求中用作凭证。
在互联网应用程序中,token通常用于实现单点登录(Single Sign-On),这样用户只需通过一次身份验证就可以访问多个应用。当用户登录成功后,应用服务器会生成一个token,并将其保存在用户的浏览器中,例如通过cookie或localStorage。
每当用户访问受保护的资源时,应用服务器会要求用户提供token,以验证其身份。服务器会通过对token进行验证来确定用户的身份和权限。
常见的token类型有JWT(JSON Web Token)和OAuth token。JWT是一种开放的标准,定义了在网络上以JSON格式传输信息的一种方式,可以用于在应用程序间安全地传输信息。OAuth token则用于授权和认证,允许用户将其身份验证信息共享给其他应用。
总之,Token是一种用于身份验证和授权的凭证,在网络应用程序中起到了重要的作用。
需要的三个工具类
java">package com.dc.utils;import com.alibaba.druid.util.StringUtils;
import io.jsonwebtoken.*;
import lombok.Data;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.context.annotation.Configuration;
import org.springframework.stereotype.Component;import java.util.Date;@Data
@Component
@ConfigurationProperties(prefix = "jwt.token")
public class JwtHelper {private long tokenExpiration; //有效时间,单位毫秒 1000毫秒 == 1秒private String tokenSignKey; //当前程序签名秘钥//生成token字符串public String createToken(Long userId) {
// System.out.println("tokenExpiration = " + tokenExpiration);
// System.out.println("tokenSignKey = " + tokenSignKey);String token = Jwts.builder().setSubject("YYGH-USER").setExpiration(new Date(System.currentTimeMillis() + tokenExpiration*1000*60)) //单位毫秒.claim("userId", userId).signWith(SignatureAlgorithm.HS512, tokenSignKey).compressWith(CompressionCodecs.GZIP).compact();return token;}//从token字符串获取useridpublic Long getUserId(String token) {if(StringUtils.isEmpty(token)) return null;Jws<Claims> claimsJws = Jwts.parser().setSigningKey(tokenSignKey).parseClaimsJws(token);Claims claims = claimsJws.getBody();Integer userId = (Integer)claims.get("userId");return userId.longValue();}//判断token是否有效public boolean isExpiration(String token){try {boolean isExpire = Jwts.parser().setSigningKey(tokenSignKey).parseClaimsJws(token).getBody().getExpiration().before(new Date());//没有过期,有效,返回falsereturn isExpire;}catch(Exception e) {//过期出现异常,返回truereturn true;}}
}
java">package com.dc.utils;/*** 全局统一返回结果类*/
public class Result<T> {// 返回码private Integer code;// 返回消息private String message;// 返回数据private T data;public Result(){}// 返回数据protected static <T> Result<T> build(T data) {Result<T> result = new Result<T>();if (data != null)result.setData(data);return result;}public static <T> Result<T> build(T body, Integer code, String message) {Result<T> result = build(body);result.setCode(code);result.setMessage(message);return result;}public static <T> Result<T> build(T body, ResultCodeEnum resultCodeEnum) {Result<T> result = build(body);result.setCode(resultCodeEnum.getCode());result.setMessage(resultCodeEnum.getMessage());return result;}/*** 操作成功* @param data baseCategory1List* @param <T>* @return*/public static<T> Result<T> ok(T data){Result<T> result = build(data);return build(data, ResultCodeEnum.SUCCESS);}public Result<T> message(String msg){this.setMessage(msg);return this;}public Result<T> code(Integer code){this.setCode(code);return this;}public Integer getCode() {return code;}public void setCode(Integer code) {this.code = code;}public String getMessage() {return message;}public void setMessage(String message) {this.message = message;}public T getData() {return data;}public void setData(T data) {this.data = data;}
}
java">package com.dc.utils;/*** 统一返回结果状态信息类**/
public enum ResultCodeEnum {SUCCESS(200,"success"),USERNAME_ERROR(501,"usernameError"),PASSWORD_ERROR(503,"passwordError"),NOTLOGIN(504,"notLogin"),USERNAME_USED(505,"userNameUsed");private Integer code;private String message;private ResultCodeEnum(Integer code, String message) {this.code = code;this.message = message;}public Integer getCode() {return code;}public String getMessage() {return message;}
}
pom文件中引入依赖
java"> <dependency><groupId>io.jsonwebtoken</groupId><artifactId>jjwt</artifactId><version>0.9.1</version></dependency><dependency><groupId>javax.xml.bind</groupId><artifactId>jaxb-api</artifactId><version>2.3.0</version></dependency>
yaml文件配置
java">#jwt配置
jwt:token:tokenExpiration: 120 #有效时间,单位分钟tokenSignKey: dc123456 #当前程序签名秘钥 自定义
Controller接收请求,然后调用对应的service接口,再具体实现类中实现
java"> @Overridepublic Result login(Weblogin weblogin) {
// System.out.println(weblogin);LambdaQueryWrapper<Weblogin> lambdaQueryWrapper=new LambdaQueryWrapper<>();lambdaQueryWrapper.eq(Weblogin::getUsername,weblogin.getUsername());Weblogin user=webloginMapper.selectOne(lambdaQueryWrapper);//账号不存在if(user==null){return Result.build(null, ResultCodeEnum.USERNAME_ERROR);//返回501异常}//密码不为空且密码正确(密码进行了加密)if(!StringUtils.isEmpty(weblogin.getPassword())&&MD5Util.encrypt(weblogin.getPassword()).equals(user.getPassword())){//登陆成功//根据用户id生成tokenString token=jwtHelper.createToken(user.getUserid());//将token封装到Result中Map data=new HashMap();data.put("token",token);return Result.ok(data);}//密码错误return Result.build(null,ResultCodeEnum.PASSWORD_ERROR);}
前端将返回的token进行存储
javascript">submit() {getMenu(this.form).then((data) => {if (data.data.code == 501) {this.$message.error('用户不存在');} else if (data.data.code == 503) {this.$message.error('密码错误');} else if (data.data.code == 200) {this.$message({message: '登陆成功',type: 'success'});Cookie.set("token",data.data.data.token)this.$router.push('/home')}})}