前后端交互 - JWT鉴权到底是何方神圣

JWT鉴权

JWT全称 JSON Web Token,是一套开放的标准(RFC 7519),它定义了一种紧凑且自URL安全的方式,以JSON对象的方式在各方之间安全地进行信息传输。
使用密钥 ( secret ) ( HMAC算法生成 ) 或者 使用RSA或ECDSA的 公有/私有密钥 对JWT进行签名。

JSON Web Token

一些常用到JWT的情况:

  • 授权:这是使用JWT的最常见方案。一旦用户登录,每个后续请求将包括JWT,从而允许用户访问该令牌允许的路由,服务和资源。单点登录是当今广泛使用JWT的一项功能,因为它的开销很小并且支持跨域。
  • 信息交换:JWT是在各方之间安全地传输信息的好方法。因为可以对JWT进行签名(例如,使用公钥/私钥对)。此外,由于签名是使用Header和Payload计算的,因此还可以验证内容是否遭到篡改。
JWT 数据结构

JWT 以紧凑的形式由三部分组成,这些部分由点(.)分隔,分别是:

  • Header — base64转码显示的头部信息 (明文)
  • Payload — base64转码显示的签发信息(明文)
  • Signature — hs256加密显示的密码 ( 密文 )
JWT 使用流程

在这里插入图片描述

  • 登录 ---- 成功 ---- 根据密钥生成 token ( 两段明文和一段密文 ) 像门票的存在
  • token ---- 存储; 获取到 token ---- 请求到头部 携带 token ---- 服务端
  • 服务端 ---- 验证通过 ---- 返还数据
  • 服务端 ---- 验证不通过 ---- 返回 401
实际使用案例

登录时验证并签发token,前端保存

  • 前端页面核心代码
	<div class="loginContainer">
		<h1>登录</h1>
		<form action="/checkUser" method="post" onsubmit="return false;" >
			姓名:<input class="inputStyle" type="text" name="username" /><br />
			密码:<input class="inputStyle" type="password" name="pwd" /><br />
			<input class="loginStyle" type="submit" value="登录" />
			<button class="btn">点击 - 认证接口</button>
		</form>
	</div>
	<script>
		// 登录按钮 
		document.querySelector(".loginStyle").onclick = function(){
			let username = document.getElementsByName("username")[0].value;
			let password = document.getElementsByName("pwd")[0].value;
	      
			let xhr = new XMLHttpRequest;
			xhr.open("post","/checkUser",true);
	      
			// 设置头部信息的位置  必须写在 open 下面 
			// post 传参不设置头部的话 服务器拿到的数据就是字符串(不转格式的情况下)
			xhr.setRequestHeader("Content-Type","application/x-www-form-urlencoded");
	      	
	      	// 接收服务器端返回的数据
			xhr.onload = function(){
				console.log(xhr.responseText);
				// 数据类型 --> 对象 --> 获取token
				let token = JSON.parse(xhr.responseText).token;
				// 本地存储 token
				localStorage.setItem("token",token);
	        	// 	后续功能可以写跳转页面
			}
			
			// 将用户的登录信息发送到后端
			let data = `username=${username}&pwd=${password}`;
			xhr.send(data);
		}
	</script>
  • 后端服务器核心代码
    注意token的有效时间设置
    在实际使用中 有效时间越短越安全
	// 直接使用 不需要通过app
	const jwt = require("jsonwebtoken"); // 签发 token
	
	router.post("/checkUser",ctx=>{
	    console.log(ctx.request.body);
	    let {username,pwd} = ctx.request.body; 
	    
	    // 信息对象 用于返还到客户端
	    let info;
	    if (username === "秦兟" && pwd === "123") {
	        // 验证成功,签发token 
	        // 参数1 : { } 信息对象 -- 用户信息,前后端交互
	        // 参数2 : 密钥 -- 后端保存,视情况给前端
	        // 参数3 : { } 时效性 -- 签发之后,时效性内不可修改 时效性越短越好
	        const token = jwt.sign({ 
	            _id:1
	        },"mytoken",{expiresIn:"2h"});
	        
	        info = {
	            message:"正确",
	            status:1,
	            token //让 info携带 token 发给前端
	        }
	    }else{
	        info = {
	            message:"错误",
	            status:0
	        }
	    }
	    ctx.body = info;
	})

需要使用 token 验证的场景

  • 前端核心代码
	<button class="btn">点击 - 认证接口</button>
	
	<script>
		document.querySelector(".btn").onclick =function(){
			let xhr = new XMLHttpRequest();    
			xhr.open("post","/apiCheck",true); 
			// 获取 本地保存的token
			let token = localStorage.getItem("token");
			// 前端的认证
			if (token) {               
		        // Authorization : 告诉浏览器 携带着 token 属性
		        // Bearer空格:固定方式 + token
		        // Bearer 带有空格  注意必须带
				xhr.setRequestHeader("Authorization","Bearer " + token)
			}
			// 接收后端验证token信息的返回值
			xhr.onload = function(){
				// Authentication Error 验证不通过 token错误 
				console.log(xhr.responseText);
			}
			xhr.send();
		}
	</script>
  • 后端服务器核心代码
const koajwt = require("koa-jwt"); // 验证 token
// token 认证的接口 jwt在这里验证
// koajwt() 验证密码
// Authentication Error 验证不通过 token错误 
router.post("/apiCheck",koajwt({secret:"mytoken"}),ctx=>{
    ctx.body = {
        name:"来自验证接口"
    }
})
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值