전통적인 디자인패턴(GoF)에서 전략패턴 public class OriginalStrategyPattern { //인터페이스 선언 public interface ValidationStrategy { boolean execute(String s); } //클래스 구현 - 소문자 검증 private class IsAllLowerCase implements ValidationStrategy { @Override public boolean execute(String s) { return s.matches("[a-z]+"); } } //클래스 구현 - 숫자 검증 private class IsNumeric implements ValidationStrategy { @Override public boolean exec..
Java 람다와 디자인패턴 언어에 새로운 기능이 추가되면서 기존 코드 패턴이나 많이 사용되던 관용코드의 인기가 식기도 한다. 예를 들어 Java5의 for-each는 기존의 반복자 코드(iterator)보다 간결하고, 에러를 유발할 가능성이 적어서 많이 사용되었고, Java7의 다이아몬드 연산자 때문에 기존의 제네릭 인스턴스를 명시적으로 생성하는 빈도가 줄었다. Java9의 var도 명시적인 타입 선언을 대체하고 형식 추론의 세계를 열어주고 있다. Java8의 람다의 등장으로 디자인 패턴에 람다 표현식이 더해지면서 이전에 디자인 패턴으로 해결하던 문제를 더 쉽고 간결하게 해결할 수 있게 되었으며, 심지어 많은 객체지향 디자인 패턴이 기존의 정형화된 패턴 구조를 벗어나서 메서드 참조를 활용한 간결한 구조로..
조건부 연기 실행(Conditional Diferred Execution) 아래 코드에서 getMessage 메서드는 1000번 호출된다. public class CDETest { private StopWatch sw; private String methodName; private boolean useLog = false; private CDETest() { sw = new StopWatch(); } @BeforeEach void startStopWatch() { sw.start(); } @AfterEach void endStopWatch() { sw.stop(); System.out.println(methodName + " running time : " + sw.getTotalTimeMillis() +..
[원본 문서] https://semaphoreci.com/blog/economics-of-tdd The Economics of TDD - Semaphore TDD can help you accelerate development and reduce costs over a project’s lifecycle. semaphoreci.com [번역] 관리 관점에서 테스트 주도 개발(TDD) 도입을 설득하기 어려울 수 있습니다. 이는 상대적으로 큰 초기 투자를 수반하고, 명백한(정량적, 사업적으로 보여줄 수 있는) 비즈니스 이점이 없으며, (가장 중요한) 고객(회사)은 테스트가 아닌 기능에 대해 개발 비용에만 주로 관심이 있습니다. 그렇지만, 프로젝트의 다음 이정표에 도달하기 위해 테스팅(TDD)을 줄이려는 유혹..
Gradle.build 설정 dependencies { testCompile('org.junit.jupiter:junit-jupiter-api') testRuntimeOnly('org.junit.jupiter:junit-jupiter-engine') testImplementation ('org.mockito:mockito-core:2.26.0') } [테스트 코드] package mock; import org.junit.jupiter.api.Test; import static org.junit.jupiter.api.Assertions.assertEquals; import static org.mockito.BDDMockito.given; import static org.mockito.Mockito.mock..
-- Junit5 예외 테스트 샘플 //빌링 금액 단위가 맞지 않으면 에러 처리 if(amount % AMOUNT_OF_MONTH != 0) { throw new InvalidParameterException("금액이 잘 못 되었습니다."); } -- Junit5 예외 발생 + 세부항목 검증 @Test void 빌링_금액예외테스트() { Billing bill; InvalidParameterException exception = assertThrows(InvalidParameterException.class, () -> new Billing(1, LocalDate.now(), 11000) ); assertEquals("금액이 잘 못 되었습니다.", exception.getMessage()); } -- J..
새 프로젝트 설정 IntelliJ -> File -> New Project Gradle, Java, Web 체크 후 [Next] Name 설정 -> [Finish] brew install gradle build.gradle 수정 //[AS-IS] plugins { id 'java' id 'war' } group 'org.example' version '1.0-SNAPSHOT' repositories { mavenCentral() } ... 생략 //[TO-BE] plugins { id 'org.springframework.boot' version '2.2.2.RELEASE' id 'io.spring.dependency-management' version '1.0.8.RELEASE' id 'java' id..
구글, 네이버 로그인 구현을 완료했고 기존 테스트에 시큐리티 적용으로 문제가 되는 것을 해결한다. 기존 테스트 코드에서는 API를 바로 호출하도록 구성되어 있었다. 그러나 시큐리티 옵션이 활성화되면 인증된 사용자만이 API를 호출할 수 있다. 기존 API 테스트 코드들은 인증에 대한 권한을 받지 못해 테스트 코드마다 인증한 사용자가 호출한 것처럼 작동할 수 있도록 수정해야 한다. 우선 전체 테스트를 수행해본다. 전체 테스트 수행하기 인텔리제이 화면 우측의 Gradle 탭을 누른 뒤 Tasks - verification - test를 차례로 선택한 뒤 전체 테스트를 수행한다. 전체 테스트를 수행하면 위와 같은 결과가 나온다. 문제 1. Test 환경 구성 src/main과 src/test의 환경은 독자적인..
테스트 코드 작성 클래스 이름 메서드 이름 메서드 파라미터 실행 결과 TDD의 시작은 이름 이름은 설계에서 매우 중요하다. 이해할 수 없는 이름, 이름과 다른 동작을 하는 객체(잘 못 지어진 이름) 등은 두고두고 개발자를 힘들게 만든다. 테스트를 통과할 만큼만 코드를 작성한다. TDD는 테스트를 통과할 만큼만 코드를 작성한다. 필요할 것으로 예측해서 미리 코드를 만들지 않는다. 설계도 동일하게 미리 예측해서 코드를 먼저 만들지 않는다. 실제 테스트 사례를 추가하고 통과시키는 과정에서 필요한 만큼만 조금씩 설계를 변경한다. 예외 처리 : Exception 타입을 미리 만들지 않는다. 테스트를 진행하는 과정에서 실제 예외가 필요한 시점에 Excetion을 도출한다. TDD로 개발을 진행하게 되면 TDD로 개..