概念
gateway翻译过来,就是网关,顾名思义,他就是要做我们服务进来的第一关
主要功能如下
- 鉴权
- 路由
- 负载均衡
- 限流 大概流程
入门
引入基础代码
- pom引入nacos和gateway
<!--nacos服务注册发现依赖-->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
</dependency>
<!--网关gateway依赖-->
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-gateway</artifactId>
</dependency>
- 高版本cloud基本都得引这个依赖
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-loadbalancer</artifactId>
</dependency>
- 配置application.yml连接nacos
server:
port: 10010
spring:
application:
name: gateway
cloud:
nacos:
server-addr: http://127.0.0.1:8848 # nacos地址
gateway:
routes:
- id: teacher-flag # 路由标示,必须唯一
uri: lb://teacher # 路由的目标地址
predicates: # 路由断言,判断请求是否符合规则
- Path=/getDubbo/** # 路径断言,判断路径是否是以/getDubbo开头,如果是则符合
运行服务,并且访问
8082是teacher放出的接口,10010是gateway路由过去的
基本的解释
- uri: lb://teacher 这种写法是走nacos服务的方式,虽然也可以写域名/ip,但是不建议
- predicates 翻译是断言,可以理解为就是规则匹配,他可以匹配很多···下面原图出自 《黑马程序员》
那么gateway如何实现鉴权呢?
鉴权
想要知道鉴权,第一步就得先了解过滤器
全局过滤器GlobalFilter
- 直接写一个类实现GlobalFilter接口就可以
@Component
public class AuthorizeFilter implements GlobalFilter, Ordered {
@Override
public Mono<Void> filter(ServerWebExchange exchange, GatewayFilterChain chain) {
// 1.获取请求参数
ServerHttpRequest request = exchange.getRequest();
MultiValueMap<String, String> params = request.getQueryParams();
// 2.获取参数中的 authorization 参数
String auth = params.getFirst("authorization");
// 3.判断参数值是否等于 admin
if ("admin".equals(auth)) {
// 4.是,放行
return chain.filter(exchange);
}
// 5.否,拦截
// 5.1.设置状态码
exchange.getResponse().setStatusCode(HttpStatus.UNAUTHORIZED);
// 5.2.拦截请求
return exchange.getResponse().setComplete();
}
@Override
public int getOrder() {
return -1;
}
}
- 请求地址添加参数http://127.0.0.1:10010/getDubbo?authorization=admin
- debug看访问情况
所有的gateway请求都会走到这个方法中,因此可以通过这个拦截器做鉴权
具体解释
- 拦截器可以有多个,都是通过Mono对象来进行传递
- 实现Ordered,决定了执行顺序,Ordered越小,越早执行
- chain.filter(exchange); 表示可以继续往下走
- exchange.getResponse().setComplete(); 表示不通过,会返回一定格式的错误码,例如
题外话
我最最最后悔的就是,所有的服务都拿的最新的版本,spring肯定有bug,之前用cloud stream就是,退一个版本就什么都好了,本来文章想举例全局filter的,怎么试都失败,放弃了。
我今晚这篇文章硬是写了三个小时,全在处理问题,吐了啊。。。。
大家用的时候尽量用老一个版本的服务,能保证无bug。
写文章写到这真的是全是血和泪啊,求点赞啊!!!