이 포스팅은 인프런 강의 중 쥬쥬님의 '쥬쥬와 함께 하루만에 시작하는 백엔드 - 스프링, 도커, AWS' 에 올라온
코드 및 사진 이미지 모두 해당 강의를 참고하였습니다.
(인프런)쥬쥬와 함께 하루만에 시작하는 백엔드 - 스프링, 도커, AWS링크
API사용이나 배포 등 전체적으로 애플리케이션이 동작하는 과정을 빠른시간 내에 학습하고 싶다는 생각에 쥬쥬님의 '쥬쥬와 함께 하루만에 시작하는 백엔드 - 스프링, 도커, AWS' 강의를 듣게 되었습니다.
이 강의는 총 4시간으로 이루어졌고
서버란 무엇인지 DB와 엔터티 만들기, 요구사항을 분석하여 맛집 리뷰 서비스 만들기, 이를 개발 및 도커와 AWS를 활용한 배포로 강의가 이루어져 있습니다.
따라서 AWS 자격증은 있지만 배포 경험이 부족하여 아쉬웠던 제가 이 강의를 선택한 가장 큰 이유입니다.
제가 이 강의를 들으며 공부했던 것을 벨로그에 적어보겠습니다.
출처: (인프런) '쥬쥬'
쥬쥬와 함께 하루만에 시작하는 백엔드 - 스프링, 도커, AWS
강의에서는 전체적으로 이런 흐름으로 진행됩니다.
기초적인 스프링 실습 및 서버에 대한 이해와 JPA 사용 실습 후
토이프로젝트를 통해 배포하게 됩니다.
서버는 클라이언트와 통신하여 필요한 데이터를 주고받을 수 있도록 해주는 것이다.
백엔드는 이러한 서버를 개발하는 것 이며 일반적으로 사용하는 통신 방식이 HTTP이다.
HTTP요청은 클라이언트가 서버에 무엇인가를 요청하는 것이며, 서버가 응답하는 것을 HTTP 응답이라 한다.
출처: (인프런) '쥬쥬'
쥬쥬와 함께 하루만에 시작하는 백엔드 - 스프링, 도커, AWS
이는 HTTP 요청과 응답의 예시이며,
출처: (인프런) '쥬쥬'
쥬쥬와 함께 하루만에 시작하는 백엔드 - 스프링, 도커, AWS
이와 같이 스프링에서는 HTTP메세지를 우리가 이해하기 쉬운 형태로 제공해준다.
@RestController
public class TestApi {
@GetMapping("/hello/world")
public String helloWorld(){
return "hello, world!";
}
}
이렇게 /hello/world 링크로 GET 요청을 보내는 API를 설계하였다. 이 요청이 잘 전달되었는지 Postman을 사용하여 확인하였다.
Postman에서 /hello/world로 요청을 보냈으며,
스프링 로그에서 확인할 수 있듯이 기본 설정에서 8080 포트로 보냈기 때문에 http://localhost:8080/hello/world를 사용해 확인하였다.
HTTP 메서드에는 여러 가지가 있지만, 그중에서 GET, POST, PUT, DELETE가 자주 사용된다.
이 메서드들을 코드로 작성해보고, 이를 Postman으로 요청하여 잘 동작하는지 확인해보았다.
@RestController
public class TestApi {
@GetMapping("/hello/world")
public String helloWorld(){
return "[GET] hello, world!";
}
@PostMapping("/hello/world")
public String postHelloWorld(){
return "[Post] Hello, world";
}
@PutMapping("/hello/world")
public String putHelloWorld() {
return "[Put] Hello, world";
}
@DeleteMapping("/hello/world")
public String deleteHelloWorld(){
return "[Delete] Hello World";
}
}
postman 캡처 이미지.
PUT 요청만 캡처하였지만, http://localhost:8080/hello/world를 사용하는 GET, POST, PUT, DELETE 요청이 모두 잘 도착했음을 확인할 수 있다.
public class TestRequest {
//Request parameter 방식
@GetMapping("test/param")
public String requestParam(
@RequestParam("name") String name,
@RequestParam("age") Integer age
){
return "Hello, Request Param, I am " + name + ", " + age;
}
}
@RequestParam ~ Integer age까지 코드를 작성하지 않고
간단한 작성만 하여 Postman에서 응답을 잘 받고 있는 것을
확인하였다.
그런 후 public String requestParam(
@RequestParam("name") String name,
@RequestParam("age") Integer age
) 이런식으로 작성 후 스프링을 실행하고,
이를 postman으로 확인하였는데
이전과 달리, Bad Request 에러가 떴다.
그 이유는 메서드 파라미터에 RequestParam이라고 정의 했으면,
이에 맞는 값을 보내주어야 메서드가 정상적으로 실행이 가능하기 때문이다.
따라서 Postman에서도 응답을 보낼 때, 파라미터에 맞는 값을 적어 보내줬더니 이번에는 Bad Ruquest가 뜨지 않고 잘 동작하는 것을 확인할 수 있었다.
즉 클라이언트나 프론트엔드와 통신을 할 때 클라이언트나 프론트엔드에서 이렇게 값으르 넣어서 서버에 API를 호출할 수 있고, 이것을 코드로 작성할 수 있다.
이번에는 Path Variable 방식으로
HTTP 요청을 보내보았다.
이전과 다르게 path라는 부분, @GetMapping("/test/path/{name}/{age}") 부분을 변수처럼 사용하는 것이다.
스프링 애플리케이션을 실행하고
Postman을 확인해 보면,
이렇게 이전엔 400 Bad Request라고 떴지만,
여기선 Not found라는 에러가 뜨는 것을 확인할 수 있다.
이 에러는 /test/path/라는 경로가 내가 실행한 스프링 애플리케이션에 없다는 의미이다.
왜냐면 pass variable 방식의 값을 받기 위해서 name과 age를 반영해 경로를 수정했기 때문이다.
따라서 postman에서
요청한 경로에 맞게
http://localhost:8080/test/path/jyujyu/20
이런식으로 경로를 수정해 주면,
결과가 잘 실행되는 것을 확인할 수 있다.
//Path Varaiable 방식
@GetMapping("/test/path/{name}/{age}")
public String requestPathVariable(
@PathVariable("name") String name,
@PathVariable("age") Integer age
){
return "Hello, Path Variable, I am " + name + ", " + age;
}
이 값을 제대로 받았는지 확인하기 위해 return을 약간 수정해준 후, postman에서 실행하면
이렇게 값이 잘 들어갔음을 확인할 수 있다.
//Request Body 방식
@PostMapping("/test/body")
public String requestBody(
@RequestBody TestRequestBody request
){
return "Hello, request body, I am " + request.name + ", " + request.age;
}
public static class TestRequestBody{
String name;
Integer age;
}
이렇게 Request Body 방식을 작성한 후,
Postman에서 Body/Raw에 들어가
jason 방식으로
{
"name": "jyujyu",
"age": 20
}
그런데 400 Not found에러는 뜨지 않았지만,
이렇게 name과 age가 null인 것을 확인할 수 있었다.
이는 스프링 규칙 중 하나로, Request Body를 사용할 때에는 생성자를 꼭 만들어주어야 한다.
//생성자를 생성한 Request Body 방식
@PostMapping("/test/body")
public String requestBody(
@RequestBody TestRequestBody request
){
return "Hello, request body, I am " + request.name + ", " + request.age;
}
public static class TestRequestBody{
String name;
Integer age;
public TestRequestBody(String name, Integer age) {
this.name = name;
this.age = age;
}
}
그러면
이렇게 성공적으로 에러도 안 뜨고, null값도 안 뜨며 정상적으로 반영된 것을 확인할 수 있다.
@RestController
public class TestResponseApi {
@GetMapping("/test/response/string")
public String stringResponse() {
return "This is String";
}
@GetMapping("/test/response/json")
public String jsonResponse(){
return "{\"name\": \"This is Json\"}";
}
}
이렇게 Response Body에서 JSON 형식의 문자열을 반환하고, Postman에서 'http://localhost:8080/test/response/json' 경로로 요청을 보내 확인해보았다.
응답으로 '{"name": "This is Json"}'이 잘 출력된 것처럼 보이지만,
헤더 부분에서 text/plain;으로 설정된 것을 확인할 수 있다.
JSON 형식의 응답이므로 application/json 형식으로 반환되어야 하지만, 현재는 텍스트 플레인 형식으로 반환되었다.
따라서 이를 application/json으로 변경해보도록 하겠다.
@RestController
public class TestResponseApi {
@GetMapping("/test/response/string")
public String stringResponse() {
return "This is String";
}
@GetMapping("/test/response/json")
public TestRequestBody jsonResponse(){
return new TestRequestBody("jyujyu", 20);
}
public static class TestRequestBody{
String name;
Integer age;
public TestRequestBody(String name, Integer age) {
this.name = name;
this.age = age;
}
public String getName() {
return name;
}
public Integer getAge() {
return age;
}
}
}
이렇게 Request Body 방식에서 사용했던 것처럼 생성자를 만들어 주고,
getter도 생성해 준다. 보통 Response Body에서는 getter도 생성해준다.
사실 이 이유가 궁금했는데 이는 챗지피티4가 잘 설명해주었다.
아무튼 다시 돌아가서 Postman에서 똑같이 send를 해보면
JSON 형식처럼 뜨는 것을 볼 수 있다.
또한 텍스트 플레인 형식이었던 것이
이렇게 application/json 형식으로 성공적으로 바뀐 것을 확인할 수 있다.