在maven中指定java版本 - 属性和编译器插件之间的差异 [英] Specifying java version in maven - differences between properties and compiler plugin

查看:187
本文介绍了在maven中指定java版本 - 属性和编译器插件之间的差异的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我对maven不太熟悉,在尝试使用多模块项目时,我开始想知道如何为父maven pom中的所有子模块指定java版本。直到今天我才使用:

I'm not very experienced with maven and while experimenting with multi-module project I started wondering how can I specify java version for all my child modules in parent maven pom. Until today I was using just:

<properties>
    <java.version>1.8</java.version>
</properties>

但在研究时我发现你也可以在maven编译器插件中指定java版本,如下所示: / p>

but when researching I found that you can also specify java version in maven compiler plugin, like that:

<plugins>
    <plugin>    
        <artifactId>maven-compiler-plugin</artifactId>
        <configuration>
            <source>1.8</source>
            <target>1.8</target>
        </configuration>
    </plugin>
</plugins>

然后将其包装到插件管理标签中以启用子poms使用。所以第一个问题是在属性和maven编译器插件中设置java版本有什么区别?

And then wrap this into plugin management tag to enable child poms usage of this. So the first question is what are the differences beetwen setting java version in properties and in maven compiler plugin?

我找不到明确的答案但在研究过程中,我发现你也可以用这种方式指定java版本:

I couldn't find clear answer but in process of researching I found that you can also specify java version in this way:

<properties>
    <maven.compiler.source>1.8</maven.compiler.source>
    <maven.compiler.target>1.8</maven.compiler.target>
</properties>

这表明编译器插件即使我没有明确声明也存在。运行mvn包输出

which suggest that compiler plugin is there even if I dont explicit declare it. Running mvn package outputs with

maven-compiler-plugin:3.1:compile (default-compile) @ testproj ---

以及我未声明的其他一些插件。 那些插件是默认的,隐藏的部分是maven pom吗?在属性和maven插件配置元素中设置源/目标是否有任何差异?

and some other plugins that I didn't declare. So are those plugins default, hidden part of maven pom? Are there any differences beetwen setting source/target in properties and in maven plugin configuration element?

其他一些问题是 - 应该使用哪种方式(以及何时使用)如果他们不平等)?哪一个最适合多模块项目,如果在pom中指定的java版本与JAVA_HOME中指向的版本不同,会发生什么?

Some other questions are - which way should be used (and when if they are not equal)? Which one is best for multi-module project and what happens if java version specified in pom is different than version pointed in JAVA_HOME?

推荐答案

如何指定JDK版本?

1)< java.version> 未在Maven文档中引用。

它是一个Spring Boot特性。

它允许将源版本和目标java版本设置为相同的版本,例如为两者指定java 1.8:

1) <java.version> is not referenced in the Maven documentation.
It is a Spring Boot specificity.
It allows to set the source and the target java version with the same version such as this one to specify java 1.8 for both :

<properties>
     <java.version>1.8</java.version>
</properties>   

如果你使用Spring Boot,请随意使用它。

Feel free to use it if you use Spring Boot.

2)使用 maven-compiler-plugin maven.compiler.source / maven.compiler.target 指定的属性和目标等效。

2) Using maven-compiler-plugin or maven.compiler.source/maven.compiler.target properties to specify the source and the target are equivalent.

<plugins>
    <plugin>    
        <artifactId>maven-compiler-plugin</artifactId>
        <configuration>
            <source>1.8</source>
            <target>1.8</target>
        </configuration>
    </plugin>
</plugins>

<properties>
    <maven.compiler.source>1.8</maven.compiler.source>
    <maven.compiler.target>1.8</maven.compiler.target>
</properties>

等同于编译器插件的Maven文档
,因为< source> 和编译器配置中的< target> 元素使用属性 maven.compiler.source maven.compiler.target 如果已定义。

are equivalent according to the Maven documentation of the compiler plugin since the <source> and the <target> elements in the compiler configuration use the properties maven.compiler.source and maven.compiler.target if they are defined.


来源

-source Java编译器的参数。

默认值为: 1.6

用户属性为: maven.compiler.source

The -source argument for the Java compiler.
Default value is: 1.6.
User property is: maven.compiler.source.

目标

-target Java编译器的参数。

默认值为: 1.6

用户属性是: maven.compiler.target

The -target argument for the Java compiler.
Default value is: 1.6.
User property is: maven.compiler.target.

关于<的默认值code>来源和目标,请注意
因为 3.8.0 的maven编译器,默认值已从 1.5 更改为 1.6

About the default values for source and target, note that since the 3.8.0 of the maven compiler, the default values have changed from 1.5 to 1.6.

3)maven-compiler-plugin 3.6 及更高版本提供了一种新方式:

3) The maven-compiler-plugin 3.6 and later versions provide a new way :

<plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-compiler-plugin</artifactId>
    <version>3.8.0</version>
    <configuration>
        <release>9</release>
    </configuration>
</plugin>

您也可以声明:

<properties>
    <maven.compiler.release>9</maven.compiler.release>
</properties>

但此时它不能作为 maven-compiler-plugin工作您使用的默认版本不依赖于最近的版本。

But at this time it will not work as the maven-compiler-plugin default version you use doesn't rely on a recent enough version.

Maven release 参数传达 release :a <我们可以从Java 9传递的href =https://docs.oracle.com/javase/9​​/tools/javac.htm#JSWOR627\"rel =noreferrer>新的JVM标准选项:

The Maven release argument conveys release : a new JVM standard option that we could pass from Java 9 :


针对
特定VM版本的公共,支持和记录的API进行编译。

Compiles against the public, supported and documented API for a specific VM version.

这种方式为指定相同版本的标准方法,目标 bootstrap JVM选项。

请注意,指定 bootstrap 是交叉汇编的良好实践,如果你不进行交叉编译也不会受到影响。

This way provides a standard way to specify the same version for the source, the target and the bootstrap JVM options.
Note that specifying the bootstrap is a good practice for cross compilations and it will not hurt if you don't make cross compilations either.

指定JDK版本的最佳方式是哪种?

只有在使用Spring Boot时才允许第一种方式(< java.version> )。

The first way (<java.version>) is allowed only if you use Spring Boot.

对于Java 8及以下版本:

关于其他两种方式:估价 maven.compiler.source / maven.compiler.target 属性使用 maven-compiler-plugin ,你可以使用其中一个。它在事实上没有任何改变,因为最终这两个解决方案依赖于相同的属性和相同的机制:maven核心编译器插件。

About the two other ways : valuing the maven.compiler.source/maven.compiler.target properties or using the maven-compiler-plugin, you can use one or the other. It changes nothing in the facts since finally the two solutions rely on the same properties and the same mechanism : the maven core compiler plugin.

好吧,如果你不需要在编译器插件中指定除Java版本之外的其他属性或行为,那么使用这种方式更有意义,因为这更简洁: / p>

Well, if you don't need to specify other properties or behavior than Java versions in the compiler plugin, using this way makes more sense as this is more concise:

<properties>
    <maven.compiler.source>1.8</maven.compiler.source>
    <maven.compiler.target>1.8</maven.compiler.target>
</properties>

来自Java 9:

release 参数(第三点)是一种强烈考虑是否要为源和目标使用相同版本的方法。

The release argument (third point) is a way to strongly consider if you want to use the same version for the source and the target.

如果JAVA_HOME中的JDK与pom.xml中指定的JDK版本不同,会发生什么?

如果 JAVA_HOME 引用的JDK与pom中指定的版本兼容但是为了确保更好的交叉编译,这不是问题兼容性考虑添加 bootstrap JVM选项,其值为 rt.jar 的路径目标版本。

It is not a problem if the JDK referenced by the JAVA_HOME is compatible with the version specified in the pom but to ensure a better cross-compilation compatibility think about adding the bootstrap JVM option with as value the path of the rt.jar of the target version.

需要考虑的一件重要事情是来源目标版本不应优于 JAVA_HOME 引用的JDK版本。

旧版本的JDK无法编译一个更新的版本,因为它不知道它的规格。

An important thing to consider is that the source and the target version in the Maven configuration should not be superior to the JDK version referenced by the JAVA_HOME.
A older version of the JDK cannot compile with a more recent version since it doesn't know its specification.

要根据使用的JDK获取有关源,目标和发行版支持版本的信息,请参阅 java编译:源,目标和发行版支持的版本

To get information about the source, target and release supported versions according to the used JDK, please refer to java compilation : source, target and release supported versions.

如何处理JAVA_HOME引用的JDK的情况与pom中指定的java目标和/或源版本不兼容?

例如,如果您的 JAVA_HOME 引用了JDK 1.7并且您指定了JDK 1.8作为源和目标你的pom.xml的编译器配置,这将是一个问题,因为正如所解释的,JDK 1.7不知道如何编译。

从它的角度来看,它是一个未知的JDK版本,因为它在它之后发布。

在这种情况下,你应该配置Maven编译器插件以这种方式指定JDK:

For example, if your JAVA_HOME refers to a JDK 1.7 and you specify a JDK 1.8 as source and target in the compiler configuration of your pom.xml, it will be a problem because as explained, the JDK 1.7 doesn't know how to compile with.
From its point of view, it is an unknown JDK version since it was released after it.
In this case, you should configure the Maven compiler plugin to specify the JDK in this way :

<plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-compiler-plugin</artifactId>
    <configuration>
        <source>1.8</source>
        <target>1.8</target>
        <compilerVersion>1.8</compilerVersion>      
        <fork>true</fork>
        <executable>D:\jdk1.8\bin\javac</executable>                
    </configuration>
</plugin>

您可以在使用maven编译器插件的示例

不会询问,但可能更复杂的情况是指定来源而非目标。根据源版本,它可能在目标中使用不同的版本。规则是特别的:您可以在 Cross-中阅读它们。编译选项部分

It is not asked but cases where that may be more complicated is when you specify source but not target. It may use a different version in target according to the source version. Rules are particular : you can read about them in the Cross-Compilation Options part.

为什么编译器插件在执行时在输出中被跟踪即使你没有在pom.xml中指定maven package 目标?

Why the compiler plugin is traced in the output at the execution of the Maven package goal even if you don't specify it in the pom.xml?

为了编译代码,更一般地说,为了执行maven目标所需的所有任务,Maven需要工具。因此,它使用核心Maven插件(您通过 groupId 识别核心Maven插件: org.apache.maven.plugins )执行所需的任务:用于编译类的编译器插件,用于执行测试的测试插件,等等...因此,即使您没有声明这些插件,它们也必然会执行Maven生命周期。 br>
在Maven项目的根目录下,您可以运行命令: mvn help:effective-pom 以获得有效使用的最终pom。您可以在其他信息中看到Maven附加的插件(在您的pom.xml中指定或未指定),使用的是已使用的版本,它们的配置以及生命周期每个阶段的已执行目标。

To compile your code and more generally to perform all tasks required for a maven goal, Maven needs tools. So, it uses core Maven plugins (you recognize a core Maven plugin by its groupId : org.apache.maven.plugins) to do the required tasks : compiler plugin for compiling classes, test plugin for executing tests, and so for... So, even if you don't declare these plugins, they are bound to the execution of the Maven lifecycle.
At the root dir of your Maven project, you can run the command : mvn help:effective-pom to get the final pom effectively used. You could see among other information, attached plugins by Maven (specified or not in your pom.xml), with the used version, their configuration and the executed goals for each phase of the lifecycle.

mvn help:effective-pom 命令的输出中,您可以看到这些核心插件的声明在< build>< plugins> 元素中,例如:

In the output of the mvn help:effective-pom command, you could see the declaration of these core plugins in the <build><plugins> element, for example :

...
<plugin>
   <artifactId>maven-clean-plugin</artifactId>
   <version>2.5</version>
   <executions>
     <execution>
       <id>default-clean</id>
       <phase>clean</phase>
       <goals>
         <goal>clean</goal>
       </goals>
     </execution>
   </executions>
 </plugin>
 <plugin>
   <artifactId>maven-resources-plugin</artifactId>
   <version>2.6</version>
   <executions>
     <execution>
       <id>default-testResources</id>
       <phase>process-test-resources</phase>
       <goals>
         <goal>testResources</goal>
       </goals>
     </execution>
     <execution>
       <id>default-resources</id>
       <phase>process-resources</phase>
       <goals>
         <goal>resources</goal>
       </goals>
     </execution>
   </executions>
 </plugin>
 <plugin>
   <artifactId>maven-compiler-plugin</artifactId>
   <version>3.1</version>
   <executions>
     <execution>
       <id>default-compile</id>
       <phase>compile</phase>
       <goals>
         <goal>compile</goal>
       </goals>
     </execution>
     <execution>
       <id>default-testCompile</id>
       <phase>test-compile</phase>
       <goals>
         <goal>testCompile</goal>
       </goals>
     </execution>
   </executions>
 </plugin>
  ...

您可以在在Maven文档中引入Maven lifecycle

然而,当你想用其他值配置它们作为默认值时,你可以声明这些插件(例如,当你在pom.xml中声明maven-compiler插件来调整它时要使用的JDK版本)或者想要添加默认情况下在Maven生命周期中未使用的一些插件执行。

Nevertheless, you can declare these plugins when you want to configure them with other values as default values (for example, you did it when you declared the maven-compiler plugin in your pom.xml to adjust the JDK version to use) or when you want to add some plugin executions not used by default in the Maven lifecycle.

这篇关于在maven中指定java版本 - 属性和编译器插件之间的差异的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆