You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何编写JUnit测试用例测试Hd构造函数的异常捕获分支

如何为构造函数的异常分支编写单元测试用例?

我有如下代码:

class Hd {
  public Hd() {
     try {
       this.hName =  InetAddress.getLocalHost().getHostName();
     } catch (UnknownHostException e){
       this.setHName("unk-host");
     }
  } 
}

请问如何为该构造函数的异常分支编写单元测试用例?因为需要让InetAddress.getLocalHost().getHostName()抛出异常,而该方法不会主动触发异常,需确保其必抛异常以验证catch逻辑。


方案一:用PowerMock Mock静态方法(最直接)

要触发UnknownHostException,核心是让InetAddress.getLocalHost()抛出异常,PowerMock支持mock静态方法,步骤如下:

1. 引入测试依赖

如果使用JUnit 4,添加以下Maven依赖:

<dependency>
    <groupId>org.powermock</groupId>
    <artifactId>powermock-module-junit4</artifactId>
    <version>2.0.9</version>
    <scope>test</scope>
</dependency>
<dependency>
    <groupId>org.powermock</groupId>
    <artifactId>powermock-api-mockito2</artifactId>
    <version>2.0.9</version>
    <scope>test</scope>
</dependency>

使用JUnit 5的话,替换为powermock-module-junit5依赖,并使用@ExtendWith(PowerMockExtension.class)注解替代JUnit 4的运行器。

2. 编写测试用例

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 java.net.InetAddress;
import java.net.UnknownHostException;
import static org.junit.Assert.assertEquals;

@RunWith(PowerMockRunner.class)
@PrepareForTest(InetAddress.class) // 声明要处理的静态类
public class HdTest {

    @Test
    public void constructor_ThrowsUnknownHostException_SetsUnkHost() throws Exception {
        // Mock静态方法,让getLocalHost()抛出异常
        PowerMockito.mockStatic(InetAddress.class);
        PowerMockito.when(InetAddress.getLocalHost()).thenThrow(new UnknownHostException());

        // 实例化Hd,触发catch分支
        Hd hd = new Hd();

        // 验证结果是否符合预期(假设Hd有getHName()方法)
        assertEquals("unk-host", hd.getHName());
    }
}

关键说明

  • @RunWith(PowerMockRunner.class):指定PowerMock作为测试运行器,才能处理静态方法mock
  • @PrepareForTest(InetAddress.class):通知PowerMock修改该类的字节码,实现静态方法mock

方案二:重构代码(无额外依赖)

如果不想引入PowerMock,可以把获取主机名的逻辑抽成独立方法,用Mockito的spy功能mock该方法:

重构后的Hd类

class Hd {
  public Hd() {
     try {
       this.hName = getLocalHostName();
     } catch (UnknownHostException e){
       this.setHName("unk-host");
     }
  }

  // 抽为protected方法,方便测试时mock
  protected String getLocalHostName() throws UnknownHostException {
    return InetAddress.getLocalHost().getHostName();
  }
}

对应的测试用例

import org.junit.Test;
import org.mockito.Mockito;
import java.net.UnknownHostException;
import static org.junit.Assert.assertEquals;

public class HdTest {

    @Test
    public void constructor_ThrowsUnknownHostException_SetsUnkHost() throws Exception {
        // 创建Hd的spy对象,保留真实逻辑的同时允许mock指定方法
        Hd hdSpy = Mockito.spy(Hd.class);

        // mock抽离后的方法,让其抛出异常
        Mockito.doThrow(new UnknownHostException()).when(hdSpy).getLocalHostName();

        // 用反射重新调用构造函数(避免spy初始化时已执行过一次构造)
        java.lang.reflect.Constructor<Hd> constructor = Hd.class.getConstructor();
        constructor.setAccessible(true);
        Hd hdInstance = constructor.newInstance();

        // 验证结果
        assertEquals("unk-host", hdInstance.getHName());
    }
}

内容的提问来源于stack exchange,提问作者pensee

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.12 13:50:35