이 페이지에서는 주요 권장사항과 이점을 포함하여 Android 앱 테스트의 핵심 원칙을 간략히 설명합니다.
테스트의 이점
테스트는 앱 개발 프로세스에서 빼놓을 수 없는 부분입니다. 앱 테스트를 일관되게 실행하여 앱을 공개적으로 출시하기 전에 앱의 정확성, 기능 동작, 사용성을 확인할 수 있습니다.
앱을 탐색하여 수동으로 테스트할 수 있습니다. 다양한 기기와 에뮬레이터를 사용하고, 시스템 언어를 변경하고, 모든 사용자 오류를 생성하거나 모든 사용자 흐름을 탐색해 볼 수 있습니다.
그러나 수동 테스트는 확장성이 떨어지며 앱 동작의 회귀를 간과하기 쉽습니다. 자동 테스트는 테스트를 자동으로 실행하는 도구를 사용하는 것을 말합니다. 이 방법은 더 빠르고 반복 가능하며 일반적으로 개발 프로세스 초기에 앱에 관한 더 실행 가능한 의견을 제공합니다.
Android의 테스트 유형
모바일 애플리케이션은 복잡하며 다양한 환경에서 잘 작동해야 합니다. 따라서 테스트 유형은 다양합니다.
제목
예를 들어 과목에 따라 다양한 유형의 테스트가 있습니다.
- 기능 테스트: 앱이 정상적인 작동을 하는가?
- 성능 테스트: 빠르고 효율적으로 실행되나요?
- 접근성 테스트: 접근성 서비스와 잘 작동하나요?
- 호환성 테스트: 모든 기기와 API 수준에서 잘 작동하나요?
범위
테스트는 크기 또는 격리 정도에 따라 달라집니다.
- 단위 테스트 또는 소규모 테스트는 메서드나 클래스와 같은 앱의 극히 일부분만 확인합니다.
- 엔드 투 엔드 테스트 또는 대규모 테스트는 전체 화면이나 사용자 흐름과 같이 앱의 더 큰 부분을 동시에 확인합니다.
- 중형 테스트는 그 중간에 있으며 두 개 이상의 단위 간의 통합을 확인합니다.
테스트를 분류하는 방법에는 여러 가지가 있습니다. 하지만 앱 개발자에게 가장 중요한 구분은 테스트가 실행되는 위치입니다.
계측 테스트와 로컬 테스트 비교
Android 기기 또는 다른 컴퓨터에서 테스트를 실행할 수 있습니다.
- 계측 테스트는 실제 기기 또는 에뮬레이션된 Android 기기에서 실행됩니다. 이 앱은 명령어를 삽입하고 상태를 읽는 테스트 앱과 함께 빌드 및 설치됩니다. 계측 테스트는 일반적으로 앱을 실행한 후 상호작용하는 UI 테스트입니다.
- 로컬 테스트는 개발 머신 또는 서버에서 실행되므로 호스트 측 테스트라고도 합니다. 일반적으로 작고 빠르며 테스트 대상을 앱의 나머지 부분과 격리합니다.
모든 단위 테스트가 로컬 테스트는 아니며 모든 엔드 투 엔드 테스트가 기기에서 실행되는 것도 아닙니다. 예를 들면 다음과 같습니다.
- 대규모 로컬 테스트: Robolectric과 같이 로컬에서 실행되는 Android 시뮬레이터를 사용할 수 있습니다.
- 소규모 계측 테스트: 코드가 SQLite 데이터베이스와 같은 프레임워크 기능과 잘 작동하는지 확인할 수 있습니다. 여러 기기에서 이 테스트를 실행하여 여러 버전의 SQLite와의 통합을 확인할 수 있습니다.
예
다음 스니펫은 요소를 클릭하고 다른 요소가 표시되는지 확인하는 계측 UI 테스트에서 UI와 상호작용하는 방법을 보여줍니다.
Espresso
// When the Continue button is clicked
onView(withText("Continue"))
.perform(click())
// Then the Welcome screen is displayed
onView(withText("Welcome"))
.check(matches(isDisplayed()))
Compose UI
// When the Continue button is clicked
composeTestRule.onNodeWithText("Continue").performClick()
// Then the Welcome screen is displayed
composeTestRule.onNodeWithText("Welcome").assertIsDisplayed()
다음 스니펫은 ViewModel의 단위 테스트 (로컬, 호스트 측 테스트)의 일부를 보여줍니다.
// Given an instance of MyViewModel
val viewModel = MyViewModel(myFakeDataRepository)
// When data is loaded
viewModel.loadData()
// Then it should be exposing data
assertTrue(viewModel.data != null)
테스트 가능한 아키텍처
테스트 가능한 앱 아키텍처를 사용하면 코드가 다양한 부분을 격리된 상태로 쉽게 테스트할 수 있는 구조를 따릅니다. 테스트 가능한 아키텍처에는 가독성, 유지 관리성, 확장성, 재사용성 등의 다른 이점도 있습니다.
테스트 불가 아키텍처는 다음을 생성합니다.
- 더 크고 느리고 불안정한 테스트 단위 테스트를 실행할 수 없는 클래스는 더 큰 통합 테스트 또는 UI 테스트로 테스트해야 할 수 있습니다.
- 다양한 시나리오를 테스트할 기회가 줄어듭니다. 테스트가 클수록 속도가 느려지므로 앱의 가능한 모든 상태를 테스트하는 것은 비현실적일 수 있습니다.
아키텍처 가이드라인에 관한 자세한 내용은 앱 아키텍처 가이드를 참고하세요.
분리 접근 방식
함수, 클래스 또는 모듈의 일부를 나머지 부분에서 추출할 수 있으면 테스트가 더 쉽고 효과적입니다. 이를 분리라고 하며 테스트 가능한 아키텍처에 가장 중요한 개념입니다.
일반적인 분리 기술에는 다음이 포함됩니다.
- 앱�� 프레젠테이션, 도메인, 데이터와 같은 레이어로 분할합니다. 앱을 기능별로 하나씩 모듈로 분할할 수도 있습니다.
- 활동과 프래그먼트 같은 종속 항목이 큰 항목에는 로직을 추가하지 마세요. 이러한 클래스를 프레임워크의 진입점으로 사용하고 UI 및 비즈니스 로직을 컴포저블, ViewModel 또는 도메인 레이어와 같은 다른 위치로 이동합니다.
- 비즈니스 로직을 포함하는 클래스에서 직접적인 프레임워크 종속 항목을 피합니다. 예를 들어 ViewModel에서 Android 컨텍스트를 사용하지 마세요.
- 종속 항목을 쉽게 대체할 수 있도록 합니다. 예를 들어 구체적인 구현 대신 인터페이스를 사용합니다. DI 프레임워크를 사용하지 않더라도 종속 항목 삽입을 사용하세요.
다음 단계
이제 테스트해야 하는 이유와 두 가지 기본 테스트 유형을 알게 되었으므로 테스트 항목을 읽거나 테스트 전략에 관해 알아보세요.
또는 첫 번째 테스트를 만들고 직접 해보려면 테스트 Codelab을 확인하세요.