-핵심 기능 : 해당 객체가 제공하는 고유 기능

-부가 기능 : 핵심 기능을 보조하기 위해 제공되는 기능 (예. 로그 추적 로직, 트랜잭션 기능 등)

V3 코드를 유심히 살펴보면 다음과 같이 동일한 패턴이 있다

TraceStatus status = null;

try {
	status = trace.begin("message");

  // 핵심 기능 호출 

  trace.end(status);	
} catch(Exception e) {
	trace.exception(status, e);
	throw e;
}

Controller, Service, Repository 모두가 로그 추적기를 사용하는 구조는 모두 동일하다. 중간에 핵심 기능을 사용하는 코드만 다를 뿐이다.

부가 기능과 관련된 코드가 중복되니 중복 코드를 별도의 메서드로 뽑아서 사용하면 될 것 같다.

“변하는 것과 변하지 않는 것을 분리”

좋은 설계는 변하는 것과 변하지 않는 것을 분리하는 것이다.

여기서 핵심 기능 부분은 변하고, 로그 추적기를 사용하는 부분은 변하지 않는 부분이다.

이 둘을 분리해서 모듈화 하도록 한다.

템플릿 메서드 패턴 (Template Method Pattern)

상속을 통한 다형성

아래 예제를 살펴볼 때 logic1() 과 logic2() 가 비즈니스 로직 부분 제외한 나머지 부분이 중복된 형태를 보인다

@Test
void templateMethodV0() {
    logic1();
    logic2();
}

private void logic1() {
    long startTime = System.currentTimeMillis();

    // 비즈니스 로직 실행
    log.info("비즈니스 로직1 실행");
    // 비즈니스 로직 종료

    long endTime = System.currentTimeMillis();
    long resultTime = endTime - startTime;
    log.info("resultTime = {}", resultTime);
}

private void logic2() {
    long startTime = System.currentTimeMillis();

    // 비즈니스 로직 실행
    log.info("비즈니스 로직2 실행");
    // 비즈니스 로직 종료

    long endTime = System.currentTimeMillis();
    long resultTime = endTime - startTime;
    log.info("resultTime = {}", resultTime);
}