[英]Can not find class define, when I build a Spring Boot application with Maven by Jenkins and execute JAR file?
I suppose it can not find the class path. 我想它找不到类路径。 Because I can run the jar file JAR in a local environment of the IDE ( IntelliJ IDEA ).
因为我可以在IDE( IntelliJ IDEA )的本地环境中运行jar文件JAR。 I use the code snippets below to print class path information.
我使用下面的代码片段来打印类路径信息。
ClassLoader cl = ClassLoader.getSystemClassLoader(); URL[] urls = ((URLClassLoader)cl).getURLs(); if (urls == null || urls.length == 0) { System.out.println("Is this a empty classpath?"); } for(URL url: urls){ System.out.println("This is classpath:" + url.getFile()); }
When I click the Run button in IntelliJ IDEA, it can list all dependency class, such as, It's right. 当我单击IntelliJ IDEA中的“运行”按钮时,它可以列出所有依赖项类,例如“正确”。
This is classpath:/Users/admin/.m2/repository/org/springframework/boot/spring-boot-starter/1.5.10.RELEASE/spring-boot-starter-1.5.10.RELEASE.jar This is classpath:/Users/admin/.m2/repository/org/springframework/boot/spring-boot/1.5.10.RELEASE/spring-boot-1.5.10.RELEASE.jar
这是类路径:/Users/admin/.m2/repository/org/springframework/boot/spring-boot-starter/1.5.10.RELEASE/spring-boot-starter-1.5.10.RELEASE.jar这是类路径:/ Users / admin / .m2 / repository / org / springframework / boot / spring-boot / 1.5.10.RELEASE / spring-boot-1.5.10.RELEASE.jar
But when I run it locally, it just prints one message. 但是当我在本地运行它时,它只显示一条消息。 It's just my JAR package directory.
这只是我的JAR软件包目录。 It's wrong.
这是不对的。
I read the documentation about the manifest file. 我阅读了有关清单文件的文档 。 It does contain a JAR file.
它确实包含一个JAR文件。 Its location is main/resources directory.
它的位置是main / resources目录。 But it has no directory prefix.
但是它没有目录前缀。 It's generated by IntelliJ IDEA automatically.
它由IntelliJ IDEA自动生成。 And I unzip the JAR package to check the META-INF/MANIFEST.MF file.
然后我解压缩JAR包以检查META-INF / MANIFEST.MF文件。 It also contains the Main-Class key.
它还包含Main-Class键。
Manifest-Version: 1.0 Class-Path: spring-data-rest-core-2.6.10.RELEASE.jar mapstruct-1.1.0.F inal.jar logback-core-1.1.11.jar javax.transaction-api-1.2.jar
清单版本:1.0类路径:spring-data-rest-core-2.6.10.RELEASE.jar mapstruct-1.1.0.F inal.jar logback-core-1.1.11.jar javax.transaction-api-1.2 。罐
I check my pom.xml file. 我检查我的pom.xml文件。 It has the maven-jar-plugin configuration.
它具有maven-jar-plugin配置。 I comment out classpathPrefix and classpathLayoutType.
我注释掉classpathPrefix和classpathLayoutType。 I consider it seems like no use.
我认为这似乎没有用。
<plugin> <!-- Build an executable JAR --> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-jar-plugin</artifactId> <version>3.1.0</version> <configuration> <archive> <manifest> <addClasspath>true</addClasspath> <!--<classpathPrefix>lib/</classpathPrefix>--> <mainClass>com.hzlf.LetFunGoApplication</mainClass> <!--<classpathPrefix>/Users/admin/.m2/repository</classpathPrefix>--> <!--<classpathLayoutType>repository</classpathLayoutType>--> </manifest> </archive> </configuration> </plugin>
I doubt it is a wrong configuration for this maven-jar-plugin. 我怀疑此maven-jar-plugin的配置错误。 Its classPathPrefix is a relative path.
它的classPathPrefix是相对路径。 How can I write it correctly about repository?
如何正确编写有关存储库的信息? My local Maven home directory is
/Users/admin/.m2/
. 我的本地Maven主目录是
/Users/admin/.m2/
。 In my Docker container, it's /root/.m2
. 在我的Docker容器中,它是
/root/.m2
。
I use a Jenkinsfile to pull an image from Docker hub in my project. 我使用Jenkinsfile从项目中的Docker集线器中提取图像。 Here is my Jenkinsfile configuration.
这是我的Jenkinsfile配置。 In the
deliver.sh
file, just to run the JAR package. 在
deliver.sh
文件中,仅运行JAR包。
pipeline { agent { docker { image 'maven:3-alpine' args '-v $HOME/.m2:/root/.m2' } } stages { stage('build') { steps { sh 'mvn --version' sh 'mvn clean package' } } stage('Test') { steps { sh 'mvn test' } post { always { junit 'target/surefire-reports/*.xml' } } } stage('Deliver') { steps { sh './jenkins/scripts/deliver.sh' } } } }
This is error information. pipeline { agent { docker { image 'maven:3-alpine' args '-v $HOME/.m2:/root/.m2' } } stages { stage('build') { steps { sh 'mvn --version' sh 'mvn clean package' } } stage('Test') { steps { sh 'mvn test' } post { always { junit 'target/surefire-reports/*.xml' } } } stage('Deliver') { steps { sh './jenkins/scripts/deliver.sh' } } } }
这是错误信息。 It confused me a long time. 很长一段时间让我感到困惑。
Error: A JNI error has occurred, please check your installation and try again Exception in thread "main" java.lang.NoClassDefFoundError: org/springframework/boot/autoconfigure/web/HttpMessageConverters at java.lang.Class.getDeclaredMethods0(Native Method) at java.lang.Class.privateGetDeclaredMethods(Class.java:2701) at java.lang.Class.privateGetMethodRecursive(Class.java:3048) at java.lang.Class.getMethod0(Class.java:3018) at java.lang.Class.getMethod(Class.java:1784) at sun.launcher.LauncherHelper.validateMainClass(LauncherHelper.java:544) at sun.launcher.LauncherHelper.checkAndLoadMain(LauncherHelper.java:526) Caused by: java.lang.ClassNotFoundException: org.springframework.boot.autoconfigure.web.HttpMessageConverters at java.net.URLClassLoader.findClass(URLClassLoader.java:381) at java.lang.ClassLoader.loadClass(ClassLoader.java:424) at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:335) at java.lang.ClassLoader.loadClass(ClassLoader.java:357) ... 7 more [Pipeline] } [Pipe
错误:发生了JNI错误,请检查您的安装,然后重试。线程“主要” java.lang.NoClassDefFoundError中的异常:java.lang.Class.getDeclaredMethods0(本机方法)上的org / springframework / boot / autoconfigure / web / HttpMessageConverters在java.lang.Class.getMethod0(Class.java:3018)在java.lang.Class.privateGetMethodRecursive(Class.java:3048)在java.lang.Class.privateGetDeclaredMethods(Class.java:2701)在sun.launcher.LauncherHelper.validateMainClass(LauncherHelper.java:544)处的Class.getMethod(Class.java:1784)在sun.launcher.LauncherHelper.checkAndLoadMain(LauncherHelper.java:526)处原因:java.lang.ClassNotFoundException:org java.net.URLClassLoader.findClass(URLClassLoader.java:381)上的.springframework.boot.auto.config.web.HttpMessageConverters,位于sun.misc.Launcher $ AppClassLoader.loadClass上的java.lang.ClassLoader.loadClass(ClassLoader.java:424) (Launcher.java:335),位于java.lang.ClassLoader.loadClass(ClassLoader.java:357)...还有7个[Pipeline]} [Pipe line] // stage [Pipeline] } $ docker stop --time=1 693b10dd721c5780761b00eef880b793f6fa2e94afb77e9ffbac9474360f8a5f $ docker rm -f 693b10dd721c5780761b00eef880b793f6fa2e94afb77e9ffbac9474360f8a5f [Pipeline] // withDockerContainer [Pipeline] } [Pipeline] // withEnv [Pipeline] } [Pipeline] // node [Pipeline] End of Pipeline ERROR: script returned exit code 1 Finished: FAILURE
行] //阶段[管道]} $ docker stop --time = 1 693b10dd721c5780761b00eef880b793f6fa2e94afb77e9ffbac9474360f8a5f $ docker rm -f 693b10dd721c5780761b00eef880b793f6fa2e94afb77e9ff [9] PipeP [e] [管道]管道结束错误:脚本返回了退出代码1已完成:失败
1 : https://docs.oracle.com/javase/tutorial/deployment/jar/manifestindex.html [2]: https://i.stack.imgur.com/CaMnb.png [3]: https://i.stack.imgur.com/kbVvJ.png 1 : https : //docs.oracle.com/javase/tutorial/deployment/jar/manifestindex.html [2]: https : //i.stack.imgur.com/CaMnb.png [3]: https:// i.stack.imgur.com/kbVvJ.png
I resolve it by modifying my deliver.sh. 我通过修改delivery.sh来解决它。 I don't know the real reason, but it works.
我不知道真正的原因,但是可以。 I just delete Test stage and Deliver stage.
我只是删除测试阶段和交付阶段。 I guess it results from the 'post' option in deliver.sh.
我猜这是由于delivery.sh中的“ post”选项引起的。
pipeline {
agent {
docker {
image 'maven:3-alpine'
args '-v $HOME/.m2:/root/.m2'
}
}
stages {
stage('build') {
steps {
sh 'mvn --version'
sh 'mvn clean package'
}
}
}
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.