苍穹外卖Day06笔记(复习了jwt的加密解密和传递)
疯玩了一个月,效率好低,今天开始捡起来苍穹外卖~
1. 为什么不需要单独引入HttpClient的dependency?
因为我们在sky-common的pom.xml中已经引入了aliyun-sdk-oss的依赖,而这个依赖低层就引入了httpclinet的依赖,根据依赖传递的原则,不需要单独再引入了
HttpClient的maven坐标
<dependency><groupId>org.apache.httpcomponents</groupId><artifactId>httpclient</artifactId><version>4.5.13</version>
</dependency>
2. 操作HttpClient请求发送的步骤
-
创建HttpClient对象
-
创建Http请求对象
-
调用HttpClient的execute方法发送请求
3. 微信登录功能需求和接口设计
4. 基于微信登录实现小程序的登录功能(如果是新用户则自动完成注册)
(1)接口设计
这个请求实现了“微信登录过程流程图”中的哪个部分?
(2)如果是新用户,则实现自动注册。在后端还得设计user表来存储用户信息
(3)代码开发
1)在application-dev.yml和application.yml中配置微信登录需要的配置项
2)在application.yml中配置为微信用户生成jwt令牌的配置项
- admin-secret-key:管理端设置jwt签名时使用的秘钥
- user-secret-key:用户端设置jwt签名时使用的秘钥
在JWT中,秘钥用于签名JWT以确保其完整性和真实性。JWT通常由三部分组成:头部(Header)、载荷(Payload)、签名(Signature)。在创建JWT时,会将头部和载荷进行Base64编码,然后用秘钥对编码后的头部和载荷进行签名,生成签名部分。
签名过程:
- 创建 JWT 的头部(Header)和载荷(Payload)。
- 将头部和载荷编码为 JSON 字符串,并使用 Base64 编码。
- 将编码后的头部和载荷通过一个字符(如".")连接起来形成一个字符串。
- 使用选定的加密算法(如HMAC、RSA、md5等)和预先配置的秘钥对上一步生成的字符串进行签名,生成签名部分。
- 将签名添加到JWT的尾部,生成最终的JWT。
验证过程:
- 接收到JWT后,将其分解为头部、载荷和签名三部分。
- 将头部和载荷进行相同的编码处理以及连接操作,生成一个字符串。
- 使用相同的加密算法和预先配置的秘钥对生成的字符串进行签名,生成一个新的签名。
- 将新生成的签名与JWT中的签名进行比较。如果两者相匹配,则JWT是有效的。
- admin-token-name和user-token-name
对于管理员身份的JWT,前端应该使用名为"token"的字段来传递JWT
对于用户身份的JWT,前端用名为“authentication”的字段来传递JWT
3)设计VO和DTO
发送的请求中有参数,接收参数需要DTO
VO用来接收返回数据
4)根据接口定义创建Controller方法
@RestController
@RequestMapping("/user/user")
@Api(tags = "C端用户相关接口")
@Slf4j
public class UserController {@Autowiredprivate UserService userService;@Autowiredprivate JwtProperties jwtProperties;/*** 微信登录* @param userLoginDTO* @return*/@PostMapping("/login")@ApiOperation("微信登录")public Result<UserLoginVO> login(@RequestBody UserLoginDTO userLoginDTO){log.info("微信用户登录:{}",userLoginDTO.getCode());// 微信登录User user = userService.wxLogin(userLoginDTO);// 为微信用户生成jwt令牌Map<String,Object> claims = new HashMap<>();claims.put(JwtClaimsConstant.USER_ID,user.getId());String token = JwtUtil.createJWT(jwtProperties.getUserSecretKey(), jwtProperties.getUserTtl(), claims);UserLoginVO userLoginVO = UserLoginVO.builder().id(user.getId()).openid(user.getOpenid()).token(token).build();return Result.success(userLoginVO);}
5) Service方法——传入微信登录授权码,返回id、openid和token
public interface UserService {/*** 微信登录* @param userLoginDTO* @return*/User wxLogin(UserLoginDTO userLoginDTO);
}
6) ServiceImpl——获得微信用户openid、返回id、openid、token方法的实现类
发送请求,传入微信登录授权码,获得微信用户的openid.
调用微信接口服务、传给微信服务端的数据都被封装在map里
/*** 调用微信接口服务,获取微信用户的openid* @param code* @return*/private String getOpenid(String code){Map<String, String> map = new HashMap<>();map.put("appid",weChatProperties.getAppid());map.put("secret",weChatProperties.getSecret());map.put("js_code", code);map.put("grant_type","authorization_code");String json = HttpClientUtil.doGet(WX_LOGIN, map);JSONObject jsonObject = JSON.parseObject(json);String openid = jsonObject.getString("openid");return openid;}
获取到openid之后,就可以实现微信登录
/*** 微信登录* @param userLoginDTO* @return*/public User wxLogin(UserLoginDTO userLoginDTO){// 调用微信接口服务,获得当前微信用户的openidString openid = getOpenid(userLoginDTO.getCode());// 判断openid是否为空,如果是空表示登录失败,抛出业务异常if(openid == null){throw new LoginFailedException(MessageConstant.LOGIN_FAILED);}// 判断当前用户是否是新用户User user = userMapper.getByOpenid(openid);// 如果是新用户,自动完成注册if(user == null){user = User.builder().openid(openid).createTime(LocalDateTime.now()).build();userMapper.insert(user);}// 返回这个用户对象return user;}
7) UserMapper的建立
为了在ServiceImpl中判断用户是否已经注册,需要获得user表的信息,因此我们创建UserMapper,以便能够通过openid查询用户是否已经注册
@Select("select * from user where openid = #{openid}")User getByOpenid(String openid);
将新用户插入user表的功能实现
/*** 插入数据* @param user*/void insert(User user);
还需要再userMapper.xml中添加insert语句
<insert id="insert" useGeneratedKeys="true" keyProperty="id">insert into user (openid, name, phone, sex, id_number, avatar, create_time)values (#{openid}, #{name}, #{phone}, #{sex}, #{idNumber}, #{avatar}, #{createTime})</insert>
8) 编写用户JWT的拦截器
5. 商品浏览功能的需求分析
6. 查询分类
后面还有根据分类id查询菜品、根据分类id查询套餐、根据套餐id查询菜品的功能,答案都在黑马的文档里面
相关文章:

苍穹外卖Day06笔记(复习了jwt的加密解密和传递)
疯玩了一个月,效率好低,今天开始捡起来苍穹外卖~ 1. 为什么不需要单独引入HttpClient的dependency? 因为我们在sky-common的pom.xml中已经引入了aliyun-sdk-oss的依赖,而这个依赖低层就引入了httpclinet的依赖,根据依…...
【ARM 嵌入式 C 字符串系列 23.9 -- strcmp 与 strncmp 在使用上的区别以及注意事项】
请阅读【嵌入式开发学习必备专栏】 文章目录 strcmp 与 strncmp 使用介绍strcmpstrncmp使用建议 strcmp 与 strncmp 使用介绍 strcmp 和 strncmp 都是 C 语言标准库中用于比较两个字符串的函数,它们定义在 <string.h> 头文件中。这两个函数在功能上相似&…...
行列视(RCV):企业数据处理的革新工具
在当前数据驱动的商业生态系统中,行列视(RCV)系统以其创新的企业数据处理功能,不断地为各行各业的企业带来变革。行列视系统能够处理大规模数据集,支持多达400种Excel函数,使得数据处理不仅限于基本的表格操…...
Oracle Patch清理
场景: 在对Oracle安装补丁后,会发现OS上被占用了大量的空间,本文档清理Opatch过程中的一些文件,释放空间 参考文档: Can You Delete $ORACLE_HOME/.patch_storage Directory ? (Doc ID 403218.1) How To Avoid Disk …...

Redis-三主三从高可用集群搭建
正式搭建之前,注意事项(坑)提前放到最开始,也可以出问题回来看, (1)第二步中最好将配置文件中的logfile自定义一个目录,以便于在第五步中启动出错的时候迅速定位错误。 ࿰…...
ImageMagick
Linux 安装 sudo apt install php8.2-imagick Windows 安装 下载 ImageMagick ImageMagick – Download 安装并将 D:\Program Files\ImageMagick-7.1.1-Q16-HDRI 加入到系统环境变量 path 中, 或者将 CORE_RL_*.dll 复制到 c:\windows\system32 下 下载 php 扩展…...

攻防世界-web-command_execution
题目: 原理: | 的作用为将前一个命令的结果传递给后一个命令作为输入 &&的作用是前一条命令执行成功时,才执行后一条命令 方法一: 第一步: 1.打开浏览器,在文本框内输入127.0.0.1 | find / -name…...
go语言自定义排序接口Interface实现示例 sort.Sort(data Interface) 快速排序 pdqsort
go语言sort.Sort(data Interface) 排序接口自定义排序实现,golang里面的sort包中的Sort方法底层使用的是 pdqsort的一个快速排序算法, 我们可以将要排序的对象实现Interface接口后直接丢个这个函数即可自动按照我们指定的方式进行数据快速排序。 sort函…...

RIP动态路由协议详解
目录 一:RIP协议的基本信息 二:RIP协议中的更新方式 三:RIP协议中的计时器 定时更新器(UPDATE timer) 无效定时器(invalid Timer) 垃圾收集定时器(garbage collection timer&a…...

ROS2 安装与测试
文章目录 ROS2 安装与测试ROS2 安装1. 设置编码2. 添加源3. 安装 ROS24. 设置环境变量 ROS2 示例测试实例一:命令行实例实例二:小海龟仿真实例 参考链接 ROS2 安装与测试 ROS2 安装 基于 Ubuntu 22.04 LTS 操作系统。 1. 设置编码 sudo apt update &…...
MySQL数据分组技术深度解析及实践
在处理大量数据库记录时,数据分组是一种强大的工具,它允许我们按照特定列的值将数据划分为逻辑上的集合,进而对每个集合执行聚合操作,如计数、求和或平均值等。MySQL中的GROUP BY子句正是实现这一功能的关键所在。本文将详细介绍GROUP BY的使用方法,结合…...

【敦煌网注册/登录安全分析报告】
敦煌网注册/登录安全分析报告 前言 由于网站注册入口容易被黑客攻击,存在如下安全问题: 暴力破解密码,造成用户信息泄露短信盗刷的安全问题,影响业务及导致用户投诉带来经济损失,尤其是后付费客户,风险巨大…...

Python读取ASC文件并转换成Excel文件(坐标)
import pandas as pd# 读取asc文件,指定空格为分隔符 df pd.read_csv(out_view2.asc, sep , headerNone)# 去掉空列 df df.dropna(howall, axis1)# 将数据保存到Excel文件 df.to_excel(out_view2.xlsx, indexFalse, headerFalse)效果图...
Rust 的 Warp 库编写的 restful api 参数传递与解析方法
Warp是一个用 Rust 编写的流行的异步 web 框架。在使用 warp 构建 RESTful API 时,可以通过多种方式传递参数到你的处理函数中。 以下是一些常见的方法,说明如何在 warp 中传递参数: 路径参数: 你可以使用 warp::path 和 warp::…...
关不掉的弹窗
这里分两种方式 第一种 #include<Windows.h> int main(){system("mode 15,14");while(1){MessageBox(NULL,TEXT("关不掉吧!"),TEXT("中病毒啦~~你这个SB!"),MB_OK);}} 实际上不是关不掉,而是关不完 解决方法:找…...

【JVM】类加载机制及双亲委派模型
目录 一、类加载过程 1. 加载 2. 连接 a. 验证 b. 准备 c. 解析 3. 初始化 二、双亲委派模型 类加载器 双亲委派模型的工作过程 双亲委派模型的优点 一、类加载过程 JVM的类加载机制是JVM在运行时,将 .class 文件加载到内存中并转换为Java类的过程。它…...

WordPress插件:链接自动识别转为超链接
WordPress插件:链接自动识别转为超链接 <?phpfunction open_links_in_new_tab() {add_filter(the_content, make_clickable);function autoblank($text) {$return str_replace(<a, <a target"_blank", $text);return $return;}add_filter(th…...

Java----数组的定义和使用
1.数组的定义 在Java中,数组是一种相同数据类型的集合。数组在内存中是一段连续的空间。 2.数组的创建和初始化 2.1数组的创建 在Java中,数组创建的形式与C语言又所不同。 Java中数组创建的形式 T[] 数组名 new T[N]; 1.T表示数组存放的数据类型…...
【C++】-QT多线程-006
1【QT】多线程 #ifndef MYWIDGET_H #define MYWIDGET_H#include <QWidget>namespace Ui { class MyWidget; }class MyWidget : public QWidget {Q_OBJECTpublic:explicit MyWidget(QWidget *parent 0);~MyWidget();/* 5 自定义信号*/ /*所有的信号函数只声明不定义&…...

vscode go语言开发中在任意包运行和调试代码 Example使用方法
一般情况下我们在进行go语言开发的时候我们都需要创建一个main方法和main包才能运行go代码, 针对这个问题,go语言给我们内置了功能强大的testing测试框架, 其中一个很有意思的Example测试就非常的方便使用。 他不管你在什么包,也…...

Qt/C++开发监控GB28181系统/取流协议/同时支持udp/tcp被动/tcp主动
一、前言说明 在2011版本的gb28181协议中,拉取视频流只要求udp方式,从2016开始要求新增支持tcp被动和tcp主动两种方式,udp理论上会丢包的,所以实际使用过程可能会出现画面花屏的情况,而tcp肯定不丢包,起码…...
DeepSeek 赋能智慧能源:微电网优化调度的智能革新路径
目录 一、智慧能源微电网优化调度概述1.1 智慧能源微电网概念1.2 优化调度的重要性1.3 目前面临的挑战 二、DeepSeek 技术探秘2.1 DeepSeek 技术原理2.2 DeepSeek 独特优势2.3 DeepSeek 在 AI 领域地位 三、DeepSeek 在微电网优化调度中的应用剖析3.1 数据处理与分析3.2 预测与…...

使用分级同态加密防御梯度泄漏
抽象 联邦学习 (FL) 支持跨分布式客户端进行协作模型训练,而无需共享原始数据,这使其成为在互联和自动驾驶汽车 (CAV) 等领域保护隐私的机器学习的一种很有前途的方法。然而,最近的研究表明&…...

关于iview组件中使用 table , 绑定序号分页后序号从1开始的解决方案
问题描述:iview使用table 中type: "index",分页之后 ,索引还是从1开始,试过绑定后台返回数据的id, 这种方法可行,就是后台返回数据的每个页面id都不完全是按照从1开始的升序,因此百度了下,找到了…...

论文浅尝 | 基于判别指令微调生成式大语言模型的知识图谱补全方法(ISWC2024)
笔记整理:刘治强,浙江大学硕士生,研究方向为知识图谱表示学习,大语言模型 论文链接:http://arxiv.org/abs/2407.16127 发表会议:ISWC 2024 1. 动机 传统的知识图谱补全(KGC)模型通过…...

HBuilderX安装(uni-app和小程序开发)
下载HBuilderX 访问官方网站:https://www.dcloud.io/hbuilderx.html 根据您的操作系统选择合适版本: Windows版(推荐下载标准版) Windows系统安装步骤 运行安装程序: 双击下载的.exe安装文件 如果出现安全提示&…...
精益数据分析(97/126):邮件营销与用户参与度的关键指标优化指南
精益数据分析(97/126):邮件营销与用户参与度的关键指标优化指南 在数字化营销时代,邮件列表效度、用户参与度和网站性能等指标往往决定着创业公司的增长成败。今天,我们将深入解析邮件打开率、网站可用性、页面参与时…...
Qt 事件处理中 return 的深入解析
Qt 事件处理中 return 的深入解析 在 Qt 事件处理中,return 语句的使用是另一个关键概念,它与 event->accept()/event->ignore() 密切相关但作用不同。让我们详细分析一下它们之间的关系和工作原理。 核心区别:不同层级的事件处理 方…...
Docker拉取MySQL后数据库连接失败的解决方案
在使用Docker部署MySQL时,拉取并启动容器后,有时可能会遇到数据库连接失败的问题。这种问题可能由多种原因导致,包括配置错误、网络设置问题、权限问题等。本文将分析可能的原因,并提供解决方案。 一、确认MySQL容器的运行状态 …...

从物理机到云原生:全面解析计算虚拟化技术的演进与应用
前言:我的虚拟化技术探索之旅 我最早接触"虚拟机"的概念是从Java开始的——JVM(Java Virtual Machine)让"一次编写,到处运行"成为可能。这个软件层面的虚拟化让我着迷,但直到后来接触VMware和Doc…...