AI Briefing

카카오 브런치·티스토리, 테스트 코드 도입기: 아키텍처부터 커버리지 측정까지

·2021.11.08 00:00

핵심 내용

카카오 창작자 앱 팀이 브런치와 티스토리에 테스트 코드를 도입하며 겪은 아키텍처 고민, Coroutines 테스트 기술, 그리고 커버리지 11% 달성 과정을 공유했다.

1 / 16

자세히 보기

카카오 창작자앱개발파트는 브런치와 티스토리 안드로이드 앱에 테스트 코드를 도입하며 겪은 시행착오와 해결책을 공유했다. 팀은 애자일 방법론의 핵심인 기술 실천(TDD, 리팩터링 등)을 위해 테스트 환경 구축을 시작했으나, 기존 아키텍처와 비동기 처리 방식에서 여러 난관에 직면했다.

테스트 도입 배경과 아키텍처

브런치와 티스토리는 Clean Architecture와 MVVM, Hilt를 적용한 멀티 모듈 구조를 갖추고 있었다. 2018년부터 MVVM 전환을 시작해 2020년에 마무리했으며, Java에서 Kotlin으로, Rx에서 Coroutines로 마이그레이션을 진행했다. 이러한 리팩터링은 테스트 가능한 코드를 만드는 기반이 되었으나, 실제 테스트 작성을 위해서는 추가적인 준비가 필요했다.

Coroutines와 LiveData 테스트 기술

테스트 작성 시 가장 큰 어려움은 메인 스레드와 테스트 스레드의 불일치였다. LiveData 변경이나 viewModelScope.launch 호출 시 메인 스레드 예외가 발생했다. 이를 해결하기 위해 InstantTaskExecutorRule을 적용하고, kotlinx-coroutines-test의 Dispatchers.setMain을 활용해 테스트용 Dispatcher를 주입했다. 또한, 다양한 Dispatcher가 사용되는 경우를 대비해 DispatcherProvider 인터페이스를 도입해 의존성 주입 방식으로 테스트 환경을 구성했다. 비동기 작업의 타이밍 제어를 위해서는 pauseDispatcher와 resumeDispatcher를 사용해 특정 시점의 상태 변경을 검증했다.

JUnit5 마이그레이션과 에러 해결

팀은 JUnit5를 도입하면서 기존 JUnit4의 Rule이 Extension으로 대체되는 변경점을 처리해야 했다. InstantTaskExecutorRule과 MainCoroutineRule을 BeforeEachCallback과 AfterEachCallback을 구현한 Extension 클래스로 마이그레이션했다. 또한, 불필요한 스텁으로 인한 UnnecessaryStubbingException을 해결하기 위해 lenient 모드나 MockitoSettings를 사용하는 것보다, 불필요한 스텁 코드를 직접 제거하거나 수정하는 것이 테스트 코드 품질 유지에 더 효과적이라고 강조했다.

커버리지 측정과 성과

테스트 대상은 UI 상태를 관리하는 ViewModel으로 한정했다. UI 테스트의 복잡성과 데이터 레이어 매퍼 미비 등으로 인해 초기에는 ViewModel에만 집중했다. Jacoco 플러그인을 이용해 ViewModel 클래스의 커버리지를 측정했으며, 사내 빌드 시스템인 MoBil의 Release 빌드 시 자동으로 커버리지를 산출하고 기록한다. 현재 커버리지는 11% 수준이며, 팀은 고정된 목표 수치보다는 배포 시마다 커버리지가 성장하는 추세를 중시하고 있다. 테스트 도입부터 적용까지 약 3개월이 소요되었으며, 이를 통해 테스트에 대한 막연한 두려움을 극복하고 지속 가능한 테스트 문화를 구축하는 계기가 되었다.

이 한국어 요약은 AI가 자동으로 만들었습니다. 원문의 주장과 맥락은 원문에서 확인해 주세요. 저작권은 원저작자에게 있습니다.

AI 처리 방식을 확인하거나, 요약 오류와 출처 표기 문제, 삭제 요청을 문의 · 건의로 알려주세요.