출처 : 인프런 강의 중 스프링 입문 - 코드로 배우는 스프링 부트, 웹 MVC, DB 접근 기술
28강 중 14강까지
스프링 입문 - 코드로 배우는 스프링 부트, 웹 MVC, DB 접근 기술
회원관리예제 - 백엔드
** getter and setter 단축키(window) : Alt + Insert
** import 단축키(window) : Alt + Enter
package hello.hellospring.repository;
import hello.hellospring.domain.Member;
import java.util.*;
public class MemoryMemberRepository implements MemberRepository{
private static Map<Long, Member> store = new HashMap<>();
private static long sequence = 0L;
@Override
public Member save(Member member) {
member.setId(++sequence);
store.put(member.getId(), member);
return member;
}
@Override
public Optional<Member> findById(Long id) {
return Optional.ofNullable(store.get(id));
}
@Override
public Optional<Member> findByName(String name) {
return store.values().stream()
.filter(member -> member.getName().equals(name))
.findAny(); // 찾은것중 하나 반환, 없으면 널 반환
}
@Override
public List<Member> findAll() {
return new ArrayList<>(store.values());
// 만들어진 필드는 Map, list(반복등으로 사용이 편하기 때문에 많이 사용)로 반환하기 위해 새로운 객체를 생성해서 반환
}
}
1. 클래스 Member 에는 두개의 필드와 getter setter만 존재 (id(데이터를 구분하기 위해 시스템에서 부여하는 값(시퀀스사용)), name)
2. interface에 오버라이딩할 메소드 정의
3. DB 미결정으로 개발 진척시 interface를 구현한 클래스에 메소드를 오버라이딩합니다
package hello.hellospring.repository;
import hello.hellospring.domain.Member;
import org.junit.jupiter.api.AfterEach;
import org.junit.jupiter.api.Assertions;
import org.junit.jupiter.api.Test;
import java.util.List;
import static org.assertj.core.api.Assertions.*;
public class MemoryMemberRepositoryTest {
MemoryMemberRepository repository = new MemoryMemberRepository();
@AfterEach
public void afterEach() {
repository.clearStore();
}
@Test
public void save(){
Member member = new Member();
member.setName("Spring");
repository.save(member);
Member result = repository.findById(member.getId()).get();
Assertions.assertEquals(member, result);
}
@Test
public void findByName() {
//given
Member member1 = new Member();
member1.setName("spring1");
repository.save(member1);
Member member2 = new Member();
member2.setName("spring2");
repository.save(member2);
//when
Member result = repository.findByName("spring1").get();
//then
assertThat(result).isEqualTo(member1);
}
@Test
public void findAll() {
//given
Member member1 = new Member();
member1.setName("spring1");
repository.save(member1);
Member member2 = new Member();
member2.setName("spring2");
repository.save(member2);
//when
List<Member> result = repository.findAll();
//then
assertThat(result.size()).isEqualTo(2);
}
}
테스트코드(JUnit 사용)
Spring 프로젝트를 진행하면서 pom.xml에서 라이브러리 등을 추가하는 작업을 하면서 종종 <!--test-->로 주석처리되어있고 junit이라고 되어있는 것을 본적이 있다.
그러나 단 한번도 이게 뭐지? 하는 의문을 가져본적이 없었는데 채용공고나 개발강의 광고 등에서 TDD, 테스트코드 라는 단어가 부각되는 것을 보고 언젠가 한번 공부해봐야지 했었는데 마침 강의에서 테스트코드 작성 방법을 알려주었다.
테스트코드는 빌드시 생성된 test 폴더 하위에 같은 이름의 패키지를 만들고 작성한다.
그리고 각 메소드마다 @Test 어노테이션으로 테스트코드임을 알려주고 내가 작성한 코드가 정상적으로 돌아가는지 확인하는 코드를 작성한다. (로직을 충분히 이해해야되고 발생할수 있는 오류를 최대한 확인할수 있게 작성한다) 따라서 테스트코드 작성자가 예상하지 못한 에러는 테스트코드 작성으로 확인할수 없다는 단점이 있지만, 매번 프로그램 실행을 통한 오류확인(파라미터값이 필요한 경우 파라미터값 전달 등등 수동으로 진행)하는 것보다는 편리하다는 장점이 있다.
테스트코드는 각 메소드별로 실행할 수도 있고 클래스 전체로 실행할수도 있다.
단, 클래스로 실행할 경우 정해진 순서 없이 실행되므로 메소드 실행 후 클리어하는 작업이 필요하다.
그때 @AfterEach 어노테이션을 사용한다.
1. Assertions.assertEquals(member, result);
2. assertThat(result).isEqualTo(member1);
Assertions는 두개의 라이브러리에 존재한다.
2번의 경우 import 해두면 Assertions를 생략하고 메소드명으로 바로 사용할수 있어 1번보다 활용도가 더 높다고한다.
위 사용법은 결국 member 와 result가 같은 값을 가지고 있는지 확인하는 내용이다.
** 리팩토링 단축키(window) : Ctrl + Alt + Shift + T
>> Extract Method : 블록 설정한 내용으로 새롭게 메소드 생성
작성한 service 클래스의 테스트코드 생성하기 (단축키 ctrl + shift + t / 오른쪽마우스버튼 > go to > test > create test )
'Programming > Java \ Spring' 카테고리의 다른 글
[인프런] 스프링 입문 - 코드로 배우는 스프링 부트, 웹 MVC, DB 접근 기술(회원 관리 예제 - 웹 MVC 개발) (0) | 2021.03.30 |
---|---|
[인프런] 스프링 입문 - 코드로 배우는 스프링 부트, 웹 MVC, DB 접근 기술(스프링 빈과 의존관계) (0) | 2021.03.29 |
[인프런] 스프링 입문 - 코드로 배우는 스프링 부트, 웹 MVC, DB 접근 기술 (0) | 2021.03.29 |
[인프런] 스프링 입문 - 코드로 배우는 스프링 부트, 웹 MVC, DB 접근 기술 (0) | 2021.03.24 |
for문을 중첩하지 않고 구구단 출력하기 (0) | 2021.03.09 |