複数のモジュールで使用する共通ユーティリティやテストヘルパーを一元化管理するため、ユーティリティモジュール :core:utils を作成します。
uiモジュールの作成と同様に、トップディレクトリで:core:utilsを作成し、javaディレクトリ名の変更を行います。
:core:utilsモジュールのbuild.gradle.ktsにLibraryConfigurePluginを適用します。
plugins {
alias(libs.plugins.android.library)
alias(libs.plugins.kotlin.android)
id("build.logic.library.configure")
}
android {
namespace = "jp.co.example.android01.core.data"
compileSdk {
version = release(36)
}
defaultConfig {
minSdk = 28
testInstrumentationRunner = "androidx.test.runner.AndroidJUnitRunner"
consumerProguardFiles("consumer-rules.pro")
}
buildTypes {
release {
isMinifyEnabled = false
proguardFiles(
getDefaultProguardFile("proguard-android-optimize.txt"),
"proguard-rules.pro"
)
}
}
compileOptions {
sourceCompatibility = JavaVersion.VERSION_11
targetCompatibility = JavaVersion.VERSION_11
}
kotlinOptions {
jvmTarget = "11"
}
}
dependencies {
implementation(libs.androidx.core.ktx)
implementation(libs.androidx.appcompat)
implementation(libs.material)
testImplementation(libs.junit)
androidTestImplementation(libs.androidx.junit)
androidTestImplementation(libs.androidx.espresso.core)
// JUnit 5
androidTestImplementation(platform(libs.junit5.bom))
androidTestImplementation(libs.junit5.api)
// Compose UI
androidTestImplementation(platform(libs.androidx.compose.bom))
androidTestImplementation(libs.androidx.compose.ui.test.junit4)
適用後、『同期アイコン』で内容をプロジェクトに反映させます。
JUnit 5スタイルで実機/エミュレータテストを行うための拡張(Extension)クラスをandroidTestに作成します。
package jp.co.example.android01.core.utils
import android.util.Log
import androidx.test.platform.app.InstrumentationRegistry
import org.junit.jupiter.api.extension.*
class AndroidJUnit5Extension : BeforeAllCallback, BeforeEachCallback, AfterEachCallback, AfterAllCallback {
override fun beforeAll(context: ExtensionContext) {
val instrumentation = InstrumentationRegistry.getInstrumentation()
Log.i("AndroidJUnit5Extension", "Instrumentation initialized: $instrumentation")
}
override fun beforeEach(context: ExtensionContext) {
Log.i("AndroidJUnit5Extension", "Starting test: ${context.displayName}")
}
override fun afterEach(context: ExtensionContext) {
Log.i("AndroidJUnit5Extension", "Finished test: ${context.displayName}")
}
override fun afterAll(context: ExtensionContext) {
Log.i("AndroidJUnit5Extension", "All tests completed for: ${context.testClass.map { it.simpleName }.orElse("UnknownClass")}")
}
}
Jetpack Composeのテストモジュールは、JUnit 4ベースなので、JUnit 5スタイルで実機/エミュレータテストを行うための拡張ラッパー(Extension)クラスをandroidTestに作成します。
package jp.co.example.android01.core.utils
import android.util.Log
import androidx.test.platform.app.InstrumentationRegistry
import androidx.compose.ui.test.junit4.ComposeTestRule
import androidx.compose.ui.test.junit4.createComposeRule
import org.junit.jupiter.api.extension.*
class ComposeExtension : BeforeAllCallback, BeforeEachCallback, AfterEachCallback, AfterAllCallback, ParameterResolver {
private val composeRule: ComposeTestRule = createComposeRule()
override fun beforeAll(context: ExtensionContext) {
val instrumentation = InstrumentationRegistry.getInstrumentation()
Log.i("ComposeExtension", "Instrumentation initialized: $instrumentation")
}
override fun beforeEach(context: ExtensionContext) {
Log.i("ComposeExtension", "Starting test: ${context.displayName}")
}
override fun afterEach(context: ExtensionContext) {
Log.i("ComposeExtension", "Finished test: ${context.displayName}")
}
override fun afterAll(context: ExtensionContext) {
Log.i("ComposeExtension", "All tests completed for: ${context.testClass.map { it.simpleName }.orElse("UnknownClass")}")
}
override fun supportsParameter(
parameterContext: ParameterContext,
extensionContext: ExtensionContext
): Boolean = parameterContext.parameter.type == ComposeTestRule::class.java
override fun resolveParameter(
parameterContext: ParameterContext,
extensionContext: ExtensionContext
): Any = composeRule
}
androidTestにあるサンプルテストクラス ComposeExtension.kt を削除します。