zoukankan      html  css  js  c++  java
  • springboot使用MockMvc测试controller

      通常,在我们平时开发项目时,如果想要输入URL对Controller进行测试,在代码编辑之后,需要重启服务器,建立http client进行测试。这样会使得测试变得很麻烦,比如,启动速度慢,测试验证不方便,依赖网络环境等,这样会导致测试无法进行,为了可以对Controller进行测试,可以通过引入MockMVC进行解决。

      MockMvc实现了对Http请求的模拟,能够直接使用网络的形式,转换到Controller的调用,这样可以使得测试速度快、不依赖网络环境,而且提供了一套验证的工具,这样可以使得请求的验证统一而且很方便。

           MockMvcBuilder是用来构造MockMvc的构造器,其主要有两个实现:StandaloneMockMvcBuilder和DefaultMockMvcBuilder,分别对应两种测试方式,即独立安装和集成Web环境测试(此种方式并不会集成真正的web环境,而是通过相应的Mock API进行模拟测试,无须启动服务器)。对于我们来说直接使用静态工厂MockMvcBuilders创建即可。

    下面就写几个简单的案例,使用MockMvc测试Controller中的get请求和post请求。

    1.引入jar包

    <dependency>
      <groupId>org.springframework.boot</groupId>
      <artifactId>spring-boot-starter-test</artifactId>
      <scope>test</scope>
    </dependency>
    

    2.编写测试controller

    /**
     * @author Sue
     * @create 2019-09-06 10:03
     **/
    @RestController
    @RequestMapping("/mock")
    public class MockmvcController {
    
        /**
         * get请求
         * @param username
         * @param password
         * @return
         */
        @GetMapping("/getInfo")
        public R getInfo(String username,String password){
            System.out.println("username:" + username + "," + "password:" + password);
            return R.ok();
        }
    
        /**
         * post请求
         * @param username
         * @param password
         * @return
         */
        @PostMapping("/getInfo2")
        public R getInfo2(String username,String password){
            System.out.println("username:" + username + "," + "password:" + password);
            return R.ok();
        }
    
        /**
         * post请求接收json格式
         * @param user
         * @return
         */
        @PostMapping("/getInfo3")
        public R getInfo3(@RequestBody User user){
            System.out.println(user);
            return R.ok(user);
        }
    
    }

    3.创建单元测试

    idea使用快捷键ctrl+alt+t

    @RunWith(SpringRunner.class)
    @SpringBootTest
    public class MockmvcTest {
        // 注入web环境的ApplicationContext容器
        @Autowired
        private WebApplicationContext context;
        /**
         * 模拟mvc测试对象
         */
        private MockMvc mockMvc;
    
        /**
         * 所有测试方法执行之前执行该方法
         */
        @Before // 这个注解的作用,在每个方法之前都会执行一遍
        public void before() throws Exception {
            //获取mockmvc对象实例
            mockMvc = MockMvcBuilders.webAppContextSetup(this.context).build();
        }
    
        @Test
        public void getInfo() throws Exception {
            MvcResult mvcResult = mockMvc.perform(
                    MockMvcRequestBuilders.get("/mock/getInfo")
                            .param("username", "Jack")
                            .param("password", "Jack001"))
                            .andExpect(MockMvcResultMatchers.status().isOk())
                            .andDo(MockMvcResultHandlers.print()).andReturn();
            System.out.println("输出 " + mvcResult.getResponse().getContentAsString());
        }
    
        @Test
        public void getInfo2() throws Exception {
            MvcResult mvcResult = mockMvc.perform(
                    MockMvcRequestBuilders.post("/mock/getInfo2")
                            .accept(MediaType.APPLICATION_JSON)
                            .param("username", "Jack")
                            .param("password", "Jack001"))
                    .andExpect(MockMvcResultMatchers.status().isOk())
                    .andDo(MockMvcResultHandlers.print()).andReturn();
            System.out.println("输出 " + mvcResult.getResponse().getContentAsString());
        }
    
        @Test
        public void getInfo3() throws Exception {
            User user = new User();
            user.setUsername("Jack");
            user.setPassword("Jack001");
            String jsonString = JSON.toJSONString(user);
            MvcResult mvcResult = mockMvc.perform(
                    MockMvcRequestBuilders.post("/mock/getInfo3")
                            .contentType(MediaType.APPLICATION_JSON)
                            .content(jsonString)
                            .accept(MediaType.APPLICATION_JSON)
                    )
                    .andExpect(MockMvcResultMatchers.status().isOk())
                    .andDo(MockMvcResultHandlers.print()).andReturn();
    
            int status = mvcResult.getResponse().getStatus();
            Assert.assertTrue("正确", status == 200);
    
            System.out.println("输出 " + mvcResult.getResponse().getContentAsString());
        }
    
    }
    

    4.测试

    代码解析 :

    • perform:执行一个RequestBuider请求,自动执行SpringMvc的流程并映射到相应的控制器执行处理
    • get: 声明一个发送get请求的方法. public static MockHttpServletRequestBuilder get(String urlTemplate, Object... uriVars) { return new MockHttpServletRequestBuilder(HttpMethod.GET, urlTemplate, uriVars);}这是个静态方法,可以直接导入,根据uri模版和uri的变量值得到一个get请求的方法. 另外提供了其他的请求方法, 如:postputdelete 等.
    • andExperct: 添加ResultMatcher验证规则,验证perform执行完成后的结果是否正确(对返回的数据进行判断)
    • andDo: 添加ResultHandler结果处理器,比如调试打印结果到控制台print()
    • andReturn: 最后返回相应的MvcResult,然后进行自定义验证/进行下一步的异步处理.

    整个测试过程如下:

    1、准备测试环境

    2、通过MockMvc执行请求

    3、添加验证断言

    4、添加结果处理器

    5、得到MvcResult进行自定义断言/进行下一步的异步请求

    6、卸载测试环境

    通过这几个方法,相信大家对mockMvc测试有了一些了解,如果想要使用更多细节,通过方法名和参数应该也能看懂方法含义,如果还是不能理解,可以查看下面的官方文档配合使用。

    官方文档 

    参考

  • 相关阅读:
    048——VUE中使用animate.css动画库控制vue.js过渡效果
    047——VUE中css过渡动作实例
    046——VUE中组件之使用动态组件灵活设置页面布局
    045——VUE中组件之父组件使用scope定义子组件模板结构
    004PHP文件处理——目录操作:glob rewinddir opendir readdir
    003PHP文件处理——目录操作:rename scandir
    044——VUE中组件之使用内容分发slot构建bootstrap面板panel
    Linux输出信息并将信息记录到文件(tee命令)
    linux下使用SVN上传项目
    linux下将文件上传到svn服务器
  • 原文地址:https://www.cnblogs.com/sueyyyy/p/11534047.html
Copyright © 2011-2022 走看看