Gateway配置动态路由,
Predicate的详细使用,
Filter的使用
Gateway配置动态路由
- 默认情况下Gateway会根据注册中心的服务列表, 以注册中心上微服务名为路径创建动态路由进行转发, 从而实现动态路由的功能.
- 修改yml文件
- 需要注意的是uri的协议为lb, 表示启用Gateway的负载均衡功能.
- lb://serviceName是SpringCloud Gateway在微服务中为我们创建的负载均衡uri
server:
port: 9527
spring:
application:
name: cloud-gateway
cloud:
gateway:
discovery:
locator:
enabled: true #开启从注册中心动态创建路由的功能, 利用微服务名进行路由
rout es:
- id: payment_routh #路由的ID, 没有固定规则但要求唯一, 建议配合服务名
uri: lb://cloud-payment-service #匹配后提供服务的路由地址
predicates:
- Path=/payment/get/** #断言, 路径相匹配的进行路由.
- id: payment_routh2
uri: lb://cloud-payment-service
predicates:
- Path=/payment/lb/**
eureka:
instance:
hostname: cloud-gateway-service
client:
service-url:
register-with-eureka: true
fetch-registry: true
defaultZone: http://eureka7001.com:7001/eureka,http://eureka7002.com:7002/eureka
- 测试
- 启动7001+8001/8002+9527: http://localhost:9527/payment/lb
Predicate的使用

- SpringCloud Gateway将路由匹配作为Spring WebFlux HandlerMapping基础架构的一部分.
- 它包括许多内置的Route Predicate工厂, 所有这些Predicate都与HTTP请求的不同属性匹配, 多个Route Predicate工厂可以进行组合.
- SpringClooud Gateway创建Route对象时, 使用RoutePredicateFactory创建Predicate对象, Predicate对象可以赋值给Route, SpringCloud Gateway包含许多内置的Route Predicate Factories.
- 所有这些谓词都匹配HTTP请求的不同属性, 多种谓词工厂可以组合, 并通过逻辑and.
- After Route Predicate
- 在设定的时间之后, 该lb请求访问才有效果.
predicates:
- Path=/payment/lb/**
- After=2020-07-02T17:18:55.216+08:00[Asia/Shanghai]
- 如何获取这种时间格式 - 使用ZonedDateTime日期类
public static void main(String[] args) {
ZonedDateTime zbj = ZonedDateTime.now(); //默认时区
System.out.println(zbj);
//2020-07-02T17:18:55.216+08:00[Asia/Shanghai]
}
- Before Route Predicate
- 在设定的时间之前, 该lb请求访问才有效果
predicates:
- Path=/payment/lb/**
- Before=2020-08-02T17:18:55.216+08:00[Asia/Shanghai]
- Between Route Predicate
- 在设定的时间之间, 该lb请求访问才有效果
predicates:
- Path=/payment/lb/**
- Between=2020-08-08T10:59:34.102+08:00[Asia/Shanghai], 2020-09-08T10:59:34.102+08:00[Asia/Shanghai]
- Cookie Route Prerdicate
- 需要两个参数, 一个是Cookie name, 另一个是正则表达式.
- 路由规则会通过Cookie name值和正则表达式去匹配, 如果匹配上才执行路由, 没有匹配则不执行.
predicates:
- Path=/payment/lb/**
- Cookie=username, aakk
- 测试
- 不带Cookie访问: curl http://localhost:9527/payment/lb
- 带Cookie访问
- Header Route Predicate
- 两个参数, 一个是属性名称, 一个是正则表达式
- 只有请求头满足上述参数配置时该请求才能访问.
predicates:
- Path=/payment/lb/**
- Header=X-Request-Id, \d+ #请求头要由X-Request-Id的属性, 值为整数
- 测试: curl http://localhost:9527/payment/lb -H "X-Request-Id: 123"
- Host Route Predicate
- 接收一组参数, 一组匹配的域名列表, 这个模板是一个ant分隔的模板, 用逗号做分隔符.
- 通过参数中的主机地址作为匹配规则
predicates:
- Path=/payment/lb/**
- Host=**.somehost.org, **.anotherhost.org
- 测试: curl http://localhost:9527/payment/lb -H "Host: aakk.somehost.org"
- Method Route Predicate
- 填写请求方法.
- 只有满足才能访问
predicates:
- Path=/payment/lb/**
- Method=GET
- Path Route Predicate
predicates:
- Path=/payment/lb/**
- Query Route Predicate
- 带查询条件的.
predicates:
- Path=/payment/lb/**
- Query=username, \d+ #要有参数名username并且值还必须时整数才能访问
- 测试: http://localhost:9527/payment/lb?username=11
Filter的使用
- 路由过滤器可用于修改进入的HTTP请求和返回的HTTP响应, 路由过滤器只能指定路由进行使用.
- Spring Cloud Gateway内置了多种路由过滤器, 他们都由Gateway的工厂类来产生.
- 生命周期
- pre: 在业务逻辑之前
- post: 在业务逻辑之后
- 种类
- 单一过滤器: GatewayFilter
- 全局过滤器: GlobalFilter
- 单一过滤器31种.
- 全局过滤器10种.
- 要实现两个接口GlobalFilter, Ordered
- 作用
- 演示
- 在配置类中添加GlobalFilter方法
@Slf4j
@Configuration
public class GatewayConfig {
@Bean
@Order(0) //优先级
public GlobalFilter myGlobalFilter() {
return (exchange, chain) -> {
log.info("****come in MyLogGatewayFilter" + new Date());
String uname = exchange.getRequest().getQueryParams().getFirst("uname");
if(uname == null) {
log.info("*****用户名为null, 非法用户");
exchange.getResponse().setStatusCode(HttpStatus.NOT_ACCEPTABLE);
return exchange.getResponse().setComplete();
}
return chain.filter(exchange);
};
}
}
- 测试
-
http://localhost:9527/payment/lb -> 该网页无法正常运作
-
http://localhost:9527/payment/lb?uname=111 -> 可以正确显示