解决JSTL报错 java.lang.ClassNotFoundException: org.apache.jsp.index_jsp home 编辑时间 2023/11/27 ## 前言 前几篇笔记用到了一个JSTL3.0依赖 [Springboot 3.x 项目使用 JSP 笔记](https://leanote.zzzmh.cn/blog/post/admin/65547240da7405001400dd8c) [关于2023年如何开发一个Java JSP JSTL项目指南](https://leanote.zzzmh.cn/blog/post/admin/655f0f75da7405001400e87f) 有小伙伴照着我的笔记运行后会出现奇怪的报错 后来我自己的项目也跟着跑偏了哈哈哈 于是就有了这篇笔记 ## 折腾 期初我写了2篇笔记,用的 `jstl3.0` 都是这段依赖 ```xml <dependency> <groupId>org.glassfish.web</groupId> <artifactId>jakarta.servlet.jsp.jstl</artifactId> <version>3.0.0</version> </dependency> ``` <br> 这段maven依赖,本来是好好的,25号以后忽然间就不行了,报这个错 `Could not find artifact jakarta.servlet.jsp.jstl:jakarta.servlet.jsp.jstl-api:jar:3.0.0-RC1 in nexus-aliyun (http://maven.aliyun.com/nexus/content/groups/public)` 大概意思就是,阿里云里没有找到这个依赖,中央仓库里 `mvnrepository` 我也搜了确实没有 `3.0.0-RC1` 只有 `3.0.0` 查看他的pom ```xml <?xml version="1.0" encoding="UTF-8"?> <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd"> <parent> <artifactId>project</artifactId> <groupId>org.eclipse.ee4j</groupId> <version>1.0.6</version> </parent> <modelVersion>4.0.0</modelVersion> <groupId>org.glassfish.web</groupId> <artifactId>jakarta.servlet.jsp.jstl</artifactId> <name>Jakarta Standard Tag Library Implementation</name> <version>3.0.0</version> <description>Jakarta Standard Tag Library Implementation</description> <url>https://projects.eclipse.org/projects/ee4j.jstl</url> <issueManagement> <system>github</system> <url>https://github.com/eclipse-ee4j/jstl-api/issues</url> </issueManagement> <mailingLists> <mailingList> <name>JSTL dev mailing list</name> <subscribe>https://dev.eclipse.org/mailman/listinfo/jstl-dev</subscribe> <unsubscribe>https://dev.eclipse.org/mailman/listinfo/jstl-dev</unsubscribe> <post>jstl-dev@eclipse.org</post> <archive>https://dev.eclipse.org/mhonarc/lists/jstl-dev</archive> </mailingList> </mailingLists> <developers> <developer> <id>yaminikb</id> <name>Yamini K B</name> <organization>Oracle Corporation</organization> <organizationUrl>http://www.oracle.com/</organizationUrl> </developer> </developers> <contributors> <contributor> <name>Kin Man Chung</name> </contributor> </contributors> <licenses> <license> <name>EPL 2.0</name> <url>http://www.eclipse.org/legal/epl-2.0</url> <distribution>repo</distribution> </license> <license> <name>GPL2 w/ CPE</name> <url>https://www.gnu.org/software/classpath/license.html</url> <distribution>repo</distribution> </license> </licenses> <scm> <connection>scm:git:https://github.com/eclipse-ee4j/jstl-api.git</connection> <developerConnection>scm:git:ssh://git@github.com/eclipse-ee4j/jstl-api.git</developerConnection> <url>https://github.com/eclipse-ee4j/jstl-api</url> </scm> <build> <resources> <resource> <directory>src/main/java</directory> <includes> <include>**/*.properties</include> <include>**/*.xml</include> </includes> </resource> <resource> <directory>src/main/resources</directory> </resource> <resource> <targetPath>META-INF</targetPath> <directory>${project.basedir}/..</directory> <includes> <include>LICENSE.md</include> <include>NOTICE.md</include> </includes> </resource> <resource> <targetPath>META-INF</targetPath> <directory>${project.basedir}</directory> <includes> <include>LICENSE.md</include> <include>NOTICE.md</include> </includes> </resource> </resources> <plugins> <plugin> <artifactId>maven-enforcer-plugin</artifactId> <version>3.0.0</version> <executions> <execution> <id>enforce-maven</id> <goals> <goal>enforce</goal> </goals> <configuration> <rules> <requireMavenVersion> <version>3.6.0</version> </requireMavenVersion> </rules> </configuration> </execution> </executions> </plugin> <plugin> <artifactId>maven-compiler-plugin</artifactId> <version>3.8.1</version> <configuration> <release>11</release> <compilerArgument>-Xlint:unchecked</compilerArgument> </configuration> </plugin> <plugin> <groupId>org.apache.felix</groupId> <artifactId>maven-bundle-plugin</artifactId> <version>5.1.3</version> <executions> <execution> <id>bundle-manifest</id> <phase>process-classes</phase> <goals> <goal>manifest</goal> </goals> </execution> </executions> <configuration> <instructions> <Bundle-SymbolicName>org.glassfish.web.jakarta.servlet.jsp.jstl</Bundle-SymbolicName> <Export-Package>org.apache.taglibs.standard, org.apache.taglibs.standard.extra.spath, org.apache.taglibs.standard.functions, org.apache.taglibs.standard.lang.jstl, org.apache.taglibs.standard.lang.jstl.parser, org.apache.taglibs.standard.lang.support, org.apache.taglibs.standard.resources, org.apache.taglibs.standard.tag.common.core, org.apache.taglibs.standard.tag.common.fmt, org.apache.taglibs.standard.tag.common.sql, org.apache.taglibs.standard.tag.common.xml, org.apache.taglibs.standard.tag.el.core, org.apache.taglibs.standard.tag.el.fmt, org.apache.taglibs.standard.tag.el.sql, org.apache.taglibs.standard.tag.el.xml, org.apache.taglibs.standard.tag.rt.core, org.apache.taglibs.standard.tag.rt.fmt, org.apache.taglibs.standard.tag.rt.sql, org.apache.taglibs.standard.tag.rt.xml, org.apache.taglibs.standard.tei, org.apache.taglibs.standard.tlv, org.glassfish.jstl.integration</Export-Package> <Import-Package>!org.apache.xpath, !org.apache.xpath.objects, !org.apache.xpath.jaxp, !org.apache.xml, !org.apache.xml.dtm, !org.apache.xml.utils, !org.apache.xalan, !org.apache.xalan.res, !org.apache.xpath.res, !org.apache.regexp, !org.apache.bcel, !java_cup.runtime, !trax, org.xml.sax.ext, *</Import-Package> </instructions> </configuration> </plugin> <plugin> <artifactId>maven-jar-plugin</artifactId> <version>3.2.0</version> <configuration> <archive> <manifestFile>${project.build.outputDirectory}/META-INF/MANIFEST.MF</manifestFile> <manifestEntries> <Extension-Name>jakarta.servlet.jsp.jstl</Extension-Name> <Specification-Version>2.0</Specification-Version> <Specification-Vendor>${project.organization.name}</Specification-Vendor> <Implementation-Version>${project.version}</Implementation-Version> <Implementation-Vendor>${project.organization.name}</Implementation-Vendor> </manifestEntries> </archive> </configuration> </plugin> <plugin> <artifactId>maven-shade-plugin</artifactId> <version>3.2.4</version> <executions> <execution> <phase>package</phase> <goals> <goal>shade</goal> </goals> <configuration> <dependencyReducedPomLocation>${project.build.directory}/dependency-reduced-pom.xml</dependencyReducedPomLocation> <artifactSet> <includes> <include>xalan:xalan</include> </includes> </artifactSet> <filters> <filter> <artifact>xalan:xalan</artifact> <excludes> <exclude>META-INF/**</exclude> </excludes> </filter> </filters> <relocations> <relocation> <pattern>org.apache.xpath</pattern> <shadedPattern>org.eclipse.tags.shaded.org.apache.xpath</shadedPattern> </relocation> <relocation> <pattern>org.apache.xml</pattern> <shadedPattern>org.eclipse.tags.shaded.org.apache.xml</shadedPattern> </relocation> <relocation> <pattern>org.apache.xalan</pattern> <shadedPattern>org.eclipse.tags.shaded.org.apache.xalan</shadedPattern> </relocation> <relocation> <pattern>org.apache.regexp</pattern> <shadedPattern>org.eclipse.tags.shaded.org.apache.regexp</shadedPattern> </relocation> <relocation> <pattern>org.apache.bcel</pattern> <shadedPattern>org.eclipse.tags.shaded.org.apache.bcel</shadedPattern> </relocation> <relocation> <pattern>java_cup.runtime</pattern> <shadedPattern>org.eclipse.tags.shaded.java_cup.runtime</shadedPattern> </relocation> <relocation> <pattern>trax</pattern> <shadedPattern>org.eclipse.tags.shaded.trax</shadedPattern> </relocation> </relocations> </configuration> </execution> </executions> </plugin> <plugin> <artifactId>maven-source-plugin</artifactId> <version>3.2.1</version> <executions> <execution> <id>attach-sources</id> <goals> <goal>jar-no-fork</goal> </goals> </execution> </executions> <configuration> <includePom>true</includePom> </configuration> </plugin> <plugin> <groupId>org.codehaus.mojo</groupId> <artifactId>build-helper-maven-plugin</artifactId> <version>3.2.0</version> <executions> <execution> <id>timestamp-property</id> <phase>validate</phase> <goals> <goal>timestamp-property</goal> </goals> <configuration> <name>current.year</name> <pattern>yyyy</pattern> <locale>en_US</locale> </configuration> </execution> </executions> </plugin> <plugin> <artifactId>maven-javadoc-plugin</artifactId> <version>3.3.1</version> <executions> <execution> <id>attach-javadocs</id> <goals> <goal>jar</goal> </goals> <configuration> <groups> <group> <title>Jakarta Standard Tag Library Documentation</title> <packages>org.apache.taglibs</packages> </group> </groups> <doclint>none</doclint> </configuration> </execution> </executions> <configuration> <source>11</source> <additionalJOption>-Xdoclint:none</additionalJOption> <quiet>true</quiet> <bottom>Copyright © 2019, ${current.year} Eclipse Foundation. All rights reserved.</bottom> <docfilessubdirs>true</docfilessubdirs> <groups> <group> <title>Jakarta Standard Tag Library Documentation</title> <packages>jakarta.servlet.jsp.jstl*</packages> </group> </groups> </configuration> </plugin> </plugins> </build> <profiles> <profile> <id>tlddocs</id> <build> <plugins> <plugin> <groupId>org.codehaus.mojo</groupId> <artifactId>exec-maven-plugin</artifactId> <version>3.0.0</version> <executions> <execution> <id>generateTldDoc</id> <phase>prepare-package</phase> <goals> <goal>java</goal> </goals> <configuration> <includePluginDependencies>true</includePluginDependencies> <includeProjectDependencies>false</includeProjectDependencies> <mainClass>com.sun.tlddoc.TLDDoc</mainClass> <arguments> <argument>-doctitle</argument> <argument>Jakarta Tags doc</argument> <argument>-windowtitle</argument> <argument>Jakarta Tags Doc</argument> <argument>-d</argument> <argument>${project.build.directory}/tlddoc</argument> <argument>${project.basedir}/src/main/resources/META-INF/sql.tld</argument> <argument>${project.basedir}/src/main/resources/META-INF/x.tld</argument> <argument>${project.basedir}/src/main/resources/META-INF/fmt.tld</argument> <argument>${project.basedir}/src/main/resources/META-INF/c.tld</argument> <argument>${project.basedir}/src/main/resources/META-INF/fn.tld</argument> </arguments> </configuration> </execution> </executions> <dependencies> <dependency> <groupId>org.glassfish.web</groupId> <artifactId>tagsdoc</artifactId> <version>1.0-SNAPSHOT</version> </dependency> </dependencies> </plugin> </plugins> </build> </profile> </profiles> <dependencies> <dependency> <groupId>jakarta.servlet</groupId> <artifactId>jakarta.servlet-api</artifactId> <version>6.0.0</version> <scope>provided</scope> </dependency> <dependency> <groupId>jakarta.servlet.jsp</groupId> <artifactId>jakarta.servlet.jsp-api</artifactId> <version>3.1.0</version> <scope>provided</scope> </dependency> <dependency> <groupId>jakarta.el</groupId> <artifactId>jakarta.el-api</artifactId> <version>5.0.0</version> <scope>provided</scope> </dependency> <dependency> <groupId>jakarta.servlet.jsp.jstl</groupId> <artifactId>jakarta.servlet.jsp.jstl-api</artifactId> <version>3.0.0-RC1</version> <scope>compile</scope> </dependency> </dependencies> </project> ``` 确实存在一个 `3.0.0-RC1` **这里可以猜测出大概的结论:他以前一直依赖着3.0.0-RC1,然后忽然3.0.0-RC1有问题被Maven中央仓库删了** <br> 故事还没完 如果版本号改成 `3.0.1` ```xml <dependency> <groupId>org.glassfish.web</groupId> <artifactId>jakarta.servlet.jsp.jstl</artifactId> <version>3.0.1</version> </dependency> ``` 就可以正常加载出依赖 表面看起来没有报错 但是有个巨坑等着我 JSP里一旦用了JSTL代码 例如 `index.jsp` ```jsp <%@ page contentType="text/html; charset=UTF-8" pageEncoding="UTF-8" %> <%@ taglib prefix="c" uri="jakarta.tags.core" %> <!DOCTYPE html> <html> <head> <title>JSP - Hello World</title> </head> <body> <c:if test="true"> 6 </c:if> </body> </html> ``` 就会出现这个巨坑的报错 全网查了2天也没找到是什么问题 完整报错如下 ```java HTTP状态 500 - 内部服务器错误 类型 异常报告 消息 org.apache.jasper.JasperException: java.lang.ClassNotFoundException: org.apache.jsp.index_jsp 描述 服务器遇到一个意外的情况,阻止它完成请求。 例外情况 org.apache.jasper.JasperException: org.apache.jasper.JasperException: java.lang.ClassNotFoundException: org.apache.jsp.index_jsp org.apache.jasper.servlet.JspServletWrapper.handleJspException(JspServletWrapper.java:578) org.apache.jasper.servlet.JspServletWrapper.service(JspServletWrapper.java:422) org.apache.jasper.servlet.JspServlet.serviceJspFile(JspServlet.java:380) org.apache.jasper.servlet.JspServlet.service(JspServlet.java:328) jakarta.servlet.http.HttpServlet.service(HttpServlet.java:658) org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:51) 根本原因。 org.apache.jasper.JasperException: java.lang.ClassNotFoundException: org.apache.jsp.index_jsp org.apache.jasper.servlet.JspServletWrapper.getServlet(JspServletWrapper.java:194) org.apache.jasper.servlet.JspServletWrapper.service(JspServletWrapper.java:410) org.apache.jasper.servlet.JspServlet.serviceJspFile(JspServlet.java:380) org.apache.jasper.servlet.JspServlet.service(JspServlet.java:328) jakarta.servlet.http.HttpServlet.service(HttpServlet.java:658) org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:51) 根本原因。 java.lang.ClassNotFoundException: org.apache.jsp.index_jsp java.base/java.net.URLClassLoader.findClass(URLClassLoader.java:445) org.apache.jasper.servlet.JasperLoader.loadClass(JasperLoader.java:129) org.apache.jasper.servlet.JasperLoader.loadClass(JasperLoader.java:58) org.apache.jasper.servlet.JspServletWrapper.getServlet(JspServletWrapper.java:189) org.apache.jasper.servlet.JspServletWrapper.service(JspServletWrapper.java:410) org.apache.jasper.servlet.JspServlet.serviceJspFile(JspServlet.java:380) org.apache.jasper.servlet.JspServlet.service(JspServlet.java:328) jakarta.servlet.http.HttpServlet.service(HttpServlet.java:658) org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:51) ):注意 主要问题的全部 stack 信息可以在 server logs 里查看 ``` <br><br> 最终的解决方案 maven依赖做如下修改 ```xml <dependency> <groupId>org.glassfish.web</groupId> <artifactId>jakarta.servlet.jsp.jstl</artifactId> <version>3.0.1</version> <!-- 排除这段可能出错的依赖 --> <exclusions> <exclusion> <groupId>jakarta.servlet.jsp.jstl</groupId> <artifactId>jakarta.servlet.jsp.jstl-api</artifactId> </exclusion> </exclusions> </dependency> <!-- 手动补上这段依赖 并指定一个安全的版本号 --> <dependency> <groupId>jakarta.servlet.jsp.jstl</groupId> <artifactId>jakarta.servlet.jsp.jstl-api</artifactId> <version>3.0.0</version> <scope>compile</scope> </dependency> ``` 也就是用 `3.0.1` 最新版,然后手动移除依赖中的依赖,再手动加载这个依赖中的依赖,用一个安全的版本号! 大功告成! ## END 送人玫瑰,手留余香 赞赏 Wechat Pay Alipay Vue Element Table 实现鼠标拖拽排序 基于 SortableJS Springboot 3.x 项目使用 JSP 笔记