SpringBoot MockMvc

SpringBoot MockMvc

  • [1 什么是 MockMvc?](#1 什么是 MockMvc?)
  • [2 为什么使用 MockMvc?](#2 为什么使用 MockMvc?)
  • [3 如何使用 MockMvc?](#3 如何使用 MockMvc?)
    • [3.1 Controller](#3.1 Controller)
    • [3.2 测试方法一](#3.2 测试方法一)
    • [3.3 测试方法二](#3.3 测试方法二)

1 什么是 MockMvc?

Spring Boot 提供了一个方便的测试工具类 MockMvc,用于对 Controller 层进行单元测试。MockMvc 提供了模拟 HTTP 请求的能力,让你可以在不启动完整的 HTTP 服务器的情况下测试 Spring MVC 控制器。

2 为什么使用 MockMvc?

快速:MockMvc 可以在不启动完整的应用程序服务器的情况下进行单元测试,因此测试速度更快。

集成度高:它能够模拟 HTTP 请求和响应,以及 Spring MVC 的所有特性,如路由、过滤器、拦截器等。

灵活性:可以对控制器的行为进行精确的模拟和验证,包括请求参数、路径变量、请求头等。

3 如何使用 MockMvc?

在使用 MockMvc 进行单元测试时,你需要创建一个 MockMvc 实例,并使用它来构建和执行 HTTP 请求,然后验证返回结果。

3.1 Controller

java 复制代码
package com.xu.test.controller;

import com.xu.test.service.TestService;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.util.HashMap;
import java.util.Map;

@RestController
@RequestMapping("/test")
public class TestController {

    @Resource
    private TestService testService;


    @RequestMapping("/test1")
    public String test1(String a, Integer b) {
        return testService.test1(a, b);
    }

    @RequestMapping("/test2")
    public Object test2(HttpServletRequest request, HttpServletResponse response, String a, Integer b) {
        testService.test2(request, response, a, b);
        Map<String, Object> body = new HashMap<>();
        body.put("a", a);
        body.put("b", b);
        return body;
    }

}

3.2 测试方法一

java 复制代码
package com.xu.test;

import cn.hutool.json.JSONUtil;
import org.junit.Assert;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.http.HttpHeaders;
import org.springframework.http.MediaType;
import org.springframework.test.context.junit4.SpringRunner;
import org.springframework.test.web.servlet.MockMvc;
import org.springframework.test.web.servlet.MvcResult;
import org.springframework.test.web.servlet.ResultActions;
import org.springframework.test.web.servlet.request.MockMvcRequestBuilders;
import org.springframework.test.web.servlet.result.MockMvcResultHandlers;
import org.springframework.test.web.servlet.result.MockMvcResultMatchers;
import org.springframework.test.web.servlet.setup.MockMvcBuilders;
import org.springframework.web.context.WebApplicationContext;

import javax.servlet.http.Cookie;
import java.util.HashMap;
import java.util.Map;

@SpringBootTest
@RunWith(SpringRunner.class)
public class MockMvcTest1 {

    private MockMvc mock;

    @Autowired
    private WebApplicationContext wac;

    @Before
    public void setUp() {
        mock = MockMvcBuilders.webAppContextSetup(wac).build();
    }

    @Test
    public void get() throws Exception {
        ResultActions actions = mock.perform(MockMvcRequestBuilders.get("/test/test1?a=1&b=2")
                .header("X-Access-Token", "0123456789")
                .cookie(new Cookie("cookie", "123456789"))
                .param("a", "1")
                .param("b", "2"));

        // 期望请求成功
        actions.andExpect(MockMvcResultMatchers.status().isOk());
        // 打印请求头
        actions.andDo(MockMvcResultHandlers.print());

        MvcResult result = actions.andReturn();
        // 断言
        Assert.assertTrue(result.getResponse().isCommitted());
    }

    @Test
    public void post() throws Exception {
        // 请求体
        Map<String, Object> body = new HashMap<>();
        body.put("a", "1");

        // 请求
        ResultActions actions = mock.perform(MockMvcRequestBuilders.post("/test/test2")
                .header("X-Access-Token", "0123456789")
                .header(HttpHeaders.AUTHORIZATION, "0123456789")
                .content(JSONUtil.toJsonPrettyStr(body))
                .param("a", "1")
                .param("b", "2")
                .contentType(MediaType.APPLICATION_JSON_VALUE));

        // 期望返回的是JSON
        actions.andExpect(MockMvcResultMatchers.content().contentType(MediaType.APPLICATION_JSON));
        // 期望返回的a=1
        actions.andExpect(MockMvcResultMatchers.jsonPath("$.a").value(1));
        // 期望请求成功
        actions.andExpect(MockMvcResultMatchers.status().isOk());
        // 打印请求头
        actions.andDo(MockMvcResultHandlers.print());
        // 结果
        MvcResult result = actions.andReturn();
        // 断言
        Assert.assertEquals(MediaType.APPLICATION_JSON_VALUE, result.getResponse().getContentType());
    }

}

3.3 测试方法二

java 复制代码
package com.xu.test;

import com.xu.test.controller.TestController;
import com.xu.test.service.TestService;
import org.junit.Assert;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.autoconfigure.web.servlet.WebMvcTest;
import org.springframework.boot.test.mock.mockito.MockBean;
import org.springframework.test.context.junit4.SpringRunner;
import org.springframework.test.web.servlet.MockMvc;
import org.springframework.test.web.servlet.MvcResult;
import org.springframework.test.web.servlet.ResultActions;
import org.springframework.test.web.servlet.request.MockMvcRequestBuilders;
import org.springframework.test.web.servlet.result.MockMvcResultHandlers;
import org.springframework.test.web.servlet.result.MockMvcResultMatchers;

import javax.servlet.http.Cookie;

@RunWith(SpringRunner.class) // 声明使用 SpringRunner 进行测试
@WebMvcTest(TestController.class) // 声明需要测试的 Controller 类
public class MockMvcTest3 {

    @Autowired
    private MockMvc mockMvc;

    @MockBean
    private TestService testService;

    @Test
    public void test1() throws Exception {
        ResultActions actions = mockMvc.perform(MockMvcRequestBuilders.get("/test/test1")
                .header("X-Access-Token", "0123456789")
                .cookie(new Cookie("cookie", "123456789"))
                .param("a", "1")
                .param("b", "2"));

        // 期望请求成功
        actions.andExpect(MockMvcResultMatchers.status().isOk());
        // 打印请求头
        actions.andDo(MockMvcResultHandlers.print());
        // 结果
        MvcResult result = actions.andReturn();
        // 断言
        Assert.assertTrue(result.getResponse().isCommitted());
    }

}
相关推荐
xixingzhe223 分钟前
spring boot对接Dify
java·spring boot·dify
步行cgn28 分钟前
Spring Boot 指定数据来源详解
spring boot·后端·python
一个有温度的技术博主1 小时前
深入理解 Spring Boot 自动装配
java·spring boot·后端
步行cgn2 小时前
Spring Boot 将配置绑定到第三方对象详解
spring boot·后端·python
凤山老林2 小时前
Spring Boot 集成 Apache Kafka Streams 构建流处理应用:状态存储、窗口聚合与
spring boot·kafka·apache
Flynt15 小时前
把公司项目迁到 Spring Boot 4.0:编译通过只是开始
java·spring boot·后端
yxlalm17 小时前
5.3解决超卖问题
java·spring boot·超卖
边境悍匪19 小时前
蜗牛学苑 Java 智能体学习 Day39|SpringAI 会话存储、Function‑Call 工具调用、MCP 思维导图复盘
java·开发语言·spring boot·学习·阿里云
xcl092520 小时前
全民健身智慧管理系统实战指南:从架构设计到部署落地
java·spring boot
Bs_MoneyMagnet21 小时前
基于springboot+vue的宠物殡葬管理平台的设计与实现 源码+文档
java·javascript·vue.js·spring boot·后端·宠物