根据权重
权重通常会有多个路由规则来组成,多个路由之间进行一个百分比的权重
权重需要配置两个参数,第一个参数是组名,第二个是权重值,多个路由如果是在一组中那么组名需要相同
spring: cloud: gateway: routes: - id: weight_high uri: https://weighthigh.org predicates: - Weight=group1,8 - id: weight_low uri: https://weightlow.org predicates: - Weight=group1,2
该路由会将约 80% 的流量转发到weighthigh.org,将约 20% 的流量转发到weightlow.org
自定义断言工厂实现
首先在配置文件中添加如下,表示参数age年龄的范围,在这之间符合要求。
gateway: routes: #路由数组,指当请求满足什么样的条件转发到哪个微服务上 - id: order_router #当前路由标识,要求唯一 uri: lb://provider #请求最终要被转发的地址,lb指的是从nacos中按照名称获取微服务,并按照负载均衡策略 order: 1 #路由的优先级,数字越小代表路由的优先级越高 predicates: #断言(条件判断,返回值是boolean,转发请求要满足的条件) - Path=/orderservice/** - Age=18,60 filters: - StripPrefix=1
自定义代码实现如下
@Component public class AgeRoutePredicateFactory extends AbstractRoutePredicateFactory<AgeRoutePredicateFactory.Config> { //断言逻辑 public Predicate<ServerWebExchange> apply(AgeRoutePredicateFactory.Config config) { return new Predicate<ServerWebExchange>() { @Override public boolean test(ServerWebExchange serverWebExchange) { String age = serverWebExchange.getRequest().getQueryParams().getFirst("age"); if(age!=null){ int myage = Integer.parseInt(age); if(myage>config.minAge&&myage<config.maxAge) return true; else return false; } return false; } }; } public AgeRoutePredicateFactory() { super(AgeRoutePredicateFactory.Config.class); } //读取配置文件中的参数值,赋值到配置类上的属性上 public List<String> shortcutFieldOrder() { return Arrays.asList("minAge","maxAge");//这个位置的顺序必须和配置文件中的顺序对应 } //用于接收配置文件中的对应参数 @Data @NoArgsConstructor public static class Config{ private int minAge; private int maxAge; } }
1.2.5 过滤器
过滤器就是对于请求和响应做一些手脚。作用流程如下图:
从过滤器生命周期(影响时机点)的⻆度来说,主要有两个pre和post:
pre:这种过滤器在请求被路由之前调用。我们可以利用这类过滤器实现身份验证、在集群中选择 请求的微服务、记录调试信息等。
post:这种过滤器在路由到微服务以后执行。这类过滤器可用来为响应添加标准的HTTP Header、收集统计信息和指标、将响应从微服务发送给客户端。
从过滤器作用范围的角度来说,可分为另外两种,一种是针对于单个路由的gateway filter,它在配置文件中的写法同predict类似;另外一种是针对于所有路由的global gateway filer。现在从作用范围划分的维度来讲解这两种filter。
区别:
GatewayFilter:网关过滤器,需要通过spring.cloud.routes.filters配置在具体的路由下,只作用在当前特定路由上,也可以通过配置spring.cloud.default-filters让它作用于全局路由上。
GlobalFilter:全局过滤器,不需要再配置文件中配置,作用在所有的路由上,最终通过GatewayFilterAdapter包装成GatewayFilterChain能够识别的过滤器。
内置局部过滤器
全局过滤器
内置的全局过滤器如下图:
自定义全局过滤器
内置的过滤器已经可以完成大部分的功能,但是对于企业开发的一些业务功能处理,还是需要我们自己编写过滤器来实现的,那么我们一起通过代码的形式自定义一个过滤器,去完成统一的权限校验。
开发中的鉴权逻辑:
1.当客户端第一次请求服务时,服务端对用户进行信息认证(登录)
2.认证通过,将用户信息进行加密形成token,返回给客户端,作为登录凭证·以后每次请求,客户端都携带认证的token
3.服务端对token进行解密,判断是否有效。
如下图:
自定义代码如下
@Component @Order(-1)//越小优先级越高 @Slf4j public class Filter implements GlobalFilter { public Mono<Void> filter(ServerWebExchange exchange, GatewayFilterChain chain) { String token = exchange.getRequest().getQueryParams().getFirst("token"); if(token==null||!token.equals("admin")){ //认证失败 log.error("认证失败"); exchange.getResponse().setStatusCode(HttpStatus.UNAUTHORIZED); return exchange.getResponse().setComplete(); } return chain.filter(exchange); } }