标签:wildfly servlet undertow nio
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"); // 绑定映射为/hello servlet1.addMapping("/hello"); // 创建名字MessageServlet为的ServletInfo ServletInfo servlet2 = Servlets.servlet("MessageServlet", MessageServlet.class); servlet2.addInitParam("message", "MyServlet"); // 绑定映射为/myservlet servlet2.addMapping("/qrcode"); // 创建DeploymentInfo应用布署 DeploymentInfo deployment = Servlets.deployment(); // 指定ClassLoader deployment.setClassLoader(WildFlyServer.class.getClassLoader()); // 应用上下文(必须与映射路径一致,否则sessionID会有问题,每次都新建) deployment.setContextPath("/myapp"); // 设置布署包名 deployment.setDeploymentName("test.war"); // 添加ServletInfo deployment.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(); // 启动Server server.start(); } }
利用运行调试,我们可以更加深入地了解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剖析
标签:wildfly servlet undertow nio
原文地址:http://blog.csdn.net/zhaowen25/article/details/45324805