📡 스프링 웹 개발 기초
1. 정적 컨텐츠
Spring Boot Features
Graceful shutdown is supported with all four embedded web servers (Jetty, Reactor Netty, Tomcat, and Undertow) and with both reactive and Servlet-based web applications. It occurs as part of closing the application context and is performed in the earliest
docs.spring.io
위 링크로 이동하면 스프링 공식 사이트에서 제공하는 정적 컨텐츠 내용이 정리되어 있다.
src/main/java/resources/static 폴더 아래 "hello-static.html"이라는 이름을 가진 파일을 하나 만들어주자.
그리고 파일은 아래 코드와 같이 작성해주자. (아주 간단한 html이다.)
그리고 서버를 실행한 뒤에 localhost:8080/hello-static.html로 들어가면 방금 만든 페이지에 들어갈 수 있다.
간단하게 원리를 알아보자.
- 웹 브라우저에서 localhost:8080/hello-static.html 을 입력하면 내장 톰캣 서버가 요청을 받아 스프링에게 넘긴다.
- 스프링은 컨트롤러에서 hello-static이 있는지 찾아본다.(컨트롤러에 우선순위를 두는 것)
- 컨트롤러가 없기 때문에 resources 아래에 static/hello-static.html을 찾는다. (다음 우선순위)
2. MVC와 템플릿 엔진
MVC란 Model, View, Controller를 뜻한다. 요즘 많이 선택되고 있는 개발 방법 중 하나이다.
이전에 만들어둔 HelloController에 아래 코드를 추가해주자.
@RequestParam()
을 통해 외부에서 파라미터를 입력받을 수 있다.
그리고 resource/templates 아래 "hello-template.html" 이름을 가진 파일을 하나 만들어주고 내용은 아래와 같이 채워주자.
타임리프의 장점 중 하나는 파일 자체의 절대 경로를 이용하여 서버없이 파일을 오픈해볼 수 있다. 이렇게 하면 hello! empty가 화면에 띄워진다.
하지만 서버를 실행시키고 템플릿 엔진으로 동작하도록 하면 hello! empty 대신 "'hello' + ${name}"이 화면에 띄워진다. 그리고 그 화면에 소스를 보면 우리가 만든 html이 아니라 "hello name" 이렇게 값이 아예 바뀐다.
템플릿 엔진으로서의 타임리프는 서버에서 받은 데이터를 바탕으로 동적으로 html로 변환한 뒤에 웹 브라우저에 띄워주는 역할을 하는 것이다.
localhost:8080/hello-mvc?name=spring을 입력해서 실행할 수 있다.
동작 과정을 알아보면 다음과 같다.
- 웹 브라우저에서 localhost:8080/hello-mvc 를 입력하면 내장 톰캣 서버가 요청을 받아 스프링에게 넘긴다.
- helloController에 매핑이 되어있는 것을 확인하고 해당 메서드를 호출한다.
- 메서드의 반환 값은 "hello-template"이고 모델에는 spring이 들어있다.
- veiwResolver(뷰를 찾아주고 템플릿 엔진에 연결시켜주는 역할)가 templates/hello-template.html을 찾아 타임리프에게 처리해달라고 넘겨준다.
- 타임리프는 렌더링하여 변환한 html을 웹 브라우저에 띄워준다.
3. API
HelloController에 다음과 같은 메서드를 추가해주자.
@ResponseBody
어노테이션은 스프링이 뷰 리졸버를 사용하지 않도록 하고 HTTP의 BODY에 문자 내용을 직접 반환하도록 한다. 때문에 웹 브라우저에서 localhost:8080/hello-string?name=spring으로 접근하면 "hello spring"을 얻을 수 있다.
앞의 메서드에서는 문자를 반환하였지만 이번에는 객체를 반환하는 예를 보자. 아래와 같은 Hello 객체를 만들어주자. 간편하게 HelloController 내부에 static class로 만들었다.
Getter와 Setter를 이용하여 프로퍼티에 접근할 수 있는데 이를 위해 인텔리제이에서 제공하는 단축키는 [ALT + INS] 다.
HelloController에 다음과 같은 메서드를 추가해주자.
앞에서 만든 메서드와의 차이점은 반환 값이 객체라는 것이다. @ResponseBody
어노테이션을 붙인 채 객체를 반환하면 스프링에서 내부적으로 JSON형태로 바꿔주는 과정을 진행하는 것이 기본이다. 때문에 위 메서드를 호출한 클라이언트나 다른 서버에서는 결과를 JSON형태로 돌려받게 된다.
동작 과정을 알아보면 다음과 같다.
- 내장 톰캣 서버에서 hello-api가 왔다고 스프링에 넘겨준다.
@ResponseBody
어노테이션을 보고 HTTP 응답에 바로 데이터를 넘기는 방식으로 동작, HttpMessageConverter가 동작(없으면 viewResolver에게 던져줌)- 메소드가 문자를 반환하는 경우 바로 데이터를 넘겨줄 수 있지만 객체를 반환하는 경우 JSON으로 변경하여 데이터를 넘겨준다.
@ResponseBody
를 사용한 경우- HTTP의 BODY에 문자 내용을 직접 반환
- viewResolver 대신 HttpMessageConverter가 동작
- 기본 문자처리 : StringHttpMessageConverter
- 기본 객체처리 : MappingJackson2HttpMessageConverter
- byte 처리 등등 기타 여러 HttpMessageConverter가 기본으로 등록되어 있음