@@ -11,10 +11,10 @@ import org.gradle.api.file.*
11
11
import org.gradle.api.model.ObjectFactory
12
12
import org.gradle.api.tasks.*
13
13
import java.io.*
14
- import java.util.TreeSet
14
+ import java.util.TreeMap
15
15
import javax.inject.Inject
16
16
17
- open class ApiCompareCompareTask @Inject constructor(private val objects : ObjectFactory ): DefaultTask() {
17
+ open class KotlinApiCompareTask @Inject constructor(private val objects : ObjectFactory ): DefaultTask() {
18
18
19
19
/*
20
20
* Nullability and optionality is a workaround for
@@ -38,6 +38,7 @@ open class ApiCompareCompareTask @Inject constructor(private val objects: Object
38
38
39
39
@OutputFile
40
40
@Optional
41
+ @Suppress(" unused" )
41
42
val dummyOutputFile: File ? = null
42
43
43
44
private val projectName = project.name
@@ -47,38 +48,48 @@ open class ApiCompareCompareTask @Inject constructor(private val objects: Object
47
48
@TaskAction
48
49
fun verify () {
49
50
val projectApiDir = projectApiDir
50
- if (projectApiDir == null ) {
51
- error(" Expected folder with API declarations '$nonExistingProjectApiDir ' does not exist.\n " +
51
+ ? : error(" Expected folder with API declarations '$nonExistingProjectApiDir ' does not exist.\n " +
52
52
" Please ensure that ':apiDump' was executed in order to get API dump to compare the build against" )
53
- }
54
53
55
54
val subject = projectName
56
- val apiBuildDirFiles = mutableSetOf<RelativePath >()
57
- // We use case-insensitive comparison to workaround issues with case-insensitive OSes
58
- // and Gradle behaving slightly different on different platforms
59
- val expectedApiFiles = TreeSet <RelativePath > { rp, rp2 ->
55
+
56
+ /*
57
+ * We use case-insensitive comparison to workaround issues with case-insensitive OSes
58
+ * and Gradle behaving slightly different on different platforms.
59
+ * We neither know original sensitivity of existing .api files, not
60
+ * build ones, because projectName that is part of the path can have any sensitvity.
61
+ * To workaround that, we replace paths we are looking for the same paths that
62
+ * actually exist on FS.
63
+ */
64
+ fun caseInsensitiveMap () = TreeMap <RelativePath , RelativePath > { rp, rp2 ->
60
65
rp.toString().compareTo(rp2.toString(), true )
61
66
}
67
+
68
+ val apiBuildDirFiles = caseInsensitiveMap()
69
+ val expectedApiFiles = caseInsensitiveMap()
70
+
62
71
objects.fileTree().from(apiBuildDir).visit { file ->
63
- apiBuildDirFiles.add( file.relativePath)
72
+ apiBuildDirFiles[file.relativePath] = file.relativePath
64
73
}
65
74
objects.fileTree().from(projectApiDir).visit { file ->
66
- expectedApiFiles.add( file.relativePath)
75
+ expectedApiFiles[file.relativePath] = file.relativePath
67
76
}
68
77
69
78
if (apiBuildDirFiles.size != 1 ) {
70
79
error(" Expected a single file $subject .api, but found: $expectedApiFiles " )
71
80
}
72
81
73
- val expectedApiDeclaration = apiBuildDirFiles.single()
82
+ var expectedApiDeclaration = apiBuildDirFiles.keys .single()
74
83
if (expectedApiDeclaration !in expectedApiFiles) {
75
84
error(" File ${expectedApiDeclaration.lastName} is missing from ${projectApiDir.relativePath()} , please run " +
76
85
" :$subject :apiDump task to generate one" )
77
86
}
78
-
87
+ // Normalize case-sensitivity
88
+ expectedApiDeclaration = expectedApiFiles.getValue(expectedApiDeclaration)
89
+ val actualApiDeclaration = apiBuildDirFiles.getValue(expectedApiDeclaration)
79
90
val diffSet = mutableSetOf<String >()
80
91
val expectedFile = expectedApiDeclaration.getFile(projectApiDir)
81
- val actualFile = expectedApiDeclaration .getFile(apiBuildDir)
92
+ val actualFile = actualApiDeclaration .getFile(apiBuildDir)
82
93
val diff = compareFiles(expectedFile, actualFile)
83
94
if (diff != null ) diffSet.add(diff)
84
95
if (diffSet.isNotEmpty()) {
0 commit comments