Skip to content

Commit 7eeb891

Browse files
test: modernize E2E matrix and enable configuration cache strict mode
1 parent 72b1c91 commit 7eeb891

File tree

1 file changed

+85
-46
lines changed
  • oss-licenses-plugin/src/test/java/com/google/android/gms/oss/licenses/plugin

1 file changed

+85
-46
lines changed

oss-licenses-plugin/src/test/java/com/google/android/gms/oss/licenses/plugin/EndToEndTest.kt

Lines changed: 85 additions & 46 deletions
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,13 @@ abstract class EndToEndTest(private val agpVersion: String, private val gradleVe
3232

3333
private fun isBuiltInKotlinEnabled() = agpVersion.startsWith("9.")
3434

35+
private fun createRunner(vararg args: String): GradleRunner {
36+
return GradleRunner.create()
37+
.withProjectDir(projectDir)
38+
.withGradleVersion(gradleVersion)
39+
.withArguments(*args, "--configuration-cache")
40+
}
41+
3542
private lateinit var projectDir: File
3643

3744
@Before
@@ -60,6 +67,10 @@ abstract class EndToEndTest(private val agpVersion: String, private val gradleVe
6067
"""
6168
android.useAndroidX=true
6269
com.google.protobuf.use_unsafe_pre22_gencode=true
70+
# Enable configuration cache globally for testing, but build cache only when requested
71+
org.gradle.configuration-cache=true
72+
org.gradle.configuration-cache.problems=fail
73+
org.gradle.caching=false
6374
""".trimIndent()
6475
)
6576
File(projectDir, "settings.gradle").writeText(
@@ -79,10 +90,7 @@ abstract class EndToEndTest(private val agpVersion: String, private val gradleVe
7990

8091
@Test
8192
fun basic() {
82-
val result = GradleRunner.create()
83-
.withProjectDir(projectDir)
84-
.withGradleVersion(gradleVersion)
85-
.withArguments("releaseOssLicensesTask", "-s")
93+
val result = createRunner("releaseOssLicensesTask", "-s")
8694
.build()
8795
Assert.assertEquals(result.task(":collectReleaseDependencies")!!.outcome, TaskOutcome.SUCCESS)
8896
Assert.assertEquals(result.task(":releaseOssDependencyTask")!!.outcome, TaskOutcome.SUCCESS)
@@ -94,21 +102,17 @@ abstract class EndToEndTest(private val agpVersion: String, private val gradleVe
94102
File(projectDir, "build/generated/res/releaseOssLicensesTask/raw/third_party_license_metadata")
95103
Assert.assertEquals(expectedContents(isBuiltInKotlinEnabled()), metadata.readText())
96104

97-
val cleanResult = GradleRunner.create()
98-
.withProjectDir(projectDir)
99-
.withGradleVersion(gradleVersion)
100-
.withArguments("clean", "-s")
105+
val cleanResult = createRunner("clean", "-s")
101106
.build()
102-
Assert.assertFalse(File(projectDir, "build").exists())
103107
Assert.assertEquals(cleanResult.task(":clean")!!.outcome, TaskOutcome.SUCCESS)
108+
// Verify files are gone, but don't assert on the build directory itself as it may be locked
109+
Assert.assertFalse(dependenciesJson.exists())
110+
Assert.assertFalse(metadata.exists())
104111
}
105112

106113
@Test
107114
fun testAbsentDependencyReport() {
108-
val result = GradleRunner.create()
109-
.withProjectDir(projectDir)
110-
.withGradleVersion(gradleVersion)
111-
.withArguments("debugOssLicensesTask", "-s")
115+
val result = createRunner("debugOssLicensesTask", "-s")
112116
.build()
113117
Assert.assertEquals(result.task(":debugOssDependencyTask")!!.outcome, TaskOutcome.SUCCESS)
114118
Assert.assertEquals(result.task(":debugOssLicensesTask")!!.outcome, TaskOutcome.SUCCESS)
@@ -118,25 +122,28 @@ abstract class EndToEndTest(private val agpVersion: String, private val gradleVe
118122
}
119123

120124
@Test
121-
fun testConfigurationCache() {
122-
// First run to store the configuration cache
123-
GradleRunner.create()
124-
.withProjectDir(projectDir)
125-
.withGradleVersion(gradleVersion)
126-
.withArguments("releaseOssLicensesTask", "--configuration-cache")
127-
.build()
125+
fun testConfigAndBuildCache() {
126+
// 1. First run to store the configuration cache and build cache
127+
createRunner("releaseOssLicensesTask", "--build-cache").build()
128128

129-
// Second run to reuse the configuration cache
130-
val result = GradleRunner.create()
131-
.withProjectDir(projectDir)
132-
.withGradleVersion(gradleVersion)
133-
.withArguments("releaseOssLicensesTask", "--configuration-cache")
134-
.build()
129+
// 2. Clean the outputs to force a re-run (which should hit build cache)
130+
createRunner("clean", "-s").build()
131+
132+
// 3. Second run to reuse the configuration cache and hit the build cache
133+
val result = createRunner("releaseOssLicensesTask", "--build-cache").build()
134+
135+
println("CACHE TEST OUTPUT:\n" + result.output)
135136

136137
Assert.assertTrue(
138+
"Should reuse configuration cache",
137139
result.output.contains("Reusing configuration cache") ||
138140
result.output.contains("Configuration cache entry reused")
139141
)
142+
143+
Assert.assertTrue(
144+
"Should hit build cache",
145+
result.output.contains("FROM-CACHE")
146+
)
140147
}
141148

142149
@Test
@@ -185,17 +192,9 @@ abstract class EndToEndTest(private val agpVersion: String, private val gradleVe
185192
)
186193

187194
// Run with configuration cache twice to ensure resolution is stable and cacheable
188-
GradleRunner.create()
189-
.withProjectDir(projectDir)
190-
.withGradleVersion(gradleVersion)
191-
.withArguments("releaseOssLicensesTask", "--configuration-cache")
192-
.build()
195+
createRunner("releaseOssLicensesTask").build()
193196

194-
val result = GradleRunner.create()
195-
.withProjectDir(projectDir)
196-
.withGradleVersion(gradleVersion)
197-
.withArguments("releaseOssLicensesTask", "--configuration-cache")
198-
.build()
197+
val result = createRunner("releaseOssLicensesTask").build()
199198

200199
Assert.assertTrue(
201200
result.output.contains("Configuration cache entry reused") ||
@@ -210,12 +209,44 @@ abstract class EndToEndTest(private val agpVersion: String, private val gradleVe
210209
Assert.assertTrue(content.contains("apache.org/licenses/LICENSE-2.0"))
211210
}
212211

212+
@Test
213+
fun testClean() {
214+
// 1. Run the task to generate files
215+
createRunner("releaseOssLicensesTask", "-s").build()
216+
217+
val dependenciesJson = File(projectDir, "build/generated/third_party_licenses/release/dependencies.json")
218+
val metadata = File(projectDir, "build/generated/res/releaseOssLicensesTask/raw/third_party_license_metadata")
219+
220+
Assert.assertTrue("dependencies.json should exist", dependenciesJson.exists())
221+
Assert.assertTrue("metadata should exist", metadata.exists())
222+
223+
// 2. Run clean
224+
createRunner("clean", "-s").build()
225+
226+
// 3. Verify files are gone
227+
Assert.assertFalse("dependencies.json should be deleted", dependenciesJson.exists())
228+
Assert.assertFalse("metadata should be deleted", metadata.exists())
229+
// build directory might still exist due to daemon/test-runner locks, which is fine
230+
// as long as our specific generated content is gone.
231+
}
232+
233+
@Test
234+
fun testCleanAndBuild() {
235+
// TDD: This is a common developer workflow. It should work.
236+
// On Gradle 9.x, this currently fails because both tasks touch the same directory
237+
// without a defined relationship.
238+
val result = createRunner("clean", "releaseOssLicensesTask", "-s")
239+
.build()
240+
241+
Assert.assertTrue(result.task(":clean")?.outcome in listOf(TaskOutcome.SUCCESS, TaskOutcome.UP_TO_DATE))
242+
Assert.assertTrue(result.task(":releaseOssLicensesTask")?.outcome in listOf(TaskOutcome.SUCCESS, TaskOutcome.UP_TO_DATE))
243+
val metadata = File(projectDir, "build/generated/res/releaseOssLicensesTask/raw/third_party_license_metadata")
244+
Assert.assertTrue("Metadata should be generated after clean", metadata.exists())
245+
}
246+
213247
@Test
214248
fun clean() {
215-
val result = GradleRunner.create()
216-
.withProjectDir(projectDir)
217-
.withGradleVersion(gradleVersion)
218-
.withArguments("clean", "-s")
249+
val result = createRunner("clean", "-s")
219250
.build()
220251
Assert.assertEquals(result.task(":clean")!!.outcome, TaskOutcome.UP_TO_DATE)
221252
}
@@ -227,8 +258,15 @@ class EndToEndTest_AGP82_G82 : EndToEndTest("8.2.0", "8.2")
227258
class EndToEndTest_AGP87_G89 : EndToEndTest("8.7.0", "8.9")
228259
class EndToEndTest_AGP810_G811 : EndToEndTest("8.10.0", "8.11.1")
229260
class EndToEndTest_AGP812_G814 : EndToEndTest("8.12.2", "8.14")
230-
class EndToEndTest_AGP90_G90 : EndToEndTest("9.0.0-alpha03", "9.0.0")
231-
class EndToEndTest_AGP91_G931 : EndToEndTest("9.1.0-alpha05", "9.3.1")
261+
262+
/**
263+
* AGP 9+ Version Matrix:
264+
* Agents: Keep these tasks up to date with the latest stable, RC, and alpha releases.
265+
* Reference: https://developer.android.com/build/releases/agp-9-0-0-release-notes
266+
*/
267+
class EndToEndTest_AGP_STABLE_90_G91 : EndToEndTest("9.0.1", "9.1.0")
268+
class EndToEndTest_AGP_RC_91_G94 : EndToEndTest("9.1.0-rc01", "9.4.0")
269+
class EndToEndTest_AGP_ALPHA_92_G94 : EndToEndTest("9.2.0-alpha02", "9.4.0")
232270

233271
private fun expectedDependenciesJson(builtInKotlinEnabled: Boolean, agpVersion: String) = """[
234272
{
@@ -399,8 +437,8 @@ private fun expectedDependenciesJson(builtInKotlinEnabled: Boolean, agpVersion:
399437
{
400438
"group": "com.google.android.gms",
401439
"name": "play-services-tasks",
402-
"version": "17.0.0"${if (builtInKotlinEnabled) """
403-
},
440+
"version": "17.0.0"
441+
}${if (builtInKotlinEnabled) """,
404442
{
405443
"group": "org.jetbrains",
406444
"name": "annotations",
@@ -409,10 +447,11 @@ private fun expectedDependenciesJson(builtInKotlinEnabled: Boolean, agpVersion:
409447
{
410448
"group": "org.jetbrains.kotlin",
411449
"name": "kotlin-stdlib",
412-
"version": "${if (agpVersion.startsWith("9.1")) "2.2.10" else "2.2.0"}"""" else ""}
413-
}
450+
"version": "2.2.10"
451+
}""" else ""}
414452
]"""
415453

454+
416455
private fun expectedContents(builtInKotlinEnabled: Boolean) = """0:46 Android Support Library Annotations
417456
0:46 Android AppCompat Library v7
418457
0:46 Android Arch-Common

0 commit comments

Comments
 (0)