图解WildFly8之Servlet容器Undertow剖析
Undertow簡介
Undertow 是RedHat(紅帽公司)的開源產品,采用 Java 開發的靈活的高性能 Web 服務器,提供包括阻塞和基于 NIO 的非堵塞機制。
WildFly8的默認Servlet容器采用的不是Tomcat,也不是Jetty,而是JBoss自己開源的Undertow,Undertow是用Java編寫的性能靈活的Servlet容器,底層基于高性能的NIO框架XNIO,XNIO也是JBoss開源的產品,JBoss開源的高性能NIO框架還有一個很有名:Netty。Undertow在WildFly8中的角色如圖:
Undertow的架構類似于Jetty,采用應用內嵌的方式,這也正是為什么說它有靈活的性能的原因,利用Undertow可以快速構建一個小巧的應用服務,實現代碼如下:
import io.undertow.Handlers; import io.undertow.Undertow; import io.undertow.server.HttpHandler; import io.undertow.server.handlers.PathHandler; import io.undertow.servlet.Servlets; import io.undertow.servlet.api.DeploymentInfo; import io.undertow.servlet.api.DeploymentManager; import io.undertow.servlet.api.ServletContainer; import io.undertow.servlet.api.ServletInfo;public class WildFlyServer {public static void main(final String[] args) throws Exception {// 創建ServletInfo,名字"MyServlet"必須唯一ServletInfo servlet1 = Servlets.servlet("MyServlet", MyServlet.class);// 設置Servlet的init方法執行時需要的數據servlet1.addInitParam("message", "Hello World");// 綁定映射為/helloservlet1.addMapping("/hello");// 創建名字MessageServlet為的ServletInfoServletInfo servlet2 = Servlets.servlet("MessageServlet", MessageServlet.class);servlet2.addInitParam("message", "MyServlet");// 綁定映射為/myservletservlet2.addMapping("/qrcode");// 創建DeploymentInfo應用布署DeploymentInfo deployment = Servlets.deployment();// 指定ClassLoaderdeployment.setClassLoader(WildFlyServer.class.getClassLoader());// 應用上下文(必須與映射路徑一致,否則sessionID會有問題,每次都新建)deployment.setContextPath("/myapp");// 設置布署包名deployment.setDeploymentName("test.war");// 添加ServletInfodeployment.addServlets(servlet1,servlet2);// 創建DeploymentInfo2應用布署DeploymentInfo deployment2 = Servlets.deployment();deployment2.setClassLoader(WildFlyServer.class.getClassLoader());deployment2.setContextPath("/myapp2");deployment2.setDeploymentName("test2.war");deployment2.addServlets(servlet1,servlet2);// 使用默認Servlet容器,并將布署添加至容器ServletContainer container = Servlets.defaultContainer();// 將布署添加至容器,生成布置對應的管理器DeploymentManager manager = container.addDeployment(deployment);DeploymentManager manager2 = container.addDeployment(deployment2);// 實施布署manager.deploy();manager2.deploy();// 生成路徑處理器(作用是dispatch servlet),默認返回"/*"處理器PathHandler path = Handlers.path();// 生成路徑處理器,返回"/*"自動重定向到"/myapp"的處理器 // PathHandler path = Handlers.path(Handlers.redirect("/myapp"));// 啟動容器,生成請求處理器HttpHandler myapp = manager.start();HttpHandler myapp2 = manager2.start();// 綁定映射關系path.addPrefixPath("/myapp", myapp);path.addPrefixPath("/myapp2", myapp2);Undertow server = Undertow.builder()// 綁定端口與主機.addHttpListener(8080, "localhost")// 設置分發處理器PathHandler.setHandler(path).build();// 啟動Serverserver.start();} }
從源代碼,我們可以抽象出Undertow生成應用的架構,如圖所示
利用運行調試,我們可以更加深入地了解Undertow中的一些概念:
ServletInfo:Servlet的最小單位,是對javax.servlet.Servlet具體實現的再次封裝
FilterInfo:過濾器封裝
DeploymentInfo:包布署對象,包含多個ServletInfo,可以說是ServletInfo的集合
ServletContainer:容器,用來管理DeploymentInfo,一個容器可以添加多個DeploymentInfo
DeploymentManager:包布署的管理,是對添加到ServletContainer的DeploymentInfo的一個引用,用于運行發布和啟動容器
HttpHandler:servlet path處理器,DeploymentManager啟動后返回的Servlet處理器,通常是HttpContinueReadHandler(連續讀處理器)
PathHandler:分發器,將用戶請求分發給對應的HttpHandler
HttpServerExchange:數據交換封裝,可以轉換成ServletRequest和ServletResponse
示例代碼的調試運行棧如下:
連接通道
作為Servlet協議協議轉換的實體HttpServerExchange的結構如下:
Undertow的性能
專業測評結果的數據如下:
總結
以上是生活随笔為你收集整理的图解WildFly8之Servlet容器Undertow剖析的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: AOE网
- 下一篇: Linux Shell之一 Shell简