gpt4 book ai didi

java - 从 PowerMock 1.6.2 升级到 1.6.6 以集成 JaCoCo 0.7.8 后, "whenNew"调用结果为空值

转载 作者:搜寻专家 更新时间:2023-11-01 03:33:11 27 4
gpt4 key购买 nike

我有一个较大的 Maven 多项目构建,单元测试主要使用 PowerMock,版本为 1.6.2。我决定集成 JaCoCo,这样我们就可以开始发布我们的代码覆盖率指标。 JaCoCo 的最新版本 0.7.8 需要 PowerMock 1.6.6,因此我升级了它的版本。

我现在看到一些关于“whenNew”调用的错误行为,该调用在代码库的整个测试过程中不断重复变化。

有问题的“whenNew()”调用如下所示:

PowerMockito.whenNew(BlahBlah.class)
.withArguments(any(SomeClass.class))
.thenReturn(blahBlahInstance);

对于 PowerMock 1.6.2,这工作正常。当我升级到 1.6.6 时,为了让它工作,我不得不做两个更改,一个可以接受但很烦人(因为我不知道为什么需要它),另一个真的不能接受。

可接受的更改是类顶部的“@PrepareForTest”注释。在 PowerMock 1.6.2 中,这过去只列出调用“new BlahBlah(...)”的类,并且工作正常。为了让它工作(除了下一个更改之外),我还必须将“BlahBlah.class”添加到该列表中。我可以接受这一点,但如果我能清楚地知道该列表中的具体内容,那将非常有帮助。

第二个 Not Acceptable 更改是我必须将“.withArguments(any(SomeClass.class))”更改为“.withAnyArguments()”。我还尝试了“withArguments(anyObject())”,但也没有成功。

更新:

请注意,我使用的是 1.10.19 版的 mockito-core。我从https://github.com/powermock/powermock/wiki/MockitoUsage#supported-versions看到PowerMock 1.6.6 (1.6.2+) 支持该版本的 mockito-core。

最佳答案

首先关于你的陈述

The latest version of JaCoCo, 0.7.8, requires PowerMock 1.6.6

JaCoCo 不需要 PowerMock,JaCoCo 0.7.8 中的 PowerMock 也没有什么特别之处。截至今天,0.7.8 只是最新发布的 JaCoCo 版本。

我猜你的说法是对 https://github.com/powermock/powermock/wiki/Code-coverage-with-JaCoCo 的阅读产生的一种误解。 , 说明

JaCoCo Offline Instrumentation works only with PowerMock version 1.6.6 and upper.

根据 https://github.com/powermock/powermock/blob/master/changelog.txt

Change log 1.6.6 (2016-11-04)

  • Fixed #645 jacoco offline instrumentation incompatibility with powermock byte-code manipulation when using @SuppressStaticInitializationFor

即仅针对一个特定案例进行了修复。在其他情况下,早期版本的 PowerMock 已经使用离线检测与早期版本的 JaCoCo 一起工作。

然后根据您对 PowerMock 升级到 1.6.6 后状态的描述,但在其他更改之前,尝试创建一个 Minimal, Complete, and Verifiable example :

pom.xml:

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/maven-v4_0_0.xsd">
<modelVersion>4.0.0</modelVersion>

<groupId>org.example</groupId>
<artifactId>example</artifactId>
<version>1.0-SNAPSHOT</version>

<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
<maven.compiler.source>1.8</maven.compiler.source>
<maven.compiler.target>1.8</maven.compiler.target>

<powermock.version>1.6.6</powermock.version>
<jacoco.version>0.7.8</jacoco.version>
</properties>

<dependencies>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.12</version>
<scope>test</scope>
</dependency>

<dependency>
<groupId>org.powermock</groupId>
<artifactId>powermock-module-junit4</artifactId>
<version>${powermock.version}</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.powermock</groupId>
<artifactId>powermock-api-mockito</artifactId>
<version>${powermock.version}</version>
<scope>test</scope>
</dependency>

<dependency>
<groupId>org.jacoco</groupId>
<artifactId>org.jacoco.agent</artifactId>
<classifier>runtime</classifier>
<version>${jacoco.version}</version>
<scope>test</scope>
</dependency>
</dependencies>

<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-surefire-plugin</artifactId>
<version>2.18.1</version>
<configuration>
<systemPropertyVariables>
<jacoco-agent.destfile>target/jacoco.exec</jacoco-agent.destfile>
</systemPropertyVariables>
</configuration>
</plugin>
<plugin>
<groupId>org.jacoco</groupId>
<artifactId>jacoco-maven-plugin</artifactId>
<version>${jacoco.version}</version>
<executions>
<execution>
<id>default-instrument</id>
<goals>
<goal>instrument</goal>
</goals>
</execution>
<execution>
<id>default-restore-instrumented-classes</id>
<goals>
<goal>restore-instrumented-classes</goal>
</goals>
</execution>
<execution>
<phase>package</phase>
<goals>
<goal>report</goal>
</goals>
</execution>
</executions>
</plugin>
</plugins>
</build>

</project>

src/main/java/org/example/BlahBlah.java:

package org.example;

public class BlahBlah {

private final SomeClass c;

public BlahBlah(SomeClass c) {
this.c = c;
}

public String run() {
return c.toString();
}
}

src/main/java/org/example/SomeClass.java:

package org.example;

public class SomeClass {

private final String s;

public SomeClass(String s) {
this.s = s;
}

@Override
public String toString() {
return s;
}

}

src/main/java/org/example/Example.java:

package org.example;

public class Example {

public String fun() {
return new BlahBlah(new SomeClass("Hello World")).run();
}

}

src/test/java/org/example/ExampleTest.java:

package org.example;

import org.junit.Test;
import org.junit.runner.RunWith;
import org.powermock.api.mockito.PowerMockito;
import org.powermock.core.classloader.annotations.PrepareForTest;
import org.powermock.modules.junit4.PowerMockRunner;

import static org.junit.Assert.assertEquals;
import static org.mockito.Matchers.any;

@PrepareForTest({Example.class})
@RunWith(PowerMockRunner.class)
public class ExampleTest {

@Test
public void test() throws Exception {
BlahBlah e = new BlahBlah(new SomeClass("Hello PowerMock"));
PowerMockito.whenNew(BlahBlah.class)
.withArguments(any(SomeClass.class))
.thenReturn(e);
assertEquals("Hello PowerMock", new Example().fun());
}

}

mvn clean verify

工作正常。因此,您的描述中应该还有其他遗漏的内容才能真正重现您的情况。希望这能有所帮助,至少可以基于此构建更好的复制器。

此外:尝试将 JaCoCo 的集成过程与 PowerMock 的升级分离 - 也许只是这个升级有问题,而不是 JaCoCo 的集成。

关于java - 从 PowerMock 1.6.2 升级到 1.6.6 以集成 JaCoCo 0.7.8 后, "whenNew"调用结果为空值,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41815826/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com