작성
·
84
0
MemberApiController의 saveMemberV2()에서 @Valid에 의해 검증 오류가 발생한 경우에도 오류에 대한 api를 내려줘야 하잖아요. 이때에도 오류가 없는 경우와 마찬가지로 CreateMemberResponse를 반환해야 하는 건가요?
검증 오류가 발생했을 때 api를 어떻게 전달해야하는지를 잘 모르겠습니다.
답변 2
0
안녕하세요. 도토리님, 공식 서포터즈 코즈위버입니다.
많은 경우 ResultMessage 같은 객체를 작성하여 클라이언트가 항상 일관된 구조의 응답을 받을 수 있도록 제어합니다. 가령 아래와 같은 형태로 객체를 작성하여 두고
public class ResultMessage {
private String resultCode;
private String resultMessage;
private Object data;
}
클라이언트의 요청결과를 담고 있는 객체가 CreateMemberResponse 라면 컨트롤러영역에서 다음과 같이 응답할 수 있습니다.
public class MemberController {
public ResultMessage createMember(CreateMemberFormDto form) {
.... logic ...
CreateMemberResponse response = service.createMember(form);
return new ResultMessage("200", "회원가입 성공", response);
}
}
그러면 클라이언트에서 이 응답을 받아 resultCode 등으로 요청이 성공하였는지 실패하였는지 판단할 수 있습니다.
감사합니다.
0
안녕하세요, 인프런 AI 인턴입니다.
도토리님께서 질문하신 검증 오류 발생 시 API 응답에 관한 내용에 대해 도움을 드리겠습니다.
검증 오류가 발생했을 때 API가 올바른 에러 응답을 반환하도록 하는 방법은 여러 가지가 있습니다. 아래와 같은 방법을 활용할 수 있습니다.
전역 예외 처리(@ControllerAdvice 또는 @RestControllerAdvice) 사용:
@ControllerAdvice
또는 @RestControllerAdvice
를 사용합니다. 예외 처리 메서드를 정의하여 특정 예외가 발생했을 때 해당 메서드가 호출되도록 설정할 수 있습니다.예를 들어, MethodArgumentNotValidException
예외가 발생했을 때 이를 처리하는 예제는 아래와 같습니다.
@RestControllerAdvice
public class GlobalExceptionHandler {
@ExceptionHandler(MethodArgumentNotValidException.class)
public ResponseEntity<ErrorResponse> handleValidationExceptions(MethodArgumentNotValidException ex) {
List<String> errors = ex.getBindingResult()
.getAllErrors()
.stream()
.map(DefaultMessageSourceResolvable::getDefaultMessage)
.collect(Collectors.toList());
ErrorResponse errorResponse = new ErrorResponse("Validation failed", errors);
return new ResponseEntity<>(errorResponse, HttpStatus.BAD_REQUEST);
}
}
위 코드에서 ErrorResponse
는 오류 메시지를 담기 위한 DTO 클래스입니다.
public class ErrorResponse {
private String message;
private List<String> errors;
public ErrorResponse(String message, List<String> errors) {
this.message = message;
this.errors = errors;
}
// getters and setters
}
검증 오류가 발생한 경우 Custom Exception을 던지고 이를 처리:
public class ValidationException extends RuntimeException {
private List<String> errors;
public ValidationException(List<String> errors) {
this.errors = errors;
}
public List<String> getErrors() {
return errors;
}
}
그리고 검증 오류가 발생하는 곳에서 이 예외를 던지도록 합니다.
@PostMapping("/api/v2/members")
public ResponseEntity<?> saveMemberV2(@RequestBody @Valid CreateMemberRequest request, BindingResult result) {
if (result.hasErrors()) {
List<String> errors = result.getAllErrors()
.stream()
.map(DefaultMessageSourceResolvable::getDefaultMessage)
.collect(Collectors.toList());
throw new ValidationException(errors);
}
Member member = new Member();
member.setName(request.getName());
Long id = memberService.join(member);
return ResponseEntity.ok(new CreateMemberResponse(id));
}
이렇게 던진 예외를 @ControllerAdvice
에서 처리합니다.
@RestControllerAdvice
public class GlobalExceptionHandler {
@ExceptionHandler(ValidationException.class)
public ResponseEntity<ErrorResponse> handleValidationException(ValidationException ex) {
ErrorResponse errorResponse = new ErrorResponse("Validation failed", ex.getErrors());
return new ResponseEntity<>(errorResponse, HttpStatus.BAD_REQUEST);
}
}
위 두 방법 모두 유효성 검사 실패 시 적절한 에러 응답을 보내는 방법입니다.
유사한 질문에 대한 답변은 다음 링크에서도 확인하실 수 있습니다:
저는 질문자님의 이해를 돕고자 지식공유자님의 기존 답변을 참고하여 유사한 답변 링크를 추천해드리고 있습니다.
현재 베타 기능으로 답변이 만족스럽지 않을 수 있는 점 양해 부탁드립니다. 🙏
추가적으로 궁금한 점이 있으시면, 이어서 질문해 주세요. 곧 지식공유자께서 답변해 주실 것입니다.