300===Dev Framework/Spring

Spring Controller 완벽 가이드 🎯

블로글러 2024. 11. 14. 12:42

안녕하세요! 오늘은 Spring Framework의 핵심 컴포넌트인 Controller에 대해 자세히 알아보겠습니다.

Controller란? 🤔

Controller는 Spring MVC에서 웹 요청을 처리하는 핵심 컴포넌트입니다. 쉽게 설명하면:

  • 사용자의 HTTP 요청을 받아서 처리하는 진입점
  • 비즈니스 로직을 호출하고 결과를 반환하는 중개자 역할
  • URL 매핑과 요청/응답 처리를 담당

Controller 종류 📚

Spring에서 제공하는 주요 Controller 어노테이션은 다음과 같습니다:

1. @Controller

@Controller
public class HomeController {
    @GetMapping("/")
    public String home() {
        return "home"; // View 이름 반환
    }
}
  • 주로 View를 반환할 때 사용
  • ViewResolver와 함께 작동하여 템플릿 엔진 활용 가능

2. @RestController

@RestController
public class UserController {
    @GetMapping("/users")
    public List<User> getUsers() {
        return userService.findAll(); // 객체를 JSON으로 자동 변환
    }
}
  • @Controller + @ResponseBody의 조합
  • REST API 개발에 최적화
  • 객체를 JSON/XML로 자동 변환하여 반환

주요 요청 매핑 어노테이션 🎯

1. @RequestMapping

@RequestMapping(value = "/users", method = RequestMethod.GET)
public List<User> getUsers() {
    return userService.findAll();
}

2. HTTP 메소드별 specialized 어노테이션

@GetMapping("/users/{id}")
@PostMapping("/users")
@PutMapping("/users/{id}")
@DeleteMapping("/users/{id}")
@PatchMapping("/users/{id}")

파라미터 바인딩 📝

1. @PathVariable

@GetMapping("/users/{id}")
public User getUser(@PathVariable Long id) {
    return userService.findById(id);
}

2. @RequestParam

@GetMapping("/users/search")
public List<User> searchUsers(@RequestParam String name) {
    return userService.findByName(name);
}

3. @RequestBody

@PostMapping("/users")
public User createUser(@RequestBody UserDto userDto) {
    return userService.create(userDto);
}

예외 처리 ⚠️

@ExceptionHandler 활용

@RestControllerAdvice
public class GlobalExceptionHandler {

    @ExceptionHandler(UserNotFoundException.class)
    public ResponseEntity<ErrorResponse> handleUserNotFound(UserNotFoundException e) {
        return ResponseEntity
                .status(HttpStatus.NOT_FOUND)
                .body(new ErrorResponse("User not found"));
    }
}

응답 처리 💫

1. ResponseEntity 활용

@GetMapping("/users/{id}")
public ResponseEntity<User> getUser(@PathVariable Long id) {
    return ResponseEntity
            .ok()
            .header("Custom-Header", "value")
            .body(userService.findById(id));
}

2. 상태 코드 지정

@ResponseStatus(HttpStatus.CREATED)
@PostMapping("/users")
public User createUser(@RequestBody UserDto userDto) {
    return userService.create(userDto);
}

실전 예제 💡

@RestController
@RequestMapping("/api/v1")
public class UserController {

    private final UserService userService;

    @GetMapping("/users")
    public ResponseEntity<List<User>> getUsers(
            @RequestParam(required = false) String name,
            @RequestParam(defaultValue = "0") int page) {

        return ResponseEntity.ok(userService.findUsers(name, page));
    }

    @PostMapping("/users")
    public ResponseEntity<User> createUser(
            @Valid @RequestBody UserDto userDto) {

        User user = userService.create(userDto);
        return ResponseEntity
                .created(URI.create("/api/v1/users/" + user.getId()))
                .body(user);
    }
}

주의사항 ⚠️

  1. Controller는 가능한 얇게 유지

    • 비즈니스 로직은 Service 계층으로 위임
    • 단순 파라미터 검증과 응답 변환에 집중
  2. 적절한 HTTP 상태 코드 사용

    • 200: 성공
    • 201: 리소스 생성
    • 400: 잘못된 요청
    • 404: 리소스 없음
    • 500: 서버 에러
  3. API 버전 관리

    • URL, 헤더, 미디어 타입 등을 통한 버전 관리 고려
    • 예: /api/v1/users, /api/v2/users

마치며 🎁

Spring Controller는 웹 애플리케이션의 진입점으로서 매우 중요한 역할을 합니다. 적절한 설계와 구현을 통해 견고하고 유지보수가 쉬운 API를 만들 수 있습니다.


참고 자료:

728x90