2장 테스트

  1. 테스트
    1. UserDaoTest 다시 보기
    2. UserDaoTest 개선
    3. 개발자를 위한 테스팅 프레임워크 JUnit
    4. 스프링 테스트 적용
      1. 테스트를 위한 애플리케이션 컨텍스트 관리

         @RunWith(SpringJUnit4ClassRunner.class)
         @ContextConfiguration(locations="/applicationContext.xml")
         public class UserDaoTest{
         	@Autowired
         	private ApplicationContext context;
        
         	@Before
         	public void setUp(){
         		this.dao = this.context.getBean("userDao", UserDao.class);
        
         		// 항상 동일, 다른 클래스에서도 같은 설정을 하였으면 동일
         		System.out.println(this.context); 
                        
         		// 항상 다름
         		System.out.println(this); 
         	}
         }
        
        • @RunWith : JUnit 프레임워크를 확장할 때 사용하는 어노테이션
        • SpringJUnit4ClassRunner : 테스트에 사용할 컨텍스트를 지정해주면, 해당 컨텍스트를 생성하고 관리하는 작업
        • @ContextConfiguration : 컨텍스트 설정파일 위치를 지정하기 위한 어노테이션
        • @Autowired : 자동으로 DI를 해주는 어노테이션
          • 선언 된 타입과 동일한 빈을 주입
          • 같은 타입의 빈이 두 개 이상인 경우 변수의 이름과 같은 이름의 빈을 주입
          • 이 외에는 예외를 던진다.
          • 실제로 구현체의 테스트가 필요한 경우, 구현체의 타입을 선언한다. 하지만 그럴 필요가 없다면 인터페이스를 사용하여 코드와 느슨하게 연결해두는게 좋다.
        • this.context는 SpringJUnit4ClassRunner가 한번 생성하고 계속 관리하므로 항상 동일
        • this는 테스트 클래스 오브젝트이므로 테스트를 할 때마다 변경됨
      2. DI와 테스트

        • applicationContext를 운영에서 사용하는거랑 동일하게 사용하면 위험할 수 있음
        • 따라서 set 메소드로 DI를 테스트 용도의 객체로 줄 수 있음

            @DirtiesContext
            public class UserDaoTest{
            	@Autowired
            	UserDao dao;
          
            	@Before
            	public void setUp(){
            		...
            		dao.setDataSource(testSuorce);
            	}
          
        • @DirtiesContext는 테스트 컨텍스트 프레임워크에게 컨텍스트의 구성이나 상태를 강제로 변경할 수 있다는 것은 알려주는 어노테이션. 만약 이 어노테이션을 사용하면, 해당하는 테스트 클래스에서만 변경한 설정이 적용되고, 나머지에서는 적용 안됨
        • 하지만 위 방법은 불편하므로, 테스트 전용 어플리케이션 컨텍스트를 만들기로 하자.
        • 스프링을 사용하지 않고도 DI 테스트가 가능하다.

            public class UserDaoTest {
            	UserDao dao;  // Autowired가 없다
          
            	@Before
            	public void setUp(){
            		...
            		dao = new UserDao();
            		Datasource datasource = ...
            		dao.setDataSource(datasource);
          
        • 코드가 더 단순하고 이해하기 쉽다.
        • 테스트를 어떻게 짜야할까?
          1. 우선적으로 스프링을 사용하지 않고 테스트할 수 있는 방법을 우선적으로 고려
          2. 여러 오브젝트와 복잡한 관계를 갖은 오브젝트를 테스트할 경우, 스프링 고려
          3. 강제로 구성해야 할 경우, 수동 DI (@DirtiesContext)
    5. 학습 테스트로 배우는 스프링
      • 학습 테스트 : 다른 사람이 만든 라이브러리를 테스트하면서 사용 방법을 익힘
        1. 학습 테스트의 장점
        • 다양한 조건에 따른 기능을 손쉽게 확인해볼수 있다.
        • 학습 테스트 코드를 개발 중에 참고할 수 있다
        • 프레임워크나 제품을 업그레이드할 때 호환성 검증을 도와준다
        • 테스트 작성에 대한 좋은 훈련이 된다
        • 새로운 기술을 공부하는 과정이 즐거워진다 2. 학습 테스트 예제 3. 버그 테스트
        • 버그 테스트 : 코드에 오류가 있을 때 그 오류를 가장 잘 드러내줄수 있는 테스트
        • 버그 테스트는 일단 실패하도록 만들어야 함
        • 버그 테스트의 필요성과 장점
          1. 테스트의 완성도를 높여준다
          2. 버그의 내용을 명확하게 분석하게 해준다
          3. 기술적인 문제를 해결하는 데 도움이 된다