Skip to content

Commit 6f3d4fb

Browse files
committed
Fix configuration cache compatibility
1 parent e14be30 commit 6f3d4fb

2 files changed

Lines changed: 84 additions & 72 deletions

File tree

include-build/gradle-plugin/src/main/java/com/telefonica/androidsnaptesting/AndroidSnaptestingPlugin.kt

Lines changed: 71 additions & 53 deletions
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,14 @@
11
package com.telefonica.androidsnaptesting
22

3-
import com.android.build.gradle.internal.tasks.AndroidVariantTask
3+
import com.android.build.gradle.TestedExtension
44
import com.android.build.gradle.internal.tasks.DeviceProviderInstrumentTestTask
55
import org.gradle.api.Plugin
66
import org.gradle.api.Project
77
import org.gradle.api.Task
8-
import org.gradle.internal.build.event.BuildEventListenerRegistryInternal
9-
import org.gradle.tooling.events.OperationCompletionListener
8+
import org.gradle.api.provider.ProviderFactory
109
import java.io.File
11-
import javax.inject.Inject
1210

13-
class AndroidSnaptestingPlugin @Inject constructor(
14-
private val buildEventListenerRegistry: BuildEventListenerRegistryInternal
15-
) : Plugin<Project> {
11+
class AndroidSnaptestingPlugin : Plugin<Project> {
1612

1713
override fun apply(project: Project) {
1814
project.afterEvaluate {
@@ -24,32 +20,76 @@ class AndroidSnaptestingPlugin @Inject constructor(
2420
throw AndroidSnaptestingNoDeviceProviderInstrumentTestTasksException()
2521
}
2622

27-
deviceProviderInstrumentTestTasks
28-
.forEach { deviceProviderTask ->
29-
val capitalizedVariant = deviceProviderTask.variantName.capitalizeFirstLetter()
30-
val beforeTaskName = "androidSnaptestingBefore$capitalizedVariant"
31-
project.tasks.register(beforeTaskName, Task::class.java) { task ->
32-
task.doFirst {
33-
deviceProviderTask.deviceFileManager().clearAllSnapshots()
34-
}
35-
}
36-
deviceProviderTask.dependsOn(beforeTaskName)
23+
val extension = project.extensions.findByType(TestedExtension::class.java)
24+
?: throw RuntimeException("TestedExtension not found")
3725

38-
val afterTaskName = "androidSnaptestingAfter$capitalizedVariant"
39-
project.tasks.register(afterTaskName, Task::class.java) { task ->
40-
task.doLast {
41-
deviceProviderTask.afterExecution()
42-
}
43-
}
44-
deviceProviderTask.onTaskCompleted {
45-
deviceProviderTask.afterExecution()
46-
}
26+
val isRecordMode = project.properties["android.testInstrumentationRunnerArguments.record"] == "true"
27+
val projectDir = project.projectDir
28+
val providerFactory: ProviderFactory = project.providers
29+
30+
deviceProviderInstrumentTestTasks.names.forEach { taskName ->
31+
val deviceProviderTask = project.tasks.named(
32+
taskName,
33+
DeviceProviderInstrumentTestTask::class.java,
34+
).get()
35+
val capitalizedVariant = deviceProviderTask.variantName.capitalizeFirstLetter()
36+
37+
@Suppress("DEPRECATION")
38+
val testedVariant = extension.testVariants
39+
.firstOrNull { it.name == deviceProviderTask.variantName }
40+
?: throw RuntimeException("TestVariant not found for ${deviceProviderTask.variantName}")
41+
val applicationIdProvider = providerFactory.provider { testedVariant.applicationId }
42+
val adbExecutablePath = extension.adbExecutable.absolutePath
43+
44+
val goldenSnapshotsSourcePath = run {
45+
val variantSourceFolder = deviceProviderTask
46+
.variantName
47+
.replace("AndroidTest", "")
48+
.capitalizeFirstLetter()
49+
.let { "androidTest$it" }
50+
"$projectDir/src/$variantSourceFolder/assets/android-snaptesting-golden-files"
51+
}
52+
53+
// Attach work directly on the deviceProviderTask (config-cache safe).
54+
// Note: in Kotlin, doFirst/doLast lambdas receive the task as 'it', not 'this'.
55+
deviceProviderTask.doFirst {
56+
(it as DeviceProviderInstrumentTestTask)
57+
.deviceFileManager(applicationIdProvider.get(), adbExecutablePath, providerFactory)
58+
.clearAllSnapshots()
59+
}
60+
61+
deviceProviderTask.doLast {
62+
(it as DeviceProviderInstrumentTestTask)
63+
.afterExecution(
64+
applicationId = applicationIdProvider.get(),
65+
adbExecutablePath = adbExecutablePath,
66+
providerFactory = providerFactory,
67+
isRecordMode = isRecordMode,
68+
goldenSnapshotsSourcePath = goldenSnapshotsSourcePath,
69+
)
4770
}
71+
72+
// Keep empty before/after tasks as dependency anchors for CI scripts
73+
// (e.g. ci.gradle.kts references these task names).
74+
val beforeTaskName = "androidSnaptestingBefore$capitalizedVariant"
75+
project.tasks.register(beforeTaskName, Task::class.java)
76+
deviceProviderTask.dependsOn(beforeTaskName)
77+
78+
val afterTaskName = "androidSnaptestingAfter$capitalizedVariant"
79+
project.tasks.register(afterTaskName, Task::class.java)
80+
deviceProviderTask.finalizedBy(afterTaskName)
81+
}
4882
}
4983
}
5084

51-
private fun DeviceProviderInstrumentTestTask.afterExecution() {
52-
val deviceFileManager = deviceFileManager()
85+
private fun DeviceProviderInstrumentTestTask.afterExecution(
86+
applicationId: String,
87+
adbExecutablePath: String,
88+
providerFactory: ProviderFactory,
89+
isRecordMode: Boolean,
90+
goldenSnapshotsSourcePath: String,
91+
) {
92+
val deviceFileManager = deviceFileManager(applicationId, adbExecutablePath, providerFactory)
5393

5494
val reportsFolder = reportsDir.get().dir("androidSnaptesting")
5595
val recordedFolderFile = reportsFolder.dir("recorded").asFile.apply {
@@ -64,7 +104,7 @@ class AndroidSnaptestingPlugin @Inject constructor(
64104
val goldenForFailuresReportFolderFile = reportsFolder.dir("golden").asFile.apply {
65105
mkdirs()
66106
}
67-
val goldenFolderFile = File(getAbsoluteGoldenSnapshotsSourcePath())
107+
val goldenFolderFile = File(goldenSnapshotsSourcePath)
68108

69109
File("${reportsFolder.asFile.absolutePath}/recorded.html").apply {
70110
createNewFile()
@@ -76,7 +116,7 @@ class AndroidSnaptestingPlugin @Inject constructor(
76116
writeText(report)
77117
}
78118

79-
if (project.properties["android.testInstrumentationRunnerArguments.record"] != "true") {
119+
if (!isRecordMode) {
80120
File("${reportsFolder.asFile.absolutePath}/failures.html").apply {
81121
createNewFile()
82122
val failuresFiles = failuresFolderFile.listFiles()?.asList() ?: emptyList()
@@ -99,35 +139,13 @@ class AndroidSnaptestingPlugin @Inject constructor(
99139
writeText(report)
100140
}
101141
} else {
102-
File(getAbsoluteGoldenSnapshotsSourcePath()).apply {
142+
File(goldenSnapshotsSourcePath).apply {
103143
mkdirs()
104144
recordedFolderFile.copyRecursively(this, true)
105145
}
106146
}
107147
}
108148

109-
private fun Task.onTaskCompleted(onCompleted: () -> Unit) {
110-
buildEventListenerRegistry.onTaskCompletion(
111-
project.provider {
112-
OperationCompletionListener {
113-
if (it.descriptor.name != path) {
114-
return@OperationCompletionListener
115-
}
116-
onCompleted()
117-
}
118-
}
119-
)
120-
}
121-
122-
private fun AndroidVariantTask.getAbsoluteGoldenSnapshotsSourcePath(): String {
123-
val variantSourceFolder = this
124-
.variantName
125-
.replace("AndroidTest", "")
126-
.capitalizeFirstLetter()
127-
.let { "androidTest$it" }
128-
return "${project.projectDir}/src/$variantSourceFolder/assets/android-snaptesting-golden-files"
129-
}
130-
131149
private fun String.capitalizeFirstLetter(): String {
132150
return replaceFirstChar { if (it.isLowerCase()) it.titlecase() else it.toString() }
133151
}

include-build/gradle-plugin/src/main/java/com/telefonica/androidsnaptesting/DeviceFileManager.kt

Lines changed: 13 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -1,33 +1,27 @@
11
package com.telefonica.androidsnaptesting
22

3-
import com.android.build.gradle.TestedExtension
4-
import com.android.build.gradle.api.TestVariant
53
import com.android.build.gradle.internal.tasks.DeviceProviderInstrumentTestTask
64
import com.android.build.gradle.internal.testing.ConnectedDevice
75
import com.android.ddmlib.CollectingOutputReceiver
86
import com.android.ddmlib.FileListingService
97
import com.android.ddmlib.FileListingService.FileEntry
108
import com.android.ddmlib.IDevice
119
import org.gradle.api.file.RegularFile
10+
import org.gradle.api.provider.ProviderFactory
1211
import java.io.File
1312

14-
fun DeviceProviderInstrumentTestTask.deviceFileManager(): DeviceFileManager =
15-
DeviceFileManager(this)
13+
fun DeviceProviderInstrumentTestTask.deviceFileManager(
14+
applicationId: String,
15+
adbExecutablePath: String,
16+
providerFactory: ProviderFactory,
17+
): DeviceFileManager = DeviceFileManager(this, applicationId, adbExecutablePath, providerFactory)
1618

1719
class DeviceFileManager(
1820
private val testTask: DeviceProviderInstrumentTestTask,
21+
private val applicationId: String,
22+
private val adbExecutablePath: String,
23+
private val providerFactory: ProviderFactory,
1924
) {
20-
private val extension: TestedExtension = testTask
21-
.project
22-
.extensions
23-
.findByType(TestedExtension::class.java)
24-
?: throw RuntimeException("TestedExtension not found")
25-
26-
@Suppress("DEPRECATION")
27-
private val testedVariant: TestVariant = extension
28-
.testVariants
29-
.firstOrNull { it.name == testTask.variantName }
30-
?: throw RuntimeException("TestVariant not found")
3125

3226
fun pullRecordedSnapshots(
3327
destinationPath: String,
@@ -61,15 +55,15 @@ class DeviceFileManager(
6155
}
6256

6357
private fun getDeviceAndroidSnaptestingRootAbsolutePath(): String =
64-
"${FileListingService.DIRECTORY_SDCARD}/Download/android-snaptesting/${testedVariant.applicationId}"
58+
"${FileListingService.DIRECTORY_SDCARD}/Download/android-snaptesting/$applicationId"
6559
private fun getDeviceAndroidSnaptestingSubfolderAbsolutePath(subFolder: String): String =
6660
"${getDeviceAndroidSnaptestingRootAbsolutePath()}/$subFolder"
6761

6862
@Suppress("UnstableApiUsage")
6963
private fun withConnectedDevices(runnable: (List<ConnectedDevice>) -> Unit) {
7064
testTask.deviceProviderFactory.getDeviceProvider(
71-
testTask.project.provider {
72-
RegularFile { File(extension.adbExecutable.absolutePath) }
65+
providerFactory.provider {
66+
RegularFile { File(adbExecutablePath) }
7367
},
7468
System.getenv("ANDROID_SERIAL"),
7569
).let {
@@ -104,4 +98,4 @@ class DeviceFileManager(
10498
device.pullFile(it.fullPath, "$destinationPath/${it.name}")
10599
}
106100
}
107-
}
101+
}

0 commit comments

Comments
 (0)