在网上找到了很多关于undertow嵌入式相关资料,基本上都是springboot的,如果是一般性的web项目,并没有太多有用的文档资料,那就记录一下,我对于undertow的测试过程。
网上最多的就是一开始的helloworld了,简单了解一下undertow,作为容器启动了~~
package io.undertow.examples.helloworld;
import io.undertow.Undertow;
import io.undertow.examples.UndertowExample;
import io.undertow.server.HttpHandler;
import io.undertow.server.HttpServerExchange;
import io.undertow.util.Headers;
/**
* @author Stuart Douglas
*/
@UndertowExample("Hello World")
public class HelloWorldServer {
public static void main(final String[] args) {
Undertow server = Undertow.builder()
.addHttpListener(8080, "localhost")
.setHandler(new HttpHandler() {
@Override
public void handleRequest(final HttpServerExchange exchange) throws Exception {
exchange.getResponseHeaders().put(Headers.CONTENT_TYPE, "text/plain");
exchange.getResponseSender().send("Hello World");
}
}).build();
server.start();
}
}
我现在的需求是想要启动jsp,通过一般的sever启动,调用jsp资源的时候,就变成了下载文件。。
import io.undertow.Undertow;
import io.undertow.examples.UndertowExample;
import io.undertow.server.handlers.resource.ClassPathResourceManager;
import io.undertow.websockets.WebSocketConnectionCallback;
import io.undertow.websockets.core.AbstractReceiveListener;
import io.undertow.websockets.core.BufferedTextMessage;
import io.undertow.websockets.core.WebSocketChannel;
import io.undertow.websockets.core.WebSockets;
import io.undertow.websockets.spi.WebSocketHttpExchange;
import static io.undertow.Handlers.*;
/**
* @author Stuart Douglas
*/
@UndertowExample("Web Sockets")
public class WebSocketServer {
public static void main(final String[] args) {
Undertow server = Undertow.builder()
.addHttpListener(8080, "localhost")
.setHandler(path()
.addPrefixPath("/myapp", websocket(new WebSocketConnectionCallback() {
@Override
public void onConnect(WebSocketHttpExchange exchange, WebSocketChannel channel) {
channel.getReceiveSetter().set(new AbstractReceiveListener() {
@Override
protected void onFullTextMessage(WebSocketChannel channel, BufferedTextMessage message) {
WebSockets.sendText(message.getData(), channel, null);
}
});
channel.resumeReceives();
}
}))
.addPrefixPath("/", resource(new ClassPathResourceManager(WebSocketServer.class.getClassLoader(), WebSocketServer.class.getPackage())).addWelcomeFiles("index.jsp")))
.build();
server.start();
}
}
启动之后,把我对应的jsp文件就下载了下来,这怎么可能是我想要的。。而且,网络上也有关于这个的提问,但是下面好像并没有解决办法,那只能自己一点点试了。
在undertow官网上有一段关于jsp的描述,
JSP 可以通过Jastow项目在 Undertow 中使用,这是一个用于在 Undertow 中使用的 Apache Jasper 的 fork(请注意,这里使用的fork非常松散,它基本上只是 Jasper 移除了其 Tomcat 依赖项)。
Jasper 通过 Servlet 提供其所有功能,因此可以通过将 JSP servlet 添加到*.jsp映射来将其添加到标准的 Undertow servlet 部署中。
JSP 还需要一些额外的上下文参数,Jastow 提供了一个帮助类来设置这些参数。
同时,也给出了一段示例代码
final PathHandler servletPath = new PathHandler();
final ServletContainer container = ServletContainer.Factory.newInstance();
DeploymentInfo builder = new DeploymentInfo()
.setClassLoader(SimpleJspTestCase.class.getClassLoader())
.setContextPath("/servletContext")
.setClassIntrospecter(TestClassIntrospector.INSTANCE)
.setDeploymentName("servletContext.war")
.setResourceManager(new TestResourceLoader(SimpleJspTestCase.class))
.addServlet(JspServletBuilder.createServlet("Default Jsp Servlet", "*.jsp"));
JspServletBuilder.setupDeployment(builder, new HashMap<String, JspPropertyGroup>(), new HashMap<String, TagLibraryInfo>(), new MyInstanceManager());
DeploymentManager manager = container.addDeployment(builder);
manager.deploy();
servletPath.addPrefixPath(builder.getContextPath(), manager.start());
比较悲催的,这段代码放过去,反正好多报红。。。没办法,只能根据servlet的示例,一点点修改。
public class JspServer {
public static final String MYAPP = "/myapp";
public static void main(String[] args) {
try {
DeploymentInfo servletBuilder = deployment()
.setClassLoader(JspServer.class.getClassLoader())
.setContextPath(MYAPP)
.setClassIntrospecter(TestClassIntrospector.INSTANCE)
.setDeploymentName("test.war")
.setResourceManager(new ClassPathResourceManager(JspServer.class.getClassLoader(), JspServer.class.getPackage()))
.addServlet(JspServletBuilder.createServlet("Default Jsp Servlet", "*.jsp"));
JspServletBuilder.setupDeployment(servletBuilder, new HashMap<String, JspPropertyGroup>(), new HashMap<String, TagLibraryInfo>(), new HackInstanceManager());
DeploymentManager manager = ServletContainer.Factory.newInstance().addDeployment(servletBuilder);
manager.deploy();
HttpHandler servletHandler = manager.start();
PathHandler path = Handlers.path(Handlers.redirect(MYAPP))
.addPrefixPath(MYAPP, servletHandler);
Undertow server = Undertow.builder()
.addHttpListener(8081, "localhost")
.setHandler(path)
.build();
server.start();
} catch (ServletException e) {
throw new RuntimeException(e);
}
}
}
这是我修改后的代码,其中HackInstanceManager这个在示例代码中用的是MyInstanceManager,并没有这个对象的存在~,找了好多,在jfinal框架下的undertow论坛找到了答案。。。另外,TestClassIntrospector也困扰了我好久,由于才疏学浅,这些还不能明白其原理,所以一开始忽略了这个参数的配置,完全仿制servlet配置,启动项目,永远的forbiddon。。想要自己写一个,又不知道具体配置是啥,好在灵机一动,Jastow项目我有啊,那在这里看看,很快,这个对象被我找到了~另外,在项目启动过程中,还会用到好几个jar包,在这里都能找到,最后启动成功。不禁感慨,官网果然没说错~可以通过Jastow运行。。。。
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>$Title$</title>
</head>
<body>
<p>MMJJcaca!Hello World!!</p>
</body>
</html>
先记录到这吧~~中间走了好多岔路,果然当小白当着轻松,干活的时候就累了。。。。