Apache POI 4.0.1 super slow getting started … 15 minutes or more. What is wrong?

别来无恙 提交于 2020-01-06 05:33:07

问题


It takes 15 minutes or more for POI to initialize its first workbook in Java 8 on Windows 10, in a Tomcat 8 instance. Based on interrupting the process in the debugger and looking at the stack, it is spending the time in the classloader, driven by xbeans.

Edit This has the feel of a classloader issue because when I implemented the workaround for the POI library (below), other classes started expressing the same issue.

Edit The stack trace looks most similar to this bug: https://bugs.java.com/bugdatabase/view_bug.do?bug_id=8022063

As you can see in jvisualvm, there is no classloader contention in the process thread taskExecutor-1.

I have a workaround, but it should not be necessary. The accepted answer will explain WHY this is happening.

EDIT: Workaround

During application initialization I added this line to the static class initializer for a configuration bean, to force the classloader to preload the classes and resources. It executes instantly there, and when the actual process is invoked it also executes instantly.

XSSFWorkbook preload = new XSSFWorkbook ();

The final workaround was to preload all of the jar files related to SSL, security, and POI. As near as I can tell, when loaded late in a spring batch context (may be a red herring), the classloader is attempting to validate the bouncycastle jar files with algorithms encoded in the bouncycastle classes, and is running everything in the SSL stack in interpreted mode.

        Reflections reflections = new Reflections("org.bouncycastle", this.getClass().getClassLoader(), new SubTypesScanner(false));
        Set<Class<? extends Object>> bouncyCastleClasses = reflections.getSubTypesOf(Object.class);



        reflections = new Reflections("sun.security", this.getClass().getClassLoader(), new SubTypesScanner(false));
        Set<Class<? extends Object>> sunSecurityClasses = reflections.getSubTypesOf(Object.class);

        reflections = new Reflections("javax.ssl", this.getClass().getClassLoader(), new SubTypesScanner(false));
        Set<Class<? extends Object>> javaSslClasses = reflections.getSubTypesOf(Object.class);

        reflections = new Reflections("org.apache.poi", this.getClass().getClassLoader(), new SubTypesScanner(false));
        Set<Class<? extends Object>> poiClasses = reflections.getSubTypesOf(Object.class);

POM excerpt:

    <poi.version>4.0.1</poi.version>

        <!-- apache poi / poi-ooxml -->
        <dependency>
            <groupId>org.apache.poi</groupId>
            <artifactId>poi</artifactId>
            <version>${poi.version}</version>
        </dependency>
        <dependency>
            <groupId>org.apache.poi</groupId>
            <artifactId>poi-scratchpad</artifactId>
            <version>${poi.version}</version>
        </dependency>
        <dependency>
            <groupId>org.apache.poi</groupId>
            <artifactId>poi-ooxml</artifactId>
            <version>${poi.version}</version>
        </dependency>

Code:

public void beforeJob(JobExecution jobExecution) {
    if (logger.isDebugEnabled()) {
        workbookname = "debuginfo-" + System.currentTimeMillis() + ".xlsx";
        logger.debug("Debug statistics dump file will be saved at [{}]", workbookname);
        debugStatsDump = new XSSFWorkbook(); // This line takes several minutes to run, apparently in the classloader???
    }
}

回答1:


It turns out that under some circumstances when you mix jars from different versions of java (say 1.5 and 1.8), the JIT will throw up its hands and run in interpreted mode. There are several reports of the behavior listed on Oracle's website that say "we don't know why it's doing this, we won't fix it".

I downloaded sources for the libraries that were not compiled in 1.8 and built from source, and all is well.



来源:https://stackoverflow.com/questions/54185197/apache-poi-4-0-1-super-slow-getting-started-15-minutes-or-more-what-is-wron

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!