文章目录
Gateway
文章目录 |
---|
SpringCloud gateway (史上最全) - 疯狂创客圈 - 博客园 (cnblogs.com) |
Spring Cloud Gateway 底层使用了高性能的通信框架Netty
一、入门
首先来看看它能够做什么
架构图
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-iMoQtoDa-1637234810344)(https://gitee.com/li-xiaoming411/drawing-bed/raw/master/gateway基本作用-1.png)]
首发案例
接下来做第一个网关入门案例,主要是三个步骤
- 启动类
- 配置文件
- 配置类
依赖搞起来
<!-- 服务注册 -->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-gateway</artifactId>
</dependency>
启动类
@SpringBootApplication
@EnableDiscoveryClient
public class GatewaySpringBootApplication {
public static void main(String[] args) {
SpringApplication.run(GatewaySpringBootApplication.class,args);
}
}
最核心的配置文件
server.port=80
## 服务名称
spring.application.name=api-gateway
## 注册中心地址
spring.cloud.nacos.discovery.server-addr=192.168.247.173:8848
## id随意,下面的断言有很多种类,这里只写了一个
spring.cloud.gateway.routes[0].id=product-admin
spring.cloud.gateway.routes[0].uri=lb://service-product
spring.cloud.gateway.routes[0].predicates[0]=Path=/admin/product/**
spring.cloud.gateway.routes[1].id=web
spring.cloud.gateway.routes[1].uri=lb://web-modules
spring.cloud.gateway.routes[1].predicates[0]=Path=/**
ribbon.eager-load.enabled=true
配置类,先把跨域问题解决
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.cors.CorsConfiguration;
import org.springframework.web.cors.reactive.CorsWebFilter;
import org.springframework.web.cors.reactive.UrlBasedCorsConfigurationSource;
import org.springframework.web.util.pattern.PathPatternParser;
@Configuration
public class CorsConfig {
@Bean
public CorsWebFilter corsFilter() {
UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource(new PathPatternParser());
source.registerCorsConfiguration("/**", buildConfig());
return new CorsWebFilter(source);
}
private CorsConfiguration buildConfig() {
CorsConfiguration corsConfiguration = new CorsConfiguration();
// 在生产环境上最好指定域名,以免产生跨域安全问题
corsConfiguration.addAllowedOrigin("*");
corsConfiguration.addAllowedHeader("*");
corsConfiguration.addAllowedMethod("*");
return corsConfiguration;
}
}
然后你就自己琢磨着玩吧
二、基本使用
在路由配置方式上,我只演示了注册中心的形式,实际上也可以URL或者配置类的形式
2.1 路由的匹配规则
spring.cloud.gateway.routes[0].predicates[0]
路径匹配
-
Path=/gate/** , /rule/**
当请求的路径为gate、rule开头的时,转发到 lb://nacos-provider 微服务上
spring:
application:
name: nacos-gateway
cloud:
sentinel:
transport:
dashboard: 192.168.247.171:8849 #sentinel控制台的请求地址
nacos:
config:
# 配置中心地址
server-addr: 47.106.207.254:8848
file-extension: yaml
discovery:
server-addr: 47.106.207.254:8848
gateway:
routes:
# 用户所有以/user开始的请求,都给http://localhost:18081服务处理
# id唯一标识,可自定义 , 随便写,可以写小红,小花都行
- id: nacos-gateway
# 路由的服务地址
uri: lb://nacos-provider
# 路由拦截的地址配置(断言)
# /user/**所有以/user开始的请求都将被路由到uri指定的服务地址,
# 将该请求交给uri指定的服务处理,比如请求:http://localhost:9994/userSay/find会把请求交给提供者
# order 请求的优先级
order: 0
predicates:
- Path=/userSay/**
# filters:
# - MyParam
时间点之前/之后/之间
-
Before
- Before=2017-01-20T17:42:47.789-07:00[America/Denver]
-
After
r- After=2017-01-20T17:42:47.789-07:00[America/Denver]
-
Between
- Between=2017-01-20T17:42:47.789-07:00[America/Denver],2017-01-21T17:42:47.789-07:00[America/Denver]
配置的日期时间需要满足ZonedDateTime格式
Cookie
这段话的意思是,Cookie里面的请求,name=sessionId,value=test(我不确定是否必须正则,反正可以玩正则
)
- Cookie=sessionId, test
请求参数
请求中包含 smile 属性的参数即可匹配路由
- Query=smile
请求头
正则还是不太会玩
要求匹配请求中的name=X-Request-Id,value正则到\d+
- Header=X-Request-Id, \d+
主机名
你的主机名要是下面这个,才给你转发
- Host=www.baidu.com
请求方法
就是必须要是GET或者POST
- Method=GET,POST
2.2 过滤器
网关的过滤器分为两种类型
- Pre:请求转发到
后端微服务之前
执行 - Post:请求执行完,
结果返回
给客户端之前
执行
主要的两种实现
- 全局过滤器
- 单路由过滤器(局部)
过滤器规则
过滤规则 | 实例 | 说明 |
---|---|---|
PrefixPath | - PrefixPath=/app | 在请求路径前加上app |
RewritePath | - RewritePath=/test, /app/test | 访问localhost:9022/test,请求会转发到localhost:8001/app/test |
SetPath | SetPath=/app/{path} | 通过模板设置路径,转发的规则时会在路径前增加app,{path}表示原请求路径 |
RedirectTo | 重定向 | |
RemoveRequestHeader | 去掉某个请求头信息 |
再说
局部过滤器
AddRequestParameter
为所有匹配的请求,添加一个foo=bar的参数
filters:
- AddRequestParameter=foo, bar
AddResponseHeader
为所有匹配的请求,在返回结果给客户端之前,在header里面添加参数,key=X-Response-Foo,Value=Bar
filters:
- AddResponseHeader=X-Response-Foo, Bar
全局过滤器
1
自定义过滤器(局部/全局)
1
限流器
令牌桶算法,对请求进行限流
filters:
# 限流实现
- name: RequestRateLimiter
args:
# 用于限流的键的解析器的 Bean 对象的名字,它使用 SpEL 表达式根据#{@beanName}从 Spring 容器中获取 Bean 对象
key-resolver: '#{@userKeyResolver}'
# 令牌桶中令牌的填充速度
redis-rate-limiter.replenishRate: 20
# 令牌桶容量
redis-rate-limiter.burstCapacity: 100
从疯狂创客圈上描述,这里根据用户ID限流,请求路径中必须携带userId参数
@Bean
KeyResolver userKeyResolver() {
return exchange -> Mono.just(exchange.getRequest().getQueryParams().getFirst("user"));
}
用到了再回来学
请求重试
用到了再回来学
2.3 跨域问题处理
配置文件
spring:
cloud:
gateway:
globalcors:
cors-configurations:
'[/**]':
allowed-origins: "*"
allowed-headers: "*"
allow-credentials: true
allowed-methods:
- GET
- POST
- DELETE
- PUT
- OPTION
配置类
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.cors.CorsConfiguration;
import org.springframework.web.cors.reactive.CorsWebFilter;
import org.springframework.web.cors.reactive.UrlBasedCorsConfigurationSource;
import org.springframework.web.util.pattern.PathPatternParser;
@Configuration
public class CorsConfig {
@Bean
public CorsWebFilter corsFilter() {
UrlBasedCorsConfigurationSource source = new UrlBasedCorsConfigurationSource(new PathPatternParser());
source.registerCorsConfiguration("/**", buildConfig());
return new CorsWebFilter(source);
}
private CorsConfiguration buildConfig() {
CorsConfiguration corsConfiguration = new CorsConfiguration();
// 在生产环境上最好指定域名,以免产生跨域安全问题
corsConfiguration.addAllowedOrigin("*");
corsConfiguration.addAllowedHeader("*");
corsConfiguration.addAllowedMethod("*");
return corsConfiguration;
}
}
三、服务集成
与注册中心的集成就不讲了
3.1 Sentinel集成
1
3.2 再说
1健康检查
四、原理分析
4.1 请求处理过程
1
4.2 网关限流原理
1
4.3 WebFlux
1