一、前言
Zuul的功能:
Zuul注册于Eureka并集成了Ribbon所以自然也是可以从注册中心获取到服务列表进行客户端负载。- 功能丰富的路由功能,解放运维。
- 具有过滤器,所以鉴权、验签都可以集成。
在项目中使用到Zuul这块主要是用在了结合 Eureka实现负载均衡反向代理。这里记录一下Zuul的路由的使用。
通过服务发现自动映射路由
Eureka配合Zuul使用的优美之处在于,不仅可以通过单个端点来访问应用的所有服务,而且,在添加或移除服务实例的时候不用修改Zuul的路由配置。另外,也可以添加一个新的服务到Eureka,而Zuul会对访问新添加的服务自动路由,因为Zuul是通过与Eureka通信然后从Eureka获取微服务实例真正物理地址,只要服务托管在Eureka中。
二、路由
路由是网关的核心功能之一,可以使系统有一个统一的对外接口,下面来看看具体的应用。
1 传统路由
传统路由非常简单,和 Nginx 类似,由开发、运维人员来维护请求地址和对应服务的映射关系,类似于:
zuul.routes.user-service.path=/user-service/**
zuul.routes.user-sercice.url=http://localhost:8080/
这样当我们访问 http://localhost:8383/user-service/getUserInfo/1 网关就会自动给我们路由到 http://localhost:8080/getUserInfo/1 上。
可见只要我们维护好这个映射关系即可自由的配置路由信息(user-sercice 可自定义),但是很明显这种方式不管是对运维还是开发都不友好。由于实际这种方式用的不多就再过多展开。
2 服务路由
对此Zuul 提供了一种基于服务的路由方式。我们只需要维护请求地址与服务 ID 之间的映射关系即可,并且由于集成了 Ribbon ,Zuul 还可以在路由的时候通过 Eureka实现负载调用。
具体配置:
zuul.routes.sbc-user.path=/api/user/**
zuul.routes.sbc-user.serviceId=sbc-user
这样当输入 http://localhost:8383/api/user/getUserInfo/1时就会路由到注册到 Eureka中服务 ID 为sbc-user的服务节点,如果有多节点就会按照 Ribbon的负载算法路由到其中一台上。
这样让我们访问 http://127.0.0.1:8383/api/user/userService/getUserByHystrix 时候就会根据负载算法帮我们路由到sbc-user 应用上,如下图所示:
启动了两个sbc-user服务。
请求结果:
一次路由就算完成了。
在上面的配置中有看到/api/user/**这样的通配符配置,具体有以下三种配置需要了解:
?只能匹配任意的单个字符,如/api/user/?就只能匹配/api/user/x /api/user/y /api/user/z这样的路径。*只能匹配任意字符,如 /api/user/* 就只能匹配/api/user/x /api/user/xy /api/user/xyz。**可以匹配任意字符、任意层级。结合了以上两种通配符的特点,如/api/user/**则可以匹配/api/user/x /api/user/x/y /api/user/x/y/zzz这样的路径,最简单粗暴!
谈到通配符匹配就不得不提到一个问题,如上面的 sbc-user服务由于后期迭代更新,将sbc-user 中的一部分逻辑抽成了另一个服务 sbc-user-pro。新应用的路由规则是 /api/user/pro/**,如果我们按照:
zuul.routes.sbc-user=/api/user/**
zuul.routes.sbc-user-pro=/api/user/pro/**
进行配置的话,我们想通过/api/user/pro/来访问 sbc-user-pro 应用,却由于满足第一个路由规则,所以会被 Zuul 路由到 sbc-user这个应用上,这显然是不对的。
解决方法:只需要将优先匹配的路由规则放前即可解决。