Flipper replaces Stetho

Aleksei Shcherbakov
2 min readMar 20, 2021

In some of my projects, I used Stetho library for app run-time inspection, like network requests, shared preferences, databases. It worked via Chrome DevTools. But some time ago it was broken, I ran inspector and could see nothing. On StackOverflow I found that it’s Chrome bug, and only workaround is downgrade Chrome or use Edge browser instead.

This frustrated me, and I started googling for another options. And I found another library from Facebook called Flipper. This library is evolution of Stetho ideas, it has standalone client application, and plugins architecture. One of benefits over Stetho is that Flipper client listens for ADB connections and re-connects automatically. With Stetho I had to open new inspection page manually on every app run. It was really annoying. Flipper is easy to set up. Just few things I found.

To create FlipperOkhttpInterceptor, you need NetworkFlipperPlugin, but you should create and add plugins in your Application class. If you set up OkHttp in Dagger module, you need somehow inject NetworkFlipperPlugin into it. But there is easier way: you can get Flipper plugin from your app context:

fun createNetworkInterceptor(context: Context): Interceptor {
return FlipperOkhttpInterceptor(
AndroidFlipperClient.getInstance(context)
.getPlugin(NetworkFlipperPlugin.ID)
)
}

If you use debugImplementation to import Flipper, your code will not compile in release build, you need provide empty classes for releaseImplementation. You can import no-op package from documentation, but it doesn’t have plugin classes. What I did: moved all Flipper-related code into one FlipperInstaller class and placed it in src/debug/kotlin folder.

object FlipperInstaller {

fun install(context: Context) {
LeakCanary.config = LeakCanary.config.copy(
onHeapAnalyzedListener = FlipperLeakListener()
)

if (FlipperUtils.shouldEnableFlipper(context)) {
SoLoader.init(context, false);
val client = AndroidFlipperClient.getInstance(context)
client.addPlugin(InspectorFlipperPlugin(context, DescriptorMapping.withDefaults()))
client.addPlugin(NetworkFlipperPlugin())
client.addPlugin(SharedPreferencesFlipperPlugin(context))
client.addPlugin(DatabasesFlipperPlugin(context))
client.addPlugin(LeakCanary2FlipperPlugin())
client.start()
}
}

fun createNetworkInterceptor(context: Context): Interceptor {
return FlipperOkhttpInterceptor(
AndroidFlipperClient.getInstance(context)
.getPlugin(NetworkFlipperPlugin.ID)
)
}
}

And in folder src/release/kotlin I placed empty implementation:

object FlipperInstaller {

fun install(context: Context) {
// No-op
}

fun createNetworkInterceptor(context: Context) : Interceptor? {
// No-op
return null
}
}

That’s all, now debug and release builds compile successfully.

PS This is my first tech blog post, yay!

--

--