[Springboot] @RequestParam, @PathVariable의 차이점과 쓰임

지영·2024년 9월 30일
0

백엔드개발자

목록 보기
11/11

요즘 주식 많이 하시죠? 개인 플젝을 하고 싶다는 생각으로 "어떤 주제로 프로젝트를 해볼까.."하는 생각 중에 주식을 주제로 프로젝트를 하고 있습니다. (👉궁금하시다면 여기로)(https://github.com/jiyoungzero/stock-dividend-project)
덕분에 스프링으로 오랜만에 개발하는 중인데, 그냥 지나갔던 어노테이션의 의미를 깊게 들어다보게 되었습니다,
그 중 스프링 공부 초반에 제가 헷갈려했던 @RequestParam, @PathVariable에 대해서 알아보겠습니다.

RequestParam과 PathVariable의 공통점은 무엇이길래 헷갈릴까?

알고보면 굉장히 쓰임이 다른데 처음에 헷갈린다고 생각하는 이유는 둘 다 URL에서 값을 가져온다는 점입니다. 즉 HTTP 요청에서 데이터를 추출하고 사용하고자 할 때 쓰는 어노테이션입니다.

또한 Springboot 공식문서에서는 매개변수 바인딩을 위한 어노테이션이라고 소개합니다. 둘 다 클라이언트가 요청한 데이터를 컨트롤러에서 쓰는 메서드 매개변수와 바인딩하는데 사용한다는 것입니다.

이렇게 보면 둘 다 비슷한 쓰임새 같지만 하나하나 알아보면 많은 곳에서 차이점을 가집니다.

1. RequestParam

Springboot 공식문서 @RequestParam : https://docs.spring.io/spring-framework/reference/web/webmvc/mvc-controller/ann-methods/requestparam.html

제가 개발했던 프로젝트 컨트롤러 메서드를 예시로 들어보겠습니다.

 @GetMapping("autocomplete")
    public ResponseEntity<?> autocompleteCompany(@RequestParam String keyword) {
        var result = this.companyService.getCompanyNamesByKeyword(keyword);
        return ResponseEntity.ok(result);
    }

어느 서비스에나 찾아볼 수 있는 자동완성 컨트롤러입니다. 클라이언트의 검색어를 받아 해당 검색어를 가진 회사를 return해주는 메서드입니다. 즉 /autocomplete?keyword=전자와 같은 요청이 들어오면 해당 쿼리 파라미터를 받아 메서드 내에서 데이터를 처리하는 것입니다.

기본적으로 해당 어노테이션을 쓰면 매개변수가 필수가 됩니다. 만약 선택사항으로 쓰고 싶다면 required = false를 명시하면 됩니다. (이 때 java.util.Optional를 이용하면 null값 처리를 안전하게 처리할 수 있고, orElse(), orElseThrow()같은 처리를 쉽게 할 수 있겠죠? 실제로 공식문서에서도 추천하는 방식입니다.)

위의 예시보다 더 간단한 것들은

@GetMapping("/search")
public String search(@RequestParam String query) {
    return "Search results for: " + query;
}

등이 될 수 있습니다. 각각의 상황에 맞춰서 url파라미터 값을 받아오고 데이터를 처리할 수 있도록 하면 됩니다.


2. PathVariable

Springboot 공식문서 @PathVariable : https://docs.spring.io/spring-framework/docs/current/javadoc-api/org/springframework/web/bind/annotation/PathVariable.html

PathVariable은 RequestParam과 달리 PostMapping에서도 사용가능한 어노테이션입니다.
왜냐하면 RequestParam은 쿼리 파라미터에서만 값을 가져올 수 있지만, PathVariable은 url경로에서 값을 가져올 수 있습니다. 당연히 url경로의 값을 가져오다보니 required=false와 같은 선택사항 옵션은 주어지지 않는다는 차이점도 존재합니다.

그래서 주로 ReqeustParam은 검색, 필터링과 같은 옵션을 전달하는 용도이고, PathVariable은 url에 기재된 리소스를 식별하거나 요청할 때도 사용합니다, 즉 GetMapping뿐만 아니라 PostMapping에서도 사용가능한 어노테이션인거죠!

아래 GetMapping 예시를 보겠습니다. url에 기재되는 companyName을 String타입으로 받고 있습니다.

  @GetMapping("/dividend/{companyName}")
  public ResponseEntity<?> searchFinance(@PathVariable String companyName) {
        var result = this.financeService.getDividendByCompanyName(companyName);
        return ResponseEntity.ok(result);
    }

간단한 PostMapping 예시는 아래와 같을 수 있습니다. /users/{userId}/posts 경로로 POST 요청을 보냅니다. 여기서 {userId}는 특정 사용자의 ID를 의미합니다.

@RestController
@RequestMapping("/users")
public class UserController {

    private final PostService postService;

    public UserController(PostService postService) {
        this.postService = postService;
    }

    @PostMapping("/{userId}/posts")
    public ResponseEntity<Post> createPost(@PathVariable String userId, @RequestBody Post newPost) {
        newPost.setUserId(userId); // 포스트에 사용자 ID 설정
        Post createdPost = postService.save(newPost);
        return ResponseEntity.status(HttpStatus.CREATED).body(createdPost);
    }
}

그래서 위의 예시로도 보이시겠지만 . @PathVariable과 @RequestBody의 조합은 클라이언트가 특정 사용자와 관련된 데이터를 처리할 때 유용합니다.

✔️ 이제 이 사진도 이해할 수 있게 되었습니다!

해당 사진을 보면 url경로인 곳에는 @PathValuable이 붙었고 ?뒤에 오는 쿼리파라미터에는 @RequestParam이 처리합니다.

이제는 헷갈리지 않고 잘 사용할 수 있을 것 같습니다 :)

profile
꾸준함의 힘을 아는 개발자📍

0개의 댓글