执行请求

本节展示了如何使用 MockMvcTester 执行请求及其与 AssertJ 的集成以验证响应。 MockMvcTester 提供了一个流畅的 API 来构建请求,它重用了与 Hamcrest 支持相同的 MockHttpServletRequestBuilder,但不需要导入静态方法。返回的构建器是 AssertJ 感知的, 因此将其包装在常规的 assertThat() 工厂方法中会触发交换并提供对 MvcTestResult 专用 Assert 对象的访问。 以下是一个简单的示例,它在 /hotels/42 上执行 POST 并配置请求以指定 Accept 头: include-code::./HotelControllerTests[tag=post,indent=0] AssertJ 通常包含多个 assertThat() 语句来验证交换的不同部分。 您可以使用 .exchange() 返回一个 MvcTestResult,该结果可以在多个 assertThat 语句中使用, 而不是像上面那样只有一个语句: include-code::./HotelControllerTests[tag=post-exchange,indent=0] 您可以按照 URI 模板样式指定查询参数,如下例所示: include-code::./HotelControllerTests[tag=query-parameters,indent=0] 您还可以添加表示查询或表单参数的 Servlet 请求参数,如下例所示: include-code::./HotelControllerTests[tag=parameters,indent=0] 如果应用程序代码依赖于 Servlet 请求参数并且不明确检查查询字符串(通常是这种情况), 那么使用哪种选项都无关紧要。 但是请记住,通过 URI 模板提供的查询参数会被解码,而通过 param(…​) 方法提供的请求参数则应假定已解码。

异步

如果请求的处理是异步完成的,exchange() 会等待请求完成,以便要断言的结果实际上是不可变的。 默认超时时间是 10 秒,但可以根据请求进行控制,如下例所示:

如果您更喜欢获取原始结果并自行管理异步请求的生命周期,请使用 asyncExchange 而不是 exchange

多部分

您可以执行文件上传请求,这些请求内部使用 MockMultipartHttpServletRequest, 因此不会实际解析多部分请求。相反,您必须将其设置为类似于以下示例:

使用 Servlet 和上下文路径

在大多数情况下,最好将上下文路径和 Servlet 路径排除在请求 URI 之外。 如果必须使用完整的请求 URI 进行测试,请务必相应地设置 contextPathservletPath, 以便请求映射正常工作,如下例所示:

在前面的示例中,为每个执行的请求设置 contextPathservletPath 将会很麻烦。 相反,您可以设置默认请求属性,如下例所示:

上述属性会影响通过 mockMvc 实例执行的每个请求。 如果在给定请求上也指定了相同的属性,它将覆盖默认值。 这就是为什么默认请求中的 HTTP 方法和 URI 无关紧要的原因,因为它们必须在每个请求上指定。