순수 JDBC로 짜면,
DIP(구현체에 의존,클라이언트 건들어야함), OCP 위반함
그래서?? 인터페이스에만 의존하게끔 설정하면 구현체를 안건들이고 할 수 있다.
private final DiscountPolicy discountPolicy = new RateDiscountPolicy(); → 구현체 의존
private final DiscountPolicy discountPolicy;  → 인터페이스 의존
근데 이렇게 설정해버리면 NullPointerException 발생할텐데?! → 누군가가 할인 인터페이스에 구현 객체를 대신 생성하고 주입해줘야 하지 않을까?! 라는 생각.
객체를 생성하고 의존성만 주입해주는 친구를 만들자!(ex.AppConfig)
→ 클라이언트 클래스에는 인터페이스 생성자를 설정해서 AppConfig에서 구현체 생성 및 의존성을 담당하자
→ Service나 Repository같은 클라이언트는 인터페이스만 의존하며 실행로직만 집중하게끔 하고 , 외부에서 생성자 주입으로 인터페이스로 구성된 실행로직에서 구현로직을 이용할 수가 있다!!!!!!
→ DIP 지킴(클라이언트 클래스 추상화 의존), OCP(소프트웨어 요소를 새롭게 확장해도 사용 영역의 변경은 닫혀있음) 지킴
그래서 Impl(구현체)는 실행만 담당하고 생성과 의존은 AppConfig같은 외부에서 설정해준다!
→ 마치 외부에서 의존성이 주입되는 것 같다 → DI(의존관계 주입, Dependency Injection)
AppConfig만들때 역할과 구현의 구분을 두자! 즉 어떤 구현체를 쓸지, 어떤 클라이언트의 생성자 주입할지.