单元测试 - 使用 MockMvc 使用 @RequestHeader 和 HashMap 测试控制器
Posted
技术标签:
【中文标题】单元测试 - 使用 MockMvc 使用 @RequestHeader 和 HashMap 测试控制器【英文标题】:Unit Test - Using MockMvc to test the controller with @RequestHeader with HashMap 【发布时间】:2021-03-14 19:24:02 【问题描述】:我有一个具有以下结构的控制器:
@RequestMapping(value="/validate", method=RequestMethod.POST)
public ResponseEntity<Jwt> IsValid(@RequestBody UserRequest userRequest, @RequestHeader Map<String, String> header) throws Exception
if(header.contains("key") && header.contains("secret")
process(header.get("key"), header.get("secret"));
...
...
我正在使用 MockMvc 为这个控制器编写一个单元测试:
@RunWith(SpringRunner.class)
@AutoConfigureMockMvc
@SpringBootTest
public class AuthenticatorServiceTest
@Autowired
private MockMvc mockMvc;
@Test
public void CorrectKeyValidation throws Exception
String key = "correct-key";
String secret = "correct-secret";
Map<String, String> map = new HashMap<>();
map.put("key", key);
map.put("secret", secret);
MvcResult result = mockMvc.perform(MockMvcRequestBuilders.post("/validate")
.header() // <- doesn't accept Map here.
.contentType(MediaType.APPLICATION_JSON))
.andExpect(status().isOk()).andReturn();
...
...
由于MockMvcRequestBuilders
的header
方法只接受字符串,我不确定如何使用MockMvc 来测试我的控制器,其中Map<String, String>
作为@RequestHeader
。任何帮助将不胜感激!
【问题讨论】:
@RequestHeader Map<String, String> header
表示它将注入该映射中的所有标题。
感谢您的回复。你能详细说明一下吗?我尝试使用 mockMvc.perform(MockMvcRequestBuilders.post("/validate") .header("key", key) .header("secret", secret) .contentType(MediaType.APPLICATION_JSON)) .andExpect(status() 发送。 isOk()).andReturn();但无法真正让它工作,因为它正在抛出org.springframework.http.converter.HttpMessageNotReadableException
。也许我在这里遗漏了一些东西..
顺便说一句:不要那样做。使用@RequestHeader("key")
。
【参考方案1】:
还有一个类似下面的方法(.headers(*)),你可以用,刚刚验证过。
Map<String, String> map = new HashMap<>();
map.put("key", key);
map.put("secret", secret);
HttpHeaders httpHeaders = new HttpHeaders();
httpHeaders.setAll(map);
MvcResult result = mvc.perform(MockMvcRequestBuilders
.post("/scheduler/enable")
.headers(httpHeaders)
.contentType(MediaType.APPLICATION_JSON_UTF8)
.content(this.getRequstAsJSON()))
.andDo(print())
.andReturn();
希望这是有用的。
【讨论】:
感谢您的回复!我试过了,但我仍然收到以下错误:Handler: Type = com.louprogramming.controller.AuthController Method = public org.springframework.http.ResponseEntity<com.louprogramming.domain.Jwt> com.louprogramming.controller.AuthController.IsValid(com.louprogramming.domain.UserRequest,java.util.Map<java.lang.String, java.lang.String>) throws java.lang.Exception. Resolved Exception: Type = org.springframework.http.converter.HttpMessageNotReadableException.
您对为什么会发生这种情况有任何见解吗?
您的 API 是否处于工作状态,意味着您可以使用 Postman 之类的东西,使用您通过测试用例的所有标头来访问您的 API 吗?
谢谢!刚刚通过添加 .content 使其工作。
我看到你的代码有一个问题,我不知道你为什么这样做,但是,@RequestHeader 意味着一次 1 个键/值,更多,你需要重复它。我相信这可能是一个问题。 baeldung.com/spring-rest-http-headers
@AjeetMaurya @RequestHeader
也可以使用地图,这甚至是一个记录和支持的案例。见docs.spring.io/spring-framework/docs/current/reference/html/…。请不要传播不真实的信息。以上是关于单元测试 - 使用 MockMvc 使用 @RequestHeader 和 HashMap 测试控制器的主要内容,如果未能解决你的问题,请参考以下文章
Spring 的 MockMvc 是用于单元测试还是集成测试?