일단 클래스를 만들었다.
@SpringBootTest는 이 테스트가 스프링 부트 상에서 돌아간 다는 것을 의미하고,
@Transactional은 해당 클래스가 트랜잭션을 만듦을 의미한다.
일단 C, R, U, D를 다 테스트해보아야 하는데,
생각해보면, 만든게 조회가 제대로 되면,
내 머리같이(?) 비어있는 데이터베이스에 데이터가 생기는 것이다.
즉, 생성은 테스트하지 말고, 그냥 생성시키는 로직을 만든 뒤, 조회를 시키면 되는 것!
그래서!
@Autowired
private MemberRepository memberRepository;
@Autowired
private EntityManager em;
@BeforeEach
public void initData(){
RegisterRequestDto registerRequestDto = RegisterRequestDto.builder()
.username("testUser")
.nickname("test")
.email("test@test.com")
.password("password")
.passwordCheck("password")
.build();
Member member = new Member(registerRequestDto);
memberRepository.save(member);
em.flush();
em.clear();
}
이렇게를 아래에 만들었다.
일단
@BeforeEach는 적힌 그대로, 각 메서드 실행 이전에 한번씩 이 기능이 동작한다는 뜻이다.
그러면 메서드 하나 동작할 때 한번, 다음꺼 동작하면 데이터가 두번 아닌가? 싶었다(내가 그랬었다)
근데 테스트 때에는, 각 테스트때 마다 데이터가 롤백된다. 그렇기에, 우리는 하나의 데이터만을 가지고 계속해서 테스트한다고 생각하면 된다. (앞으로의 설명들도 그렇게 이루어질 것이다)
일단, 엔티티가 만들어지고 저장을 해도 1차 캐시에 남아있기 때문에 em.flush(), em.clear()을 해주었다. (무슨 말일까 싶으면 여기로!)
이후, Read부터 테스트를 해보겠다.
@Test
@DisplayName("생성과 조회를 테스트")
public void createAndReadTest() throws Exception{
//given
//when
//then
assertThat(memberRepository.findByUsername("testUser").get().getNickname()).isEqualTo("test");
}
추가적인 조건이 없으므로, 그렇다면 조회하면 하나가 나올꺼고, 우리가 만든 nickname이 test인 놈이 나와야 한다.
이걸 검증해보았다.
메서드에 추가적인 코드가 없었지만, 쿼리가 아주 잘 나간다.
마찬가지로 수정과 삭제도 테스트해볼 것이다.
@Test
@DisplayName("수정시 변경감지로 쿼리가 나가고 조회해오면 변경이 반영되었는지 테스트")
public void updateTest() throws Exception{
//given
//when
memberRepository.findByUsername("testUser").get().changeNickname(new ChangeNicknameRequestDto("이건줄 몰랐지"));
em.flush();
em.clear();
//then
assertThat(memberRepository.findByUsername("testUser").get().getNickname()).isEqualTo("이건줄 몰랐지");
}
이러한 수정 로직이 있다.
em.flush, em.clear을 넣은 이유는 데이터베이스에 변경이 감지되었을 때, 이를 데이터베이스에 넣어주고, 쿼리문이 정상적으로 나가는지 보기 위해서이다.
일단 BeforeEach로 멤버가 만들어졌고,
업데이트로 수정 쿼리가 나갔으며
마지막으로 조회쿼리가 잘 나갔다.
이렇게 아무 문제가 없음을 알 수 있었다.
(참고로 Em.clear, em.flush가 없어도 update쿼리가 정상적으로 동작하는 것을 볼 수 있었다)
이렇게 update가 동작함을 보았고, 이제 delete를 보자.
여기 있는 findAll이라는 메서드를 이용할 것이다.
@Test
@DisplayName("")
public void deleteTest() throws Exception{
//given
//when
Member member = memberRepository.findByUsername("testUser").get();
//then
memberRepository.delete(member);
assertThat(memberRepository.findAll().size()).isEqualTo(0);
}
하나뿐인 데이터를 모두 지워버린다면, 데이터를 전부 가져오면 그 크기는 0일 것이다.
그걸 확인해보자.
여기에서 객체와 테이블의 차이점을 엿볼 수 있다.
우리가 java List에서 삭제를 할 때에는 클래스를 보고 삭제를 하지만,
데이터는 기본키인 id의 값을 비교해서 삭제를 하는 것을 알 수 있다.
이렇게 C, R, U, D를 만들어보았다.
이제, 조금 더 다양한 방식의 멤버 리포지토리 기능들을 만들어내볼 것이다. (쉽게말하면 고급진거)
이걸 위해서 나중에 의존성을 주입하고, 여러 방황을 해야한다.
글쓰는 지금 순간에 일단 내 머리속엔 그래도 다 들어와있는 것 같다.
...
..
.
여러분 차례 겠지??
이제부턴 리포지토리를 더 다듬어보자.
다음 씨간에~
'스프링 공부 > 게시판 프로젝트 만들기' 카테고리의 다른 글
[스프링] 19. QueryDsl 넣어주기 (0) | 2023.02.05 |
---|---|
[스프링] 18. MemberRepository커스텀해서 검색기능 만들기 (0) | 2023.02.04 |
[스프링] 16. MemberRepository 만들기 (0) | 2023.02.02 |
[스프링] 15. Member 테스트대로 코드 짜보기 (0) | 2023.01.17 |
[스프링] 14. Member에 대한 테스트 만들기 (0) | 2023.01.11 |