ansman/kotshi

@KotshiJsonAdapterFactory generates a file with non-deterministic ordering, defeating Gradle's remote cache

autonomousapps opened this issue · 2 comments

I tried with Kotshi 1.0.5 and 1.0.6.
AGP 3.3.0.
Gradle 5.0.

Scenario:

  1. I have a remote build cache node
  2. I have a class with the @KotshiJsonAdapterFactory annotation (as below), in the :net module
  3. :app depends on :net
  4. I run ./gradlew :app:kaptDebugKotlin --build-cache on machine 1
  5. I run ./gradlew :app:kaptDebugKotlin --build-cache on machine 2

Observation:
The run on machine 2 fails to pull the :app:kaptDebugKotlin task from the remote cache because the class KotshiApplicationJsonAdapterFactory is different on the different machines. I diffed the file from one machine against the other and see many differences, but from what I can tell, the differences are only the order of the if statements. See this attached file for an example: diff.txt

Expectation:
The file is generated in the exact same way each time.

fun getMoshi(): Moshi = Moshi.Builder()
    .add(ApplicationJsonAdapterFactory.INSTANCE)
    .add(Date::class.java, Rfc3339DateJsonAdapter().nullSafe())
    .add(TypeAdapters())
    .build()

@KotshiJsonAdapterFactory
abstract class ApplicationJsonAdapterFactory : JsonAdapter.Factory {
    companion object {
        val INSTANCE: ApplicationJsonAdapterFactory = KotshiApplicationJsonAdapterFactory()
    }
}

Interesting, currently the order of the if statements is the same as the order in which the classes are processed meaning that it’s probably undefined. We should probably sort them based on the name to make it stable. Thanks for the report!

Will fix this for 2.0 which I'm working on right now.