我们一起聊一聊JWT的那些事

news2024/11/24 23:07:34

我们一起聊一聊JWT的那些事

在这里插入图片描述
一切美好,如期而至…

什么是JWT

JWT,全称为 JSON Web Token,是一种用于在网络上安全地传递信息的开放标准(RFC 7519)。JWT 是一种紧凑且独立的方式,用于在各方之间以 JSON 对象形式安全地传输信息。该信息可以被验证和信任,因为它是经过数字签名的。JWT 可以使用秘密(使用 HMAC 算法)或使用公钥/私钥对(使用 RSA 或 ECDSA 算法)进行签名。

JWT 通常用于身份验证和信息交换。在身份验证方面,当用户成功登录后,服务器会生成一个包含用户标识信息的 JWT,并将其发送回客户端。客户端随后可以在每个后续请求中包含 JWT,以证明其身份。在信息交换方面,由于 JWT 的信息是经过签名的,接收方可以验证其来源和完整性。

JWT 的结构如下:

xxxxx.yyyyy.zzzzz

其中,每一部分由点号分隔:

  • 第一部分是头部(Header),通常包含两部分信息:令牌类型(JWT)和所使用的签名算法,例如 HMAC SHA256 或 RSA。

  • 第二部分是载荷(Payload),包含声明(claims)。声明是关于实体(通常是用户)和其他数据的声明。有三种类型的声明:注册的声明,公共的声明和私有的声明。

  • 第三部分是签名(Signature),用于验证消息在传递过程中没有被篡改,并确保消息的发送方是可信的。

JWT 的优点包括:

  1. 自包含: JWT 包含了所有需要的信息,减少了在服务器存储会话状态的需要。

  2. 跨域: 由于 JWT 是在各方之间传递的标准格式,可以在不同域之间轻松传递信息。

  3. 安全性: 当使用数字签名时,可以确保 JWT 的来源和完整性。

然而,需要注意的是,为了确保安全性,不应该在 JWT 中存储敏感信息,尤其是在使用对称加密算法的情况下。对于敏感信息,最好在服务器端进行验证。

和普通的token有啥区别子

JSON Web Token(JWT)和普通的 token 之间有一些关键区别,主要涉及到它们的结构、用途和安全性等方面:

  1. 结构差异:

    • 普通 Token: 通常是一个简单的字符串,可能是随机生成的一串字符,例如 UUID(Universally Unique Identifier)。
    • JWT: 具有明确定义的结构,包含头部、载荷和签名三个部分,并以点号分隔。这种结构使得 JWT 可以携带更多的信息,并且具有更灵活的用途。
  2. 内容携带:

    • 普通 Token: 只是一个标识符,不携带其他有关用户或实体的信息。
    • JWT: 可以携带一些声明(claims),这些声明包含有关用户、角色、权限等信息。由于 JWT 是基于 JSON 格式的,因此它可以以一种结构化的方式携带更多的信息。
  3. 签名和验证:

    • 普通 Token: 通常需要在服务器端进行验证,但不一定使用数字签名或加密。
    • JWT: 通常使用数字签名来验证其真实性。这使得 JWT 在传递过程中能够被验证,确保它没有被篡改。JWT 还支持使用非对称加密来提供额外的安全性。
  4. 安全性:

    • 普通 Token: 可能存在被伪造或截获的风险,因为它没有内置的安全机制。
    • JWT: 通过数字签名或加密,提供了一定程度的安全性。如果使用对称加密,需要确保密钥的安全性;如果使用非对称加密,可以更安全地传递公钥。
  5. 用途:

    • 普通 Token: 通常用于简单的身份验证,例如在会话中保存用户的登录状态。
    • JWT: 由于其结构和灵活性,可用于更广泛的用途,包括身份验证、信息交换和声明传递。

总体而言,JWT 是一种更为灵活、结构化且安全的令牌,适用于需要携带更多信息和在跨域环境中进行安全传递的场景。普通 Token 更适合简单的身份验证场景。选择使用哪种令牌取决于具体的应用需求和安全要求。

如何生成JWT

前端生成

生成 JSON Web Tokens(JWT)涉及以下步骤:

  1. 选择一个密钥: JWT 使用密钥进行签名以确保数据的完整性和来源。密钥可以是对称密钥(HMAC算法)或非对称密钥(RSA或ECDSA算法)。

  2. 构建JWT的头部(Header): JWT的头部包含有关令牌的元信息,如算法和令牌类型。这部分信息通常以Base64编码的JSON字符串表示,并放置在JWT的第一部分。

  3. 构建JWT的载荷(Payload): 载荷包含有关JWT主体(subject)的声明和其他信息。与头部一样,这部分信息也是以Base64编码的JSON字符串表示,并放置在JWT的第二部分。

  4. 对头部和载荷进行签名: 使用选择的算法和密钥对头部和载荷进行签名。签名是通过将Base64编码的头部和载荷字符串与密钥一起进行加密而生成的。

  5. 将头部、载荷和签名组合成JWT: 将Base64编码的头部、Base64编码的载荷和签名以点号分隔组合在一起形成JWT。

下面是一个简单的例子,使用Node.js中的jsonwebtoken库生成JWT:

const jwt = require('jsonwebtoken');

// 构建头部
const header = {
  "alg": "HS256",  // HMAC SHA-256算法
  "typ": "JWT"
};

// 构建载荷
const payload = {
  "sub": "1234567890",  // 主体标识
  "name": "John Doe",
  "iat": Math.floor(Date.now() / 1000)  // 签发时间(当前时间)
};

// 选择密钥
const secretKey = "yourSecretKey";

// 生成JWT
const token = jwt.sign(payload, secretKey, { header });

console.log(token);

在实际应用中,建议使用更安全的随机生成的密钥,并根据具体的需求选择适当的算法和配置选项。生成JWT的代码示例可能会根据所选的编程语言和库而有所不同,但上述步骤是通用的。

后端生成

在Java中,你可以使用 io.jsonwebtoken 库来生成 JSON Web Tokens(JWT)。以下是一个简单的例子:

首先,你需要将 jjwt 库添加到你的项目中。如果使用 Maven,可以在 pom.xml 文件中添加以下依赖:

<dependency>
    <groupId>io.jsonwebtoken</groupId>
    <artifactId>jjwt-api</artifactId>
    <version>0.11.2</version>
</dependency>
<dependency>
    <groupId>io.jsonwebtoken</groupId>
    <artifactId>jjwt-impl</artifactId>
    <version>0.11.2</version>
    <scope>runtime</scope>
</dependency>
<dependency>
    <groupId>io.jsonwebtoken</groupId>
    <artifactId>jjwt-jackson</artifactId>
    <version>0.11.2</version>
    <scope>runtime</scope>
</dependency>

然后,你可以使用以下Java代码生成JWT:

import io.jsonwebtoken.Jwts;
import io.jsonwebtoken.SignatureAlgorithm;

import java.util.Date;

public class JwtGenerator {

    public static void main(String[] args) {
        // 构建头部
        String algorithm = SignatureAlgorithm.HS256.getJcaName();
        String header = "{\"alg\":\"" + algorithm + "\",\"typ\":\"JWT\"}";

        // 构建载荷
        String subject = "1234567890";  // 主体标识
        String name = "John Doe";
        long nowMillis = System.currentTimeMillis();
        Date iat = new Date(nowMillis);  // 签发时间(当前时间)

        // 选择密钥
        String secretKey = "yourSecretKey";

        // 生成JWT
        String token = Jwts.builder()
                .setHeader(header)
                .setSubject(subject)
                .claim("name", name)
                .setIssuedAt(iat)
                .signWith(SignatureAlgorithm.HS256, secretKey)
                .compact();

        System.out.println(token);
    }
}

请确保替换示例中的密钥和其他参数为你实际的值。这个例子中使用了 HMAC SHA-256 算法,但你可以根据需求选择其他算法。在实际应用中,密钥应该是安全的,并且可能需要使用环境变量或其他方式来管理。

还有那些库

除了 io.jsonwebtoken,还有一些其他常用的Java库可以用于生成和处理JSON Web Tokens(JWT)。以下是一些常见的JWT库:

  1. Nimbus JOSE + JWT:
    在这里插入图片描述

    • 官方网站: Nimbus JOSE + JWT
    • 主要功能:
      • 提供了处理JOSE(JSON Object Signing and Encryption)和JWT的Java库。
      • 支持各种JWT相关的标准和规范,如JWT、JWS(JSON Web Signature)、JWE(JSON Web Encryption)等。
      • 提供了易于使用的API,支持生成和验证JWT。
  2. Java-JWT:
    在这里插入图片描述

    • GitHub地址: Java-JWT
    • 主要功能:
      • Auth0开发的Java库,用于生成和验证JWT。
      • 支持标准的JWT算法,如HMAC SHA256、RS256等。
      • 提供了简洁的API,适用于各种JWT用例。
  3. JJWT:
    在这里插入图片描述

    • GitHub地址: JJWT
    • 主要功能:
      • 一个简单的Java库,用于生成、解析和验证JWT。
      • 支持各种算法,包括HMAC SHA256、RS256等。
      • 提供了流畅的API,易于使用。
        当然,还有HuTool工具类,就不多赘述了
        在这里插入图片描述

选择使用哪个库取决于你的具体需求、项目的特点以及个人偏好。在使用之前,请仔细查阅相关文档,了解库的功能、性能和安全性。

JWT的解析和验证

解析和验证 JSON Web Tokens(JWT)通常包括以下步骤:

  1. 拆分 JWT: JWT 由三部分组成,分别是头部(Header)、载荷(Payload)、签名(Signature),它们之间用点号分隔。首先,将 JWT 字符串拆分成这三个部分。

  2. 解码 Base64: 对头部和载荷进行 Base64 解码,得到 JSON 字符串。

  3. 解析 JSON: 将解码后的头部和载荷 JSON 字符串解析为 JSON 对象。

  4. 验证签名(可选): 如果 JWT 使用签名算法进行签名,需要对头部、载荷和签名进行验证。验证的步骤通常包括获取密钥(对称或非对称密钥),使用相同的签名算法对头部和载荷进行签名,然后比较生成的签名与 JWT 中的签名是否匹配。

以下是一个使用 Java 的示例,使用 io.jsonwebtoken 库进行 JWT 解析和验证的过程:

import io.jsonwebtoken.Claims;
import io.jsonwebtoken.ExpiredJwtException;
import io.jsonwebtoken.Jws;
import io.jsonwebtoken.Jwts;
import io.jsonwebtoken.SignatureException;

public class JwtParser {

    public static void main(String[] args) {
        // 要解析和验证的 JWT 字符串
        String jwtString = "yourJwtStringHere";

        try {
            // 解析 JWT
            Jws<Claims> jws = Jwts.parserBuilder()
                    .setSigningKey("yourSecretKey")  // 设置密钥
                    .build()
                    .parseClaimsJws(jwtString);

            // 获取载荷(Claims)
            Claims claims = jws.getBody();

            // 在此可以获取 JWT 中的信息,例如:
            String subject = claims.getSubject();
            String name = (String) claims.get("name");
            // 其他声明的获取方法...

            // 验证通过,可以继续处理业务逻辑
            System.out.println("JWT验证通过");

        } catch (ExpiredJwtException e) {
            // JWT 过期异常
            System.out.println("JWT已过期");
        } catch (SignatureException e) {
            // JWT 签名异常
            System.out.println("JWT签名验证失败");
        } catch (Exception e) {
            // 其他异常
            System.out.println("JWT解析失败");
        }
    }
}

请注意,上述代码中的密钥和其他参数需要根据你的实际情况进行调整。此外,对于非对称加密的情况,需要提供公钥进行验证。在实际应用中,也可以考虑使用库提供的更复杂的配置选项和错误处理机制。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1292542.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

Docker部署开源分布式任务调度系统DolphinScheduler与远程访问办公

文章目录 前言1. 安装部署DolphinScheduler1.1 启动服务 2. 登录DolphinScheduler界面3. 安装内网穿透工具4. 配置Dolphin Scheduler公网地址5. 固定DolphinScheduler公网地址 前言 本篇教程和大家分享一下DolphinScheduler的安装部署及如何实现公网远程访问&#xff0c;结合内…

STM32 定时器配置步骤

定时中断基本框架结构图&#xff1a; 根据结构图可按步骤配置定时器 第1步&#xff1a;RCC开启时钟。打开时钟后定时器的基准时钟和整个外设的工作时钟就会同时打开。 第2步&#xff1a;选择时基单元的时钟源。对于定时中断可选择内部时钟源. 第3步&#xff1a;配置时基单元…

12.7作业

1.头文件 #ifndef WIDGET_H #define WIDGET_H#include <QWidget> #include <QIcon> #include <QLabel> #include <QMovie> #include <QLineEdit> #include <QPushButton> class Widget : public QWidget {Q_OBJECTpublic:Widget(QWidge…

论文笔记——DAS

论文&#xff1a;https://arxiv.org/pdf/2311.12091.pdf 代码&#xff1a;暂无 卷积神经网络&#xff08;CNNs&#xff09;在局部空间模式识别方面表现出色。对于许多视觉任务&#xff0c;如物体识别和分割&#xff0c;显著信息也存在于CNN核边界之外。然而&#xff0c;由于CN…

在Spring Cloud使用Hystrix核心组件,并注册到Eureka注册中心去

其实吧&#xff0c;写Spring Cloud系列&#xff0c;我有时候觉得也挺难受的&#xff0c;因为Spring Cloud的微服务启动都需要一个一个来&#xff0c;并且在IDea中也需要占用比较大的内存&#xff0c;并且我本来可以一篇写完5大核心组件的&#xff0c;但是我却分了三篇&#xff…

Implicit Neural Representation for Cooperative Low-light Image Enhancement

GitHub - Ysz2022/NeRCo: [ICCV 2023] Implicit Neural Representation for Cooperative Low-light Image Enhancement 参考&#xff1a;ICCV2023 | 将隐式神经表征用于“低光增强”&#xff0c;北大张健团队提出NeRCo (qq.com) 以下三个因素限制了现有低光图像增强方法的应用…

状态机的练习:按键控制led灯

设计思路&#xff1a; 三个按键控制led输出。 三个按键经过滤波(消抖)&#xff0c;产生三个按键标志信号。 三个led数据的产生模块&#xff08;流水&#xff0c;跑马&#xff0c;闪烁模块&#xff09;&#xff0c;分别产生led信号。 这六路信号&#xff08;三路按键信号&am…

Java网络编程——Socket用法解析

在客户/服务器通信模式中&#xff0c;客户端需要主动创建与服务器连接的Socket&#xff0c;服务器端收到了客户的连接请求&#xff0c;也会创建与客户连接的Socket。Socket可以被看作是通信连接两端的收发器&#xff0c;服务器与客户都通过套接字来收发数据。 1、构造Socket …

企业数字化转型的七个成功案例

尽管经济形势严峻&#xff0c;但60%的企业告诉波士顿咨询公司&#xff0c;他们将在2023年增加数字化转型投资。根据Precedence Research最近的一份报告&#xff0c;到2025年&#xff0c;数字化转型市场预计将达到1.458万亿美元。 成长型股权公司PSG的董事总经理安东尼爱德华兹…

【hacker送书第10期】AI时代系列丛书(五选一)

AI时代系列丛书 AI时代程序员开发之道✨内容简介参与方式 AI时代项目经理成长之道✨内容简介参与方式 AI时代架构师修炼之道✨内容简介参与方式 AI时代产品经理升级之道✨内容简介参与方式 AI时代Python量化交易实战✨内容简介参与方式 AI时代程序员开发之道✨ 内容简介 本书是…

C#中GDI+图形图像技术(Graphics类、Pen类、Brush类)

目录 一、创建Graphics对象 1.创建Pen对象 2.创建Brush对象 &#xff08;1&#xff09;SolidBrush类 &#xff08;2&#xff09;HatchBrush类 ​​​​​​​&#xff08;3&#xff09;LinerGradientBrush类 用户界面上的窗体和控件非常有用&#xff0c;且引人注目&#…

优雅提效:Guava的字符串处理工具

第1章&#xff1a;引言 大家好&#xff0c;我是小黑&#xff0c;今天咱们要聊一聊Google Guava这个超棒的Java库&#xff0c;尤其是它的字符串处理工具。对于Java程序员来说&#xff0c;字符串处理是日常工作的一部分&#xff0c;而Guava在这方面提供了非常强大的支持。使用Gu…

Unity中Batching优化的GPU实例化(3)

文章目录 前言一、UNITY_SETUP_INSTANCE_ID(v);二、在UnityInstancing.cginc文件中&#xff0c;看一下Unity这句话做了什么1、使用了该 .cginc 后&#xff0c;会自动预定义该函数2、需要满足GPU实例化条件&#xff0c;才会执行对应语句3、满足GPU实例化后&#xff0c;主要执行的…

Python Tornado 框架的终极指南!

更多资料获取 &#x1f4da; 个人网站&#xff1a;ipengtao.com Python Tornado框架是一个高性能的异步Web框架&#xff0c;被广泛应用于构建实时Web应用和API服务。本文将深度解析Tornado框架&#xff0c;介绍其核心概念、异步特性、路由系统、模板引擎以及WebSocket支持等方…

通过Powershell远程控制windows服务器

1、被测服务器5985、5986端口开启&#xff0c;在网络设置中&#xff0c;点击“更改连接属性”。 2、网络配置文件中选择“专用”。 3、以管理员权限运行Powershell&#xff0c; 4.通过powershell命令在本地电脑上添加远端信任主机 winrm set winrm/config/client {TrustedHos…

世微 AP3266 大功率同步降压恒流芯片 过EMC 车灯驱动

产品描述 AP3266 是高效率、外围简单、内置功率管的同步降压恒流芯片&#xff0c;适用于4-40V输入的降压LED恒流驱动芯片。输出最大功率可达 40W&#xff0c;最大电流3.6A。AP3266 可通过调节 OVP 端口的分压电阻&#xff0c;设定输出空载电压 保护&#xff0c;避免高压 空载上…

如何搭建一套完整的智能安防视频监控平台?关于设备与软件选型的几点建议

安防视频监控系统主要由前端摄像机设备、视频显示设备、视频存储设备、安防应用软件/平台以及其它传输、辅助类设备组成。一般来说&#xff0c;安防监控系统具有可扩展和开放性&#xff0c;以方便未来的扩展和与其他系统的集成。今天我们就来介绍一下&#xff0c;搭建一套完整的…

JAVA全栈开发 MySql详解

一、数据库 1.数据储存在哪里&#xff1f; 硬盘、网盘、U盘、光盘、内存&#xff08;临时存储&#xff09; 数据持久化 使用文件来进行存储&#xff0c;数据库也是一种文件&#xff0c;像excel &#xff0c;xml 这些都可以进行数据的存储&#xff0c;但大量数据操作&#x…

搜维尔科技:Varjo XR-4 系列-专为极致沉浸感而打造!

Varjo 的新一代头显将世界上最先进的混合现实技术与顶尖的图形处理能力连接起来&#xff0c;满足最高级别的视觉保真度和沉浸感至关重要的工业用例。 光学设计的根本性突破 体验全新的沉浸感。大幅扩展的视野&#xff0c;跨越 120 x 105 度&#xff0c;打破了受人尊敬的“全双眼…

跨域的多种方案详解

浏览器的同源策略是为了保护用户的安全&#xff0c;限制了跨域请求。同源策略要求请求的域名、协议和端口必须完全一致&#xff0c;只要有一个不同就会被认为是跨域请求。 本文列举了一些处理跨域请求的解决方案&#xff1a; JSONPCORS跨域资源共享http proxynginx反向代理web…