gpt4 book ai didi

java - 使用 Tomcat/Websphere 将 JSP 编译为字符串或内存字节数组

转载 作者:塔克拉玛干 更新时间:2023-11-03 05:11:50 28 4
gpt4 key购买 nike

我正在转换为图像和 PDF 输出。我需要一个由我们的应用程序 JSP 生成的输入 HTML 文档。本质上,我需要将基于 JSP 的应用程序的最终输出结果呈现为字符串或内存,然后将该字符串用于其他处理。

有哪些方法可以仅调用 JSP 呈现器来获取通常输出给用户的最终 HTML 内容?理想情况下,我正在寻找适用于多个应用程序服务器(如 websphere)的东西。但是 Tomcat 特定的东西也可以工作。

还有其他几种不同的方法,但我认为呈现 JSP(可能包括子 JSP)是最好的方法。

我宁愿远离的可选路径。

  1. 我可以使用套接字 API 对页面执行网络请求,然后读取从该特定页面呈现的最终输出。这可能是下一个最佳选择,但我们在多个服务器和 JVM 上工作,定位我需要的页面会很复杂。

  2. 使用过滤器获得最终页面输出。这很好,但我一直遇到过滤器和非法状态异常的问题。它似乎从来没有按照我需要的方式 100% 工作。

这看起来应该很简单。 JSP 编译器本质上只是一个库,用于解析输入的 JSP 文档和子文档,然后输出一些 HTML 内容。我想通过 Java 代码调用该过程。在服务器上并可能作为独立的控制台应用程序。

最佳答案

这是一个彻头彻尾的恼人问题,我不得不处理好几次,但我从未找到令人满意的解决方案。

基本问题是 servlet API 在这里毫无帮助,因此您必须欺骗它。我的解决方案是编写 HttpServletResponseWrapper 的子类,它覆盖 getWriter() 和 getOutput() 方法并将数据捕获到缓冲区中。然后将您的请求转发()到您要捕获的 JSP 的 URI,用您的包装器响应替换原始响应。然后,您从缓冲区中提取数据,对其进行操作,并将最终结果写回原始响应。

这是我执行此操作的代码:

public class CapturingResponseWrapper extends HttpServletResponseWrapper {

private final OutputStream buffer;

private PrintWriter writer;
private ServletOutputStream outputStream;

public CapturingResponseWrapper(HttpServletResponse response, OutputStream buffer) {
super(response);
this.buffer = buffer;
}

@Override
public ServletOutputStream getOutputStream() {
if (outputStream == null) {
outputStream = new DelegatingServletOutputStream(buffer);
}
return outputStream;
}

@Override
public PrintWriter getWriter() {
if (writer == null) {
writer = new PrintWriter(buffer);
}
return writer;
}

@Override
public void flushBuffer() throws IOException {
if (writer != null) {
writer.flush();
}
if (outputStream != null) {
outputStream.flush();
}
}

}

使用它的代码可以是这样的:

HttpServletRequest originalRequest = ...
HttpServletResponse originalResponse = ...

ByteArrayOutputStream bufferStream = new ByteArrayOutputStream();
CapturingResponseWrapper responseWrapper = new CapturingResponseWrapper(originalResponse, bufferStream);

originalRequest.getRequestDispatcher("/my.jsp").forward(originalRequest, responseWrapper);

responseWrapper.flushBuffer();
byte[] buffer = bufferStream.toByteArray();
// now use the data

虽然很丑,但这是我找到的最好的解决方案。如果您想知道,包装响应必须包含原始响应,因为 servlet 规范规定您在转发时不能替换完全不同的请求或响应对象,您必须使用原始响应或它们的包装版本。

关于java - 使用 Tomcat/Websphere 将 JSP 编译为字符串或内存字节数组,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/1189094/

28 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com