Gateway网关的实现

API网关

  • 网关路由必须支持负载均衡,服务列表是从注册中心拉取的
  • 客户端发出请求的URL指向的是网关,URL还必须要包含目标信息
  • 网关收到URL,通过一定的规则,要能识别出交给哪个实例去处理
  • 网关有能力对请求响应进行修改

引入依赖包

<dependencies><dependency><groupId>org.springframework.cloud</groupId><artifactId>spring-cloud-starter-gateway</artifactId></dependency><dependency><groupId>com.alibaba.cloud</groupId><artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId></dependency><dependency><groupId>org.springframework.cloud</groupId><artifactId>spring-cloud-starter-loadbalancer</artifactId></dependency><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-actuator</artifactId></dependency><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-configuration-processor</artifactId></dependency>
</dependencies>

配置启动类

@SpringBootApplication
@EnableDiscoveryClient
public class GateWayApplication {public static void main(String[] args) {SpringApplication.run(GateWayApplication.class, args);}
}

编写application.yaml的配置文件

server:port: 8341
Spring:application:name: gateway-servicecloud:nacos:discovery:server-addr: 192.168.200.130:8848namespace: ce6fa22e-fc35-4fd3-9568-2cf609059088group: JIAGOU_GROUPfile-extension: yamlprefix: ${Spring.application.name}heart-beat-interval: 5gateway:discovery:locator:enabled: true #启用DiscoveryClient的标志routes:- id: course-service-route # 路由的唯一标识 http://localhost:8341/course/api/courses/1uri: lb://course-agg-service #网关收到请求后将请求转发到 lb://course-agg-servicepredicates:- Path=/course/** # 断言匹配请求路径filters: # 过滤器,可以做认证、限流、日志等- StripPrefix=1 # 针对URL剪切前缀,这里去掉了前缀/course

主要概念

  • routes:路由定义了匹配请求的条件,以及如何将请求转发到下游服务
  • predicates:用于匹配请求的条件,比如请求路径、请求参数、头部信息等。
  • filter:过滤器,进行模式匹配

路由谓词工厂

- After=2017-01-20T17:42:47.789-07:00[America/Denver] # 在某个时间之后
- Before=2017-01-20T17:42:47.789-07:00[America/Denver] #在某个时间之前- Between=2017-01-20T17:42:47.789-07:00[America/Denver], 2017-01-21T17:42:47.789-07:00[America/Denver] # 两者之间- Cookie=chocolate, ch.p #cookie谓词工厂,此谓词匹配具有给定名称且其值与正则表达式匹配的 Cookie。- Header=X-Request-Id, \d+- Host=**.somehost.org,**.anotherhost.org- Method=GET,POST- Path=/red/{segment},/blue/{segment}- Query=green- RemoteAddr=192.168.1.1/24

Filter工厂

  • AddRequestHeader:向请求添加一个 HTTP 头。
  • AddResponseHeader:向响应添加一个HTTP 头。
  • DedupeResponseHeader:去除响应头中的重复值。
  • PrefixPath:为请求路径添加前缀。
  • PreserveHostHeader:保留原始请求的 Host 头。
  • RedirectTo:重定向请求到另一个 URL。章
  • RemoveRequestHeader:移除请求中的一个 HTTP 头。
  • RemoveResponseHeader:移除响应中的一个HTTP 头。
  • RewritePath:重写请求路径。
  • SetPath:设置请求路径。
  • SetRequestHeader:设置请求头。
  • SetResponseHeader:设置响应头。
  • SetStatus:设置响应状态码。
  • StripPrefix:去除请求路径中的前缀

1网关全局过滤器

@Component
@Order(1)
@Slf4j
public class LoggingGlobalFilter implements GlobalFilter {@Overridepublic Mono<Void> filter(ServerWebExchange exchange, GatewayFilterChain chain) {ServerHttpRequest request = exchange.getRequest();long startTime = System.currentTimeMillis();return chain.filter(exchange).then(Mono.fromRunnable(() -> {//Mono.fromRunnable此时所有的请求都处理完成后才执行ServerHttpResponse response = exchange.getResponse();long endTime = System.currentTimeMillis();log.info("请求地址:{},请求方法:{},响应状态码:{},响应时间:{}",request.getURI(),request.getMethod(),response.getStatusCode().value(),endTime-startTime);}));}
}

2实现认证过滤器

在微服务中,服务数量较多,不能再服务中进行认证,会进行统一的认证,认证成功后颁发Token,前端会将令牌放在RequestHeader中

创建一个对所有的请求进行认证的全局过滤器

import org.springframework.cloud.gateway.filter.GatewayFilterChain;
import org.springframework.cloud.gateway.filter.GlobalFilter;
import org.springframework.http.HttpStatus;
import org.springframework.stereotype.Component;
import org.springframework.web.server.ServerWebExchange;
import reactor.core.publisher.Mono;@Component
public class AuthenticationGlobalFilter implements GlobalFilter {// 认证头private  static final String AUTHENTICATION_HEADER = "Authorization";// 登录URLprivate static final String LOGIN_URL = "/api/login";@Overridepublic Mono<Void> filter(ServerWebExchange exchange, GatewayFilterChain chain) {if(exchange.getRequest().getPath().toString().contains(LOGIN_URL)){return chain.filter(exchange);}String token = exchange.getRequest().getHeaders().getFirst(AUTHENTICATION_HEADER);if(token == null || IsValid(token)){exchange.getResponse().setStatusCode(HttpStatus.UNAUTHORIZED);// 请求结束return exchange.getResponse().setComplete();}return chain.filter(exchange);}private boolean IsValid(String token) {//此处通过工具类校验return true;}
}

3网关的限流

此处集成了redis

<dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-data-redis</artifactId>
</dependency>

自定义一个Config类:但要注意此处的限流策略只能选择一种,也就是说@Bean只能生效一个方法

import org.springframework.cloud.gateway.filter.ratelimit.KeyResolver;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import reactor.core.publisher.Mono;@Configuration
public class RateLimiterConfiguration {/*** 使用ip地址作为限流* @return*/@Beanpublic KeyResolver ipKeyResolver(){return exchange -> Mono.just(exchange.getRequest().getRemoteAddress().getAddress().getHostAddress());}/*** 使用用户id作为限流,需要在请求中携带userId参数* @return*///@Beanpublic KeyResolver userKeyResolver() {return exchange -> Mono.just(exchange.getRequest().getQueryParams().getFirst("userId"));}/*** 返回一个KeyResolver对象,用于解析请求的路径** @return KeyResolver路径解析器,通过请求对象获取路径值*///@Beanpublic KeyResolver pathResolver() {// Lambda表达式用于创建KeyResolver的实例// Mono.just确保返回一个包含请求路径的Mono Fluxreturn exchange -> Mono.just(exchange.getRequest().getPath().value());}
}

在application.yaml文件中修改策略配置

server:port: 8341
Spring:application:name: gateway-servicecloud:nacos:discovery:server-addr: 192.168.200.130:8848namespace: ce6fa22e-fc35-4fd3-9568-2cf609059088group: JIAGOU_GROUPfile-extension: yamlprefix: ${Spring.application.name}heart-beat-interval: 5gateway:discovery:locator:enabled: true #启用DiscoveryClient的标志routes:- id: course-service-route # 路由的唯一标识 http://localhost:8341/course/api/courses/1uri: lb://course-agg-service #网关收到请求后将请求转发到 lb://course-agg-servicepredicates:- Path=/course/** # 断言匹配请求路径filters: # 过滤器,可以做认证、限流、日志等- StripPrefix=1 # 针对URL剪切前缀,这里去掉了前缀/course- name: RequestRateLimiter # 定义限流策略args:redis-rate-limiter.replenishRate: 1 # 每秒填充的令牌数redis-rate-limiter.burstCapacity: 2 # 令牌桶的容量key-resolver: "#{@ipKeyResolver}" # 限流key的生成策略redis:host: 43.143.110.136port: 6379database: 0pool:max-active: 8 # 连接池最大连接数(使用负值表示没有限制)max-wait: -1ms # 连接池最大阻塞等待时间(使用负值表示没有限制)max-idle: 8 # 连接池中的最大空闲连接password: 1234

当请求数量大于令牌个数时,触发限流策略,状态码显示429
在这里插入图片描述

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

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

相关文章

使用LangGPT提示词让大模型比较浮点数

使用LangGPT提示词让大模型比较浮点数 背景介绍环境准备创建虚拟环境安装一些必要的库安装其他依赖部署大模型启动图形交互服务设置提示词与测试 LangGPT结构化提示词 背景介绍 LLM在对比浮点数字时表现不佳&#xff0c;经验证&#xff0c;internlm2-chat-1.8b (internlm2-cha…

计算机视觉—3d点云数据基础

点云数据 3d点云数据由来 3d点云 3D Point Cloud是一种用于表示三维空间中对象或场景的数据结构。在最基础的形式中&#xff0c;它是一个包含多个三维坐标点&#xff08;X, Y, Z&#xff09;的集合。这些点是通过对实际物体或场景表面进行离散采样而获得的&#xff0c;因此&a…

代码随想录:动态规划4-5

42.接雨水 题目 给定 n 个非负整数表示每个宽度为 1 的柱子的高度图&#xff0c;计算按此排列的柱子&#xff0c;下雨之后能接多少雨水。 示例 1&#xff1a; 输入&#xff1a;height [0,1,0,2,1,0,1,3,2,1,2,1] 输出&#xff1a;6 解释&#xff1a;上面是由数组 [0,1,0,2,…

python正则表达式如何不区分大小写

使用python的re模块做模式匹配时&#xff0c;有时需要忽略大小写&#xff0c;只需要在re.search()函数中添加参数re.IGNORECASE即可。 mystring some string pattern some pattern match re.search(pattern, mystring, re.IGNORECASE)

【Linux】理解和解释shell命令的工具

&#x1f41a;作者简介&#xff1a;花神庙码农&#xff08;专注于Linux、WLAN、TCP/IP、Python等技术方向&#xff09;&#x1f433;博客主页&#xff1a;花神庙码农 &#xff0c;地址&#xff1a;https://blog.csdn.net/qxhgd&#x1f310;系列专栏&#xff1a;C语言编程&…

2025年最新大数据毕业设计选题-Hadoop综合项目

选题思路 回忆学过的知识(Python、Java、Hadoop、Hive、Sqoop、Spark、算法等等。。。) 结合学过的知识确定大的方向 a. 确定技术方向&#xff0c;比如基于Hadoop、基于Hive、基于Spark 等等。。。 b. 确定业务方向&#xff0c;比如民宿分析、电商行为分析、天气分析等等。。。…

必备工具,AI生成证件照,再也不用麻烦他人,电子驾驶证等多种证件照一键生成

最近有一个生成证件照的开源项目很火&#xff0c;今天我们来学习一下。之前我生成证件照都是线下去拍照&#xff0c;线上使用也是各种限制&#xff0c;需要付费或看广告&#xff0c;而且效果也不是很理想&#xff0c; 今天要分享的这个 AI 证件照生成工具可以一键可以生成一寸…

深度学习之图像数据集增强(Data Augmentation)

文章目录 一、 数据增强概述二、python实现传统数据增强参考文献 一、 数据增强概述 数据增强&#xff08;Data Augmentation&#xff09;是一种技术&#xff0c;通过对现有数据进行各种变换和处理来生成新的训练样本&#xff0c;从而增加数据集的多样性和数量。这些变换可以是…

一文入门生成式AI(理解ChatGPT的原理)

一、什么是生成式AI&#xff1f; 以ChatGPT为代表的生成式AI&#xff0c;是对已有的数据和知识进行向量化的归纳&#xff0c;总结出数据的联合概率。从而在生成内容时&#xff0c;根据用户需求&#xff0c;结合关联字词的概率&#xff0c;生成新的内容。 可以这么联想&#x…

C++对象拷贝时的优化编译

在现代编译器中&#xff0c;当我们在 C中进行对象的拷贝操作时&#xff0c;编译器并非只是机械地执行逐字节的复制。相反&#xff0c;它会进行优化&#xff0c;避免不必要的拷贝构造等等&#xff0c;这种优化包括“返回值优化”&#xff08;RVO&#xff09;&#xff0c;“拷贝省…

电脑的主板,内存条插多少合适?

首先&#xff0c;不是插满4条内存就是最好的。 内存条插得多&#xff0c;确实可以扩充容量&#xff0c;提升性能。但是有些低端的主板配低端CPU&#xff0c;插满4条内存&#xff0c;稳定性下降。这里的稳定性包括供电&#xff0c;单独的内存供电容量等。此时CPU会通过降低内存…

Weapons Armor PBR Pack 1 - Fantasy RPG 武器护甲游戏模型

武器和护甲包#1有30个武器和护甲,每个对象都有默认外观,大多数都有网格变形和Substance Painter源文件,用于自定义纹理。 无限PBR&我的哲学 Infinity PBR是十几位艺术家的作品,他们都在做自己最擅长的事情。我想为独立游戏开发者制作最通用、最优质的资产,按照我希望的…

大数据新视界 --大数据大厂之数据驱动决策:如何利用大数据提升企业竞争力

&#x1f496;&#x1f496;&#x1f496;亲爱的朋友们&#xff0c;热烈欢迎你们来到 青云交的博客&#xff01;能与你们在此邂逅&#xff0c;我满心欢喜&#xff0c;深感无比荣幸。在这个瞬息万变的时代&#xff0c;我们每个人都在苦苦追寻一处能让心灵安然栖息的港湾。而 我的…

MySQL之内置函数

目录 一&#xff1a;日期函数 二:字符串函数 三&#xff1a;数学函数 四&#xff1a;其他函数 一&#xff1a;日期函数 举例: (1) mysql> select current_date(); ---------------- | current_date() | ---------------- | 2024-09-17 | ---------------- 1 row …

了解云容器实例云容器实例(Cloud Container Instance)

1.什么是云容器实例&#xff1f; 云容器实例&#xff08;Cloud Container Instance&#xff0c; CCI&#xff09;服务提供 Serverless Container&#xff08;无服务器容器&#xff09;引擎&#xff0c;让您无需创建和管理服务器集群即可直接运行容器。 Serverless是一种架构理念…

中秋节程序员一般在干啥?

中秋节作为一个传统的中国节日&#xff0c;主要庆祝活动围绕着家庭团聚、赏月、吃月饼等文化习俗展开。然而&#xff0c;对于程序员这个职业群体来说&#xff0c;他们的中秋节活动可能因工作性质和个人安排而有所不同。但大致上&#xff0c;程序员在中秋节期间可能会有以下几种…

SpaceX实现人类首次商业太空行走:航天历史新篇章

导语 2023年9月&#xff0c;SpaceX成功完成了人类历史上首次商业太空行走&#xff0c;这不仅是航天领域的重要突破&#xff0c;也是商业航天的一次重大胜利。这一事件标志着普通人离太空更近了一步&#xff0c;为未来的太空探索和火星移民奠定了基础。 一、背景介绍&#xff1a…

【C++二叉树】102.二叉树的层序遍历

107. 二叉树的层序遍历 II - 力扣&#xff08;LeetCode&#xff09; 思路分析&#xff1a; 层序遍历&#xff0c;但是要注意输出的结果是一个二维数组&#xff0c;不是一层一个值一个值的输出&#xff0c;而是要一层一层的输出。可以通过一个循环控制每一层的数据个数&#xff…

2-97 基于matlab的小波变换模量最大值 (WTMM) 方法进行图像边缘检测

基于matlab的小波变换模量最大值 &#xff08;WTMM&#xff09; 方法进行图像边缘检测。利用小波基函数的局部化和振荡特性来检测图像中的边缘&#xff0c;沿每个像素的梯度方向搜索局部最大值&#xff0c;保留局部最大值&#xff0c;抑制其他系数&#xff0c;实现边缘检测。程…

C++11(4)

万众瞩目的C11特辑来了&#xff0c;本章将继续讲解C11更新的内容&#xff0c;不过C11的内容也快接近尾声了。 目录 10。lambda表达式 11。lambda捕捉列表[] 捕捉列表说明 lambda捕捉列表实际应用 10。lambda表达式 #include<iostream> using namespace std; #inclu…