✏️스프링 MVC (Model-View-Controller) 란?
스프링 프레임워크 의 웹 애플리케이션 개발을 위한 서브 프로젝트로, 웹 애플리케이션의 구조를 정의하고 관리하는 데 도움을 줌.
모델(Model), 뷰(View), 컨트롤러(Controller) 의 세 가지 주요 구성 요소로 웹 애플리케이션을 구성 각 구성 요소는 애플리케이션의 다른 부분을 처리하며, 이들 간의 명확한 분리로 코드의 유지보수성과 재사용성을 높임
📌 모델 (Model)
- 모델은 애플리케이션의 데이터와 비즈니스 로직을 표현.
모델은 사용자 인터페이스와 관련이 없으며, 주로 데이터베이스와의 상호작용을 처리하거나 비즈니스 로직을 수행
- 모델은 데이터와 그 데이터의 상태를 나타내며, 일반적으로 POJO(Plain Old Java Object) 클래스로 구현
public class User {
private Long id;
private String name;
private String email;
}
📌 뷰 (View)
- 뷰는 모델의 데이터를 사용자에게 표시해주는 역할을 함.
사용자 인터페이스를 구성하는 요소로, HTML, JSP, Thymeleaf 템플릿 등이 사용됨
- 뷰는 데이터를 표시하는 데 집중하며, 비즈니스 로직은 처리하지 않음
<!DOCTYPE html>
<html xmlns:th="http://www.thymeleaf.org">
<head>
<title>User Infomation</title>
</head>
<body>
<h1>User Details</h1>
<p>Name: <span th:text="${User.name}"></span>
<p>Email: <span th:text="${User.email}"></span></p>
</body>
</html>
📌 컨트롤러 (Controller)
- 컨트롤러는 사용자의 요청을 처리하고 적절한 모델과 뷰를 반환.
사용자의 입력을 받아 비즈니스 로직을 호출하고, 그 결과를 뷰에 전달하여 사용자에게 응답을 반환
- 컨트롤러는
@Controller 또는 @RestController 어노테이션을 사용하여 정의하며, 각 메서드는 특정 URL 요청을 처리
@Controller
public class UserController {
@Autowired
private UserService userService;
@GetMapping('/user/{id}")
public String getUser(@PathVariable Long id, Model model) {
User user = userService.findById(id);
model.addAttribute("user", user);
return "userView";
}
}
👉스프링 MVC 작동 원리
- 사용자 요청 : 사용자가 웹 애플리케이션에 요청을 보내면, 요청은 스프링 MVC의 디스패처 서블릿(DispatcherServlet) 으로 전달됨. 디스패처 서블릿은 모든 요청을 중앙에서 처리하는 역할을 함
- 요청 매핑 : 디스패처 서블릿은 요청 URL을 기반으로 적절한 컨트롤러를 찾아 호출. 각 컨트롤러는 요청을 처리하고, 필요한 모델을 준비
- 모델과 뷰 : 컨트롤러는 모델을 준비하고, 모델 데이터를 기반으로 어떤 뷰를 반환할지 결정. 디스패처 서블릿은 모델과 뷰 정보를 사용하여 적절한 뷰를 렌더링
- 응답 반환 : 뷰는 사용자에게 최종적으로 표시될 내용을 생성하고, 디스패처 서블릿을 통해 사용자에게 응답을 반환
👉스프링 MVC의 주요 구성 요소
- DispatcherServlet : 모든 요청을 중앙에서 처리하는 서블릿으로, 요청을 적절한 컨트롤러로 전달하고, 응답을 적절한 뷰로 렌더링 함
- HandlerMapping : 요청 URL과 컨트롤러의 매핑을 관리. 요청 URL에 맞는 컨트롤러를 찾기 위해 사용됨
- Controller : 요청을 처리하고, 모델과 뷰를 반환
- ModelAndView : 뷰 이름을 실제 뷰 구현으로 반환. JSP, Thymeleaf 등 다양한 뷰 기술을 지원
- View : 모델 데이터를 사용자에게 표시하는 역할
👉스프링 MVC의 장점
- 분리된 관심사 : 모델, 뷰, 컨트롤러가 명확히 분리되어 있어 코드의 유지보수성과 재사용성이 높음
- 유연성 : 다양한 뷰 기술과 데이터 접근 방법을 지원하며, 필요한 경우 사용자 정의 구현을 추가할 수 있음.
- 테이트 용이성 : 컨트롤러와 모델이 분리되어 있어 단위 테스트가 용이