Gateway实现统一网关
新建一个子项目,然后导入gateway依赖,同时也需要被nacos注册发现
<!-- 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>
application.yml文件配置
server:
port: 10010
spring:
application:
name: gateway # 服务名称
cloud:
nacos:
server-addr: localhost:80 #nacos地址
gateway:
routes:
- id: user-service #路由id,自定义,唯一即可
uri: lb://userservice #路由的目标地址,lb会自动负载均衡userservice服务名的服务,也可以直接写http表示固定的目标地址
predicates:
- Path=/user/** #Path以地址判断是否替换本服务ip地址为上述uri进行访问
- After=2020-04-20T23:57:57.308+08:00[Asia/Shanghai] #还可以通过After,Before等方式进行判断配置,例如这样
- id: order-service
uri: lb://orderservice
predicates:
- Path=/order/**
filters:
- AddRequestHeader=Truth,666 #给当前请求添加一个请求头,Key为Truth,Value为666
#- RemoveRequestHeader #移除请求中的一个请求头
#- AddResponseHeader #给响应结果中添加一个请求头
#- RemoveResponseHeader #从响应结果中移除一个请求头
#- RequestRateLimiter #限制请求的流量
default-filters: #我们可以在与routes同级的位置,写上该配置,来统一现实配置过滤,无需挨个路由配置filters
globalcors: # 全局的跨域处理,采用CORS方案
add-to-simple-url-handler-mapping: true # 浏览器会先用options请求询问一次服务器,所以需要解决options请求被拦截问题
corsConfigurations:
'[/**]':
allowedOrigins: # 允许哪些网站的跨域请求
- "http://localhost:8090"
- "http://www.leyou.com"
allowedMethods: # 允许的跨域ajax的请求方式
- "GET"
- "POST"
- "DELETE"
- "PUT"
- "OPTIONS"
allowedHeaders: "*" # 允许在请求中携带的头信息
allowCredentials: true # 是否允许携带cookie
maxAge: 360000 # 这次跨域检测的有效期
用@RequestHeader可以自动获取请求头中Key为Truth的值
@GetMapping("/{id}")
public User queryById(@PathVariable("id") Long id, @RequestHeader(value = "Truth", required = false) String truth) {
return userService.queryById(id);
}
自定义全局过滤器
利用上述方法实现过滤会比较局限,所以我们还是需要有自定义过滤器的方法。
新建一个类实现GlobalFilter接口的方法,并加入IOC容器,即可自定义一个全局过滤器。
需要注意的是,defaultFilter,还有路由过滤器filter,他们在配置文件中,order值是从1开始逐步递增的,并且是分开计数的,而当这两过滤器,还有全局过滤器的order相同时,优先级是defaultFilter>filter>GlobalFilter
@Order(1) //过滤优先级,数字小的优先过滤
@Component
public class AuthorizeFilter implements GlobalFilter {
@Override
public Mono<Void> filter(ServerWebExchange exchange, GatewayFilterChain chain) {
ServerHttpRequest request = exchange.getRequest();
MultiValueMap<String, String> params = request.getQueryParams();
String auth = params.getFirst("authorization");
if (auth.equals("admin")){ //检验请求头authorization的属性是否等于admin
return chain.filter(exchange); //过滤放行
}
exchange.getResponse().setStatusCode(HttpStatus.UNAUTHORIZED); //插入一个状态码
return exchange.getResponse().setComplete(); //过滤拦截,不往下执行
}
}