본문 바로가기
개발 관련 공부/스프링 김영한 로드맵

[스프링 기본] 2. 스프링 핵심 원리 이해1-예제 만들기

by 슴새 2022. 10. 7.
반응형

프로젝트 생성

https://start.spring.io/ 사이트로 가서 zip 파일을 생성-다운 후 인텔리제이에서 임포트

임포트 방법: 압축 푼 파일 위치로 가서 해당 파일의 build.gradle 선택 후 프로젝트로 열기

일단 순수 자바로 개발하고 추후 점점 스프링의 요소들을 추가해 나갈 것이다.(스프링 부트는 환경 설정을 편리하게 하려고 사용한 것.)

 

비지니스 요구사항과 설계 & 회원 도메인 설계

회원

회원 가입과 조회 가능. 일반 회원과 VIP 회원 존재.

회원 db는 자체 db로 할지 외부 시스템과 연동할지 미확정.

 

주문

회원들은 상품을 주문할 수 있는데, 회원 등급에 따라 할인 정책 다름.(VIP는 무조건 1000원 할인)

할인 정책은 회사의 사정으로 변경 가능성이 높은 상태.

 

변경 가능성이 있으므로 인터페이스를 만들고 구현체를 언제든 갈아끼울 수 있게 설계하자.

회원 도메인 개발

평범한 Member 클래스를 만든다.

특이점은 enum 클래스 Grade 타입 객체 grade를 가진다는 것 정도.  

save와 findID 함수를 가진 인터페이스 MemberRepository를 만들고 그 구현체 MemoryMemberRepository를 작성한다.

private static Map<Long, Member> store = new HashMap<>();

save, findID의 구현은, 일단 db가 없으므로 HashMap으로 진행한다. 

 

이어서 join 함수와 findMember 함수를 가진 인터페이스 MemberService를 만든다.

 

package hello.core.member;
public class MemberServiceImpl implements MemberService {
    //다형성!
    private final MemberRepository memberRepository = new MemoryMemberRepository();
    public void join(Member member) {
        memberRepository.save(member);
    }
    public Member findMember(Long memberId) {
        return memberRepository.findById(memberId);
    }
}

이후 MemberService의 구현체 MemberServiceImpl를 만든다.

MemberServiceImpl는 MemoryMemberRepository의 객체를 가진다. 

 

아직 이전 강의에서 언급했던 DIP, OCP 위반 문제가 해결되지 않았다. 

하지만 일단 그대로 개발하고 나중에 고칠 것이다.

회원 도메인 실행과 테스트

junit 프레임워크를 이용한다.

test 폴더 아래에 member 패키지 만들고 MemberServiceTest 클래스를 만든다.

작성한 테스트 함수 위에 @Test 어노테이션을 붙이면 된다. 

@Test
 void join() {
 	//given
 	Member member = new Member(1L, "memberA", Grade.VIP);
 	//when
 	memberService.join(member);
 	Member findMember = memberService.findMember(1L);
 	//then
 	Assertions.assertThat(member).isEqualTo(findMember);
 }

given, when, then으로 나눠서 생각한 후 작성하자.

실행하면 성공하는 것을 볼 수 있다.

 

주문과 할인 도메인 설계

주문을 하면, 회원조회해서 등급을 확인 후 알맞은 할인 정책을 적용해 반환한다.

클래스 다이어그램은 다음과 같다. 

 

주문과 할인 도메인 개발

설계한대로 DiscountPolicy 인터페이스와 그 구현체를 만든다.

DiscountPolicy 인터페이스는 discount 함수를 가진다.

@Override
public int discount(Member member, int price) {
    if (member.getGrade() == Grade.VIP) {
        return discountFixAmount;
    } else {
        return 0;
    }
}

구현한 함수는 이렇다.

 

 

Order 객체와 OrderService 인터페이스, 그 구현체 OrderServiceImpl를 만든다. 

OrderService는 createOrder 함수를 가진다. 

@Override
public Order createOrder(Long memberId, String itemName, int itemPrice) {
    Member member = memberRepository.findById(memberId);
    int discountPrice = discountPolicy.discount(member, itemPrice);
    return new Order(memberId, itemName, itemPrice, discountPrice);
}

구현한 함수는 이렇다. 

 

주문과 할인 도메인 실행과 테스트

역시 JUnit으로 테스트 코드를 작성하자. OrderServiceTest 클래스를 만든다.

@Test
void createOrder() {
    long memberId = 1L;
    Member member = new Member(memberId, "memberA", Grade.VIP);
    memberService.join(member);
    Order order = orderService.createOrder(memberId, "itemA", 10000);
    Assertions.assertThat(order.getDiscountPrice()).isEqualTo(1000);
}

마찬가지로 잘 동작하는 것을 볼 수 있다.

이 포스팅은 인프런 김영한님의 '스프링 핵심 원리 기본편'을 듣고 정리한 것입니다.
강의 링크: https://url.kr/udopsk  
반응형

댓글