在前面的篇章都是一个服务消费者去调用一个服务提供者,但事实上我们的系统基本不会那么简单,如果真的是那么简单的业务架构我们也没必要用Spring Cloud,直接部署一个Spring Boot应用就够了。所以当我们的服务消费者有很多个,比如说在一个电商系统里,会员中心是一个微服务,商品详情又是一个微服务,订单又是一个微服务,支付又是一个等等,在这么多的微服务中,每个系统都需要自己的url,这种情况我们需要一个组件来集中管理和分发这些请求,把不同url转发给不同的微服务去处理。Zuul就可以很好地完成这件事,但是Zuul可以做的远不止是路由功能。先看一下官方对Zuul的简介:

Routing is an integral part of a microservice architecture. For example, / may be mapped to your web application, /api/users is mapped to the user service and /api/shop is mapped to the shop service. Zuul is a JVM-based router and server-side load balancer from Netflix.

Netflix uses Zuul for the following:

  • Authentication
  • Insights
  • Stress Testing
  • Canary Testing
  • Dynamic Routing
  • Service Migration
  • Load Shedding
  • Security
  • Static Response handling
  • Active/Active traffic management

Zuul’s rule engine lets rules and filters be written in essentially any JVM language, with built-in support for Java and Groovy.

内容来源:https://cloud.spring.io/spring-cloud-netflix/reference/html/#router-and-filter-zuul

Zuul提供的功能有很多,这里限于篇幅先介绍路由和过滤功能。

一、路由

1.1、创建新的module

新建一个新的module,名称为zuul,选择Eureka Discovery Client和Zuul两个依赖,如下:

<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-eureka-client</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.cloud</groupId>
<artifactId>spring-cloud-starter-netflix-zuul</artifactId>
</dependency>

1.2、修改配置文件

在application.properties中添加以下配置

server.port=8033
spring.application.name=server-zuul eureka.client.serviceUrl.defaultZone=http://localhost:8761/eureka/ zuul.routes.api-ribbon.service-id=consumer-ribbon
zuul.routes.api-ribbon.path=/api-ribbon/* zuul.routes.api-feign.service-id=consumer-feign
zuul.routes.api-feign.path=/api-feign/*

另外在启动类加上@EnableEurekaClient和@EnableZuulProxy注解

解释一下上面的zuul的配置,zuul配置路由时zuul.routes.XXX.service-id指定的是XXX服务的服务名,这里指定的是消费者的应用名,比如我们的两个服务消费者的应用名分别是consumer-ribbon和consumer-feign,而zuul.routes.XXX.path指定是映射路径,配置之后的请求地址就可以直接是zuul的地址+端口+url。举个例子,比如zuul的主机是localhost,端口是8033,那么当我们所有url为localhost:8033/api-ribbon/的请求就会被映射到consumer-ribbon服务,所有url为localhost:8033/api-feign/的请求就会被映射到consumer-feign。

1.3、启动&测试

依次启动注册中心、服务提供者、ribbon消费者、feign消费者和zuul,访问http://localhost:8033/api-ribbon/index?uid=ribbon,可以看到返回了

服务8770的消息:用户ribbon调用了此服务

访问http://localhost:8033/api-feign/index?uid=ribbon也能看到同样的信息,这说明我们的路由功能已经生效了。

二、过滤

我们可以对某些请求进行一些过滤的工作,比如对分发给ribbon这个服务的请求都进行参数校验,要求所有这个服务的请求都要带上token。

在zuul的module新建一个CustomFilter继承ZuulFilter

@Component
public class CustomFilter extends ZuulFilter { private Logger logger = LoggerFactory.getLogger(getClass()); @Override
public String filterType() {
return "pre";
} @Override
public int filterOrder() {
return 0;
} @Override
public boolean shouldFilter() {
return true;
} @Override
public Object run() throws ZuulException {
RequestContext ctx = RequestContext.getCurrentContext();
HttpServletRequest request = ctx.getRequest();
logger.info("request uri:" + request.getRequestURI());
String uri = request.getRequestURI();
String token = request.getParameter("token");
if (uri.startsWith("/api-ribbon") && StringUtils.isEmpty(token)) {
ctx.setSendZuulResponse(false);
ctx.setResponseStatusCode(401);
ctx.setResponseBody("Token must not be empty.");
}
return null;
}
}

需要重写的这四个方法:

  • filterType:返回过滤的类型,允许的有四个值:

    1. pre:路由前
    2. routing:路由时
    3. post:路由后
    4. error:发送错误调用
  • filterOrder:过滤顺序。这个方法返回一个整型数值,其实表示的是过滤的优先级,当有多个过滤器存在时,数字越大,优先级越高。

  • shouldFilter:返回一个布尔类型的值,它和run方法一起使用,返回true时会执行run方法,否则不执行。可以把这个方法理解问某种过滤规则的开关。

  • run:该方法是核心方法,过滤的具体规则在这个方法实现。虽然该方法要求返回一个对象,但是现在的实现往往会忽略,直接返回null就可以了。

上面的代码就是先获取路由前的请求uri和请求参数token的值,如果请求的是ribbon服务,就需要token参数,否则不需要。

依次启动注册中心、服务提供者、ribbon消费者、feign消费者和zuul,然后当访问http://localhost:8033/api-ribbon/index?uid=ribbon时会返回

Token must not be empty.

再访问http://localhost:8033/api-feign/index?uid=ribbon即会返回

服务8770的消息:用户ribbon调用了此服务

这说明我们的过滤器已经生效了

三、总结

以上就是Zuul的简单介绍,更多功能可以自行探索。下一篇介绍配置中心。

源码已经上传到github:https://github.com/spareyaya/spring-cloud-demo/tree/master/chapter5

Spring Cloud系列(五):服务网关Zuul的更多相关文章

  1. Spring Cloud(十):服务网关zuul(转)

    前面的文章我们介绍了,Eureka用于服务的注册于发现,Feign支持服务的调用以及均衡负载,Hystrix处理服务的熔断防止故障扩散,Spring Cloud Config服务集群配置中心,似乎一个 ...

  2. SpringCloud学习笔记(20)----Spring Cloud Netflix之服务网关Zuul的各种姿势

    1. 禁用过滤器 # zuul.<SimpleClassName>.<filterType>.disable=true # 例如禁用 自定义的过滤器 zuul.MyFilter ...

  3. SpringCloud学习笔记(18)----Spring Cloud Netflix之服务网关Zuul原理

    1. Zuul的工作机制 Zuul提供了一个框架,可以对过滤器进行动态的加载,编译,运行.过滤器之间没有直接的相互通信,他们是通过一个RequestContext的静态类来进行数据传递的.Requet ...

  4. SpringCloud学习笔记(17)----Spring Cloud Netflix之服务网关Zuul的使用

    1. 什么时候Zuul? Zuul是一个基于jvm路由和服务端的负载均衡器,在云平台上提供动态路由,监控,弹性,安全等边缘服务的框架. 路由功能:相当于nginx的反向代理 比如: / 可能需要映射到 ...

  5. SpringCloud学习笔记(19)----Spring Cloud Netflix之服务网关Zuul自定义过滤器

    zuul不仅只是路由,还可以自定义过滤器来实现服务验证. 实现案例:自定义过滤器,检验头部是否带有token,如果token=wangx,则通过校验,若不存在或不为wangx则返回提示token错误. ...

  6. spring cloud 系列第6篇 —— zuul 服务网关 (F版本)

    源码Gitub地址:https://github.com/heibaiying/spring-samples-for-all 一.zuul简介 1.1 API 网关 api 网关是整个微服务系统的门面 ...

  7. Spring Cloud 系列之 Netflix Zuul 服务网关

    什么是 Zuul Zuul 是从设备和网站到应用程序后端的所有请求的前门.作为边缘服务应用程序,Zuul 旨在实现动态路由,监视,弹性和安全性.Zuul 包含了对请求的路由和过滤两个最主要的功能. Z ...

  8. Spring Cloud实战之初级入门(六)— 服务网关zuul

    目录 1.环境介绍 2.api网关服务 2.1 创建工程 2.3 api网关中使用token机制 2.4 测试 2.5 小结 3.一点点重要的事情 1.环境介绍 好了,不知不觉中我们已经来到了最后一篇 ...

  9. Spring Cloud(十):服务网关 Zuul(路由)【Finchley 版】

    Spring Cloud(十):服务网关 Zuul(路由)[Finchley 版]  发表于 2018-04-23 |  更新于 2018-05-09 |  通过之前几篇 Spring Cloud 中 ...

  10. Spring Cloud(十一):服务网关 Zuul(过滤器)【Finchley 版】

    Spring Cloud(十一):服务网关 Zuul(过滤器)[Finchley 版]  发表于 2018-04-23 |  更新于 2018-05-07 |  在上篇文章中我们了解了 Spring ...

随机推荐

  1. DVWA之SQL Injection

    SQL Injection SQL Injection,即SQL注入,是指攻击者通过注入恶意的SQL命令,破坏SQL查询语句的结构,从而达到执行恶意SQL语句的目的.SQL注入漏洞的危害是巨大的,常常 ...

  2. hdu 3265 线段树扫描线(拆分矩形)

    题意:        给你n个矩形,每个矩形上都有一个矩形的空洞,所有的矩形都是平行于x,y轴的,最后问所有矩形的覆盖面积是多少. 思路:       是典型的矩形覆盖问题,只不过每个矩形上多了一个矩 ...

  3. POJ3160强连通+spfa最长路(不错)

    题意:       给你一个有向图,每个点上有一个权值,可正可负,然后给你一些链接关系,让你找到一个起点,从起点开始走,走过的边可以在走,但是拿过权值的点就不能再拿了,问最多能拿到多少权值? 思路: ...

  4. 4.PHP正则表达式与数组

    PHP正则表达式相关 行定位符 开头 ^tm 结尾 tm$ 不限制 tm 单词定界符 \btm\b   单词tm,如果想取反的话就是大写的 \Btm\B 或的关系,[Tt][Mm] 可以表达 tm T ...

  5. Docker网络配置进阶

    Docker启动会默认创建docker0虚拟网桥,是Linux的一个bridge,可以理解成一个软件交换机.它会在挂载到它的网口之间进行转发. 之后所有容器都是在172.17.0.x的网段上,并且可以 ...

  6. NumPy中文文档搬砖(划掉)学习笔记(1)

    原文地址 前言 况下加速Python中的操作运行时.适用于快速数值运算的一个选项是NumPy,它当之无愧地将自己称为使用Python进行科学计算的基本软件包. 当然,很少有人将50微秒(百万分之五十秒 ...

  7. 攻防世界Web刷题记录(新手区)

    攻防世界Web刷题记录(新手区) 1.ViewSource 题如其名 Fn + F12 2.get post 3.robots robots.txt是搜索引擎中访问网站的时候要查看的第一个文件.当一个 ...

  8. Yii2访问gii模块403

    出现问题 访问Yii2的gii模块没有权限,403 找到原因 在Yii2-gii源码文件中(vendor/yiisoft/yii2-gii/src/Module.php)可以看到有一个配置项$allo ...

  9. Mybatis学习之自定义持久层框架(六) 自定义持久层框架:完善CRUD方法并进行测试

    前言 没想到会等到半年以后才来写这篇文章,我已经不记得当初自己想要在这篇文章中写什么了,还好有一些零散的笔记留着,就对照着上一篇文章及零散的笔记,把内容给补充完吧. 完善CRUD方法 完善Defaul ...

  10. FreeSWITCH的安装与使用

    FreeSWITCH