Spring MVC의 처리 과정을 더 자세히 알면 이해가 쉽지 않을까 싶어 작성했습니다.

실제로는 몇 가지 단계를 더 거쳐야 합니다.

 

  1. 클라이언트(사용자)는 List라는 페이지(요청하는 View)를 요청한다.
  2. Dispatcher Servlet은 해당하는 @Controller를 찾아본다.
  3. 해당하는 @Controller를 찾으면 View로부터 받아온 데이터를 Model 객체에 추가한다.
  4. Model에 담은 데이터가 DB의 필요 여부에 따라 판단한다.
    1. Model에 담은 데이터가 DB를 필요로 하지 않는다면 요청한 View를 찾아서 보여주며 끝이 난다. 
    2. DB를 필요로 한다면 다음 과정을 거친다.
  5. 해당 데이터를 들고 @Service로 가서 비즈니스 로직을 실행한다.
  6. DB 접근이 필요하면 @Repository에 요청한다.
  7. Repository는 DB에 CRUD 요청을 해서 DB로부터 필요한 값을 받아온다.
  8. Service는 받아온 값을 해당하는 로직을 통해 값을 반환한다.
  9. Controller는 Service로부터 받아온 값을 Model에 담은 후 해당하는 View를 찾는다.
  10. 해당하는 View를 찾으면 클라이언트가 요청한 View를 보여준다.

해당 로직에 대해 더 자세히 알고 싶다면 SpringMVC 처리 과정에 대해서 검색하면 많은 자료가 나옵니다.

@Controller부터 순서대로 작성

 

@Controller : 클라이언트로부터 전달된 데이터를 가공하기 위한 Controller이다.

@RequestMapping(@GetMapping / @PostMapping)을 통해 경로 설정을 하게 된다.

 

@Serive : Repository를 통해 DB에 데이터를 가져온 후 컨트롤러에게 전달해주는 클래스

애플리케이션의 비즈니스 로직 처리와 비즈니스와 관련된 도메인 모델의 적합성을 검증하고, 트랜잭션을 처리한다.

서비스 클래스에 @Transactional 애노테이션을 사용한다.

그 이유는 서비스에서 레포지토리의 메소드를 호출하니 레포지토리에까지 @Transactional 애노테이션이 적용되기 때문이다.

참고로 @Service는 다른 @Component와는 달리 아무런 기능을 가지고 있지 않다. 

핵심 로직이 여기 있겠구나라고 계층을 인식하는데 도움을 줄 뿐이다.

 

@Repository는 해당 클래스가 DB에 접근하는 클래스임을 명시한다.

스프링 데이터 접근 계층으로 인식하고 데이터 계층의 예외를 스프링 예외로 변환해준다.

JPA를 사용하면 보통 JpaRepository를 상속받는다.

대부분은 존재하지만 검색해보고 없다면 직접 만드는 것도 가능하다.

 

++

@Entity는 일반적인 DBMS

Spring Data JPA를 사용할 시 DB에 테이블을 생성하거나 데이터를 가공하기 위한 클래스

 

@Controller
@RequestMapping("/members") // 클래스 레벨에 작성하면 URL 출력시 기준이 된다.
@RequiredArgsConstructor // lombok
public class MemberController {

  //@RequiredArgsConstructor를 사용하면 따로 생성자를 만들지 않아도 된다.
  private final MemberSerive memberService;

  @GetMapping("/add")
  public String [원하는 메소드명](Model model) {
    model.addAttribute("[attributeName]", [attributeValue]);
    return "view페이지명";
    //templates 폴더에서 찾을 수 있는 view 페이지
    //@ModelAttribute를 사용할 수도 있다.
  }
  
    @PostMapping("/add")
  public String [원하는 메소드명](@Valid @ModelAttribute [데이터] [변수명] ,BindingResult bindingResult) {
    ...
    memberService.[호출할 메소드]([필요한 매개변수]);
    return "redirect:/"; //해당 방식을 사용하면 원하는 URL로 보낼 수 있다.
  }
  
}

-----------------------------------------
@Service
@Transactional(readOnly = true)
@RequiredArgsConstructor
public class MemberService {

  private final MemberRepository memberRepository;
  
  @Transactional
  public Long join(Member member) {
    memberRepository.save(member);
    return member.getId();
  }
}
-----------------------------------------
@Repository
@RequiredArgsConstructor
public class MemberRepository {

  private final EntityManager em;

  public void save(Member member) {
    em.persist(member);
  }
}

 

마지막으로 @Controller, @Service, @Repository 모두 @Component에 속합니다.

 

더 자세한 내용이 궁금하다면 @Component를 검색해보는 것을 추천드립니다.

 

추가적으로 스프링 웹 계층이 어떻게 되어 있는지 알면 조금은 더 이해가 되지 않을까 싶어서 작성합니다.

 

계층은 어떤 게 있는지, 각 계층에는 뭐가 있는지, 어떤 역할을 하는지 알면 이해하는 데 도움이 될 거라고 생각합니다.

 

좀 더 자세한 설명은 spring layerd architecture로 검색하는 것을 추천드립니다.

 

스프링의 3 계층

Presentation Layer(Web Layer)
Business Layer(Service Layer)
Data Access Layer(Repository Layer)

 

Presentation Layer

  • 웹 클라이언트의 요청 및 응답을 처리한다.
  • 사용자와의 최종 접점에 위치하여 사용자로부터 데이터를 입력받거나 요청된 데이터를 출력해 보이는 계층이다.
  • 보통 서비스 계층, 데이터 엑세스 계층에서 발생하는 예외를 처리한다.
  • @Controller 애노테이션으로 작성된 Controller 클래스가 이 계층에 속한다.
  • @RequestMapping / View도 이 계층에 포함된다.

Business Layer(Service Layer)

  • Controller Layer와 Persistence Layer를 연결하는 역할, Transaction 처리

Data Access Layer(Repository Layer)

  • ORM(MyBatis, Hibernate)를 주로 사용하는 계층
  • DAO 인터페이스와 @Repository 애노테이션을 사용하여 작성된 DAO 구현 클래스가 이 계층에 속한다.
  • DB에 Data를 CRUD하는 계층