Ian's Archive 🏃🏻

thumbnail
Spring Request Annotation을 정리해보자
Spring
2024.12.16.

1. @RequestParam

copyButtonText
    @GetMapping("/")
    public String listBoard(@RequestParam(value = "page", defaultValue = "1") int page1,
                            @RequestParam(defaultValue = "10") int size,
                            Model model) {
        // 게시글 데이터와 페이징 정보 가져오기
        Page<PostVO> boardPage = postService.getPosts(page1, size);

        // Model에 데이터 추가
        model.addAttribute("boardPage", boardPage);

        return "list"; // list.jsp 반환
    }

요청 URL : http://localhost:8080/?page=2&size=10

  • @RequestParam : 파라미터 이름으로 바인딩
  • 원래는 변수명을 작성해야 하지만 파라미터 이름과 변수이름이 같으면 위의 size같이 생략 가능

스프링 부트 3.2부터 파라미터 인식 문제

스프링 부트 3.2부터 자바 컴파일러에 -parameters 옵션을 넣어줘야 어노테이션에 적는 이름을 생략이 가능하다.

주로 @RequestParam, @PathVariable어노테이션에서 문제가 발생
(IllegalArgumentException 에러)

해결 방안으로는 어노테이션에 이름을 생략하지 않고 항상 이름을 넣어준다.

  • @RequestParam(“page”) int page

추가로 파라미터 필수 여부를 설정하는 required 와 기본 값을 적용할 수 있게 도와주는 defaultValue속성이 있다
(required 속성은 기본값이 true)

2. @PathVariable

copyButtonText
    @GetMapping("/delete/{id}")
    // public String deletePost(@PathVariable("id") int id) {
    public String deletePost(@PathVariable int id) {
        // 해당 게시글을 삭제
        postService.deletePost(id);

        // 삭제 후 목록 페이지로 리디렉션
        return "redirect:/";  // 리다이렉트가 정상적으로 작동합니다.
    }

요청 URL : http://localhost:8080/delete/3

URI에서 식별자 값을 받아올 때 사용

리소스 경로 내 변수 사용이 가능하다.

@PathVariable의 이름이 파라미터 이름과 같으면 생략 가능

3. @ModelAttribute

copyButtonText
// vo
@Getter
@Setter
public class ListVO {
    private int page;
    private int size;
}

// controller
@Controller
@RequiredArgsConstructor
public class HomeController {
    ...

    @GetMapping("/")
    public String listBoard(@ModelAttribute ListVO listVO,
                            Model model) {
        // 게시글 데이터와 페이징 정보 가져오기
        Page<PostVO> boardPage = postService.getPosts(listVO.getPage(), listVO.getSize());

        // Model에 데이터 추가
        model.addAttribute("boardPage", boardPage);

        return "list"; // list.jsp 반환
    }

    ...
}

바인딩 받을 객체 앞에 @ModelAttribute어노테이션을 적어주면 알아서 바인딩 되어 값이 들어간다.

실행과정은 다음과 같다.

  1. listVO 객체 생성
  2. 요청 파라미터 이름으로 listVO객체의 프로퍼티를 찾는다.
  3. 해당 프로퍼티에서 setter를 호출해 파라미터 값을 바인딩한다.

Form데이터를 받아올 때 RequestParam을 사용해도 되지만 @ModelAttribute를 사용하면 바인딩 된 값이 들어간다.
=> Query String 형태 혹은 요청 본문에 삽입되는 Form 형태의 데이터를 처리

4. @RequestBody

copyButtonText
// VO
@Getter @Setter
public class PostWriteVO {
    private List<Integer> fileIds;  // 파일 ID 목록
    private PostVO post;
}

// Controller
@RestController
@RequiredArgsConstructor
public class PostController {
    ...

    @PostMapping(value = "/writeBoard", consumes = "application/json")
    public Map<String, String> submitPost(@RequestBody PostWriteVO postWriteVO) {
        // 받은 데이터를 로그에 출력
        postService.insertPost(postWriteVO);

        // 리다이렉트 URL을 JSON 형식으로 반환
        Map<String, String> response = new HashMap<>();
        response.put("redirectUrl", "/");  // 게시글 목록 페이지 URL
        return response;
    }
    ...
}

요청 URL : http://localhost:8080/writeBoard

JSON형태의 body값을 전송해 줄 수 있다.

@RequestBody를 사용하면 요청 본문의 JSON, XML, Text 등의 데이터가

적합한 HttpMessageConverter를 통해 파싱되어 Java 객체로 변환 된다.

5. @RequestHeader

copyButtonText
    @GetMapping("/detail")
    public String detail(@RequestParam("id") int id,
                         @RequestHeader MultiValueMap<String, String> headers,
                         @RequestHeader("host") String host,
                         @CookieValue(value="myCookie", required = false) String cookie,
                         Model model) {
        ...

        return "detail";
    }

Header값을 가져오기 위해선 @RequestHeader를 사용한다.

추가로 Cookie값을 사용하기 위해선 @CookieValue를 사용한다.


6. 조합해서 사용

copyButtonText
    @PostMapping(value = "/editBoard/{id}", consumes = "application/json")
    public Map<String, String> updatePost(@PathVariable("id") int id, @RequestBody PostWriteVO postWriteVO) {
        // 수정된 게시글 정보를 처리
        postService.updatePost(id, postWriteVO);

        // 리다이렉트 URL을 JSON 형식으로 반환
        Map<String, String> response = new HashMap<>();
        response.put("redirectUrl", "/");  // 수정 후 게시글 목록 페이지로 리다이렉트
        return response;
    }

Reference

스프링 MVC 1편 - 백엔드 웹 개발 핵심 기술 - 김영한


Thank You for Visiting My Blog, I hope you have an amazing day 😆
© 2023 Ian, Powered By Gatsby.