很早之前的文章,写过一篇关于加速Web应用的功能之一:「JSP预编译」JSP预编译,加速你的应用,在其中我们提到通过JSP的预编译,我们可以提前生成JSP对应的Servlet文件,从而节省执行时再生成所带来的时间占用。
JSPC
而整个JSP预编译的核心入口是 JspC这个工具。
下面两篇是预编译具体的工作原理:
新的 Tomcat Release Note 里,有一个功能,是新增了多线程编译,来加速JSP预编译。是一位热心网友提供的 patch。
我们来看下具体内容:
Make the Jasper (JSP Engine) Java file generation process multi-threaded. By default, one thread will be used per core. Based on a patch by Dan Fabulich.
这个 patch主要做了些什么事情呢? 我把其中的重点代码摘出来一起看下:
通过输入参数,设置线程数
public void setThreadCount(String threadCount) {
if (threadCount == null) {
return;
}
int newThreadCount;
try {
if (threadCount.endsWith("C")) {
double factor = Double.parseDouble(threadCount.substring(0, threadCount.length() - 1));
newThreadCount = (int) (factor * Runtime.getRuntime().availableProcessors());
} else {
newThreadCount = Integer.parseInt(threadCount);
}
} catch (NumberFormatException e) {
throw new BuildException("Couldn't parse thread count: " + threadCount);
}
if (newThreadCount < 1) {
throw new BuildException("There must be at least one thread: " + newThreadCount);
}
this.threadCount = newThreadCount;
}
增加线程池的使用
上面根据输入配置好的threadCount,会在后面生成线程池的时候被使用到,同时生成的线程池,会做为提交JSP编译工作的入口。
ExecutorService threadPool = Executors.newFixedThreadPool(threadCount);
ExecutorCompletionService<Void> service = new ExecutorCompletionService<>(threadPool);
int pageCount = pages.size();
for (String nextjsp : pages) {
File fjsp = new File(nextjsp);
if (!fjsp.isAbsolute()) {
fjsp = new File(uriRootF, nextjsp);
}
if (!fjsp.exists()) {
if (log.isWarnEnabled()) {
log.warn(Localizer.getMessage(
"jspc.error.fileDoesNotExist", fjsp.toString()));
}
continue;