• MockMvc


    ★  MockMvc - SpringMVC单元测试的独立测试:
    一、简介
    为何使用MockMvc?
            对模块进行集成测试时,希望能够通过输入URL对Controller进行测试,如果通过启动服务器,建立http client进行测试,这样会使得测试变得很麻烦,比如,启动速度慢,测试验证不方便,依赖网络环境等,所以为了可以对Controller进行测试,我们引入了MockMVC。
            MockMvc实现了对Http请求的模拟,能够直接使用网络的形式,转换到Controller的调用,这样可以使得测试速度快、不依赖网络环境,而且提供了一套验证的工具,这样可以使得请求的验证统一而且很方便。

    二、测试逻辑

    MockMvcBuilder构造MockMvc的构造器;

    mockMvc调用perform,执行一个RequestBuilder请求,调用controller的业务处理逻辑;

    perform返回ResultActions,返回操作结果,通过ResultActions,提供了统一的验证方式;

    使用StatusResultMatchers对请求结果进行验证;

    使用ContentResultMatchers对请求返回的内容进行验证;

    三、MockMvcBuilder
    MockMvc是spring测试下的一个非常好用的类,他们的初始化需要在setUp中进行。
    MockMvcBuilder是用来构造MockMvc的构造器,其主要有两个实现:StandaloneMockMvcBuilder和DefaultMockMvcBuilder,前者继承了后者。
    ① MockMvcBuilders.webAppContextSetup(WebApplicationContext context):指定WebApplicationContext,将会从该上下文获取相应的控制器并得到相应的MockMvc;
    ② MockMvcBuilders.standaloneSetup(Object... controllers):通过参数指定一组控制器,这样就不需要从上下文获取了,比如this.mockMvc = MockMvcBuilders.standaloneSetup(this.controller).build();
    这些Builder还提供了其他api,可以自行百度

    四、MockMvcRequestBuilders
            从名字可以看出,RequestBuilder用来构建请求的,其提供了一个方法buildRequest(ServletContext servletContext)用于构建MockHttpServletRequest;其主要有两个子类MockHttpServletRequestBuilder和MockMultipartHttpServletRequestBuilder(如文件上传使用),即用来Mock客户端请求需要的所有数据。
    主要API:
    MockHttpServletRequestBuilder get(String urlTemplate, Object... urlVariables):根据uri模板和uri变量值得到一个GET请求方式的RequestBuilder,如果在controller的方法中method选择的是RequestMethod.GET,那在controllerTest中对应就要使用MockMvcRequestBuilders.get。
    post(String urlTemplate, Object... urlVariables):同get类似,但是是POST方法;
    put(String urlTemplate, Object... urlVariables):同get类似,但是是PUT方法;
    delete(String urlTemplate, Object... urlVariables) :同get类似,但是是DELETE方法;
    options(String urlTemplate, Object... urlVariables):同get类似,但是是OPTIONS方法;

    五、ResultActions
        调用MockMvc.perform(RequestBuilder requestBuilder)后将得到ResultActions,对ResultActions有以下三种处理:

    ResultActions.andExpect:添加执行完成后的断言。添加ResultMatcher验证规则,验证控制器执行完成后结果是否正确;

    ResultActions.andDo:添加一个结果处理器,比如此处使用.andDo(MockMvcResultHandlers.print())输出整个响应结果信息,可以在调试的时候使用。

    ResultActions.andReturn:表示执行完成后返回相应的结果

    备注:
        ResultHandler用于对处理的结果进行相应处理的,比如输出整个请求/响应等信息方便调试,Spring mvc测试框架提供了MockMvcResultHandlers静态工厂方法,该工厂提供了ResultHandler print()返回一个输出MvcResult详细信息到控制台的ResultHandler实现

    例子:

    package com.jd.overseas.promo.trade.controller;
    
    import com.alibaba.fastjson.JSONObject;
    import org.junit.After;
    import org.junit.Before;
    import org.junit.Test;
    import org.junit.runner.RunWith;
    import org.springframework.beans.factory.annotation.Autowired;
    import org.springframework.context.ApplicationContext;
    import org.springframework.http.MediaType;
    import org.springframework.test.context.ContextConfiguration;
    import org.springframework.test.context.junit4.SpringRunner;
    import org.springframework.test.web.servlet.MockMvc;
    import org.springframework.test.web.servlet.MockMvcBuilder;
    import org.springframework.test.web.servlet.MvcResult;
    import org.springframework.test.web.servlet.ResultActions;
    import org.springframework.test.web.servlet.request.MockHttpServletRequestBuilder;
    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.servlet.resource.DefaultServletHttpRequestHandler;
    
    import java.util.HashMap;
    import java.util.Map;
    
    import static org.junit.Assert.*;
    import static org.springframework.test.web.client.match.MockRestRequestMatchers.content;
    
    /**
     * @ProjectName: of-trade-promo-finish
     * @Package: com.jd.overseas.promo.trade.controller
     * @ClassName: ScenePromoControllerTest
     * @Author: zhoujunming3
     * @Description: ${description}
     * @Date: 2020/1/17 11:51
     * @Version: 1.0
     */
    @RunWith(SpringRunner.class)
    @ContextConfiguration(locations = {"classpath:spring-config.xml","classpath:spring-mvc.xml"})
    public class ScenePromoControllerTest {
    
        //DefaultServletHttpRequestHandler
        @Autowired
        ApplicationContext ctx;
    
        private ScenePromoController scenePromoController;
    
        private MockMvc mockMvc;
    
        @Before
        public void setUp() throws Exception {
            scenePromoController = (ScenePromoController) ctx.getBean("scenePromoController");
            mockMvc = MockMvcBuilders.standaloneSetup(scenePromoController).build();
    
        }
        @After
        public void tearDown() throws Exception {
    
        }
        @Test
        public void getPromoLinkPrize() {
    
            try {
                JSONObject obj = new JSONObject();
                obj.put("promoId", "55555");
                MockHttpServletRequestBuilder requestBuilder = MockMvcRequestBuilders.post("/th/promo/getPromoLinkPrize")
                        .contentType(MediaType.APPLICATION_JSON)
                        .content(obj.toJSONString());
                ResultActions result = mockMvc.perform(requestBuilder);
                MvcResult mvcResult = result.andExpect(MockMvcResultMatchers.status().isOk())
                        .andDo(MockMvcResultHandlers.print())
                        .andReturn();// 返回执行请求的结果
                System.out.println(mvcResult.getResponse().getContentAsString());
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    }

    备注:使用Content-type来指定不同格式的请求信息,下面例举在日常的开发中,常会用的若干content-type的内容格式
        例如: Content-Type: text/html;charset:utf-8;
     常见的媒体格式类型如下:
        text/html : HTML格式
        text/plain :纯文本格式      
        text/xml :  XML格式 /
        image/gif :gif图片格式    
        image/jpeg :jpg图片格式 
        image/png:png图片格式
       以application开头的媒体格式类型:
       application/xhtml+xml :XHTML格式
       application/xml     : XML数据格式
       application/atom+xml  :Atom XML聚合格式    
       application/json    : JSON数据格式
       application/pdf       :pdf格式  
       application/msword  : Word文档格式
       application/octet-stream : 二进制流数据(如常见的文件下载)
       application/x-www-form-urlencoded : <form encType=””>中默认的encType,form表单数据被编码为key/value格式发送到服务器(表单默认的提交数据的格式)
       另外一种常见的媒体格式是上传文件之时使用的:
        multipart/form-data : 需要在表单中进行文件上传时,就需要使用该格式

    附录:Requests & Responses 的标识及解释 


    六、ResultMatchers 
            ResultMatcher用来匹配执行完请求后的结果验证,其就一个match(MvcResult result)断言方法,如果匹配失败将抛出相应的异常,spring mvc测试框架提供了很多***ResultMatchers来满足测试需求。

    七、MvcResult
            即执行完控制器后得到的整个结果,并不仅仅是返回值,其包含了测试时需要的所有信息。
    MockHttpServletRequest getRequest():得到执行的请求;
    MockHttpServletResponse getResponse():得到执行后的响应;
    Object getHandler():得到执行的处理器,一般就是控制器;
    HandlerInterceptor[] getInterceptors():得到对处理器进行拦截的拦截器;
    ModelAndView getModelAndView():得到执行后的ModelAndView;
    Exception getResolvedException():得到HandlerExceptionResolver解析后的异常;
    FlashMap getFlashMap():得到FlashMap;
    Object getAsyncResult()/Object getAsyncResult(long timeout):得到异步执行的结果;

  • 相关阅读:
    如何对已上架的宝贝进行调整不被降权?
    报错ERR_CONNECTION_REFUSED,如何解决(原创)
    ***在Linux环境下mysql的root密码忘记解决方法(三种)-推荐第三种
    微信获取用户基本信息,头像是一张“暂时无法查看”的图?
    Linux中zip压缩和unzip解压缩命令详解
    Android必知必会-App 常用图标尺寸规范汇总
    国外主机海外主机测评总结
    美国主机BlueHost vs HostEase
    cPanel中添加设置附加域(Addon domain)
    香港新世界机房和电讯盈科机房,沙田机房,葵芳机房哪数据中心一个好?服务器托管
  • 原文地址:https://www.cnblogs.com/zjm-1/p/12206864.html
Copyright © 2020-2023  润新知