当前位置:   article > 正文

Spring Cloud Gateway---自定义过滤器_spring cloud gateway 自定义过滤器 part

spring cloud gateway 自定义过滤器 part

前言


即使Spring Cloud Gateway自带有许多实用的GatewayFilter Factory、Gateway Filter、Global Filter,但是在很多情景下我们仍然希望可以自定义自己的过滤器。实现一些骚操作。所以自定义过滤器就显得非常有必要。本文主要介绍了自定义Gateway Filter、自定义Global Filter、自定义Gateway Filter Factory

案例


实现自己的过滤器我们其实可以去查看Spring Cloud Gateway自带过滤器源码是如何实现的,

自定义Gateway Filter


实现自定义的Gateway Filter我们需要GatewayFilter、Ordered两个接口

  1. /**
  2. * 此过滤器功能为计算请求完成时间
  3. */
  4. public class MyFilter implements GatewayFilter, Ordered {
  5. private static final String ELAPSED_TIME_BEGIN = "elapsedTimeBegin";
  6. @Override
  7. public Mono<Void> filter(ServerWebExchange exchange, GatewayFilterChain chain) {
  8. exchange.getAttributes().put(ELAPSED_TIME_BEGIN, System.currentTimeMillis());
  9. return chain.filter(exchange).then(
  10. Mono.fromRunnable(() -> {
  11. Long startTime = exchange.getAttribute(ELAPSED_TIME_BEGIN);
  12. if (startTime != null) {
  13. System.out.println(exchange.getRequest().getURI().getRawPath() + ": " + (System.currentTimeMillis() - startTime) + "ms");
  14. }
  15. })
  16. );
  17. }
  18. /*
  19. *过滤器存在优先级,order越大,优先级越低
  20. */
  21. @Override
  22. public int getOrder() {
  23. return Ordered.LOWEST_PRECEDENCE;
  24. }
  25. }
  26. 复制代码

定义好MyFilter以后,其需要跟Route绑定使用,不能在application.yml文件中配置使用

  1. @Bean
  2. public RouteLocator routeLocator(RouteLocatorBuilder builder) {
  3. return builder.routes().route(r ->
  4. r.path("/aa")
  5. //转发路由
  6. .uri("http://localhost:8003/provider/test")
  7. //注册自定义过滤器
  8. .filters(new MyFilter())
  9. //给定id
  10. .id("user-service"))
  11. .build();
  12. }
  13. 复制代码

测试结果:可以在控制台看到请求响应时间。

自定义Gateway Filter Factory


很多时候我们更希望在配置文件中配置Gateway Filter,所以我们可以自定义过滤器工厂实现。
自定义过滤器工厂需要继承AbstractGatewayFilterFactory

  1. @Component
  2. public class AuthorizeGatewayFilterFactory extends AbstractGatewayFilterFactory<AuthorizeGatewayFilterFactory.Config> {
  3. private static final Log logger = LogFactory.getLog(AuthorizeGatewayFilterFactory.class);
  4. private static final String AUTHORIZE_TOKEN = "token";
  5. private static final String AUTHORIZE_UID = "uid";
  6. @Autowired
  7. private StringRedisTemplate stringRedisTemplate;
  8. public AuthorizeGatewayFilterFactory() {
  9. super(Config.class);
  10. logger.info("Loaded GatewayFilterFactory [Authorize]");
  11. }
  12. @Override
  13. public List<String> shortcutFieldOrder() {
  14. return Arrays.asList("enabled");
  15. }
  16. @Override
  17. public GatewayFilter apply(AuthorizeGatewayFilterFactory.Config config) {
  18. return (exchange, chain) -> {
  19. if (!config.isEnabled()) {
  20. return chain.filter(exchange);
  21. }
  22. ServerHttpRequest request = exchange.getRequest();
  23. HttpHeaders headers = request.getHeaders();
  24. String token = headers.getFirst(AUTHORIZE_TOKEN);
  25. String uid = headers.getFirst(AUTHORIZE_UID);
  26. if (token == null) {
  27. token = request.getQueryParams().getFirst(AUTHORIZE_TOKEN);
  28. }
  29. if (uid == null) {
  30. uid = request.getQueryParams().getFirst(AUTHORIZE_UID);
  31. }
  32. ServerHttpResponse response = exchange.getResponse();
  33. if (StringUtils.isEmpty(token) || StringUtils.isEmpty(uid)) {
  34. response.setStatusCode(HttpStatus.UNAUTHORIZED);
  35. return response.setComplete();
  36. }
  37. String authToken = stringRedisTemplate.opsForValue().get(uid);
  38. if (authToken == null || !authToken.equals(token)) {
  39. response.setStatusCode(HttpStatus.UNAUTHORIZED);
  40. return response.setComplete();
  41. }
  42. return chain.filter(exchange);
  43. };
  44. }
  45. public static class Config {
  46. // 控制是否开启认证
  47. private boolean enabled;
  48. public Config() {}
  49. public boolean isEnabled() {
  50. return enabled;
  51. }
  52. public void setEnabled(boolean enabled) {
  53. this.enabled = enabled;
  54. }
  55. }
  56. }
  57. 复制代码

application.yml配置使用

  1. # 网关路由配置
  2. spring:
  3. cloud:
  4. gateway:
  5. routes:
  6. - id: user-service
  7. uri: http://localhost:8077/api/user/list
  8. predicates:
  9. - Path=/user/list
  10. filters:
  11. # 关键在下面一句,值为true则开启认证,false则不开启
  12. # 这种配置方式和spring cloud gateway内置的GatewayFilterFactory一致
  13. - Authorize=true
  14. 复制代码

自定义Global Filter


实现自定义全局过滤器需要继承GlobalFilterOrdered

  1. @Component
  2. public class MyGloablFilter implements GlobalFilter, Ordered {
  3. @Override
  4. public Mono<Void> filter(ServerWebExchange exchange, GatewayFilterChain chain) {
  5. System.out.println("1111111111111111");
  6. return chain.filter(exchange);
  7. }
  8. @Override
  9. public int getOrder() {
  10. return 0;
  11. }
  12. }
  13. 复制代码

使用它只需要加上@Component注解

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/Monodyee/article/detail/667813
推荐阅读
相关标签
  

闽ICP备14008679号