Spring编写单元测试以及一些常用方式


一般使用的常见的单元测试工具是: JUnit,Mockito,AssertJ

一、引入相关的maven依赖

JUnit

JUnit是最常用的Java单元测试框架之一,提供了丰富的API来编写和组织测试用例。

<dependency>
    <groupId>org.junit.jupiter</groupId>
    <artifactId>junit-jupiter-api</artifactId>
    <version>5.9.1</version>
    <scope>test</scope>
</dependency>

Mockito

用于模拟各个外部接口或者属性方法的数据

<dependency>
    <groupId>org.mockito</groupId>
    <artifactId>mockito-core</artifactId>
    <version>4.8.1</version>
    <scope>test</scope>
</dependency>

AssertJ

提供了丰富的断言库,使得断言更加简洁和易读。

<dependency>
    <groupId>org.assertj</groupId>
    <artifactId>assertj-core</artifactId>
    <version>3.24.2</version>
    <scope>test</scope>
</dependency>

二. 常见模拟用法

1. 静态类

使用MockedStatic @Cleanup注解自动close

@Cleanup MockedStatic<URLDecoder> urlDecoderMockedStatic =
                        Mockito.mockStatic(URLDecoder.class);
                urlDecoderMockedStatic.when(()->URLDecoder.decode(
                        Mockito.any(),Mockito.anyString())).
                        thenReturn(JSONUtil.toJsonStr(depositTradeResp));

2. 工具类

使用mockConstruction

 Mockito.mockConstruction(AesUtil.class,
                        (util,context)->
                                Mockito.when(util.decryptMsg(Mockito.anyString())).thenReturn(true));

3. 私有方法

使用反射机制

 Method checkCouponByQuery = createGoOrderService.getClass().getDeclaredMethod("checkCouponByQuery", List.class, List.class, List.class);
            checkCouponByQuery.setAccessible(true);
            try {
                checkCouponByQuery.invoke(createGoOrderService, addedXPlusOrderInfoList, usableCoupon, checkCouponResultList);
            } catch (Exception e) {
                logger.info("异常信息:{}", e.getMessage());
            }

3. 局部模拟

  ReflectUtil.setFieldValue(changeOrderService, "changeInfoMapper", changeInfoMapperOne);
BDDMockito.when(changeInfoMapperOne.getSubSegOrderList()).thenReturn(Arrays.asList("sdsd", "sds"));

三. 单测类实现

BaseTest 工具类

package com.csair.ecs;

import org.junit.After;
import org.junit.Before;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.test.context.ActiveProfiles;
import org.springframework.test.context.junit4.SpringRunner;
import org.springframework.test.context.web.WebAppConfiguration;
import org.springframework.test.web.servlet.MockMvc;
import org.springframework.test.web.servlet.setup.MockMvcBuilders;
import org.springframework.web.context.WebApplicationContext;

import java.io.BufferedInputStream;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;

@RunWith(SpringRunner.class)
@WebAppConfiguration
@SpringBootTest(
        classes = GroupNeedServiceApplication.class
)
public class BaseTest{
	public static final String UTF_8 = "UTF-8";
	@Autowired
	private WebApplicationContext webAppConfiguration;

	private MockMvc mockMvc;
	/**
	 * 读取json字符串
	 */
	private String paramJsonStr;

	/**
	 * 提供子类进行调用,获取自己需要的参数 通过Thread的classLoader进行获取当前classPath的数据
	 *
	 * @param classPathJsonFileName
	 *            testResources中的文件名称.
	 */
	public void loadJsonParam(String classPathJsonFileName) {
		StringBuilder sb = new StringBuilder(300);
		try (BufferedInputStream inputStream = new BufferedInputStream(
				Thread.currentThread().getContextClassLoader().getResourceAsStream(classPathJsonFileName));
				BufferedReader reader = new BufferedReader(new InputStreamReader(inputStream, UTF_8));) {
			String temp;
			while ((temp = reader.readLine()) != null) {
				sb.append(temp);
			}
		} catch (IOException e) {
			e.printStackTrace();
		}
		this.paramJsonStr = sb.toString();
	}

	/**
	 * 测试准备操作.准备好mockMvc环境
	 */
	@Before
	public void init() {
		mockMvc = MockMvcBuilders.webAppContextSetup(webAppConfiguration).build();
	}

	/**
	 * 测试扫尾操作
	 */
	@After
	public void after() {
		
	}

	public MockMvc getMockMvc() {
		return mockMvc;
	}

	public String getParamJsonStr() {
		return paramJsonStr;
	}

}

测试类

@Slf4j
public class SystemParamsConfigServiceImplTest extends BaseTest {
    @Autowired
    private SystemParamsConfigService systemParamsConfigService;
    @SneakyThrows
    @Test
    public void testSelectParamsPageList(){
        {
            final SystemParamsConfigReq req = new SystemParamsConfigReq();
            req.getPage().setPageNo(1);
            req.getPage().setPageSize(5);
            final ResponseBase<PageData<SystemParamsConfig>> responseBase = systemParamsConfigService.selectParamsPageList(req);
            // Verify the results
            log.info("结果" + JSONUtil.parseObj(responseBase));
        }
        {
            final SystemParamsConfigReq req = new SystemParamsConfigReq();
            req.getPage().setPageNo(1);
            req.getPage().setPageSize(5);
            req.setParamKey("dd");
            final ResponseBase<PageData<SystemParamsConfig>> responseBase = systemParamsConfigService.selectParamsPageList(req);
            // Verify the results
            log.info("结果" + JSONUtil.parseObj(responseBase));
        }
        {
            final SystemParamsConfigReq req = new SystemParamsConfigReq();
            req.getPage().setPageNo(1);
            req.getPage().setPageSize(5);
            req.setRemark("d");
            final ResponseBase<PageData<SystemParamsConfig>> responseBase = systemParamsConfigService.selectParamsPageList(req);
            // Verify the results
            log.info("结果 =====> " + JSONUtil.parseObj(responseBase));
        }
    }


    @SneakyThrows
    @Test
    public void testGetByParamKey(){
        final ResponseBase<SystemParamsConfig> responseBase = systemParamsConfigService.getByParamKey("aa");
        // Verify the results
        log.info(" 结果 =====> " + JSONUtil.parseObj(responseBase));
    }

    @SneakyThrows
    @Test
    public void testInsertParamConfig(){
        final SystemParamsConfig paramsConfig = new SystemParamsConfig();
        paramsConfig.setParamKey(RandomUtil.randomNumbers(6));
        paramsConfig.setParamValue("测试");
        paramsConfig.setOperator("测试人员");
        paramsConfig.setRemark("备注备注");
        {
            final ResponseBase<Integer> responseBase = systemParamsConfigService.insertParamConfig(paramsConfig);
            // Verify the results
            log.info(" 结果 =====> " + JSONUtil.parseObj(responseBase));
            setParamKey(paramsConfig.getParamKey());
        }
        {
            paramsConfig.setParamKey("ferferfrefrefrefer");
            final ResponseBase<Integer> responseBase = systemParamsConfigService.insertParamConfig(paramsConfig);
            // Verify the results
            log.info(" 结果 =====> " + JSONUtil.parseObj(responseBase));
        }
    }

四.idea查看覆盖率

在IntelliJ IDEA中,鼠标右键选中某个单元测试类或包,选择 更多运行/调试 - 使用覆盖率 - 使用覆盖率运行。
等待单元测试运行结束,会在IDEA右侧弹出覆盖率面板。
在代码中查看具体覆盖情况,红色为未覆盖的,绿色为覆盖的。

在这里插入图片描述
在这里插入图片描述


五.官方文档

Mockito 的官方文档提供了详细的说明和示例,帮助开发者更好地理解和使用 Mockito。以下是官方文档的链接:

Mockito

  • 7
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值