SpringClound——网关、服务保护和分布式事务

一、网关

网络的关口,负责请求的路由、转发、身份验证

server:port: 8080
spring:cloud:nacos:discovery:server-addr: 192.168.96.129:8848gateway:routes:- id: item-serviceuri: lb://item-servicepredicates:- Path=/items/**,/search/**- id: user-serviceuri: lb://user-servicepredicates:- Path=/addresses/**,/users/**- id: cart-serviceuri: lb://cart-servicepredicates:- Path=/carts/**- id: trade-serviceuri: lb://trade-servicepredicates:- Path=/orders/**application:name: hm-gateway

二、网关登录校验

自定义过滤器:

package com.hmall.gateway.filters;import org.springframework.cloud.gateway.filter.GatewayFilterChain;
import org.springframework.cloud.gateway.filter.GlobalFilter;
import org.springframework.core.Ordered;
import org.springframework.http.server.reactive.ServerHttpRequest;
import org.springframework.stereotype.Component;
import org.springframework.web.server.ServerWebExchange;
import reactor.core.publisher.Mono;@Component
public class MyGlobalFilter implements GlobalFilter, Ordered {@Overridepublic Mono<Void> filter(ServerWebExchange exchange, GatewayFilterChain chain) {ServerHttpRequest request = exchange.getRequest();System.out.println("GlobalFilter pre阶段 执行了");return chain.filter(exchange);}@Overridepublic int getOrder() {return 0;}
}

微服务项目网关:

package com.hmall.gateway.filters;import com.hmall.common.exception.UnauthorizedException;
import com.hmall.gateway.config.AuthProperties;
import com.hmall.gateway.utils.JwtTool;
import lombok.RequiredArgsConstructor;
import org.springframework.cloud.gateway.filter.GatewayFilterChain;
import org.springframework.cloud.gateway.filter.GlobalFilter;
import org.springframework.core.Ordered;
import org.springframework.http.HttpStatus;
import org.springframework.http.server.reactive.ServerHttpRequest;
import org.springframework.http.server.reactive.ServerHttpResponse;
import org.springframework.stereotype.Component;
import org.springframework.util.AntPathMatcher;
import org.springframework.web.server.ServerWebExchange;
import reactor.core.publisher.Mono;import java.util.List;@Component
@RequiredArgsConstructor
public class AuthGlobalFilter implements GlobalFilter, Ordered {//不需要处理的请求路径public final AuthProperties authProperties;public final JwtTool jwtTool;private final AntPathMatcher antPathMatcher = new AntPathMatcher();@Overridepublic Mono<Void> filter(ServerWebExchange exchange, GatewayFilterChain chain) {//获得请求头ServerHttpRequest request = exchange.getRequest();//放行不需要拦截的请求//路径合法,需要放行if (isUnique(request.getPath().toString())){//合法,放行return chain.filter(exchange);}//判断令牌是否合法String token=null;Long userId=null;List<String> authorization = request.getHeaders().get("authorization");if (authorization != null && authorization.size() > 0) {token = authorization.get(0);}try {userId = jwtTool.parseToken(token);}catch (UnauthorizedException e) {//401 未登录、未授权ServerHttpResponse response = exchange.getResponse();response.setStatusCode(HttpStatus.UNAUTHORIZED);return response.setComplete();}//TODO 保存用户id到请求头,实现多个微服务间用户id的共享String userInfo = userId.toString();ServerWebExchange swe=exchange.mutate().request(builder -> builder.header("user-info", userInfo)).build();//System.out.println(userId);//放行return chain.filter(swe);}@Overridepublic int getOrder() {return 0;}private boolean isUnique(String path) {for (String excludePath : authProperties.getExcludePaths()) {if (antPathMatcher.match(excludePath, path)) {return true;}}return false;}
}

server:port: 8080
spring:application:name: hm-gatewaycloud:nacos:discovery:server-addr: 192.168.96.129:8848gateway:routes:- id: item-serviceuri: lb://item-servicepredicates:- Path=/items/**,/search/**- id: user-serviceuri: lb://user-servicepredicates:- Path=/addresses/**,/users/**- id: cart-serviceuri: lb://cart-servicepredicates:- Path=/carts/**- id: trade-serviceuri: lb://trade-servicepredicates:- Path=/orders/**- id: pay-serviceuri: lb://pay-servicepredicates:- Path=/pay-orders/**
hm:jwt:location: classpath:hmall.jksalias: hmallpassword: hmall123tokenTTL: 30mauth:excludePaths:- /search/**- /users/login- /items/**- /hi

网关传递用户:将用户的id保存在请求头当中,通过统一拦截处理,获取用户的id,放入ThreadLocal当中;请求完成,清理ThreadLocal,实现用户id从网关到各个项目模块的传递

OpenFeign传递用户:OpenFeign中提供了一个拦截器接口,所有由OpenFeign发起的请求都会先调用拦截器处理请求,在拦截处理过程中,我们将ThreadLocal中的用户id放入OpenFeign的请求头当中,其他微服务拦截处理的过程中获得用户id并放入线程当中

三、配置管理

1.拉取共享配置

2.加入相关依赖

        <!--nacos配置管理--><dependency><groupId>com.alibaba.cloud</groupId><artifactId>spring-cloud-starter-alibaba-nacos-config</artifactId></dependency><!--读取bootstrap文件--><dependency><groupId>org.springframework.cloud</groupId><artifactId>spring-cloud-starter-bootstrap</artifactId></dependency>

3.配置热更新

(1)nacos中要有一个与微服务名有关的配置文件

(2)微服务中要以特定方式读取需要热更新的配置属性

package com.hmall.cart.config;
import lombok.Data;
import org.springframework.boot.context.properties.ConfigurationProperties;
import org.springframework.stereotype.Component;
@Component
@Data
@ConfigurationProperties(prefix = "hm.cart")
public class MaxCommodityConfig {private Integer maxCommodity;
}

4.动态路由

package com.hmall.gateway.routes;
import cn.hutool.json.JSONUtil;
import com.alibaba.cloud.nacos.NacosConfigManager;
import com.alibaba.nacos.api.config.listener.Listener;
import com.alibaba.nacos.api.exception.NacosException;
import lombok.RequiredArgsConstructor;
import org.springframework.cloud.gateway.route.RouteDefinition;
import org.springframework.cloud.gateway.route.RouteDefinitionWriter;
import org.springframework.stereotype.Component;
import reactor.core.publisher.Mono;import javax.annotation.PostConstruct;
import java.util.HashSet;
import java.util.List;
import java.util.concurrent.Executor;@Component
@RequiredArgsConstructor
public class DynamicRounterLoader {private final NacosConfigManager nacosConfigManager;private final RouteDefinitionWriter writer;private final String dataId="gateway-routes.json";private final String group="DEFAULT_GROUP";//记录路由的idprivate HashSet<String> set=new HashSet<String>();//在Bean初始化之后执行@PostConstructpublic void initRoutesConfigListener() throws NacosException {//拉取配置并更新配置String configInfo = nacosConfigManager.getConfigService().getConfigAndSignListener(dataId, group, 5000, new Listener() {@Overridepublic Executor getExecutor() {return null;}@Overridepublic void receiveConfigInfo(String configInfo) {//路由表更新,更新监听器System.out.println(configInfo+"监听器更新执行了");updateRouters(configInfo);}});System.out.println(configInfo+"监听器更新了");//第一次启动,更新监听器updateRouters(configInfo);}private void updateRouters(String configInfo) {//将json数据转换为实体类List<RouteDefinition> routeDefinitionList = JSONUtil.toList(configInfo, RouteDefinition.class);//删除原来的路由表for (String id : set) {writer.delete(Mono.just(id)).subscribe();}set.clear();//添加新的路由表并记录idfor (RouteDefinition routeDefinition : routeDefinitionList) {writer.save(Mono.just(routeDefinition)).subscribe();set.add(routeDefinition.getId());}}}

将yaml配置转换为json配置:

[{"id": "item","predicates": [{"name": "Path","args": {"_genkey_0":"/items/**", "_genkey_1":"/search/**"}}],"filters": [],"uri": "lb://item-service"},{"id": "cart","predicates": [{"name": "Path","args": {"_genkey_0":"/carts/**"}}],"filters": [],"uri": "lb://cart-service"},{"id": "user","predicates": [{"name": "Path","args": {"_genkey_0":"/users/**", "_genkey_1":"/addresses/**"}}],"filters": [],"uri": "lb://user-service"},{"id": "trade","predicates": [{"name": "Path","args": {"_genkey_0":"/orders/**"}}],"filters": [],"uri": "lb://trade-service"},{"id": "pay","predicates": [{"name": "Path","args": {"_genkey_0":"/pay-orders/**"}}],"filters": [],"uri": "lb://pay-service"}
]

三、服务保护和分布式事务

1.雪崩问题

微服务调用链路中的某个服务故障,引起整个链路中的所有微服务都不可用

解决方案:保证代码的健壮性、保证网络的畅通、能应对高并发请求

2.服务保护

请求限流:限制访问服务器的并发量,避免服务因流量激增出现故障

线程隔离:模拟船舱隔板的防水原理。通过限定每个业务能使用的线程数量而将故障业务隔离,避免故障扩散

服务熔断:由断路器统计请求的异常比例或慢调用比例,如果超出阈值则会熔断业务,则拦截该接口请求

3.分布式事务

事务协调者(TC):维护全局和分支事务的状态,协调全局事务提交和回滚

事务管理器(TM):定义全局事务范围、开始全局事务、提交或回滚全局事务

资源管理器(RM):管理分支事务,与TC交谈以注册分支事务和报告分支事务状态

XA模式:

优点:事务的强一致性,满足ACID原则​,常用数据库都支持,实现简单,并且没有代码侵入

缺点:因为一阶段需要锁定数据库资源,等待二阶段结束才释放,性能较差​,依赖关系型数据库实现事务​

AT模式:

优点:满足ACID原则​,常用数据库都支持,实现简单,并且没有代码侵入,单个RM完成之后进行事务的提交,不占用资源,提高了性能

缺点:难以实现复的事务控制,如特定隔离级别;当事务的隔离级别过低时会出现脏读、不可重复读、幻读问题


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

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

相关文章

【C++】模版(初阶)

目录 一. 函数模版 1. 格式 原理 2. 函数模版的实例化 二. 类模板 void Swap(int& left, int& right) {int temp left;left right;right temp; }void Swap(double& left, double& right) {double temp left;left right;right temp; }void Swap(char&…

InfluxDB 开发工具链:IDE 插件与调试技巧(二)

四、利用 IDE 插件提升开发效率 4.1 代码编写技巧 在使用安装了 InfluxDB 插件的 IDE 进行代码编写时&#xff0c;我们可以充分利用插件提供的代码导航和智能提示功能&#xff0c;来显著提高编写 InfluxDB 相关代码的效率和准确性。 以一个涉及多个 Measurement 和复杂查询条…

定制开发开源AI智能名片S2B2C商城小程序:场景体验新维度与四重目标达成

摘要&#xff1a;本文聚焦于定制开发开源AI智能名片S2B2C商城小程序&#xff0c;探讨其在场景体验领域的应用与价值。通过深入分析场景体验的最高境界——深体验、强认知、高传播、关系深化这四个目标&#xff0c;阐述该小程序如何凭借自身特性与功能&#xff0c;在商业场景中实…

开源 GIS 服务器搭建:GeoServer 在 Linux 系统上的部署教程

GeoServer 是一个开源的地理信息服务服务器&#xff0c;可以发布地图、矢量数据和栅格数据。 1. 更新系统 sudo apt update && sudo apt upgrade -y2. 安装 Java 11 GeoServer 需要 Java 运行环境&#xff0c;这里用 OpenJDK 11。 sudo apt install openjdk-11-jdk…

前端面试通关:Cesium+Three+React优化+TypeScript实战+ECharts性能方案

前端面试题详解与更多面试题 WebGLCesiumThree 1. 自我介绍 回答要点&#xff1a; 教育背景和工作经验技术栈和专长领域参与过的重点项目个人优势和学习能力职业规划 示例&#xff1a; “我是一名有前端开发经验的工程师&#xff0c;熟练掌握React、Vue等主流框架&#x…

集成电路学习:什么是Object Tracking目标跟踪

Object Tracking:目标跟踪 Object Tracking,即目标跟踪,是计算机视觉领域的一个重要研究方向,它专注于在视频帧序列中连续地监测和定位一个或多个目标对象的位置。以下是对目标跟踪技术的详细解析: 一、定义与目的 定义: 目标跟踪是指在视频序列中,通过特定的算法…

深入理解计算机系统

参考书籍 8-18 处理器体系结构不同于冯诺依曼与哈佛体系 压栈与退栈与理解c等高级语言的工作原理息息相关&#xff0c;也是常用的攻击手段 Buffer Overflow的主要技术基础 day2 继续读前言之类的 本书前言 这本书&#xff0c;讲述应用程序员如何能够利用系统知识来编写更好…

LLM 中 token 简介与 bert 实操解读

一、什么是 LLM&#xff1f; LLM&#xff0c;全称为 Large Language Model&#xff08;大语言模型&#xff09;&#xff0c;是一种基于神经网络&#xff08;主要是 Transformer 结构&#xff09;的大规模自然语言处理&#xff08;NLP&#xff09;模型。其核心能力在于理解、生成…

【运维心得】三步更换HP笔记本电脑外壳

目录 准备工作 第一步&#xff1a;拆卸电池与后盖 第二步&#xff1a;处理隐藏螺丝 第三步&#xff1a;断开内部排线 总结一下 今天又碰到了两台HP的笔记本&#xff0c;一台外壳完好&#xff0c;但是无法开机&#xff0c;判断是主板问题。另外一台外壳有损坏&#xff0c;但…

深入 Linux 网络(一) -- 网卡队列

文章目录网卡网卡的核心功能网卡的关键技术单队列网卡多队列网卡查看网卡信息ifconfigethtool查看网卡队列Linux 查看中断绑定网卡中断查询查看中断绑定的 cpu总结1. 默认情况&#xff08;单队列网卡&#xff09;2. 多队列网卡3. 如何查看和配置绑定关系&#xff1f;4. 性能优化…

HTTP 1.0, 2.0 和 3.0 有什么区别?

HTTP/1.0 就像是“一问一答”的电话&#xff0c;每次打电话&#xff08;请求&#xff09;都得先拨号&#xff08;建立连接&#xff09;&#xff0c;说完一句话&#xff08;发送数据&#xff09;就挂断&#xff08;关闭连接&#xff09;&#xff0c;再打下一通电话。效率比较低。…

无畏契约手游上线!手机远控模拟器畅玩、抢先注册稀有ID!

终于来了&#xff01;《无畏契约》手游今天已经全平台上线&#xff01;保留了端游经典的英雄技能与射击体验&#x1f3ae;&#xff3b;新服开启&#xff0c;ID争夺战一触即发&#xff3d;《无畏契约》手游备受FPS玩家期待&#xff0c;累计获得超6000万线上预约&#xff01;每次…

《WINDOWS 环境下32位汇编语言程序设计》第4章 第一个窗口程序

4.1 开始了解窗口4.1.1 窗口是什么窗口是什么&#xff1f;大家每天在使用Windows&#xff0c;屏幕上的一个个方块就是一个个窗口&#xff01;那么&#xff0c;窗口为什么是这个样子呢&#xff1f;窗口就是程序吗&#xff1f;1.使用窗口的原因回想一下DOS时代的计算机屏幕&#…

Mybatis执行sql流程(二)之加载Mapper

Mybatis加载Mapper注册方式注册时机特点MapperScanBean定义阶段注册接口定义批量注册&#xff0c;推荐方式Mapper (接口注解)同 MapperScan需每个接口单独标注XML 配置 <mapper>MyBatis 初始化时传统方式&#xff0c;不依赖 Spring 容器SqlSessionTemplate 直接获取调用时…

基于 JSP+Mysql实现MVC房屋租赁系统

基于 MVC 的房屋租赁系统的设计与实现摘 要&#xff1a;房屋租赁管理系统与网络相结合&#xff0c;给用户提供更加周到和人性化的服务。网站模式为 MVC 模式&#xff0c;基于 MySQL 数据库,采用 JSP&#xff0c;Session 绘画跟踪、JavaScript 等技术,实现了普通用户可以浏览、查…

第六天~提取Arxml中CAN采样点信息Creat_ECU--Standard

⏱️ ARXML探秘:解码CAN采样点的精准艺术 在汽车电子的交响乐中,CAN采样点(Sample Point) 如同指挥家挥棒的关键时刻——它决定了何时"聆听"总线上的信号。这个看似微小的百分比数值,却是保障整车通信可靠性的核心密码。本文将带您深入ARXML中的采样点配置世界…

Windows Git安装配置

进入git官网Git - Downloading Package 点击下载&#xff08;可复制链接到迅雷&#xff09; 双击运行exe安装包 选择安装目录 下一步 选择 Git 默认编辑器&#xff0c;下一步设置初始化新项目(仓库)的主干名字 让Git决定&#xff08;Let Git decide&#xff09;使用默认的…

面试经验分享-某电影厂

java会吗&#xff1f;不会。。。。。hdfs读文件写文件的流程 数据写入 1-客户端向NameNode发起请求 2-NameNode审核权限和剩余空间&#xff0c;满足条件即允许写入&#xff0c;并告知客户端写入的DataNode地址 3-客户端向指定的DataNode发送数据包 4-被写入数据的DataNode同时完…

数据清理后续

前篇&#xff1a;Python 项目里的数据清理工作&#xff08;数据清洗步骤应用&#xff09; 一&#xff0c;先接上文添加两种数据填充的方法 1、线性回归填充 def lr_train_fill(train_data,train_label):train_data_all pd.concat([train_data, train_label], axis1)train_d…

nuc设置脚本开机自启动

在终端执行gnome-session-properties这个是带有图型化页面的设置开机自启动的软件没有这个软件的可以直接下载sudo apt update sudo apt install gnome-startup-applications一般都有&#xff0c;ubunutu自带的右边有添加&#xff0c;名称和注释随便写&#xff0c;只需要把命令…