Baeldung - Spring `@RequestParam` Annotation

sycho·2024년 3월 30일
0

Baeldung - Spring MVC

목록 보기
4/7

Baeldung의 이 글을 정리 및 추가 정보를 넣은 글입니다.

1. Overview

  • 이전 글에서 query parameter을 추출하는데 사용되었는데 form parameter나 파일을 URL에서 추출하는 것도 가능하다.

2. A Simple Mapping

  • 간단한 사용법은 지난 글에서도 봤는데 밑과 같이 하면 id라는 query paramter을 추출해서 method의 paramter에 저장하는게 가능하다.
@GetMapping("/api/foos")
@ResponseBody
public String getFoos(@RequestParam String id) {
    return "ID: " + id;
}

3. Specifying the Request Parameter Name

  • 그러나 method의 parameter 이름이 query parameter이랑 다르게 하고 싶을 때가 있는데, 이 경우 annotation의 name element를 사용한다. 밑은 fooIdid를 추출한 값을, namename을 추출한 값을 저장한다.
@PostMapping("/api/foos")
@ResponseBody
public String addFoo(@RequestParam(name = "id") String fooId, @RequestParam String name) { 
    return "ID: " + fooId + " Name: " + name;
}
  • 참고로 valuename에 해당되어서 그냥 @RequestParam("id")를 해도 된다.

4. Optional Request Parameters

  • @RequestParam은 기본적으로 해당 parameter들이 '무조건' 필요하다고 설정을 한다. 즉 2번에서 /api/foos에 GET request를 했는데 id가 없으면 오류가 나온다. mapping을 저기로 했는데 query parameter이 없어서...(...)

  • 이런 경우를 대비해 필수로 요구하지 않도록 설정하는게 가능한데, required element를 false로 설정하면 된다.

@GetMapping("/api/foos")
@ResponseBody
public String getFoos(@RequestParam(required = false) String id) { 
    return "ID: " + id;
}
  • 이때 값은 null로 설정된다...만 5번에서 이걸 해결하는 방법을 소개하겠다.

4.1. Using Java 8 Optional

  • Java 8의 경우 최근 언어 트렌드를 따라 Optional이라는 class가 생겼다.

  • 알고있다고 가정하겠고... 이걸 사용하면 requiredfalse로 설정 안해도 문제가 없다.

@GetMapping("/api/foos")
@ResponseBody
public String getFoos(@RequestParam Optional<String> id){
    return "ID: " + id.orElseGet(() -> "not provided");
}
  • 위의 경우 default value는 not provided인 셈.

5. A Default Value for the Request Parameter

  • 앞에서 required만 false로 설정을 하면 없는 경우 null이 저장되는데, default를 사용하면 이때 사용할 기본값을 설정하는게 가능하다. 이때 default를 설정하면 required는 자동으로 false가 된다는 것도 참고
@GetMapping("/api/foos")
@ResponseBody
public String getFoos(@RequestParam(defaultValue = "test") String id) {
    return "ID: " + id;
}

6. Mapping All Parameters

  • 그런데 이러다보면 request에서 받을 수 있는 (필수, 혹은 필수가 아닌) parameter 종류가 늘어나면 늘어날수록 너저분해진다. 이름을 일일이 짓는 것도 피곤하고 말이다. 이 경우 Map<String, String>을 활용하면 된다.
@PostMapping("/api/foos")
@ResponseBody
public String updateFoos(@RequestParam Map<String,String> allParams) {
    return "Parameters are " + allParams.entrySet();
}
  • 위와 같이 하면 예를들어 http://localhost:8080/spring-mvc-basics/api/foos?name=John&age=30&city=New York와 같은 url에 POST가 오면 name, age, city가 key인 map이 이루어진다. 각각의 value는 John, 30, New York. (30String이라는 점 유의)

  • 여기서 유의해야하는게 Map<String, String>만 이 기능이 가능하다. 그냥 Map을 쓰는 경우 documentation에 따르면 @RequestParam에서 name을 지정해야하고, 이게 일치하는 경우에 그 값들이 Map형태로 parameter에 저장된다고 한다.

7. Mapping a Multi-Value Parameter

  • 아니면 List type에 @RequestParam annotation을 붙이고 request에서 해당 이름의 request parameter이 여러개의 값을 ,, 혹은 &의 구별을 통해 가지는 경우 이를 List로 변환하는 것이 가능하다. 이는 밑과 같이 한다.
@GetMapping("/api/foos")
@ResponseBody
public String getFoos(@RequestParam List<String> id) {
    return "IDs are " + id;
}
profile
안 흔하고 싶은 개발자. 관심 분야 : 임베디드/컴퓨터 시스템 및 아키텍처/웹/AI

0개의 댓글