Java Maven-使用JDK7为JVM5编译
我已经试着让它工作了一段时间,但还没有运气 我想使用指向JDK7的Java Maven-使用JDK7为JVM5编译,java,maven,jdk1.5,Java,Maven,Jdk1.5,我已经试着让它工作了一段时间,但还没有运气 我想使用指向JDK7的JAVA_HOME运行,但我想为jvm5编译一个项目。我已经通读了,我发现是这样的,但在我的设置中它们似乎都不起作用 我第一次尝试只设置目标和源,但出现了一个错误: <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-compiler-plugin</artifactId&
JAVA_HOME
运行,但我想为jvm5编译一个项目。我已经通读了,我发现是这样的,但在我的设置中它们似乎都不起作用
我第一次尝试只设置目标
和源
,但出现了一个错误:
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<configuration>
<source>1.5</source>
<target>1.5</target>
</configuration>
</plugin>
我在我的系统上正确设置了JAVA5_HOME,我可以看到它在日志中加载了正确的类,但我遇到了另一个错误:
[加载ZipFileIndexFileObject[c:\Program Files\Java\jdk1.5.0\U 22\jre\lib\rt.jar(*.class)]
…
…
[ClassName]
错误:包javax.crypto
不存在
这很公平,因为我没有在bootclasspath
中包含jce.jar
(加密类)。但有一件事让我困惑。即使bootclasspath
只包含Java5运行时,我在类路径中有很多来自JRE7的库。它们没有在任何地方指定
[类文件的搜索路径:c:\Program files
(x86)\Java\jdk1.5.0\u 22\jre\lib\rt.jar,c:\Program
Files\Java\jdk1.7.0\u 02\jre\lib\ext\dnsns.jar,c:\Program
Files\Java\jdk1.7.0\u 02\jre\lib\ext\localedata.jar,c:\Program
Files\Java\jdk1.7.0\u 02\jre\lib\ext\sunec.jar,c:\Program
Files\Java\jdk1.7.0\u 02\jre\lib\ext\sunjce\u provider.jar,c:\Program
Files\Java\jdk1.7.0\u 02\jre\lib\ext\sunmsapi.jar,c:\Program
Files\Java\jdk1.7.0\u 02\jre\lib\ext\zipfs.jar,…]
如果我尝试添加jce.jar(来自JRE5),我会返回到第一个错误:
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<configuration>
<verbose>true</verbose>
<source>1.5</source>
<target>1.5</target>
<compilerArguments>
<bootclasspath>${env.JAVA5_HOME}/jre/lib/rt.jar${path.separator}${env.JAVA5_HOME}/jre/lib/jce.jar</bootclasspath>
</compilerArguments>
</configuration>
</plugin>
org.apache.maven.plugins
maven编译器插件
真的
1.5
1.5
${env.JAVA5_HOME}/jre/lib/rt.jar${path.separator}${env.JAVA5_HOME}/jre/lib/jce.jar
类型[ClassName]必须实现继承的抽象方法
CommonDataSource.getParentLogger()
我也没有看到加载rt.jar
的痕迹,但我没有看到java.lang
未找到错误,因此在类路径上加载了一些类
我将通过在构建之前编写一个覆盖JAVA\u HOME
的批处理脚本来临时修复它,并在构建之后将其设置回原处,但我确实希望以正确的方式完成此操作。这似乎不是一个极端的用例。:)
我做错了什么?如果需要,可以使用maven编译器插件上的bootclasspath配置选项:
<compilerArguments>
<bootclasspath>xxxxxxxxx</bootclasspath>
</compilerArguments>
xxxxxxxxx
你可以阅读更多关于它的内容。参见示例下的注释。Java的早期版本我们并不特别擅长支持Java的早期版本。对于Java7来说,它似乎要好得多 这是一个可以在任何版本下编译的程序
public class Main {
public static void main(String[] args) {
System.out.println("Hello World!");
}
}
$ javac -target 1.7 -source 1.7 Main.java
$ javac -target 1.6 -source 1.6 Main.java
warning: [options] bootstrap class path not set in conjunction with -source 1.6
1 warning
$ javac -Xbootclasspath:/usr/java/jdk1.6.0_29/jre/lib/rt.jar -target 1.6 -source 1.6 Main.java
$ javac -Xbootclasspath:/usr/java/jdk1.5.0_22/jre/lib/rt.jar -target 1.5 -source 1.5 Main.java
$ javac -Xbootclasspath:/usr/java/jdk1.4.0_30/jre/lib/rt.jar -target 1.4 -source 1.4 Main.java
$ javac -Xbootclasspath:/usr/java/jdk1.3.1_29/jre/lib/rt.jar -target 1.3 -source 1.3 Main.java
$ javac -Xbootclasspath:/usr/java/jdk1.2.2_017/jre/lib/rt.jar -target 1.2 -source 1.2 Main.java
$ javac -Xbootclasspath:/usr/java/jdk1.1.8_16/jre/lib/rt.jar -target 1.1 -source 1.2 Main.java
$ javac -Xbootclasspath:/usr/java/jdk1.1.8_16/jre/lib/rt.jar -target 1.1 -source 1.1 Main.java
javac: invalid source release: 1.1
Usage: javac
use -help for a list of possible options
$ javac -Xbootclasspath:/usr/java/jdk1.1.8_16/jre/lib/rt.jar -target 1.0 -source 1.0 Main.java
javac: invalid target release: 1.0
Usage: javac
use -help for a list of possible options
如果您需要为以前版本的Java进行编译,那么您需要提供一个bootclasspath,最理想的情况是为您想要编译的Java版本提供一个bootclasspath。Java 7似乎能够支持所有回到Java 1.2的方法,问题在于Java 7向后兼容性 由于不可能解决不同性质的问题,很少有类不保留向后兼容性,DataSource恰好是其中之一 因此,要么调整类以尊重新签名(即使在向后兼容模式下),要么被迫使用不同版本的虚拟机 您可以在此处阅读更多信息:
要在Maven编译器选项中使用多个JAR,请在JAR之间使用${path.separator}字符串:
<compilerArguments>
<bootclasspath>${env.JAVA5_HOME}/jre/lib/rt.jar${path.separator}${env.JAVA5_HOME}/jre/lib/jce.jar${path.separator}${env.JAVA5_HOME}/jre/lib/jsse.jar</bootclasspath>
</compilerArguments>
${env.JAVA5_HOME}/jre/lib/rt.jar${path.separator}${env.JAVA5_HOME}/jre/lib/jce.jar${path.separator}${env.JAVA5_HOME}/jre/lib/jsse.jar
此答案针对的是问题的标题,而不是问题的具体细节
我最终在我的项目中使用了这个解决方案,它允许我通过激活maven概要文件有选择地使用自定义引导类路径。我强烈建议为此使用概要文件,因为否则它会使未设置环境变量的任何人的构建失败(非常糟糕,尤其是对于开源项目)。
我仅在IDE中激活此配置文件以执行“清理和构建”操作
编译Java5
${env.JAVA5_HOME}
${java.5.home}/jre/lib
${java.5.libs}/rt.jar${path.separator}${java.5.libs}/jce.jar
org.apache.maven.plugins
maven编译器插件
1.5
1.5
${java.5.bootclasspath}
即使我使用
和
?我从文档中了解到,这就是他们应该做的——生成与其他JVM兼容的代码。您可以使用最新的JDK为早期JVM编译代码。如果您试图使用目标JVM中不可用的语言结构,它将生成相应的字节码并抛出错误。您只需要格外小心,因为javac不会阻止您使用旧JVM标准系统中没有的新方法/类…@AlexCiminian如果您使用的是正确的选项,问题是您的javac
是否支持此选项。Java 5.0和6在为以前的版本进行编译方面非常差,但是如果您使用较旧版本的rt.jar
,Java 7似乎可以覆盖到Java 1.2,这应该会阻止您使用目标版本中不存在的方法/功能。如果我指定rt.jar
,它会“起作用”,但是由于运行时需要其他依赖项(jce.jar
),它会中断。如果我尝试将两者都添加,就好像我根本没有指定rt.jar
(我的最后一个示例)
<compilerArguments>
<bootclasspath>${env.JAVA5_HOME}/jre/lib/rt.jar${path.separator}${env.JAVA5_HOME}/jre/lib/jce.jar${path.separator}${env.JAVA5_HOME}/jre/lib/jsse.jar</bootclasspath>
</compilerArguments>
<profile>
<id>compileWithJava5</id>
<!--
NOTE
Make sure to set the environment variable JAVA5_HOME
to your JDK 1.5 HOME when using this profile.
-->
<properties>
<java.5.home>${env.JAVA5_HOME}</java.5.home>
<java.5.libs>${java.5.home}/jre/lib</java.5.libs>
<java.5.bootclasspath>${java.5.libs}/rt.jar${path.separator}${java.5.libs}/jce.jar</java.5.bootclasspath>
</properties>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<configuration>
<source>1.5</source>
<target>1.5</target>
<compilerArguments>
<bootclasspath>${java.5.bootclasspath}</bootclasspath>
</compilerArguments>
</configuration>
</plugin>
</plugins>
</build>
</profile>