四、测试用例
1.准备工作
-
添加依赖
<dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-devtools</artifactId> <optional>true</optional> </dependency> <dependency> <groupId>com.alibaba</groupId> <artifactId>druid-spring-boot-starter</artifactId> <version>1.2.15</version> </dependency> <dependency> <groupId>org.projectlombok</groupId> <artifactId>lombok</artifactId> </dependency> <dependency> <groupId>org.mybatis.spring.boot</groupId> <artifactId>mybatis-spring-boot-starter</artifactId> <version>2.2.2</version> </dependency> <dependency> <groupId>com.mysql</groupId> <artifactId>mysql-connector-j</artifactId> <scope>runtime</scope> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-web</artifactId> </dependency> <dependency> <groupId>org.springframework.boot</groupId> <artifactId>spring-boot-starter-test</artifactId> <scope>test</scope> <exclusions> <exclusion> <groupId>org.junit.vintage</groupId> <artifactId>junit-vintage-engine</artifactId> </exclusion> </exclusions> </dependency>
-
写mapper
@Mapper @Repository public interface ItemMapper { @Insert("insert into item(name,remark) value(#{name},#{remark})") boolean insert(Item item); @Select("select * from item where id = #{id}") public Item getById(Long id); }
-
写接口
@RestController @RequestMapping("/item") @Slf4j public class ItemController { @Autowired ItemMapper mapper; @GetMapping("/{id}") public Item getById(@PathVariable Long id){ return mapper.getById(id); } @PostMapping public boolean save(@RequestBody Item item){ log.info("获取方法的入参为:{}",item); return mapper.insert(item); } }
-
写 domain
@Data public class Item { private Long id; private String name; private String remark; }
-
提供配置文件
spring: datasource: druid: url: jdbc:mysql://localhost:3306/springboot_ssm username: root password: 123456 driver-class-name: com.mysql.cj.jdbc.Driver
2.Web环境模拟测试
2.1目前存在的问题
-
实际测试没有走mvcweb环境,是直接调用接口的
@SpringBootTest class SpringbootTestApplicationTests { @Autowired ItemController controller; @Test public void testSave(){ Item item = new Item(); item.setName("键盘"); item.setRemark("1000元"); controller.save(item); } }
-
数据是实际添加到数据库的,应该回滚
-
缺乏实际返回值的对比
2.2模拟web环境测试
-
添加如下属性
@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT)
-
开启虚拟mvc调用
@AutoConfigureMockMvc
-
测试一个请求方法
@Test public void getById(@Autowired MockMvc mvc) throws Exception {// @Autowired MockMvc mvc 也可以通过设置全局变量进行注入 //创建虚拟请求的 MockHttpServletRequestBuilder builder = MockMvcRequestBuilders.get("/item/29"); mvc.perform(builder); }
2.3预期结果比较
-
对于请求结果的比对,使用andExcept方法比较
-
比较请求状态码
@Test public void getById(@Autowired MockMvc mvc) throws Exception { //创建虚拟请求的 MockHttpServletRequestBuilder builder = MockMvcRequestBuilders.get("/item/20"); ResultActions actions = mvc.perform(builder); //定义请求结果的预期值 ResultMatcher ok = MockMvcResultMatchers.status().isOk(); actions.andExpect(ok); }
-
比较实际返回值
@Test public void getById(@Autowired MockMvc mvc) throws Exception { //创建虚拟请求的 MockHttpServletRequestBuilder builder = MockMvcRequestBuilders.get("/item/20"); ResultActions actions = mvc.perform(builder); //定义请求结果的预期值 ResultMatcher ok = MockMvcResultMatchers.status().isOk(); actions.andExpect(ok); //比较你实际结果值 ResultMatcher json = MockMvcResultMatchers.content().json( "{\n" + " \"id\": 20,\n" + " \"name\": \"笔记本电脑\",\n" + " \"remark\": \"1二手电脑只要一千块\"\n" + "}" ); actions.andExpect(json); }
- 如果返回值和实际不匹配会提示如下错误
-
比较响应头
@Test public void getByIdHeader(@Autowired MockMvc mvc) throws Exception { //创建虚拟请求的 MockHttpServletRequestBuilder builder = MockMvcRequestBuilders.get("/item/20"); ResultActions actions = mvc.perform(builder); //比较响应头 ResultMatcher header = MockMvcResultMatchers.header().string("Content-Type","application/json"); actions.andExpect(header); }
-
发起post 请求直接在 content 中添加json转字符串即可
@Test public void postItemBoolean(@Autowired MockMvc mvc,@Autowired ItemTest itemTest) throws Exception { Item item = new Item(); item.setName("键盘111"); item.setRemark("1000元1111"); System.out.println("=================="); System.out.println(itemTest); //创建虚拟请求的 MockHttpServletRequestBuilder builder = MockMvcRequestBuilders.post("/item"); builder.contentType("application/json"); builder.accept(MediaType.APPLICATION_JSON); ObjectMapper objectMapper = new ObjectMapper(); String s = objectMapper.writeValueAsString(itemTest); builder.content(s); ResultActions actions = mvc.perform(builder); MvcResult mvcResult = actions.andReturn(); System.out.println(mvcResult.getResponse().getStatus()); ResultMatcher ret = MockMvcResultMatchers.content().string("true"); actions.andExpect(ret); }
-
2.4.测试用例数据设定###
-
直接提供配置即可
testcase: item: name: ${random.int(5)} remark: ${random.int(5)}
-
domain
@ConfigurationProperties(prefix = "testcase.item") @Component @Data public class ItemTest { private String name; private String remark; }
2.5数据层测试回滚
-
使用注解 rollback + Transactional
@SpringBootTest(webEnvironment = SpringBootTest.WebEnvironment.RANDOM_PORT) //开启虚拟mvc的调用 @AutoConfigureMockMvc @Rollback @Transactional class SpringbootTestApplicationTests { }
-
开启事务和回滚之后,数据就不会写入数据库了。