路由器和过滤器:Zuul
Zuul是 Netflix 的基于JVM的路由器和服务器端负载均衡器。
默认集成了 Ribbon,实现了负载均衡功能。
Netflix使用Zuul进行以下操作:
- 认证
- 洞察
- 压力测试
- 金丝雀测试
- 动态路由
- 服务迁移
- 负载脱落
- 安全
- 静态响应处理
- 主动/主动流量管理
测试、代理、路由、过滤。
zuul 将自己也注册进 Eureka 注册中心,使用方向代理:
zuul:
ignoredServices: '*'
routes:
users: /myusers/**
在此示例中,除 “用户” 之外,所有服务都被忽略。
要获得对路由的更细粒度的控制,可以独立地指定路径和serviceId:
zuul:
routes:
users:
path: /myusers/**
serviceId: users_service
zuul不仅只是路由,并且还能过滤,做一些安全验证。
package com.xuxx.dept.filter;
import javax.servlet.http.HttpServletRequest;
import org.springframework.stereotype.Component;
import com.netflix.zuul.ZuulFilter;
import com.netflix.zuul.context.RequestContext;
import lombok.extern.slf4j.Slf4j;
@Slf4j
@Component
public class MyFilter extends ZuulFilter {
@Override
public boolean shouldFilter() {
return true;
}
@Override
public Object run() {
RequestContext ctx = RequestContext.getCurrentContext();
HttpServletRequest request = ctx.getRequest();
log.info(String.format("%s >>> %s", request.getMethod(), request.getRequestURL().toString()));
Object accessToken = request.getParameter("token");
if (accessToken == null) {
log.warn("token is empty");
ctx.setSendZuulResponse(false);
ctx.setResponseStatusCode(401);
try {
ctx.getResponse().getWriter().write("token is empty");
} catch (Exception e) {
}
return null;
}
log.info("ok");
return null;
}
@Override
public String filterType() {
return "pre";
}
@Override
public int filterOrder() {
return 0;
}
}
这个例子声明了一个 filterType
为 pre
的前置过滤器,filterOrder 为 0,shouldFilter 为 true 表始终过滤。在 run 方法中,我们从 request 中获取 token,不存在返回错误代码。
Zuul Request Lifecycle.png
将此过滤器加入到 Spring Context 中(加 @Component 注解,并保证在包路径扫描中),Zuul 会自动去加载、调用这个过滤器。