2022-06-23([Spring MVC] API 계층)

이상수·2022년 6월 23일
0

TIL_Spring MVC

목록 보기
1/11
post-thumbnail
  1. 시작하게 된 계기 및 다짐 😮
  • 이번 코드스테이츠의 백엔드 엔지니어링 개발자 부트캠프에 참여하게 되면서 현직개발자 분들의 빠른 성장을 위한 조언 중 자신만의 블로그를 이용하여 배운 것 들을 정리하는게 많은 도움이 된다 하여 시작하게 되었다.

    • 그 날 배웠던 것을 길지 않아도 좋으니 정리하며 복습하는 습관 기르기
    • 주말에 다음주에 배울 내용들을 예습
    • 코딩 문제와 java코드들은 꾸준히 학습
    • 자료구조를 이용한 알고리즘 문제 해결 학습
  1. 학습 목표 😮
목표결과
API 엔드 포인트인 Controller의 구성 요소를 이해O
실제 동작하는 Controller의 기본 기능을 구현O
Spring MVC의 이해와 해당 동작방식과 구성요소를 이해O
실습 - Controller 구현O
  1. 정리

Spring MVC


1. Spring MVC란? 
 - Spring webmvc
 - 웹 계층을 담당하는 모듈 중, 서블릿(Servlet) API를 기반으로 클라이언트 처리하는 모듈 
 - [클라이언트 요청을 편리하게 처리해주는 프레임워크]

2. Model(MVC)
 - 클라이언트의 요청을 처리한 결과 데이터를 Model이라한다.

3. View
 - Model 데이터를 이용해 웹 브라우저 같은 클라이언트 화면에 보여지는 리소스를 제공하는 역할

[View - 기술]
 1). HTML 페이지 출력
  - HTML페이지를 직접 렌더링해서 클라에 전송
  - HTML태그로 구성된 페이지에 Model 데이터를 채워 넣은 후, 최종적이 HTML 페이지 클라에 전송
  - FreeMaker, Thymeleaf, JST+TSTL, Tiles등

 2). PDF,Excel 문서 형태로 출력
  - Model데이터를 문서로 만들어 클라에 전송
  - 문서 내에서 데이터가 동적으로 변경되어야 하는 경우 사용

 3). ★XML,JSON 등 특정 형식 포맷으로 변환
  - Model 데이터를 특정 프로토콜 형태로 변환하여 클라이 전송, 데이터만 전송
  - 프론트측에서 비 동기적으로 앱 만드는것이 가능, 유지보수 및 개발 용이


4. Controller
 - 클라이언트 측의 요청을 직접 받는 엔드포인트로, Model과 View의 중간에서 상호작용 역할
 - @GetMapping을 통한 클라요청 수신

5. Spring MVC 동작 흐름
 - Client가 요청 데이터 전송
→ Controller가 요청 데이터 수신 → 비즈니스 로직 처리 → Model 데이터 생성
→ Controller에게 Model 데이터 전달 → Controller가 View에게 Model 데이터 전달
→ View가 응답 데이터 생성

[Extra]
1). JSON(JavaScript Object Notation)
 - {"속성" : "값"} 형태의 데이터 형식
 - https://ko.wikipedia.org/wiki/JSON
 
2). 서비스 계층 
 - 클라이언트 요청 사항을 구체적으로 처리하는 계층
3). 비지니스 로직
 - 실제 Java코드로 구현한 것 






Spring MVC의 동작 방식과 구성요소 [# 사진]

 (1) 먼저 클라이언트가 요청을 전송하면 DispatcherServlet이라는 클래스에 요청이 전달됩니다.

 (2) DispatcherServlet은 클라이언트의 요청을 처리할 Controller에 대한 검색을 HandlerMapping 인터페이스에게  요청합니다.

 (3) HandlerMapping은 클라이언트 요청과 매핑되는 Controller 정보를 다시 DispatcherServlet에게 리턴해줍니다.
Controller 정보에는 해당 Controller안에 있는 Handler 메서드 정보를 포함하고 있습니다.
Handler 메서드는 Controller 클래스 안에 구현된 요청 처리 메서드를 의미합니다.

 (4) 요청을 처리할 Controller 클래스를 찾았으니 이제는 실제로 클라이언트 요청을 처리할 Handler 메서드를 찾아서 호출해야 합니다. DispatcherServlet은 Handler 메서드를 직접 호출하지 않고, HandlerAdpater에게 Handler 메서드 호출을 위임합니다.

 (5) HandlerAdapter는 DispatcherServlet으로부터 전달 받은 Controller 정보를 기반으로 해당 Controller의 Handler 메서드를 호출합니다.
이제 전체 처리 흐름의 반환점을 돌았습니다. 이제부터는 반대로 되돌아 갑니다. ^^

 (6) Controller의 Handler 메서드는 비즈니스 로직 처리 후 리턴 받은 Model 데이터를 HandlerAdapter에게 전달합니다.
 
 (7) HandlerAdapter는 전달받은 Model 데이터와 View 정보를 다시 DispatcherServlet에게 전달합니다.
 
 (8) DispatcherServlet은 전달 받은 View 정보를 다시 ViewResolver에게 전달해서 View 검색을 요청합니다.

 (9) ViewResolver는 View 정보에 해당하는 View를 찾아서 View를 다시 리턴해줍니다.

 (10) DispatcherServlet은 ViewResolver로부터 전달 받은 View 객체를 통해 Model 데이터를 넘겨주면서 클라이언트에게 전달할 응답 데이터 생성을 요청합니다. 

 (11) View는 응답 데이터를 생성해서 다시 DispatcherServlet에게 전달합니다.

 (12) DispatcherServlet은 View로부터 전달 받은 응답 데이터를 최종적으로 클라이언트에게 전달합니다.

[Extra]
1). DispatcherServlet의 역할
 - 애플리케이션의 가장 앞단에 배치되어 다른 구성요소들과 상호작용하면서 클라이언트의 요청을 처리하는 패턴을 Front Controller Pattern이라고 합니다.

2). Handler 용어의 의미 
 -  Controller클래스의 @GetMapping, @PostMapping 같은 애너테이션이 붙은 메서드들

3). Adapter의 의미
 - 다른 프레임워크의 Handler를 Spring MVC에 통합하여 사용가능한

4). ViewResolver의 의미
 - DispatcherServlet에서 ‘이런 이름을 가진 View를 줘’ 라고 요청하면 DispatcherServlet에서 전달한 View 이름을 해석한 뒤 적절한 View 객체를 리턴해주는 역할을 합니다.






Controller 클래스 설계 및 구조 생성


1. 패키지 구조 생성

 1). ★기능 기반 패키지 구조[#사진]
   - 제공해야 될 리소스(Resource, 자원)
   - 패키지마다 하나의 기능을 완성하기 위한 계층별(API,서비스,데이터)클래스들을 모아 놓음
   - 각각의 패키지에 레이어 별 클래스들이 존재
   - [ex. 회원기능, 커피기능]

 2). 계층 기반 패키지 구조[#사진]
   - 패키지를 각 하나의 계층으로 보고 클래스들을 묶어서 관리하는 구조
   - API(controller,dto),비지니스(model,service), 데이터 엑세스(repository) 계층으로 나누어 

2. 엔트리포인트(EntryPoint)클래스 작성
 - main() 메서드가 포함된 애플리케이션의 엔트리포인트 작성 시작

[엔트리포인트 알아야할 기능(코드)]
1). @SpringBootApplication
 - 자동 구성을 활성화
 - @Component가 붙은 클래스 검색 후, Spring Bean으로 등록
 - @Configuration이 붙은 클래스를 찾아주고, Spring Bean으로 등록

2). SpringApplication.run(Section3Week1Application.class, args);
 - Spring 애플리케이션을 부트스트랩하고, 실행하는 역할을 합니다.
 - 부트스트랩(Bootstrap) : 애플리케이션이 실행되기 전에 여러가지 설정 작업을 수행하여 실행 가능한 애플리케이션으로 만드는 단계

3. 커피 주문 애플리케이션의 Controller 구조 작성

[Controller_애너테이션]
1). @RestController
 - Spring MVC에서 REST API의 리소스(자원)을 처리하기 위한 API 엔드포인트로 동작함을 의미
 - 애플리케이션 로딩 시, Spring Bean으로 등록

2). @RequestMapping
 - 클라이언트 요청과 클라이언트 요청을 처리하는 핸들러 메서드를 매핑해주는 역할
 - Controller클래스 레벨에 추가하여 클래스 전체에 사용되는 공통(URL)을 설정


[Extra]
1). REST API URI 작성규칙
 - https://itvillage.tistory.com/35

2). @SpringBootApplication의 역할
 - https://itvillage.tistory.com/36

3). Spring boot의 부트스트랩
 - https://itvillage.tistory.com/37






핸들러 메서드(Handler Method)


 1. 애너테이션 
 1). @RestController
 - Spring MVC에서는 특정 클래스에 @RestController 를 추가하면 해당 클래스가 REST API의 리소스(자원, Resource)를 처리하기 위한 API 엔드포인트로 동작함을 정의합니다.
 - 또한 @RestController 가 추가된 클래스는 애플리케이션 로딩 시, Spring Bean으로 등록해줍니다.

 2). @RequestMapping
 - @RequestMapping 은 클라이언트의 요청과 클라이언트 요청을 처리하는 핸들러 메서드(Handler Method)를 매핑해주는 역할을 합니다.
 - @RequestMapping 은 Controller 클래스 레벨에 추가하여 클래스 전체에 사용되는 공통 URL(Base URL) 설정을 합니다.
 - produces 애트리뷰트(Attribute)는 응답 데이터를 어떤 미디어 타입으로 클라이언트에게 전송할 지를 설정합니다.
    여기서는 JSON 형식의 데이터를 응답 데이터로 전송하겠다는 의미로 MediaType.APPLICATION_JSON_VALUE 값을 설정

 3). @postMapping
 - @PostMapping 은 클라이언트의 요청 데이터(request body)를 서버에 생성할 때 사용하는 애너테이션이며,
    클라이언트 쪽에서 요청 전송 시, HTTP Method 타입을 동일하게 맞춰주어야 합니다.

 4). @GetMapping
  - 클라이언트가 서버에 리소스를 조회할 때 사용하는 애너테이션
  - 애너테이션의 괄호 안에는 몇 가지 애트리뷰트(Attribute), 전체 HTTP URI의 일부 지정가능
  - 이 URI는 클래스 레벨의 @RequestMapping에 설정된 URI와 @GetMapping에 설정한 URI가 합쳐진 형태
   그외, @PutMapping, @DeleteMapping 등일 있음 
   

 5). @RequestParam
  - @RequestParam은 핸들러 메서드의 파라미터 종류 중 하나
  - 주로 클라이언트 쪽에서 전송하는 요청 데이터를 쿼리 파라미터(Query Parmeter 또는 Query String), 폼 데이터(form-data), x-www-form-urlencoded 형식으로 전송하면 이를 서버 쪽에서 전달 받을 때 사용하는 애너테이션
  [ex. public ResponseEntity getMember(@RequestParam("member-id") long memberId)]

 6). @PathVariable
  - 핸들러 메서드의 파라미터
  - 괄호 안에 입력한 문자열 값은 @GetMapping("/{member-id}") 처럼 중괄호({ }) 안의 문자열과 동일
  [ex. public ResponseEntity getMember(@PathVariable("member-id") long memberId)]

[Extra]

1). 쿼리 파라미터(Query Parameter)
  - 요청 URL에서 ‘?’를 기준으로 붙는 key/value 쌍의 데이터

2). @RequestMapping
 - https://itvillage.tistory.com/40

3). Controller의 핸들러 메서드 파라미터 
 - https://itvillage.tistory.com/41

4). 미디어 타입
 - https://ko.wikipedia.org/wiki/미디어_타입
 - https://developer.mozilla.org/ko/docs/Web/HTTP/Basics_of_HTTP/MIME_Types
 - https://developer.mozilla.org/ko/docs/Web/HTTP/Basics_of_HTTP/MIME_types/Common_types

5). HTTP Method
 - https://developer.mozilla.org/ko/docs/Web/HTTP/Methods

6).  HTTP POST Method 요청 데이터 형식
 - https://developer.mozilla.org/ko/docs/Web/HTTP/Methods/POST

7). HTTP 응답 상태(Response Status)
 - https://developer.mozilla.org/ko/docs/Web/HTTP/Status






응답 데이터에 ResponseEntity 적용

1. 레거시 코드 변경

1). @RequestMapping의 produces 애트리뷰트 생략
 - Map 객체를 리턴하게 되면 내부적으로 ‘이 데이터는 JSON 형식의 응답 데이터로 변환해야 되는구나’라고
   이해하고 JSON 형식으로 자동 변환

2). 리턴 값으로 JSON 문자열을 리턴하던 부분이 ResponseEntity 객체를 리턴
 - new ResponseEntity<>(map, HttpStatus.CREATED); 처럼 ResponseEntity 객체를 생성하면서
   생성자 파라미터로 응답 데이터(map)와 HTTP 응답 상태를 함께 전달
 - ResponseEntity 객체로 응답 데이터를 래핑함으로써 조금 더 세련된 방식으로 응답 데이터를 생성(그냥 map으로 보내도됨)



[Extra]
1). ResponseEntity
 - https://itvillage.tistory.com/44






실습 - Controller 구현

실습 코드 : https://github.com/tkdtn1427/be-homework-controller-Section3_Controller-.git

1). MemberController와 CoffeeController의 수정/삭제 메서드를 구현하는 과제 였는데, 기존에 생성(Create), 읽기(Read)를 기반으로 약간의 변화를 주는 코드라 크게 어렵지 않았다.

2). 수정 같은 경우는 @PutMapping과 @PatchMapping중 어느걸 사용해야 하나 해서 찾아 봤더니 Put의 경우 자원 전체를 바꿔 해당 클래스의 모든 필드값을 주어야하고 @PatchMapping의 경우 자읜의 부분만 바꿔 일부 필드만 사용하면 되어 어떤것을 사용해도 되지만 @PatchMapping을 사용하는게 더 바람직해 보인다.

3). @PathVariable의 경우, 클라이언트의 요청 메시지의 URI의 파라미터를 받아 서버에서 사용

4). @ReqeustParam의 경우, 클라이언트의 요청 데이터(Requestbody)를 받아 이를 서버에서 처리한다.

5). ResponseEntity의 경우 개발자가 데이터와 HTTP 상태 코드를 직접 제어가능한 클래스로, 데이터와 HTTP 상태코드를 함께 전송할 수 있어 세밀한 제어가 가능하다.
      






  1. 피드백 😮
  • Spring MVC란 Spring의 웹 계층을 담당하는 모듈로, 서블릿 API를 기반으로 처리해주는 프레임워크다.
    이는 Model/View/Controller를 의미하는데,
    Model : 처리된 결과 데이터
    View : Model을 이용한 클라이언트에 제공하는 리소스
    Controller : Model 과 View의 중간에서 상호작용 역할
    의 역할을 한다.

  • 패키지의 경우 기능 기반 패키지(리소스 기반 ex. Member패키지)와 계층 기반 패키지(각 패키지를 하나의 계층으로)가 있는데, 일반적으로 기능 기반 패키지를 사용하고 이는 테스팅과 리팩토링이 용이해서 자주 사용

  • 핸들러 메서드의 경우 실제 데이터를 처리하는 클래스의 메서드를 의미한다.

  • 실제로 PostMan을 사용하여 Client-server의 구조에서 데이터를 주고 받아 보았는데, 처음 접해보는 코드들이라 난해하고 코드,애너테이션들이 어떤 기능들을 사용하는지 익숙해지기 위해 꾸준히 학습해야 겠다.

  1. 앞으로 해야 될 것 😮
  • 매일 꾸준히 할 것
    • 꾸준히 velog 작성
    • Java 언어 및 Algorithm 공부(Coding-Test)
    • 틈틈히 운동 하기

  • 내일 해야 할 것
    • DTO를 이용한 HTTP 요청/응답
    • DTO 적용 실습
profile
Will be great Backend-developer

0개의 댓글