T_era

@RequestParam과 @ModelAttribute 본문

Programing/Spring

@RequestParam과 @ModelAttribute

블스뜸 2025. 5. 7. 11:43

@RequestParam은 URL을 통해 전달되는 파라미터 값을 Controller 메서드의 파라미터에 바인딩하는 Spring MVC 어노테이션이다.
HTTP GET 메서드 요청 시 URL 뒤 ?와 함께 이름-값 쌍으로 전달되는 파라미터 접근에 주로 활용된다. URL ? 뒤 부분은 Query String, Query Parameter, Request Param으로 지칭된다.

예시 1:

@Slf4j
@Controller
public class RequestParamControllerV2 {

    @ResponseBody
    @GetMapping("/v1/request-param")
    public String requestParamV1(
                    @RequestParam("name") String userName,
                    @RequestParam("age") int userAge
    ) {
        // logic
        log.info("name={}", userName);
        log.info("age={}", userAge);
        return "success";
    }

}

@Controller + @ResponseBody: View 탐색 없이 HTTP 응답 본문에 직접 내용 작성 (@RestController와 동일 기능). @RequestParam("속성값"): URL 파라미터 이름("name", "age")을 명시하여 메서드 파라미터에 바인딩한다.

예시 2:

// GET http://localhost:8080/v2/request-param?name=sparta&age=100
@ResponseBody
@GetMapping("/v2/request-param")
public String requestParamV2(
                @RequestParam String name,
                @RequestParam int age
) {
    // logic
    log.info("name={}", name);
    log.info("age={}", age);
    return "success";
}

메서드 파라미터 변수명과 URL 파라미터 이름이 동일한 경우 @RequestParam 속성값 생략 가능하다. 변수명과 파라미터 이름을 동일하게 설정하고 @RequestParam 자체 생략도 가능하나, 코드 명확성 저하로 인해 권장하지 않는다.

required 속성:

파라미터 필수 여부 설정. API 스펙 정의 시 활용. 기본값은 true.

@RequestParam(required = true) String name, // 필수 파라미터
@RequestParam(required = false) int age    // 선택적 파라미터

null 비허용 기본 타입(int, long 등)의 경우, @RequestParam에 required = false 설정 시 예외 발생 가능하므로 래퍼 클래스(Integer, Long 등) 또는 default 속성 활용 필요.

default 속성:

파라미터 기본값 설정.

@RequestParam(required = true, defaultValue = "sparta") String name,
@RequestParam(required = false, defaultValue = "1") int age

Map 사용:

모든 파라미터를 Map 또는 MultiValueMap 형태로 조회 가능하다.

@RequestParam Map<String, String> map
@RequestParam MultiValueMap<String, String> map

@ModelAttribute

@ModelAttribute는 HTTP 요청 파라미터를 객체에 바인딩하는 또 다른 Spring MVC 어노테이션이다. HTTP POST 요청과 같이 요청 본문에 데이터가 담겨 전송될 때 (application/x-www-form-urlencoded 형식 등) 객체 자동 생성 및 데이터 바인딩에 주로 사용된다.

예시:

@Data
public class Tutor {

    private String name;
    private int age;

}

@Controller
public class ModelAttributeController {

    @ResponseBody
    @PostMapping("/v1/tutor")
    public String requestParamV1(
            @RequestParam String name,
            @RequestParam int age
    ) {
        Tutor tutor = new Tutor();
        tutor.setName(name);
        tutor.setAge(age);

        return "tutor name = " + name + " age = " + age;
    }

    @ResponseBody
    @PostMapping("/v2/tutor")
    public String modelAttributeV2(
                    @ModelAttribute Tutor tutor
    ) {

        String name = tutor.getName();
        int age = tutor.getAge();

        return "tutor name = " + name + " age = " + age;
    }

}

@Data는 Lombok 라이브러리 어노테이션으로, @Getter, @Setter, @ToString, @EqualsAndHashCode, @RequiredArgsConstructor 자동 설정. 실무에서 사용 지양되는 경우 존재. @RequestParam을 이용한 객체 생성 및 필드 값 할당 코드를 @ModelAttribute가 자동화한다.

@ModelAttribute 동작 순서:

  1. @ModelAttribute 파라미터 선언 시, Spring은 해당 타입 객체(Tutor)를 생성한다.
  2. 요청 파라미터 이름과 객체 필드 이름이 동일한 경우, 해당 필드의 Setter 메서드를 호출하여 파라미터 값을 바인딩한다
    (예: 파라미터 이름 name -> setName(value) 호출).
  3. 요청 파라미터 이름과 필드 이름은 반드시 일치해야 바인딩이 이루어진다.
  4. Setter 메서드 부재 시 필드 값 설정 불가.
  5. 요청 파라미터 값이 필드 타입과 불일치 시 (age에 문자열 전달), BindException 발생 가능. 따라서 Validation (검증) 필요.

@RequestParam 및 @ModelAttribute 생략 규칙:

메서드 파라미터에 @RequestParam 또는 @ModelAttribute 명시적 선언 없을 시, 다음과 같은 규칙에 따라 자동 매핑된다.

단순 타입(String, int, Integer 등)은 @RequestParam으로 간주한다. 나머지 객체 타입은 @ModelAttribute로 간주한다.

'Programing > Spring' 카테고리의 다른 글

HttpEntity와 더 편리한 방법  (0) 2025.05.07
HTTP Message Body (요청)  (0) 2025.05.07
Client에서 Server로 데이터 전달 방식 정리  (0) 2025.05.06
MultiValueMap  (0) 2025.05.06
MediaMapping의 속성별 차이점  (0) 2025.05.06