2017-05-02 7 views
2

에서 테스트 목적으로 Time dependent unit tests내가 질문에 관련하여 질문이 방법을 추상화 java.time.Clock 봄

이의 나는 경우 서비스 인터페이스와 그 구현

을 포함 Spring 애플리케이션을 구축한다고 가정 해 봅시다 I 테스트에서 시계를 바꾸고 싶다면, 예를 들어 생산 코드와 인터페이스를 "오염시켜야"합니다. setClock 방법은 다음과 같이

public interface MyService { 
    void heavyBusinessLogic(); 
    void setClock(Clock clock); 
} 

@Service 
public class MyServiceImpl implements MyService { 

    private Clock clock = Clock.systemDefaultZone(); 

    @Override 
    public void heavyBusinessLogic() { 
     if (LocalDate.now(clock)...) { 
      ... 
     } 
    } 

    @Override 
    public void setClock(Clock clock) { 
     this.clock = clock; 
    } 
} 

테스트에서, 내가 호출 할 수있는, 예컨대 :

service.setClock(Clock.fixed(Instant.parse("2017-02-14T01:22:00Z"), ZoneOffset.UTC)); 

내가 어떻게 봄 추상 멀리 크로스 커팅 우려?

내가 java.time.Clock을 고수 할 ...

+0

대신 생성자 삽입을 사용하지 않는 이유는 무엇입니까? 그런 다음 인터페이스에'setClock()'메소드가 없다. –

+0

java.time.Clock은 bean이 아니다. –

+2

... 당신은 당신의 생산적인 설정에서 Clock 빈을 정의 할 수 있고, 테스트 구성 ... –

답변

5

개인적으로, 나는 단순히 생성자에서 시계를 추가

public MyServiceImpl(Clock clock) { 
    this.clock = clock; 
} 

을 (내가 Joda를 사용하지 않음). .. 그리고 당신의 테스트에서, 예를 들어, 아마도 ...

public MyServiceImpl() { 
    this(Clock.systemDefaultZone()); 
} 

당신이 봄을 통해 기본 일을 얻을 수있는이 방법을 멋진 기본 생성자를 추가하고 수동으로 사용자 정의 클럭 버전을 만들 수 있습니다. 물론

사용할 수있는 ... ...

@Bean 
public Clock clock() { 
return Clock.systemDefaultZone(); 
} 

을, 당신은 또한 기본 생성자를 포기 수를 간단히이 같은 예를 들어, 생산적인 구성에서 Clock 콩을 추가 Clock 조롱 테스트 구성에서 bean으로 생성자 삽입을 통해 Spring을 자동으로 @Autowire으로 허용합니다.

+0

방금 ​​다른 문제를 발견했습니다. 엔티티 자체에서 시간에 민감한 비교를 위해 시계를 사용하고 싶습니다. 클럭 빈을 주입하는 것이 좋지 않다고 생각합니다. 너는 무엇을 제안 하는가? –

+0

왜 이것이 좋은 생각이 아니라고 생각합니까? 나는 그 문제를 꽤 보지 못했다 ... –

+0

aspectj로드 시간 짜기 또는 Hibernate LoadEventListener가 필요하다. 나는 그것을 할 더 표준화 된 방법이 있다고 생각했다 :) –