Zuul【工作原理】
2019-10-28 06:22:19来源:博客园 阅读 ()
Zuul【工作原理】
zuul的核心逻辑都是由一系列filter过滤器链实现的,但是filter的类型不同,执行的时机也不同,效果自然也不一样,主要特点如下:
- filter的类型:filter的类型,决定了它在整个filter链中的执行顺序,可能在端点路由前执行,也可能在端点路由时执行,还有可能在端点路由后执行,甚至是端点路由发生异常时执行。
- filter的执行顺序:同一种类型的filter,可以通过filterOrder()方法设置执行顺序,一般都是根据业务场景自定义filter执行顺序。
- filter执行条件:filter运行所需的标准,或条件。
- filter执行效果:符合某个filter执行条件,产生执行效果。
zuul内部有一套完整的机制,可以动态读取编译运行filter机制,filter与filter之间不直接通信,在请求线程中会通过RequestContext来共享状态,它内部是用ThreadLocal实现的,例如HttpServletRequest、HttpServletResponse、异常信息等。部分源码如下:
public class RequestContext extends ConcurrentHashMap<String, Object> { private static final Logger LOG = LoggerFactory.getLogger(RequestContext.class); protected static Class<? extends RequestContext> contextClass = RequestContext.class; private static RequestContext testContext = null; protected static final ThreadLocal<? extends RequestContext> threadLocal = new ThreadLocal<RequestContext>() { @Override protected RequestContext initialValue() { try { return contextClass.newInstance(); } catch (Throwable e) { throw new RuntimeException(e); } } };
//.......
}
zuul中不同类型的filter执行逻辑的核心在ZuulServlet类中,主要代码如下:
public class ZuulServlet extends HttpServlet { private static final long serialVersionUID = -3374242278843351500L; private ZuulRunner zuulRunner; @Override public void init(ServletConfig config) throws ServletException { super.init(config); String bufferReqsStr = config.getInitParameter("buffer-requests"); boolean bufferReqs = bufferReqsStr != null && bufferReqsStr.equals("true") ? true : false; zuulRunner = new ZuulRunner(bufferReqs); } @Override public void service(javax.servlet.ServletRequest servletRequest, javax.servlet.ServletResponse servletResponse) throws ServletException, IOException { try { init((HttpServletRequest) servletRequest, (HttpServletResponse) servletResponse); // Marks this request as having passed through the "Zuul engine", as opposed to servlets // explicitly bound in web.xml, for which requests will not have the same data attached RequestContext context = RequestContext.getCurrentContext(); context.setZuulEngineRan(); try { preRoute(); //如果preRoute方法在执行的时候出现异常,直接就抛出500异常,不会走catch中的error方法,见下图FilterProcessor类中的preRoute方法。 } catch (ZuulException e) { error(e); //如果preRoute在执行过程中,抛出Zuul异常,这里被捕捉到以后,会执行error方法,打印堆栈信息,见下图FilterProcessor类中的error方法。 postRoute(); return; } try { route(); } catch (ZuulException e) { error(e); postRoute(); return; } try { postRoute(); } catch (ZuulException e) { error(e); return; } } catch (Throwable e) { error(new ZuulException(e, 500, "UNHANDLED_EXCEPTION_" + e.getClass().getName())); } finally { RequestContext.getCurrentContext().unset(); } }
//....... }
zuul一共有4种不同的生命周期:
- pre:在zuul网关按照规则路由到下级服务之前执行,如果需要对请求进行预处理,可以使用这种类型的过滤器。如:认证鉴权,限流等。
- route:这种过滤器是zuul路由动作的执行者,是Apache HttpClient或Ribbon构建和发送原始HTTP请求的地方,现在也支持OKHTTP。
- post:这种过滤器是在端点请求完毕,返回结果或者发生异常后执行的filter。如果需要对返回的结果进行再次处理,可以在这种过滤中处理逻辑。
- error: 这种过滤器是在整个生命周期内,如果发生异常,就执行该filter,可以做全局异常处理。
原文链接:https://www.cnblogs.com/idoljames/p/11741382.html
如有疑问请与原作者联系
标签:
版权申明:本站文章部分自网络,如有侵权,请联系:west999com@outlook.com
特别注意:本站所有转载文章言论不代表本站观点,本站所提供的摄影照片,插画,设计作品,如需使用,请与原作者联系,版权归原作者所有
- Spring Boot 实现配置文件加解密原理 2020-06-08
- Java跨平台原理(字节码文件、虚拟机) 以及Java安全性 2020-06-07
- 因为 MongoDB 没入门,我丢了一份实习工作 2020-06-07
- 面了一个工作4年的程序员,这个些面试题一个都答不上来 2020-06-05
- Java生鲜电商平台-生鲜电商接口幂等性原理与防重复提交方案( 2020-06-05
IDC资讯: 主机资讯 注册资讯 托管资讯 vps资讯 网站建设
网站运营: 建站经验 策划盈利 搜索优化 网站推广 免费资源
网络编程: Asp.Net编程 Asp编程 Php编程 Xml编程 Access Mssql Mysql 其它
服务器技术: Web服务器 Ftp服务器 Mail服务器 Dns服务器 安全防护
软件技巧: 其它软件 Word Excel Powerpoint Ghost Vista QQ空间 QQ FlashGet 迅雷
网页制作: FrontPages Dreamweaver Javascript css photoshop fireworks Flash