Spring 강의/springMVC

springMVC 활용 - (8) HTTP응답

lxexjx 2022. 5. 12. 21:54

[정적 리소스, 뷰 템플릿]

 

스프링에서 응답 데이터를 받는 방법

1. 정적 리소스 예) 웹 브라우저에 정적인 HTML, css, js을 제공할 때는, 정적 리소스를 사용

2. 뷰 템플릿 사용 예) 웹 브라우저에 동적인 HTML을 제공할 때는 뷰 템플릿을 사용

3.HTTP 메시지 사용

 

 

2.<ResponseViewController> - 뷰 템플릿을 호출하는 컨트롤러

@Controller
public class ResponseViewController {

    @RequestMapping("/response-view-v1")
    public ModelAndView responseViewV1() {
        ModelAndView mav = new ModelAndView("response/hello").addObject("data", "hello!");
        return mav;
    }

//string으로 반환
//@Responsebody를 사용하면 그냥 문자로 나와버려
    @RequestMapping("/response-view-v2")
    public String responseViewV2(Model model) {
        model.addAttribute("data", "hello!!");
        return "response/hello";
    }

    /*컨트롤러 이름이랑 뷰의 논리적 이름이랑 같은거 비추*/
    @RequestMapping("/response/hello")
    public void responseViewV3(Model model) {
        model.addAttribute("data", "hello!!");
    }
}

String을 반환하는 경우 - View or HTTP 메시지 @ResponseBody 가 없으면 response/hello 로 뷰 리졸버가 실행되어서 뷰를 찾고, 렌더링 한다. @ResponseBody 가 있으면 뷰 리졸버를 실행하지 않고, HTTP 메시지 바디에 직접 response/hello 라는 문자가 입력

 

 

3. HTTP API, 메시지 바디에 직접 입력

<ResponseBodyController>

@Slf4j
@Controller
public class ResponseBodyController {

    @GetMapping("/response-body-string-v1")
    public void responseBodyV1(HttpServletResponse response) throws IOException
    {
        response.getWriter().write("ok");
    }

    /**
     * HttpEntity, ResponseEntity(Http Status 추가)
     * @return
     */
    @GetMapping("/response-body-string-v2")
    public ResponseEntity<String> responseBodyV2() {
        return new ResponseEntity<>("ok", HttpStatus.OK);
    }

    @ResponseBody
    @GetMapping("/response-body-string-v3")
    public String responseBodyV3() {
        return "ok";
    }

    @GetMapping("/response-body-json-v1")
    public ResponseEntity<HelloData> responseBodyJsonV1() {
        HelloData helloData = new HelloData();
        helloData.setUsername("userA");
        helloData.setAge(20);
        return new ResponseEntity<>(helloData, HttpStatus.OK);
    }

    @ResponseStatus(HttpStatus.OK) /*원하는 지정*/
    @ResponseBody
    @GetMapping("/response-body-json-v2")
    public HelloData responseBodyJsonV2() {
        HelloData helloData = new HelloData();
        helloData.setUsername("userA");
        helloData.setAge(20);
        return helloData;
    }
}

 

responseBodyV1

서블릿을 직접 다룰 때 처럼 HttpServletResponse 객체를 통해서 HTTP 메시지 바디에 직접 ok 응답 메시지를 전달한다. response.getWriter().write("ok")

 

 

responseBodyV2

ResponseEntity 엔티티는 HttpEntity 를 상속 받았는데, HttpEntity는 HTTP 메시지의 헤더, 바디 정보를 가지고 있다. ResponseEntity 는 여기에 더해서 HTTP 응답 코드를 설정할 수 있다

 

responseBodyV3

@ResponseBody 를 사용하면 view를 사용하지 않고, HTTP 메시지 컨버터를 통해서 HTTP 메시지를 직접 입력할 수 있다. ResponseEntity 도 동일한 방식으로 동작한다

 

 

responseBodyJsonV1

ResponseEntity 를 반환한다. HTTP 메시지 컨버터를 통해서 JSON 형식으로 변환되어서 반환된

 

 

responseBodyJsonV2

ResponseEntity 는 HTTP 응답 코드를 설정할 수 있는데, @ResponseBody 를 사용하면 이런 것을 설정하기 까다롭다. @ResponseStatus(HttpStatus.OK) 애노테이션을 사용하면 응답 코드도 설정할 수 있다. 물론 애노테이션이기 때문에 응답 코드를 동적으로 변경할 수는 없다. 프로그램 조건에 따라서 동적으로 변경하려면 ResponseEntity 를 사용

@RestController= @Controller + @ResponsrBody

 


 

 

 

[HTTP 메세지 컨버터] - HTTP API처럼 JSON 데이터를 HTTP 메시지 바디에서 직접 읽거나 쓰는 경우 HTTP 메시지 컨버터를 사용하면 편리

 

HTTP 요청: @RequestBody , HttpEntity(RequestEntity) 컨트롤러 호출전에 컨버터가 적용돼서 바디에서 꺼내서 변환후에 그 객체를 넘겨줘

HTTP 응답: @ResponseBody , HttpEntity(ResponseEntity) 

 

http메세지 컨버터는 http요청,응답 둘다에 사용. 컨버터는 양방향

1)요청 : 응답에 있는 메세지 바디를 읽어서 객체로 바꿔서 컨트롤러에 파라미터 넘겨주는 역할도하고

2)응답 : 컨트롤러에서 나오느 리턴값을 http응답 메세지에 넣는 역할도 하고

 

 


 

 

[요청 매핑 헨들러 어뎁터 구조]

ArgumentResolver를 통해서 객체가 다 나와

ArgumentResolver라는게 컨트롤러(핸들러)가 필요로 하는 다양한 파라미터의 값(객체)을 생성하고 핸들러 어뎁터가 핸들러(실제 컨트롤러)를 호출하면서  ArgumentResolver에 의해 생성도니 파라미터 값을 넘겨줌. 

한마디로 ArgumentResolver가 파라미터를 가져다 주는데 그거를 핸들러 어뎁터가 받으면 ArgumentResolver를 통해서 생성된 파라미터를 넣어주면서 핸들러 호출함.

 

ReturnValueHandler라는게 응답 값을 변환하고 처리

 

[HTTP 메시지 컨버터 위치]

컨버터는 ArgumentResolver가 사용함.  ArgumentResolver 들이 HTTP 메시지 컨버터를 사용해서 필요한 객체를 생성

 

스프링은 다음을 모두 인터페이스로 제공. 필요하면 언제든지 기능을 확장.
1) HandlerMethodArgumentResolver
2) HandlerMethodReturnValueHandler
3) HttpMessageConverter