Skip to content

Commit 1d54ec7

Browse files
author
Marcel Schnelle
committed
Working towards addressing classpath issues on 3.0.0+
* Include AGP as compile-only dep. to be able to access its version * Rework Compat class to properly collect output dirs on 3.0.0+; also utilize semantic versioning rather than property checks directly * Added unit tests for Compat class
1 parent 07015f5 commit 1d54ec7

File tree

5 files changed

+188
-32
lines changed

5 files changed

+188
-32
lines changed

android-junit5/build.gradle

Lines changed: 10 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -19,11 +19,15 @@ configurations {
1919
sourceSets {
2020
testAgp2x {
2121
java.srcDir "src/testAgp2x/groovy"
22+
compileClasspath += sourceSets.main.output
23+
runtimeClasspath += sourceSets.main.output
2224
compileClasspath += sourceSets.test.output
2325
runtimeClasspath += sourceSets.test.output
2426
}
2527
testAgp3x {
2628
java.srcDir "src/testAgp3x/groovy"
29+
compileClasspath += sourceSets.main.output
30+
runtimeClasspath += sourceSets.main.output
2731
compileClasspath += sourceSets.test.output
2832
runtimeClasspath += sourceSets.test.output
2933
}
@@ -39,15 +43,16 @@ idea {
3943
dependencies {
4044
compile gradleApi()
4145
compile localGroovy()
46+
compile "com.github.zafarkhaja:java-semver:$SEMVER_VERSION"
4247
compile "org.junit.platform:junit-platform-gradle-plugin:$JUNIT_PLATFORM_VERSION"
48+
compileOnly "com.android.tools.build:gradle:$ANDROID_PLUGIN_VERSION_2X"
4349

4450
testCompile "junit:junit:$JUNIT4_VERSION"
45-
testCompile("org.spockframework:spock-core:$SPOCK_VERSION") {
46-
transitive = false
47-
}
51+
testCompile("org.spockframework:spock-core:$SPOCK_VERSION") { transitive = false }
52+
testCompileOnly "com.android.tools.build:gradle:$ANDROID_PLUGIN_VERSION_3X"
4853

49-
testAgp2xCompile "com.android.tools.build:gradle:2.3.2"
50-
testAgp3xCompile "com.android.tools.build:gradle:3.0.0-alpha1"
54+
testAgp2xCompile "com.android.tools.build:gradle:$ANDROID_PLUGIN_VERSION_2X"
55+
testAgp3xCompile "com.android.tools.build:gradle:$ANDROID_PLUGIN_VERSION_3X"
5156
}
5257

5358
// Run Unit Tests against Android Gradle Plugin version 2.x
Lines changed: 21 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,22 +1,37 @@
11
package de.mannodermaus.gradle.anj5
22

3+
import com.android.build.gradle.internal.scope.VariantScope
4+
import com.github.zafarkhaja.semver.Version
5+
36
class AndroidJUnit5Compat {
47

8+
private static final Version AGP_2_2_0 = Version.valueOf("2.2.0-alpha1")
9+
private static final Version AGP_3_0_0 = Version.valueOf("3.0.0-alpha1")
10+
511
/**
612
* Fetches the Java output directories for the given Variant scopes
713
* across different versions of the Android Gradle plugin.
14+
* @param agpVersion Version of the Android Gradle Plugin
815
* @param variantScope VariantScope to look up the Java outputs from
16+
* @see {@link VariantScope}
917
* @return An Iterable container depicting the output directories
1018
*/
11-
static Iterable<File> getJavaOutputDirs(variantScope) {
12-
if (variantScope.hasProperty("javaOutputs")) {
13-
return variantScope.javaOutputs
14-
15-
} else if (variantScope.hasProperty("javaOuptuts")) {
19+
static Iterable<File> getJavaOutputDirs(Version agpVersion, def variantScope) {
20+
if (agpVersion.lessThan(AGP_2_2_0)) {
21+
// Below the first alpha of AGP 2.2.0, there was a typo in VariantScope
22+
// related to the Java outputs of a Variant
1623
return variantScope.javaOuptuts
1724

25+
} else if (agpVersion.lessThan(AGP_3_0_0)) {
26+
// Below the first alpha of AGP 3.0.0, use the unified VariantScope method
27+
return variantScope.javaOutputs
28+
1829
} else {
19-
return Collections.singletonList(variantScope.javaOutputDir)
30+
// On and after AGP 3.0.0, use the separated methods for Java and annotation processors
31+
return [
32+
variantScope.javaOutputDir as File,
33+
variantScope.annotationProcessorOutputDir as File
34+
]
2035
}
2136
}
2237
}

android-junit5/src/main/groovy/de/mannodermaus/gradle/anj5/AndroidJUnitPlatformPlugin.groovy

Lines changed: 16 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,7 @@
11
package de.mannodermaus.gradle.anj5
22

3+
import com.android.build.gradle.internal.scope.VariantScope
4+
import com.github.zafarkhaja.semver.Version
35
import org.gradle.api.GradleException
46
import org.gradle.api.Project
57
import org.gradle.api.ProjectConfigurationException
@@ -91,6 +93,8 @@ class AndroidJUnitPlatformPlugin extends JUnitPlatformPlugin {
9193
}
9294

9395
private void configure(Project project, AndroidJUnit5PlatformExtension junitExtension) {
96+
def agpVersion = Version.valueOf(com.android.builder.Version.ANDROID_GRADLE_PLUGIN_VERSION)
97+
9498
// Add the test task to each of the project's unit test variants
9599
def allVariants = isAndroidLibrary(project) ? "libraryVariants" : "applicationVariants"
96100
def testVariants = project.android[allVariants].findAll { it.hasProperty("unitTestVariant") }
@@ -101,13 +105,14 @@ class AndroidJUnitPlatformPlugin extends JUnitPlatformPlugin {
101105

102106
// Obtain variant properties
103107
def variantData = variant.variantData
104-
def variantScope = variantData.scope
105-
def scopeJavaOutputs = AndroidJUnit5Compat.getJavaOutputDirs(variantScope)
108+
VariantScope variantScope = variantData.scope
109+
def scopeJavaOutputs = AndroidJUnit5Compat.getJavaOutputDirs(agpVersion, variantScope)
106110

107111
// Obtain tested variant properties
108112
def testedVariantData = variant.testedVariant.variantData
109-
def testedVariantScope = testedVariantData.scope
110-
def testedScopeJavaOutputs = AndroidJUnit5Compat.getJavaOutputDirs(testedVariantScope)
113+
VariantScope testedVariantScope = testedVariantData.scope
114+
115+
def testedScopeJavaOutputs = AndroidJUnit5Compat.getJavaOutputDirs(agpVersion, testedVariantScope)
111116

112117
// Collect the root directories for unit tests from the variant's scopes
113118
def testRootDirs = []
@@ -128,13 +133,13 @@ class AndroidJUnitPlatformPlugin extends JUnitPlatformPlugin {
128133
}
129134

130135
// 2) Add the runtime configurations
131-
// def testRuntime = project.configurations.findByName("testRuntimeOnly")
132-
// if (testRuntime == null) {
133-
// testRuntime = project.configurations.findByName("testApk")
134-
// }
135-
// if (testRuntime != null) {
136-
// classpath.add(testRuntime)
137-
// }
136+
def testRuntime = project.configurations.findByName("testRuntimeOnly")
137+
if (testRuntime == null) {
138+
testRuntime = project.configurations.findByName("testApk")
139+
}
140+
if (testRuntime != null) {
141+
classpath.add(testRuntime)
142+
}
138143

139144
// 3) Add test resources
140145
classpath.add(variantData.javaResourcesForUnitTesting)
Lines changed: 128 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,128 @@
1+
package de.mannodermaus.gradle.anj5
2+
3+
import com.github.zafarkhaja.semver.Version
4+
import spock.lang.Specification
5+
6+
/**
7+
* Test the behavior of AndroidJUnit5Compat methods on different versions of the AGP.
8+
*/
9+
@SuppressWarnings("GroovyAssignabilityCheck")
10+
class AndroidJUnit5CompatSpec extends Specification {
11+
12+
MockedVariantScope mockedScope
13+
14+
def setup() {
15+
mockedScope = new MockedVariantScope()
16+
}
17+
18+
def "Use javaOuptuts below AGP 2.2.0"() {
19+
when:
20+
def versions = [
21+
"2.0.0-alpha1",
22+
"2.0.0-beta2",
23+
"2.0.0-rc1",
24+
"2.0.0",
25+
"2.1.0-alpha1",
26+
"2.1.0-beta1",
27+
"2.1.0-rc1",
28+
"2.1.0",
29+
"2.1.2",
30+
"2.1.3",
31+
]
32+
33+
versions.forEach {
34+
AndroidJUnit5Compat.getJavaOutputDirs(Version.valueOf(it), mockedScope)
35+
}
36+
37+
then:
38+
assert mockedScope.calledJavaOuptuts == versions.size()
39+
assert mockedScope.calledJavaOutputs == 0
40+
assert mockedScope.calledJavaOutputDir == 0
41+
assert mockedScope.calledAnnotationProcessorOutputDir == 0
42+
}
43+
44+
def "Use javaOutputs below AGP 3.0.0"() {
45+
when:
46+
def versions = [
47+
"2.2.0-alpha1",
48+
"2.2.0-beta1",
49+
"2.2.0-rc1",
50+
"2.2.0",
51+
"2.2.1",
52+
"2.2.2",
53+
"2.2.3",
54+
"2.3.0-alpha1",
55+
"2.3.0-beta1",
56+
"2.3.0-rc1",
57+
"2.3.0",
58+
"2.4.0-alpha1",
59+
]
60+
61+
versions.forEach {
62+
AndroidJUnit5Compat.getJavaOutputDirs(Version.valueOf(it), mockedScope)
63+
}
64+
65+
then:
66+
assert mockedScope.calledJavaOuptuts == 0
67+
assert mockedScope.calledJavaOutputs == versions.size()
68+
assert mockedScope.calledJavaOutputDir == 0
69+
assert mockedScope.calledAnnotationProcessorOutputDir == 0
70+
}
71+
72+
def "Use separated outputs after AGP 3.0.0"() {
73+
when:
74+
def versions = [
75+
"3.0.0-alpha1",
76+
"3.0.0-alpha2",
77+
]
78+
79+
versions.forEach {
80+
AndroidJUnit5Compat.getJavaOutputDirs(Version.valueOf(it), mockedScope)
81+
}
82+
83+
then:
84+
assert mockedScope.calledJavaOuptuts == 0
85+
assert mockedScope.calledJavaOutputs == 0
86+
assert mockedScope.calledJavaOutputDir == versions.size()
87+
assert mockedScope.calledAnnotationProcessorOutputDir == versions.size()
88+
}
89+
90+
/* Inner classes & mocks */
91+
92+
/**
93+
* VariantScope mock, which simulates
94+
* all different versions of the VariantScope interface relevant to the plugin,
95+
* and simply counts the invocations of its methods.
96+
*/
97+
static final class MockedVariantScope {
98+
99+
private int calledJavaOutputs = 0
100+
private int calledJavaOuptuts = 0
101+
102+
private int calledJavaOutputDir = 0
103+
private int calledAnnotationProcessorOutputDir = 0
104+
105+
MockedVariantScope() {
106+
}
107+
108+
Iterable<File> getJavaOuptuts() {
109+
calledJavaOuptuts++
110+
return []
111+
}
112+
113+
Iterable<File> getJavaOutputs() {
114+
calledJavaOutputs++
115+
return []
116+
}
117+
118+
File getJavaOutputDir() {
119+
calledJavaOutputDir++
120+
return new File("")
121+
}
122+
123+
File getAnnotationProcessorOutputDir() {
124+
calledAnnotationProcessorOutputDir++
125+
return new File("")
126+
}
127+
}
128+
}

gradle.properties

Lines changed: 13 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,17 +1,20 @@
11
# suppress inspection "UnusedProperty" for whole file
22

33
# Artifact configuration
4-
GROUP_ID = de.mannodermaus.gradle.plugins
5-
ARTIFACT_ID = android-junit5
6-
VERSION_NAME = 1.0.0-M4-rev1
7-
DESCRIPTION = Unit Testing with JUnit 5 for Android.
8-
VCS_URL = https://github.com/aurae/android-junit5
4+
GROUP_ID = de.mannodermaus.gradle.plugins
5+
ARTIFACT_ID = android-junit5
6+
VERSION_NAME = 1.0.0-M4-rev1
7+
DESCRIPTION = Unit Testing with JUnit 5 for Android.
8+
VCS_URL = https://github.com/aurae/android-junit5
99

1010
# Dependency versions (plugins)
11-
ANDROID_PLUGIN_VERSION = 3.0.0-alpha1
12-
BINTRAY_PLUGIN_VERSION = 1.3.1
11+
ANDROID_PLUGIN_VERSION_2X = 2.3.2
12+
ANDROID_PLUGIN_VERSION_3X = 3.0.0-alpha2
13+
BINTRAY_PLUGIN_VERSION = 1.3.1
1314

1415
# Dependency versions
15-
JUNIT_PLATFORM_VERSION = 1.0.0-M4
16-
SPOCK_VERSION = 1.0-groovy-2.4
17-
JUNIT4_VERSION = 4.12
16+
SEMVER_VERSION = 0.9.0
17+
JUNIT_PLATFORM_VERSION = 1.0.0-M4
18+
19+
JUNIT4_VERSION = 4.12
20+
SPOCK_VERSION = 1.0-groovy-2.4

0 commit comments

Comments
 (0)