13

我有一个依赖于 commons-httpclient [2.0](编译)的项目。

我想写一些 jbehave 测试 - jbehave-core 3.4.5 (test)。这两个依赖项都依赖于 commons-lang,但版本不同 - 1.0.1 和 2.5。

依赖

当我执行mvn package时,我在测试部分得到 [BUID FAILURE]。在surefire-plugin输出中我的测试用例有一个例外:

java.lang.NoSuchMethodError: org.apache.commons.lang.StringUtils.substringBeforeLast(Ljava/lang/String;Ljava/lang/String;)Ljava/lang/String;

正如我在源代码中查看的那样——在 commons-lang 1.0.1 中——确实,没有 StringUtils.substringBeforeLast(...) 方法。为什么maven在测试中使用commons-httpclient(编译)而不是jbehave-core中的commons-lang?

我无法在 commons-httpclient 中排除这种冲突的依赖关系,因此它必须保持在编译时。

那么如何解决呢?- 测试中的 commons-lang 2.5 版本和编译时的 1.0.1。

4

3 回答 3

9

马文 3:

Maven 3 将尝试获取最近的依赖项,有效地确保在编译和测试阶段只使用编译或测试范围的依赖项之一。

(感谢 Vineet Reynolds)

Maven 2(旧):

尝试定义<dependency>具有不同版本和范围的 2 个不同标签。在依赖项中使用标签<scope>test</scope>进行测试和<scope>compile</scope>编译。

于 2011-07-04T20:34:23.083 回答
1

在 Maven 3 中,您可以通过在 groupId 后添加一个点来欺骗 maven

<dependency>
  <groupId>groupId.</groupId>
  <artifactId>artifactId</artifactId>
  <version>version1</version>
  <scope>test</scope>
</dependency>

<dependency>
  <groupId>groupId</groupId>
  <artifactId>artifactId</artifactId>
  <version>version2</version>
  <scope>compile</scope>
</dependency>

顺序在这里很重要。需要先测试,然后编译。

于 2021-05-28T17:33:30.670 回答
-4

有两个不同的版本来编译和测试依赖是一个非常糟糕的主意:

您的非测试代码可能依赖于较新 JAR 的行为,并且在使用较旧 JAR 的类时会失败。当您在测试中使用旧 JAR 时,非测试代码会因旧 JAR 而失败。

否则,您可以在任何地方使用相同版本的旧 JAR... 如果您将两个 JAR 版本都放入您的类路径中,您将无法知道在运行测试时会选择哪一个。这也是个坏主意。

因此,您应该对相同的 JAR 版本依赖项进行非测试和测试。

于 2018-06-08T06:33:12.620 回答