SpringCloud--Gateway解析

news2024/11/27 14:39:23

一、Gateway简介

Gateway是Spring Cloud官方推出的第二代微服务网关,它旨在提供统一的路由方式以及为微服务应用提供强大的负载均衡能力。与第一代Spring Cloud Netflix Zuul相比,Spring Cloud Gateway在性能、可扩展性、易用性等方面都有了显著的提升。其主要特性有以下几点:

  1. 基于Spring Boot 和Spring Cloud 开发,支持RESTful和WebSocket;
  2. 支持通过Feign或RestTemplate进行服务调用;
  3. 支持负载均衡、熔断、限流等操作;
  4. 支持动态路由、灵活的路由策略;
  5. 支持多种协议,如HTTP、WebSocket等。

二、Gateway工作流程

在这里插入图片描述
Spring Cloud Gateway的工作流程主要包括以下几个步骤:

  1. 客户端请求到达Gateway。
  2. 再由Gateway Handler Mapping根据请求路径匹配路由表,找到对应的路由规则。路由规则中包含断言,再根据断言规则对请求进行匹配,只有当请求符合断言规则时才会继续转发到Gateway Web Handler进行处理。
  3. Gateway Web Handler会根据路由规则将该请求转发到目标服务实例。
  4. 在将请求转发到目标服务实例前会经过过滤器的处理。
  5. 通过过滤器对该请求的处理后,最后到达目标服务进行该请求的处理。
  6. 目标服务处理完成后,将响应结果再根据路由规则并应用过滤器对响应进行处理,最后将响应返回给客户端。

三、Gateway使用

  1. 在项目中创建一个Gateway模块,在其中pom文件中引入gataway、nacos、以及loadbalancer的依赖。
	<dependencies>
		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter</artifactId>
		</dependency>
		<dependency>
			<groupId>org.springframework.boot</groupId>
			<artifactId>spring-boot-starter-test</artifactId>
			<scope>test</scope>
		</dependency>
		 <!-- gateway -->
		<dependency>
			<groupId>org.springframework.cloud</groupId>
			<artifactId>spring-cloud-starter-gateway</artifactId>
		</dependency>
		 <!-- SpringCloud 负载均衡 -->
		<dependency>
			<groupId>org.springframework.cloud</groupId>
			<artifactId>spring-cloud-starter-loadbalancer</artifactId>
		</dependency>
	</dependencies>

在这里插入图片描述
3. 路由配置,可以在YML中配置,也可以通过配置类@Configuration,这两种方式的功能一样,建议使用在YML中配置。
(1)配置类方式:通过@Bean注入一个RouteLocator配置类型。

	@Bean
	public RouteLocator customRouteLocator(RouteLocatorBuilder builder) {
		return builder.routes()
			.route("path_route", r -> r.path("/get")
				.uri("http://httpbin.org"))
			.route("host_route", r -> r.host("*.myhost.org")
				.uri("http://httpbin.org"))
			.route("hystrix_route", r -> r.host("*.hystrix.org")
				.filters(f -> f.hystrix(c -> c.setName("slowcmd")))
				.uri("http://httpbin.org"))
			.route("hystrix_fallback_route", r -> r.host("*.hystrixfallback.org")
				.filters(f -> f.hystrix(c -> c.setName("slowcmd").setFallbackUri("forward:/hystrixfallback")))
				.uri("http://httpbin.org"))
			.build();
	}

(2)YML文件配置方式:

# 服务配置
server:
  port: 9003

spring:
  application:
    name: njh-gateway-app  
  cloud:
    loadbalancer:
      ribbon:
        enabled: false
      cache:
        enabled: true
        caffeine:
          spec: initialCapacity=500,expireAfterWrite=5s
    # nacos配置
    nacos:
      discovery:
        server-addr: ${spring.cloud.nacos.config.server-addr}
        namespace: ${spring.cloud.nacos.config.namespace}
        group: ${spring.cloud.nacos.config.group}
        username: ${spring.cloud.nacos.config.username}
        password: ${spring.cloud.nacos.config.password}
    # gateway配置
    gateway:
      routes:
        - id: njh-web-app				#路由id,保证唯一,这里配置成服务名
          uri: lb://njh-web-app			#匹配成功后路由的服务,lb表示启用负载均衡
          predicates:
            - Path=/api/webapp/**		#断言,根据路径进行匹配
          filters:
            - name: Retry
              args:
                retries: 1 				#重试次数
        - id: njh-biz-app
          uri: lb://njh-biz-app
          predicates:
            - Path=/api/bizapp/**
          filters:
            - name: Retry
              args:
                retries: 1 #重试次数

这样配置完后,当请求到达gateway后就会根据请求的路径进行匹配,然后将其转发到指定的服务去进行处理。例如:上面yml文件中配置的,请求中所有包含/api/webapp/路径的请求都会转发到njh-web-app服务上进行处理,所有包含/api/bizapp/路径的请求都会转发到njh-biz-app服务上进行处理。

四、Gateway三大核心组件

Gateway的三大组件通常指的是路由(Routing)、断言(Assertions)和过滤器(Filters)。通过这三大组件共同协作,使得Spring Cloud Gateway可以灵活地处理各种网络请求,并提供强大的API网关功能。

  1. 路由(Routing):路由是Spring Cloud Gateway中的基本组成,它由ID、目标URL、断言和过滤器组成。路由定义了如何将请求路由到特定的微服务。下面是routes属性的一些关键组成部分:
spring:
  cloud:
    gateway:
      routes:
        - id: user_service_route
          uri: lb://USER-SERVICE
          predicates:
            - Path=/users/**
          filters:
            - RewritePath=/users/(?<remaining>.*), /$\{remaining}
id:路由的唯一标识符。上面设置为user_service_route。
uri:请求被转发到的目标服务的URI。上面使用服务发现(lb://USER-SERVICE)来找到并转发请求到用户服务。
predicates:一组断言(条件),用于匹配请求。如果断言条件满足,请求将被路由到相应的URI。上面配置中的Path=/users/**断言匹配所有以/users/开头的路径。
filters:一组过滤器,用于在请求到达目标服务之前或响应返回客户端之后对请求和响应进行操作。上面配置中的RewritePath过滤器用于重写路径,移除/users/前缀。
  1. 断言(Assertions):断言主要用于匹配请求,只有当断言为true时,请求才会被路由到相应的URI。Spring Cloud Gateway提供了多种方式来定义断言,例如路径匹配、参数匹配等。Spring Cloud Gateway提供了多种内置的断言工厂,例如:
    • Path:根据请求路径匹配断言。例如,Path=/api/**会匹配任何以/api/开头的路径。
    • Query:根据请求查询参数匹配断言。例如,Query=name,aaa会匹配查询参数中包含name=aaa的请求。
    • Header:根据请求头匹配断言。例如,Header=X-Requested-By,myapp会匹配请求头中包含X-Requested-By: myapp的请求。
    • Method:根据HTTP请求方法匹配断言。例如,Method=GET仅匹配GET请求。
    • Cookie:根据请求中的Cookie值匹配断言。例如,Cookie=session,mySessionId会匹配cookie中包含session=mySessionId的请求。
    • Host=:根据请求的主机头匹配。例如,Host=**.example.com会匹配任何以example.com结尾的主机头。
  2. 过滤器(Filters):过滤器是Spring Cloud Gateway的核心组件之一,它可以在请求转发到相应微服务之前或之后执行一些操作,例如请求转发、响应修改、限流、认证等。Spring Cloud Gateway提供了许多默认的过滤器,同时也允许开发者自定义过滤器以满足特定的需求。过滤器可以链式执行,即一个请求可以经过多个过滤器的处理。每个过滤器都能够访问到请求和响应对象,并对它们进行修改。以下是一些常用的内置GatewayFilter类型:
    • AddRequestHeader:向请求添加一个新的头部信息。
    • AddResponseHeader:向响应添加一个新的头部信息。
    • RewritePath:重写请求的路径。
    • RemoveRequestHeader:从请求中移除一个头部信息。
    • Hystrix:为网关提供断路器功能,防止服务故障导致网关崩溃。
    • StripPrefix=2:去掉Path中前两个节点。

五、实现自定义过滤器

在Spring Cloud Gateway中实现自定义Filter主要分为以下几个步骤:

  1. 创建一个类实现GlobalFilter接口或者GatewayFilter接口。GlobalFilter允许你创建全局过滤器,而GatewayFilter通常用于创建特定路由的过滤器。
  2. 在该类中,实现filter方法,该方法接收ServerWebExchange对象和GatewayFilterChain对象作为参数。
  3. 通过ServerWebExchange对象,你可以访问和修改请求和响应的信息。
  4. 调用GatewayFilterChain对象的filter方法来继续执行后续的过滤器链。
  5. 如果需要,可以通过实现Ordered接口来指定过滤器的执行顺序。
  6. 要使Spring Cloud Gateway识别并使用这个自定义过滤器,需要在启动类上添加@EnableGatewayWebFlux注解,并确保自定义过滤器组件被Spring容器扫描到。
@Component
public class CustomRequestHeaderFilter implements GatewayFilter, Ordered {

    private static final int DEFAULT_ORDER = 0;

    @Override
    public Mono<Void> filter(ServerWebExchange exchange, GatewayFilterChain chain) {
        // 添加自定义请求头
        ServerHttpRequest request = exchange.getRequest().mutate()
                .header("X-Custom-Header", "MyCustomValue")
                .build();
        
        // 将修改后的请求传递给下一个过滤器
        return chain.filter(exchange.mutate().request(request).build());
    }

    @Override
    public int getOrder() {
        // 返回过滤器的执行顺序,值越小,优先级越高。
        return DEFAULT_ORDER;
    }
}

六、实现负载均衡

在Spring Cloud Gateway中实现负载均衡主要依赖于内置的负载均衡器或者集成的服务发现组件。以下是实现负载均衡的几种方式:
(1)使用Ribbon实现负载均衡:
默认使用Netflix Ribbon作为负载均衡器。要启用Ribbon负载均衡,需要在application.yml配置文件中添加相关配置。

  1. 添加依赖,在pom.xml文件中添加以下依赖:
<dependencies>
    <!-- Spring Cloud Gateway -->
    <dependency>
        <groupId>org.springframework.cloud</groupId>
        <artifactId>spring-cloud-starter-gateway</artifactId>
    </dependency>
    <!-- Spring Cloud Ribbon -->
    <dependency>
        <groupId>org.springframework.cloud</groupId>
        <artifactId>spring-cloud-starter-netflix-ribbon</artifactId>
    </dependency>
    <!-- Eureka (如果使用服务发现) -->
    <dependency>
        <groupId>org.springframework.cloud</groupId>
        <artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
    </dependency>
</dependencies>
  1. 在application.yml中配置Ribbon,启用服务发现功能:
spring:
  cloud:
    nacos:
      discovery:
        enabled: true
    gateway:
      routes:
        - id: service_route
          uri: lb://SERVICE_ID
          filters:
            - AddRequestHeader=X-Request-Redirected, By-Gateway
  1. 自定义Ribbon规则:通过实现IRule接口来创建自定义的Ribbon规则,然后在配置文件中指定这个规则。例如,创建一个自定义的轮询规则:
@Configuration
public class RibbonConfiguration {
    @Bean
    public IRule ribbonRule() {
        return new RoundRobinRule();
    }
}

# 在application.yml中引用这个规则:
spring:
  ribbon:
    NFLoadBalancerRuleClassName: com.yourpackage.RibbonConfiguration$YourCustomRule

(2)基于Spring Cloud LoadBalancer的负载均衡:

  1. 添加依赖
<dependency>
    <groupId>org.springframework.cloud</groupId>
    <artifactId>spring-cloud-starter-loadbalancer</artifactId>
</dependency>
  1. 在application.yml文件中配置路由
# 禁用ribbon
spring:
  cloud:
    loadbalancer:
      ribbon:
        enabled: false
     
     gateway:
       routes:
        - id: service_route
          uri: lb://SERVICE_ID
          filters:
            - AddRequestHeader=X-Request-Redirected, By-Gateway

(3)自定义负载均衡器:
在Spring Cloud Gateway中,自定义负载均衡器可以通过实现LoadBalancerClientFactory接口来完成。

  1. 实现LoadBalancerClientFactory接口
public class CustomLoadBalancerClientFactory implements LoadBalancerClientFactory {

    @Override
    public LoadBalancerClient create(String serviceId) {
        // 实现创建自定义LoadBalancerClient的逻辑
        // 返回自定义的LoadBalancerClient实例
        return new CustomLoadBalancerClient();
    }
}
  1. 创建自定义LoadBalancerClient
public class CustomLoadBalancerClient implements LoadBalancerClient {

    @Override
    public Mono<ServerWebExchange> execute(Request request, ServerWebExchange exchange) {
        // 实现自定义的负载均衡逻辑
        // 返回处理后的ServerWebExchange
        return Mono.just(exchange);
    }
}
  1. 配置Spring Cloud Gateway使用自定义的负载均衡器
spring:
  cloud:
    loadbalancer:
      client:
        factory: com.yourpackage.CustomLoadBalancerClientFactory
  1. 使用自定义负载均衡器
@Configuration
public class GatewayConfig {

    @Bean
    public RouteLocators customRouteLocations(RouteLocatorBuilder builder) {
        return builder.routes()
            .route("path_route", r -> r.path("/customPath/**")
                .uri("lb://CUSTOM_SERVICE"))
            .build();
    }
}

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

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

相关文章

Python深入理解collections模块:常见数据结构及应用场景分析

Python深入理解collections模块&#xff1a;常见数据结构及应用场景分析 介绍collections模块的常见数据结构代码演示defaultdictCounterOrderedDict 介绍 在Python编程中&#xff0c;经常需要使用一些内置的数据结构&#xff0c;如列表、字典等。然而&#xff0c;在某些特定的…

uniapp 本地存储的方式

1. uniapp 本地存储的方式 在uniapp开发中&#xff0c;本地存储是一个常见的需求。本地存储可以帮助我们在客户端保存和管理数据&#xff0c;以便在应用程序中进行持久化存储。本文将介绍uniapp中本地存储的几种方式&#xff0c;以及相关的代码示例。 1.1. 介绍 在移动应用开发…

OSPF综合实验报告

实验要求&#xff1a; 实验预览图&#xff1a; 实验分析&#xff1a; 1、对R4仅仅配置端口IP和环回&#xff0c;使用共有IP 2、对R3-R7配置MGRE环境&#xff0c;以R3为hub&#xff0c;R5、R7、R6为spoke。 3、对172.16.0.0/16 IP进行子网划分&#xff0c;使得全网IP基于该网…

数据结构第十天(排序算法总结)

目录 前言 常数时间复杂度&#xff1a;O(1) 线性时间复杂度&#xff1a;O(n) 线性对数时间复杂度&#xff1a;O(n log n) 平方时间复杂度&#xff1a;O(n^2) 对数时间复杂度&#xff1a;O(log n) 前言 排序算法的学习可以告一段落了。但算法的学习永不停止。 今天&…

用python编写爬虫,爬取二手车信息+实验报告

题目 报告要求 工程报告链接放在这里 https://download.csdn.net/download/Samature/88805518使用 1.安装jupyter notebook 2.用jupyter notebook打开工程里的ipynb文件&#xff0c;再run all就行 注意事项 可能遇到的bug 暂无&#xff0c;有的话私信我

通过dockerfile 生成自定义nginx镜像

通过dockerfile生成自定义nginx镜像 &#xff01;&#xff01;&#xff01;docker 必须在linux环境下才能进行如果你是window则需要装虚拟机 新建一个文件名字为Dockerfile&#xff0c;无需后缀 文件完整名就是Dockerfile 编写dockerfile FROM nginx RUN echo hello nginx!…

golang windows 环境搭建 环境配置

golang windows 环境搭建 环境配置 Golang学习之路一环境搭建 MacBook Linux 树莓派raspberrypi安装Golang环境 官网下载地址: https://go.dev/dl/ https://golang.google.cn/dl/ 下载对应系统版本&#xff0c;例如windows 64位系统&#xff0c;下载&#xff1a;xxx.window…

年终奖,有人欢喜有人忧

每年的年终奖&#xff0c;有人欢喜有人忧&#xff0c;这是科技圈的一种共同现象。最近&#xff0c;科技界最热门的新闻无疑是Meta公布了其Q4和2023年全年财报&#xff0c;被许多人誉为“史上最强财报”。 Meta的股价也从2022年的最低点90美元左右&#xff0c;一路飙升至现在的每…

2024.02.06

TCP提供面向有连接的&#xff0c;可靠的数据传输服务&#xff0c;传输过程中&#xff0c;数据无误、数据无丢失、数据无失序、数据无重复 UDP面向无连接的&#xff0c;不保证数据可靠的&#xff0c;尽最大努力传输的协议&#xff0c;数据传输过程中&#xff0c;可能出现数据丢…

【C++11】统一初始化 和 initializer_list

文章目录 一、概念辨析1. 声明、定义、初始化、赋初值的概念2. 默认初始化 和 未被初始化 的概念 二、C98 的列表初始化三、C11 对列表初始化的扩展&#xff08;统一初始化&#xff09;四、标准库中的 initializer_list 类五、正确理解“统一初始化”和 initializer_list 的区别…

JRT监听程序

本次设计避免以往设计缺陷&#xff0c;老的主要为了保持兼容性&#xff0c;在用的设计就不好调了。 首先&#xff0c;接口抽象时候就不在给参数放仪器ID和处理类了&#xff0c;直接放仪器配置实体&#xff0c;接口实现想用什么属性就用什么属性&#xff0c;避免老方式要扩参数时…

Golang GC 介绍

文章目录 0.前言1.发展史2.并发三色标记清除和混合写屏障2.1 三色标记2.2 并发标记问题2.3 屏障机制Dijkstra 插入写屏障Yuasa 删除写屏障混合写屏障 3.GC 过程4.GC 触发时机5.哪里记录了对象的三色状态&#xff1f;6.如何观察 GC&#xff1f;方式1&#xff1a;GODEBUGgctrace1…

cocos creator 3.x 预制体无法显示

双击预制体&#xff0c;进入详情页&#xff0c;没有显示资源 Bomb 是个预制体&#xff0c;但是当我双击进来什么都没有了&#xff0c;无法对预制体进行可视化编辑 目前我只试出来一个解决方法&#xff1a; 把预制体拖进Canvas文件中&#xff0c;这样就能展示到屏幕上&#xff…

springboot集成easypoi导出多sheet页

pom文件 <dependency><groupId>cn.afterturn</groupId><artifactId>easypoi-base</artifactId><version>4.1.0</version> </dependency> 导出模板&#xff1a; 后端代码示例&#xff1a; /*** 导出加油卡进便利店大额审批列…

三网码支付系统源码,三网免挂有PC软件,有云端源码,附带系统搭建教程

搭建教程 1.先上传云端源码 然后配置Core/Config.php文件里面数据库信息注改&#xff1b;数据库帐号密码 2.云端源码里面Core/Api_Class/Instant_Url_List.php文件配置终端地址注改&#xff1b;第4 http://终端地址/ 3.导入云端数据库 账号admin 密码123456注改&#xff1…

ELAdmin 前端启动

开发工具 官方指导的是使用WebStorm&#xff0c;但是本人后端开发一枚&#xff0c;最终还是继续使用了 idea&#xff0c;主打一个能用就行。 idea正式版激活方式&#xff1a; 访问这个查找可用链接&#xff1a;https://3.jetbra.in/进入任意一个能用的里面&#xff0c;顶部提…

java---查找算法(二分查找,插值查找,斐波那契[黄金分割查找] )-----详解 (ᕑᗢᓫ∗)˒

目录 一. 二分查找&#xff08;递归&#xff09;&#xff1a; 代码详解&#xff1a; 运行结果&#xff1a; 二分查找优化&#xff1a; 优化代码&#xff1a; 运行结果&#xff08;返回对应查找数字的下标集合&#xff09;&#xff1a; ​编辑 二分查找&#xff08;非递归…

YUM | 包安装 | 管理

YUM 功能 软件包安装&#xff1a; 通过yum命令安装软件包。例如&#xff0c;安装一个名为 example-package 的软件包 yum install example-package更新包 检查更新&#xff1a; 检查可用更新&#xff1a; sudo yum check-update <package_name>软件包更新&#xff1a; y…

k8s报错记录(持续更新中....)

k8s报错记录(持续更新中…) 1. 部署k8s遇到kube-flannel已经构建&#xff0c;但是coredns一直处于ContainerCreating和pending状态 解决问题&#xff1a; 通过 kubectl describe pod -n kube-system coredns-7ff77c879f-9ls2b 查看pod的详细信息&#xff0c;报错说是cni 配置没…

Linux系统调试课:硬件断点

沉淀、分享、成长,让自己和他人都能有所收获!😄 📢在linux内核编程中,经常会遇到由于内存被篡改,例如 buffer overflow,野指针,write after free等。查找分析此类问题非常的麻烦。 一、什么是硬件断点 硬件断点,是Linux内核中是一种被ptrace和内核内调试器使用调试…