kotlinx-serialization-diff

A diffing library for Kotlin/Multiplatform which uses kotlinx.serialization for performant, type-safe diffing without reflection.
Dokka Documentation
Features
- Multiplatform: Supports JVM, JS, Wasm, Android, iOS, and Native targets.
- No Reflection: Leverages
kotlinx.serialization's compile-time generated serializers.
- Flexible: Supports deep diffing of nested objects, lists, and maps.
- Customizable: Choose between index-based diffing or Longest Common Subsequence (LCS) for list collections.
Getting Started
Add the dependency to your build.gradle.kts (check Maven Central for the latest version):
implementation("com.jessecorbett:kotlinx-serialization-diff:1.1.0")
Basic Usage
Use the diff function to get a list of changes:
import kotlinx.serialization.diff.diff
import kotlinx.serialization.Serializable
@Serializable
data class User(val name: String, val age: Int)
val user1 = User("Alice", 30)
val user2 = User("Alice", 31)
changes = diff(user1, user2)
Human-Readable Statements
For logging or UI display, use diffStatements to get a pre-formatted multi-line string:
import kotlinx.serialization.diff.diffStatements
val statements = diffStatements(user1, user2)
println(statements)
Alternatively, call .format() on any List<Diff>:
import kotlinx.serialization.diff.format
val output = diff(user1, user2).format()
Configuration
You can customize the diffing behavior by passing a DiffConfig.
List Diffing Strategies
kotlinx-serialization-diff supports two strategies for diffing lists and collections:
INDEX_BY_INDEX (Default): Compares elements at the same index. Best for fixed-position data.
LCS: Uses the Longest Common Subsequence (Myers' diff algorithm) to identify insertions and deletions. Best for lists where items might be shifted.
import kotlinx.serialization.diff.DiffConfig
import kotlinx.serialization.diff.ListDiffStrategy
val config = DiffConfig(listStrategy = ListDiffStrategy.LCS)
val changes = diff(oldList, newList, config)
Custom Serializers Modules
If your models use contextual or polymorphic serialization that requires a custom SerializersModule, you can provide it in the configuration:
import kotlinx.serialization.modules.SerializersModule
val myModule = SerializersModule {
contextual(MyCustomSerializer)
}
val config = DiffConfig(serializersModule = myModule)
val changes = diff(obj1, obj2, config)
Types of Diffs
The library identifies several types of changes:
License
This project is licensed under the Apache License, Version 2.0.