提问人:Syrious 提问时间:11/16/2023 最后编辑:Syrious 更新时间:11/16/2023 访问量:31
使用 OpenAPI 生成的接口时不会注入服务
Services don't get injected when using OpenAPI generated interface
问:
使用 openApi 生成的接口时,服务不会注入到 MockMvc 测试中。让我告诉你。
控制器
@RestController
@Slf4j
@RequiredArgsConstructor
public class MyController implements MyApi {
private final CodeService codeService;
@Override
@PutMapping("/path")
public ResponseEntity<Void> putStuff(@RequestBody @Valid final Stuff stuff) {
// do stuff
return ResponseEntity.ok().build();
}
@ExceptionHandler(MethodArgumentNotValidException.class)
private ResponseEntity<ResponseWithError> handleException(final MethodArgumentNotValidException e, HttpServletRequest request) {
log.error(e.getMessage());
final ResponseWithError body = new ResponseWithError();
body.setTimestamp(TimeUtil.getCurrentTimestampString());
body.setId(UUID.randomUUID().toString());
body.setMessage(e.getMessage());
body.setPath(request.getRequestURI());
body.code(codeService.getErrors(e.getAllErrors()));
return ResponseEntity.badRequest().body(body);
}
}
我的 Api
@Generated(value = "org.openapitools.codegen.languages.SpringCodegen", date = "2023-11-15T16:01:27.640187200+01:00[Europe/Berlin]")
@Validated
@Tag(name = "stuff", description = "handles stuff")
public interface MyApi {
default Optional<NativeWebRequest> getRequest() {
return Optional.empty();
}
/**
* PUT /stuff : creates stuff
* creates stuff
*
* @param stuff (required)
* @return OK (status code 200)
* or CREATED (status code 201)
* or UNAUTHORIZED (status code 401)
* or BAD REQUEST (status code 400)
* or INTERNAL SERVER ERROR (status code 500)
*/
@Operation(
operationId = "putStuff",
summary = "creates stuff",
description = "creates stuff",
tags = {"stuff"},
responses = {
@ApiResponse(responseCode = "200", description = "OK"),
@ApiResponse(responseCode = "201", description = "CREATED"),
@ApiResponse(responseCode = "401", description = "UNAUTHORIZED", content = {
@Content(mediaType = "application/json", schema = @Schema(implementation = ResponseWithError.class))
}),
@ApiResponse(responseCode = "400", description = "BAD REQUEST", content = {
@Content(mediaType = "application/json", schema = @Schema(implementation = ResponseWithError.class))
}),
@ApiResponse(responseCode = "500", description = "INTERNAL SERVER ERROR", content = {
@Content(mediaType = "application/json", schema = @Schema(implementation = ResponseWithError.class))
})
},
security = {
@SecurityRequirement(name = "bearerAuth")
}
)
@RequestMapping(
method = RequestMethod.PUT,
value = "/path",
produces = {"application/json"},
consumes = {"application/json"}
)
default ResponseEntity<Void> putStuff(
@Parameter(name = "stuff", description = "", required = true) @Valid @RequestBody Stuff stuff
) {
return new ResponseEntity<>(HttpStatus.NOT_IMPLEMENTED);
}
}
测试
@WebMvcTest(controllers = {MyController.class}, excludeAutoConfiguration = {SecurityAutoConfiguration.class})
class MyControllerTest {
@Autowired
private MockMvc mvc;
@MockBean
private CodeService codeService;
@Test
void invalidRequest() throws Exception {
// @GIVEN
final Stuff stuff = new Stuff();
stuff.setThings("");
final String body = new ObjectMapper().writeValueAsString(stuff);
given(codeService.getErrors(anyList())).willReturn(MY_VALIDATION_ERROR);
// @WHEN
mvc.perform(MockMvcRequestBuilders.put("/path")
.contentType("application/json")
.content(body));
// @THEN
// Assertions
}
}
- 我正在使用Spring-Boot 2.7.12
- CodeService 带有 @Component 注释
- MyApi 是 OpenAPI 生成的接口
执行测试时,它会触发异常并运行到处理程序中。一切都很好,直到它撞到线.不知何故没有被注入,但是 - 这是我不担心的事情 - 当我不使用生成的接口 MyApi 时,codeService 会被注入并且测试按应有的方式运行。body.code(codeService.getErrors(e.getAllErrors()));
codeService
有人可以解释一下,为什么当我使用 MyApi 接口时服务没有被注入?有没有办法让测试使用生成的 api?
编辑
- 似乎是注解导致了这种行为。无论是直接注释控制器还是使用生成的接口。有人可以解释为什么吗?
@Validated
答:
0赞
Syrious
11/16/2023
#1
正如 M. Deinum 所评论的那样,我将访问器更改为 public。不,它有效!
评论
public
private
@Validated
@Validated
private