rebugger
1.0.1indexedTracks changes in composable arguments, printing recomposition reasons in Logcat. Customizable for tagging and logging methods. Includes IntelliJ plugin for generating function calls automatically.
Tracks changes in composable arguments, printing recomposition reasons in Logcat. Customizable for tagging and logging methods. Includes IntelliJ plugin for generating function calls automatically.
Rebugger : A recomposition debugger
Being a “compose dev” our enemy number one is unnecessary recompositions 🤕. Often times we use tools like recompositionHighligher, LogComposition, and layout inspector to count the recomposition, but there’s no direct way to understand “why” the recomposition has happened.
Rebugger is a simple compose utility function that can track the change in the given arguments. It’ll print the reason for recomposition in your Logcat window.

Kotlin Script
repositories {
...
mavenCentral()
}
dependencies {
// [latest version - i promise!]
implementation("io.github.theapache64:rebugger:1.0.1")
}
Groovy
repositories {
...
mavenCentral()
}
dependencies {
// [latest version - i promise!]
implementation 'io.github.theapache64:rebugger:1.0.1'
}
Rebugger callCall
Rebuggerwith the states or args you want to track
@Composable
fun VehicleUi(
car: Car,
bike: Bike,
) {
var human by remember { mutableStateOf(Human("John")) }
// Call Rebugger and pass the states you want to track.
// It could be a function arg or a state
Rebugger(
trackMap = mapOf(
"car" to car,
"bike" to bike,
"human" to human
),
)
LogCatSearch for
Rebugger





You can use the RebuggerConfig.init function to override default properties of Rebugger.
class App : Application() {
// ...
override fun onCreate() {
super.onCreate()
// ...
RebuggerConfig.init(
tag = "MyAppRebugger", // changing default tag
logger = { tag, message -> Timber.i(tag, message) } // use Timber for logging
)
}
}
You can use the Rebugger IntelliJ plugin to generate the Rebugger function call.
https://user-images.githubusercontent.com/9678279/235495156-445e7ced-30fa-41dd-9b37-84b80502187f.mov
When Rebugger is placed deep inside the composable, it may not be able to pick the correct composable name. For example, if I place the Rebugger somewhere inside the Button lambda like this
@Composable
fun VehicleUi(
car: Car,
bike: Bike,
) {
// ...
Column {
// ...
Button(
onClick = {
//...
}
) {
// 🟠 Inside Button's content lambda
Rebugger(
trackMap = mapOf(
"car" to car,
"bike" to bike,
"human" to human
),
)
}
}
}
It’ll print something like this

To fix this, you can pass composableName argument to override the automatic name picking behaviour
Rebugger(
composableName = "Button's body",
trackMap = mapOf(
"car" to car,
"bike" to bike,
"human" to human
),
)
Surfaced from shared tags and platforms — no rankings paid for.