해당 스프링 부트 프로젝트는 인텔리제이로 진행한다.
젯브레인의 툴박스를 통해 여러 IDE를 관리하고, IntelliJ도 설치한다.
인텔리제이를 통해 git과 연동도 가능하다.
.gitignore 파일을 통해 원하지 않는 파일들은 add하지 않고 나머지는 자동으로 add 하도록 설정했다.
[Ctrl + K]를 통해 커밋 메세지를 작성한 후 Commit 한다.
[Ctrl + Shift + K] 단축키로 Push까지 하면 내 Repository에 성공적으로 반영된다.
단위 테스트는 TDD와 다르다
TDD란 테스트가 주도하는 개발로, 실패하는 테스트 코드를 먼저 작성한 후 테스트를 통과하도록 코드를 작성하고,
리팩토링하는 사이클로 개발한다.
반면 단위 테스트는 기능 단위의 테스트를 작성하는 것 자체이다. TDD처럼 테스트 코드를 먼저 작성하거나, 리팩토링을 해야하지도 않다.
단위 테스트 코드의 이점
- 개발단계 초기에 문제를 발견하게 도와준다.
- 나중에 코드를 리팩토링하거나 라이브러리 업그레이드 등에서 기존 기능이 잘 작동하는지 확인할 수 있다.
- 기능에 대한 불확실성을 감소시킬 수 있다.
- 시스템에 대한 실제 문서를 제공한다. 즉 단위 테스트 자체가 문서이다.
단위 테스트를 작성하지 않는다면 코드를 작성하고, 매번 톰캣을 다시 실행하여, 결과를 System.out.print()로 눈으로 검증해야 한다. 톰캣을 다시 실행하는 것 자체에서 시간이 많이 소요된다.
반면에 테스트 코드는 사람이 눈으로 검증하는 것이 아닌 자동 검증이 가능하다.
또한 개발자가 만든 기능을 안전하게 보호해준다.
Java에서는 JUnit이라는 테스트 프레임워크를 사용해서 테스트 코드 작성을 돕는다.
패키지명을 작성할 때 일반적으로 웹 사이트 주소의 역순으로 한다.
ex) admin.spring.com이라는 사이트라면 패키지는 com.spring.admin으로 하면 된다.
@SpringBootApplication : 스프링 부트의 자동 설정, Bean 읽기와 생성을 모두 자동으로 생성한다. 그리고 이 어노테이션이 있는 위치부터 설정을 읽어가기 때문에 이 클래스는 프로젝트의 최상단에 위치해야한다.
해당 프로젝트에서 이 클래스는 main.java.com.dal.book.springboot.web에 위치한다.
@SpringBootApplication
public class Application {
public static void main(String[] args){
SpringApplication.run(Application.class, args);
}
}
SpringApplication.run()으로 인해 내장 WAS가 실행된다. 내장 WAS란 외부에 별도로 WAS를 두지 않고 애플리케이션을 실행할 때 내부에서 WAS를 실행하는 것을 말한다. 따라서 항상 서버에 톰캣을 설치할 필요가 없게 되고, 스프링 부트로 만들어진 Jar 파일로 실행하면 된다.
내장 WAS를 사용하는 것이 성능 저하 문제가 있지 않을까 걱정했지만, 오히려 사용하는 것을 권장하고, 대형 트래픽의 회사에서도 내장 WAS를 사용한다고 한다. 내장 WAS의 장점은 언제 어디서나 같은 환경에서 스프링 부트를 배포할 수 있다는 것이다.
간단한 Test Code 작성하기
@RestController
public class HelloController {
@GetMapping("/hello")
public String hello(){
return "hello";
}
}
@RestController : 컨트롤러를 JSON을 반환하는 컨트롤러로 만들어 준다.
@GetMapping : Http의 get 요청을 받을 수 있다.
@RunWith(SpringRunner.class)
@WebMvcTest(controllers = HelloController.class)
public class HomeControllerTest {
@Autowired
private MockMvc mvc;
@Test
public void hello가_리턴된다() throws Exception{
String hello = "hello";
mvc.perform(get("/hello"))
.andExpect(status().isOk())
.andExpect(content().string(hello));
}
}
@RunWith : JUnit에 내장된 실행자 외에 다른 실행자를 실행한다. 여기서는 SpringRunner라는 스프링 실행자를 사용한다.
@WebMvcTest : Web에 집중할 수 있는 어노테이션이다. 선언할 시 @Controller는 사용 가능하나, @Service, @Repository, @Component 등은 사용할 수 없다.
MockMvc mvc : 웹 API를 테스트할 때 사용한다. MVC테스트의 시작점이다.
mvc.perform(get("/hello")) : MockMvc를 통해 /hello 주소로 GET요청을 보낸다. 체이닝을 통해 여러 기능을 검증할 수 있다.
.andExpect(status().isOk()) : perform의 결과를 검증한다. 즉 hello로 요청이 갔을 때 Status를 검증한다.
.andExpect(content().string(hello)) : 응답 본문의 내용을 검증한다. "hello"를 리턴하기 때문에 이 값이 맞는지 검증한다.
롬복
롬복이란 자바를 개발할 때 자주 사용하는 Getter, Setter, Constructor, toString 등을 어노테이션으로 자동 생성해주는 필수 라이브러리이다.
build.gradle에 compile('org.projectlombok:lombok')을 추가해준 후 플러그인에서 lombok을 설치해서 사용할 수 있다.
helloResponseDto를 생성해서 코드를 롬복으로 전환해보자.
@Getter
@RequiredArgsConstructor
public class HelloResponseDto {
private final String name;
private final int amount;
}
@Getter : 선언된 모든 필드의 get 메소드를 작성해준다. 즉 name과 amount의 get 메소드 생성
@RequiredArgsConstructor : final 필드가 포함된 생성자를 생성해준다.
즉 public HelloResponseDto(String name, int amount) { ~ }를 생성해준다.
public class HelloResponseDtoTest {
@Test
public void 롬복_기능_테스트(){
//given
String name = "test";
int amount = 1000;
//when
HelloResponseDto dto = new HelloResponseDto(name,amount);
//then
assertThat(dto.getName()).isEqualTo(name);
assertThat(dto.getAmount()).isEqualTo(amount);
}
}
@assertThat : 테스트 검증 라이브러리의 검증 메소드이다. 검증하고 싶은 대상을 인자로 받아서 체이닝을 통해 검증한다.
isEqualTo() : 값이 같은지를 검증한다.
이제 helloController와 helloControllerTest에 dto를 사용하는 코드를 추가한다.
@RunWith(SpringRunner.class)
@WebMvcTest(controllers = HelloController.class)
public class HomeControllerTest {
@Autowired
private MockMvc mvc;
@Test
public void hello가_리턴된다() throws Exception{
String hello = "hello";
mvc.perform(get("/hello"))
.andExpect(status().isOk())
.andExpect(content().string(hello));
}
@Test
public void helloDto가_리턴된다() throws Exception{
String name="hello";
int amount = 1000;
mvc.perform(
get("/hello/dto")
.param("name",name)
.param("amount",String.valueOf(amount))
)
.andExpect(status().isOk())
.andExpect(jsonPath("$.name", is(name)))
.andExpect(jsonPath("$.amount", is(amount)));
}
}
param : API 테스트를 할 때 사용될 요청 파라미터를 설정한다. 단 값은 String만 허용되므로 문자열로 모두 변환해야 한다.
jsonPath : JSON 응답값을 필드별로 검증한다. $를 기준으로 필드명을 명시한다.
즉 ~/hello/dto로 get 요청이 오면 파라미터 name과 amount를 검증한다.
'프로그래밍 이론 & 책 > 스프링 부트와 AWS로 혼자 구현하는 웹 서비스' 카테고리의 다른 글
[Spring Boot] Mustache (0) | 2020.04.30 |
---|---|
[Spring Boot] JPA (0) | 2020.04.29 |