聊聊MockMvc+Junit单元测试

什么是MockMvc

MockMvc是在服务端实现,依赖于spring框架和环境而不需要依赖网络环境的Http请求模拟,便于用来模拟客户端测试,其基于RESTFull风格的SpringMVC单元测试,可以测试完整的springMVC流程。

MockMvc测试的优点

  • 减少模块开发间的耦合度
  • 不依赖于网络
  • 轻量、简单、灵活

MockMvc应用

通过MockMVCBuilders建造者的静态方法去建造MockMVCBuilder,MockMvc由MockMVCBuilder构造。
核心方法:perform(RequestBuilder rb),执行一个RequestBuilder请,会自动执行SpringMVC的流程并映射到相应的控制器执行处理,该方法的返回值是一个ResultActions。

说明:MockMVCBuilders
负责创建MockMVCBuilder对象。
有两种创建方式
standaloneSetup(Object… controllers): 通过参数指定一组控制器,这样就不需要从上下文获取了。
webAppContextSetup(WebApplicationContext wac):指定WebApplicationContext,将会从该上下文获取相应的控制器并得到相应的MockMvc

1、MockMvcRequestBuilders 用构建MockHttpServletRequestBuilder

  • GET请求、 POST请求、PUT请求、DELETE请求、param(String name, String… values) 传递参数 K-V…

2、MockHttpServletRequestBuilder用于构建 MockHttpServletRequest,它用于作为 MockMvc的请求对象

Junit注解介绍

  • @Before 在每个方法测试前执行,一般用来初始化方法(比如我们在测试别的方法时,类中与其他测试方法共享的值已经被改变,为了保证测试结果的有效性,我们会在@Before注解的方法中重置数据)
  • @After 在每个测试方法执行后,在方法执行完成后要做的事情。
  • @Test(timeout = 1000) 测试方法执行超过1000毫秒后算超时,测试将失败。
  • @Test(expected = Exception.class) 测试方法期望得到的异常类,如果方法执行没有抛出指定的异常,则测试失败。
  • @Ignore(“not ready yet”) 执行测试时将忽略掉此方法,如果用于修饰类,则忽略整个类。
  • @Test 编写一般测试用例用。
  • @RunWith 在 Junit 中有很多个 Runner,他们负责调用你的测试代码,每一个 Runner 都有各自的特殊功能,你根据需要选择不同的 Runner 来运行你的测试代码。

测试方法执行顺序
按照设计,Junit不指定test方法的执行顺序。
@FixMethodOrder(MethodSorters.JVM):保留测试方法的执行顺序为JVM返回的顺序。每次测试的执行顺序有可能会所不同。
@FixMethodOrder(MethodSorters.NAME_ASCENDING) :根据测试方法的方法名排序,按照词典排序规则(ASC,从小到大,递增)。
Failure 是测试失败,Error 是程序出错。

MockMvc具体应用

1、在控制包层级准备一个类进行请求测试

@RestController
public class HelloWorldController {

    @RequestMapping("/hello")
    public String hello(){
        return "hello world";
    }
}

2、在测试文件下建一个测试类进行验证


@RunWith(SpringRunner.class)
@SpringBootTest
public class HelloWorldTests {
    //模拟mvc测试对象
    public MockMvc mvc;

    @Before //所有测试方法执行之前执行该方法
    public void setUp() throws Exception{
        mvc = MockMvcBuilders.standaloneSetup(new HelloWorldController()).build(); //调用 build() 方法,初始化 MockMvc
    }

    @Test
    public void getHello() throws Exception{
        mvc.perform(MockMvcRequestBuilders.get("/hello").accept(MediaType.APPLICATION_JSON))
        .andExpect(status().isOk())  //添加ResultMatcher验证规则,验证控制器执行完成后结果是否正确。(预期响应成功)
        .andDo(print())  //添加ResultHandler结果处理器,比如调试时打印结果到控制台。
        .andReturn().getResponse().getContentAsString(); //最后返回相应的MvcResult;然后进行自定义验证/进行下一步的异步处理。
    }

}

3、运行getHello后控制台可以看到所有信息。

MockHttpServletRequest:
      HTTP Method = GET
      Request URI = /hello
       Parameters = {}
          Headers = [Accept:"application/json"]
             Body = <no character encoding set>
    Session Attrs = {}

Handler:
             Type = com.hello.controller.HelloWorldController
           Method = com.hello.controller.HelloWorldController#hello()

Async:
    Async started = false
     Async result = null

Resolved Exception:
             Type = null

ModelAndView:
        View name = null
             View = null
            Model = null

FlashMap:
       Attributes = null

MockHttpServletResponse:
           Status = 200
    Error message = null
          Headers = [Content-Type:"application/json", Content-Length:"11"]
     Content type = application/json
             Body = hello world
    Forwarded URL = null
   Redirected URL = null
          Cookies = []

版权声明:本文为weixin_39769179原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接和本声明。