【问题标题】:Mocking static methods + running parameterized tests = "no match found"模拟静态方法+运行参数化测试=“找不到匹配”
【发布时间】:2018-09-23 00:59:24
【问题描述】:

我有一个这样的单元测试类:

import junitparams.JUnitParamsRunner;

@RunWith(JUnitParamsRunner.class)
public class CustomerTest
{

    @Test
    @Parameters({
    "true",
    "false",
    })
    public void testMaritalStatus(boolean married) {


    }

}

现在,我需要模拟一些静态方法,所以我这样做:

import org.junit.runner.RunWith;
import org.mockito.Mockito;
import org.powermock.api.mockito.PowerMockito;
import org.powermock.modules.junit4.PowerMockRunner;
import org.powermock.modules.junit4.PowerMockRunnerDelegate;

@Before
public void setup() {
     PowerMockito.mockStatic(Helpers.class)
}

但为了使用它,我也需要这样做:

@RunWith(PowerMockRunner.class)
@PowerMockRunnerDelegate(JUnitParamsRunner.class)
public class CustomerTest {


}

问题:我收到此错误:

No match found

java.lang.IllegalStateException: No match found
at java.util.regex.Matcher.group(Matcher.java:536)
at java.util.regex.Matcher.group(Matcher.java:496)
at org.powermock.modules.junit4.internal.impl.NotificationBuilder.determineTestMethod(NotificationBuilder.java:141)
at org.powermock.modules.junit4.internal.impl.NotificationBuilder.access$000(NotificationBuilder.java:37)
at org.powermock.modules.junit4.internal.impl.NotificationBuilder$OngoingTestRun.<init>(NotificationBuilder.java:85)
at org.powermock.modules.junit4.internal.impl.NotificationBuilder.testStartHasBeenFired(NotificationBuilder.java:231)
at org.powermock.modules.junit4.internal.impl.PowerMockRunNotifier.fireTestStarted(PowerMockRunNotifier.java:109)
at junitparams.internal.ParameterisedTestMethodRunner.runTestMethod(ParameterisedTestMethodRunner.java:41)
at junitparams.internal.ParameterisedTestClassRunner.runParameterisedTest(ParameterisedTestClassRunner.java:143)
at junitparams.JUnitParamsRunner.runChild(JUnitParamsRunner.java:388)
at junitparams.JUnitParamsRunner.runChild(JUnitParamsRunner.java:366)
at org.powermock.modules.junit4.internal.impl.DelegatingPowerMockRunner$2.call(DelegatingPowerMockRunner.java:143)
at org.powermock.modules.junit4.internal.impl.DelegatingPowerMockRunner$2.call(DelegatingPowerMockRunner.java:136)
at org.powermock.modules.junit4.internal.impl.DelegatingPowerMockRunner.withContextClassLoader(DelegatingPowerMockRunner.java:127)
at org.powermock.modules.junit4.internal.impl.DelegatingPowerMockRunner.run(DelegatingPowerMockRunner.java:136)
at org.powermock.modules.junit4.common.internal.impl.JUnit4TestSuiteChunkerImpl.run(JUnit4TestSuiteChunkerImpl.java:106)
at org.powermock.modules.junit4.common.internal.impl.AbstractCommonPowerMockRunner.run(AbstractCommonPowerMockRunner.java:53)
at org.powermock.modules.junit4.PowerMockRunner.run(PowerMockRunner.java:59)

【问题讨论】:

  • 不要模拟静态方法。自行彻底测试它们,然后将它们视为被测类的主代码路径的一部分。

标签: java unit-testing static-methods powermockito


【解决方案1】:

这是由于 PowerMock 中的 bug。显然,JUnitParams 传递给 PowerMock 的方法的 DisplayName 不符合其相当狭窄的要求。给出了以下解决方法:

<plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-surefire-plugin</artifactId>
    <version>2.19.1</version>
    <configuration>
        <systemPropertyVariables>
            <JUnitParams.flat>true</JUnitParams.flat>
        </systemPropertyVariables>
    </configuration>
</plugin>

这给了我们:

<dependencies>
    <dependency>
        <groupId>junit</groupId>
        <artifactId>junit</artifactId>
        <version>4.12</version>
        <scope>test</scope>
    </dependency>
    <dependency>
        <groupId>pl.pragmatists</groupId>
        <artifactId>JUnitParams</artifactId>
        <version>1.0.4</version>
        <scope>test</scope>
    </dependency>
    <dependency>
        <groupId>org.powermock</groupId>
        <artifactId>powermock-module-junit4</artifactId>
        <version>1.7.4</version>
        <scope>test</scope>
    </dependency>
    <dependency>
        <groupId>org.powermock</groupId>
        <artifactId>powermock-api-mockito</artifactId>
        <version>1.7.4</version>
        <scope>test</scope>
    </dependency>
</dependencies>

<!-- workaround -->
<build>
    <plugins>
        <plugin>
            <groupId>org.apache.maven.plugins</groupId>
            <artifactId>maven-surefire-plugin</artifactId>
            <version>2.19.1</version>
            <configuration>
                <systemPropertyVariables>
                    <JUnitParams.flat>true</JUnitParams.flat>
                </systemPropertyVariables>
            </configuration>
        </plugin>
    </plugins>
</build>

在我的pom.xml 中有这个,在将@PrepareForTest(Helpers.class) 添加到CustomerTest 之后,测试运行良好:

import junitparams.JUnitParamsRunner;
import junitparams.Parameters;
import org.junit.Before;
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 org.powermock.modules.junit4.PowerMockRunnerDelegate;

@RunWith(PowerMockRunner.class)
@PowerMockRunnerDelegate(JUnitParamsRunner.class)
@PrepareForTest(Helpers.class)
public class CustomerTest {

    @Before
    public void setup() {
        PowerMockito.mockStatic(Helpers.class);
    }

    @Test
    @Parameters({
            "true",
            "false",
    })
    public void testMaritalStatus(boolean married) {

    }
}

【讨论】:

  • 设置flat=true有什么作用?我讨厌设置这个属性只是为了发现它在其他地方有一些副作用。
猜你喜欢
  • 2017-10-12
  • 2018-12-23
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2019-11-18
  • 1970-01-01
  • 2017-05-04
相关资源
最近更新 更多