본문 바로가기
개발/Spring

[5] 페이지 처리 controller 동작

by 민지기il 2025. 3. 6.

[1] rest 방식 controller 설계

pathvariable: /api/todo/33 : 33의 content가 불변

queryString: /list?page=3 : 오늘의 3페이지가 내일과 달라질 있음 : 다른 상황

@RestController
@Log4j2
@RequiredArgsConstructor
@RequestMapping("/api/todo")
public class TodoController {

    private final TodoService todoService;
    @GetMapping("/{tno}")
    public TodoDTO get(@PathVariable("tno") Long tno){
        return todoService.get(tno);
    }
    @GetMapping("/list")
    public PageResponseDTO<TodoDTO> list(PageRequestDTO pageRequestDTO){//페이지 사이즈, 검색 조건 등등 들어오면 dto에서 수집
        log.info("list..." + pageRequestDTO);
        return todoService.getList(pageRequestDTO);
    }
}

실행 결과 다음과 같이 나온다.

 

[2] @RestControllerAdvice

@RestControllerAdvice
public class CustomControllerAdvice {
    @ExceptionHandler(NoSuchElementException.class)
    public ResponseEntity<?> notExist(NoSuchElementException e){
        return ResponseEntity.status(HttpStatus.NOT_FOUND).body(Map.of("msg", e.getMessage()));
    }
    @ExceptionHandler(MethodArgumentNotValidException.class)
    public ResponseEntity<?> notExist(MethodArgumentNotValidException e){
        return ResponseEntity.status(HttpStatus.NOT_ACCEPTABLE).body(Map.of("msg", e.getMessage()));
    }
}

없는 목록 22에 대해 조회하면 아래처럼 뜬다.

1. @ExceptionHandler(NoSuchElementException.class): NoSuchElementException이 발생하면 자동으로 spring이 이 메서드를 실행함

2. notExist(NoSuchElementException e)
→ 발생한 예외 객체(e)가 파라미터로 전달됨.

3. ResponseEntity.status(HttpStatus.NOT_FOUND).body(...) → HTTP 상태 코드를 404 NOT FOUND로 설정하고, JSON 형식으로 응답을 반환.

4. ResponseEntity로 HTTP 상태 코드와 응답 바디를 직접 지정

 

[3] page 처리 exception

잘 못 들어가면 org.springframework.web.bind.MethodArgumentNotValidException: 오류가 뜬다.

    @ExceptionHandler(MethodArgumentNotValidException.class)
    public ResponseEntity<?> notExist(MethodArgumentNotValidException e){
        return ResponseEntity.status(HttpStatus.NOT_ACCEPTABLE).body(Map.of("msg", e.getMessage()));
    }

이렇게 생성해준다.

 

[4]  LocalDateFormatter

public class LocalDateFormatter implements Formatter<LocalDate> {
    @Override
    public LocalDate parse(String text, Locale locale) throws ParseException {
        return LocalDate.parse(text, DateTimeFormatter.ofPattern("yyyy-MM-dd"));
    }
    @Override
    public String print(LocalDate object, Locale locale) {
        return DateTimeFormatter.ofPattern("yyyy-MM-dd").format(object);
    }
}

: LocalDate를 JSON 요청과 응답으로 변환할 때 필요한 커스텀 포맷터

. parse(String text, Locale locale) → 문자열을 객체(LocalDate)로 변환

print(LocalDate object, Locale locale) → 객체(LocalDate)를 문자열로 변환

 

즉, REST API에서 요청(Request)과 응답(Response)에서 날짜를 다룰 때,

기본적으로 "2025-03-06T00:00:00" 같은 형태로 반환되는데,

이걸 "2025-03-06" 형식으로 변환하기 위해 LocalDateFormatter를 사용함

 

Servlet: Java 웹 애플리케이션에서 client의 요청을 처리하고, 응답을 생성하는 server 프로그램

즉, 웹 서버에서 HTTP 요청을 받고, 필요한 로직을 실행한 후, HTML 또는 JSON 등의 응답을 반환하는 역할을 함

@Configuration
@Log4j2
public class CustomServletConfig implements WebMvcConfigurer {
    @Override
    public void addFormatters(FormatterRegistry registry){
        log.info("--------------");
        log.info("addFormatters");
        registry.addFormatter(new LocalDateFormatter());
    }
}

[5] register 함수

    @PostMapping("/") //새로 register 된 todo가 몇 번인지 반환 -> Map으로 하기
    public Map<String, Long> register(@RequestBody TodoDTO dto) { //json 형태로 받기 위함임 -> 이 DTO로 만들어줌
        log.info("todoDTO: "+dto);
        Long tno = todoService.register(dto);
        return Map.of("TNO ", tno);
    }

@RequestBody TodoDTO dto는 클라이언트가 보낸 JSON 데이터를 TodoDTO 객체로 변환함

raw 값으로 dto 값인 title, content, LocalDate를 넣어주면

TNO 값이 반환된다.

이때 json 형태로 받기 위해  @RequestBody를 사용했고 DTO로 만들어 준다.

Map.of를 사용해서 json 형태로 반환한다.

이후  Map<String, Object>를 return 하면

return Map.of(

"TNO", tno,

"message", "Todo가 성공적으로 등록되었습니다.",

"status", "success"

); 이렇게 확장 가능함

[6] modify와 remove

    @PutMapping("/{tno}")
    public Map<String, String> modify(@PathVariable("tno") Long tno,
                                      @RequestBody TodoDTO todoDTO){
        todoDTO.setTno(tno);
        todoService.modify(todoDTO);
        return Map.of("RESULT", "SUCCESS");
    }
    @DeleteMapping("/{tno}")
    public Map<String, String> remove(@PathVariable Long tno){
        todoService.remove(tno);
        return Map.of("RESULT", "SUCCEESS");
    }

DELETE 요청: Body에 데이터를 담지 않음 -> (get: url 쿼리 파라미터, post & put: body 사용, delete: body 사용 x)

서버에서 삭제할 대상 정보를 요청 경로(URL)에서 직접 전달하기 위해 @PathVariable을 사용함.

 

'개발 > Spring' 카테고리의 다른 글

[6] 이미지 파일 업로드  (0) 2025.03.07
[6] Todo get, register, modify, remove  (0) 2025.03.07
[4] 페이지 처리하는 DTO 설계  (0) 2025.03.05
[3] DTO 설정  (0) 2025.03.04
[2] Querydsl  (0) 2025.03.04