2016-03-04 136 views
1

我有3罐,即jar1,jar2,jar3。类路径和maven配置文件

在jar1有一些代码读取从类路径的文件。但是该文件不会出现在jar1的类路径中。相反,jar2将作为jar1的依赖插入,并且jar2 classpath将包含该文件。

我有jar3,它也会在其classpath中包含相同的文件,但我会声明范围为test jar3中的jar1的pom.xml

现在,当测试例的执行,我们怎么能告诉Maven来总是从jar3文件(如范围测试)的classpath虽然jar2给出主要依赖(范围不是测试)?

基于Maven型材这可能吗?如果是的话我们如何指定它? 或者我们可以使用maven-resources-plugin在测试范围内复制文件吗?

究竟是怎样的classpath会,如果相同的文件存在于给出依赖多个罐子设置?

样品jar1的pom.xml

<dependencies> 
     <dependency> 
      <groupId>com.test</groupId> 
      <artifactId>jar2</artifactId> 
      <version>0.1-SNAPSHOT</version> 
     </dependency> 
     <dependency> 
      <groupId>com.test</groupId> 
      <artifactId>jar3</artifactId> 
      <version>0.1-SNAPSHOT</version> 
      <scope>test</scope> 
     </dependency> 
</dependencies> 

两个jar2和jar3具有资源文件。

问题:哪些将有所回升,为什么?

回答

1

如果你的依赖是在依赖关系树同级别,申报在你的pom的订货会胜利,因为每Maven Dependency Mediation DOC:

注意,如果两个依赖的版本是在同一深度依赖关系树,直到Maven 2.0.8它没有定义哪一个会赢,但自从Maven 2.0.9它是在声明中的顺序计数:第一个声明赢得

所以在你的情况下,两个依赖在依赖关系树(第一级,在POM中声明)和处于同一级别范围将(根据您发布的剪断)的方式存在,只要test范围会,因为这样jar2会赢,因为你在你的POM宣布它第一。

如果您希望文件始终从jar3加载,但仅在测试期间,只需在您的依赖关系中首先声明jar3即可。它不会影响最终的可交付成果(在test作用域中),但它将定义到类路径的测试顺序,并为您提供预期的方案。你不需要Maven配置文件。


一个简单的测试用例来验证:

让我们来定义一个属性file.properties到Maven项目的src\main\resources。该文件看起来像项目resource-provider(的artifactId)以下:

property=from-resource-provider 

而且如下项目resource-provider2(的artifactId):

property=from-resource-provider2 

注:相同的文件名与不同的两个不同的项目内容。

然后在消费项目(resource-consumer),我们可以有以下示例JUnit测试案例:

public class MainTest { 

    @Test 
    public void checkClassPath() { 
     InputStream is = MainTest.class.getResourceAsStream("/file.properties"); 
     Scanner s = new Scanner(is); 
     System.out.println(s.nextLine()); 
    } 

} 

对于下面的依赖关系到resource-consumer

<dependencies> 
    <dependency> 
     <groupId>com.sample</groupId> 
     <artifactId>resource-provider2</artifactId> 
     <version>0.0.1-SNAPSHOT</version> 
     <scope>test</scope> 
    </dependency> 
    <dependency> 
     <groupId>com.sample</groupId> 
     <artifactId>resource-provider</artifactId> 
     <version>0.0.1-SNAPSHOT</version> 
    </dependency> 
    <dependency> 
     <groupId>junit</groupId> 
     <artifactId>junit</artifactId> 
     <version>4.11</version> 
     <scope>test</scope> 
    </dependency> 
</dependencies> 

测试执行的输出将是:

------------------------------------------------------- 
T E S T S 
------------------------------------------------------- 
Running com.sample.MainTest 
property=from-resource-provider2 
Tests run: 1, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 0.051 sec 

因此,第一个de申报失败,resource-provider2,赢了(注意范围,test)。

改变依赖以:

<dependencies> 
    <dependency> 
     <groupId>com.sample</groupId> 
     <artifactId>resource-provider</artifactId> 
     <version>0.0.1-SNAPSHOT</version> 
    </dependency> 
    <dependency> 
     <groupId>com.sample</groupId> 
     <artifactId>resource-provider2</artifactId> 
     <version>0.0.1-SNAPSHOT</version> 
     <scope>test</scope> 
    </dependency> 
    <dependency> 
     <groupId>junit</groupId> 
     <artifactId>junit</artifactId> 
     <version>4.11</version> 
     <scope>test</scope> 
    </dependency> 
</dependencies> 

反而会提供以下的输出:

------------------------------------------------------- 
T E S T S 
------------------------------------------------------- 
Running com.sample.MainTest 
property=from-resource-provider 
Tests run: 1, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 0.07 sec 

注意:这个时候resource-provider韩元,因为它被宣布第一,因为compile范围也部分test的范围,而相反的情况并非如此。

+0

..谢谢你..很明确的解释.. –

+0

@svsteja不客气。附注:当使用这种方法时(基于订购),我会建议添加评论给你的POM,以帮助其他开发人员或未来的维护和故障排除:) –