GSoC 2026: Compose Multiplatform Migration of ListenBrainz-Android

Hi everyone,

I’m Nirvan Jain (nirvan_jain on IRC, nirvan73 on GitHub), I’m currently a pre-final year student at IIIT Jabalpur. This summer I was offered this opportunity to work with MetaBrainz through Google Summer of Code on migrating the ListenBrainz android app to Kotlin Multiplatform and Compose Multiplatform, so that most of the same codebase can eventually run on iOS under the mentorship of Jasjeet Singh (jasje on IRC).

This post covers what the project was, everything I worked on, the parts that went wrong, what’s still left, and what the summer was actually like.

How I got here

I started contributing to ListenBrainz in December 2025. It was the first external open source project I’d worked on. Everything before that was coursework, side projects, or intra-college events.

My first PRs were small work which helped me a lot to understand the codebase from the ground, the shimmer effect across the Feed and Profile tabs, then extending search to cover playlists, artists, albums and tracks, plus some bug fixes. Small changes, but they taught me the codebase and how review works when nobody knows you and the code has to stand on its own.

I picked ListenBrainz because music is a constant in my day, whether I’m coding or not, and because I like that it treats your listening history as something you own.

The Problem

ListenBrainz has an Android app but no iOS version. A previous Swift attempt just duplicated the codebase, so every bug fix had to be written twice.

This project solves that by migrating to Kotlin Multiplatform, one shared codebase for both platforms. A large part of the work is replacing Android-only libraries with multiplatform equivalents across navigation, dependency injection and paging. Media playback is the harder case. ExoPlayer and WorkManager are tied too closely to Android to share, so both go behind common interfaces, with ExoPlayer on Android and AVPlayer on iOS underneath.

Getting this foundation right is what makes the rest cheap. Once it’s in place a feature or a bug fix is written once, instead of the same business logic being implemented twice and two apps being kept in sync by hand.

One thing genuinely can’t move. The notification listener that reads what’s playing in Spotify depends on an Android-only permission, and iOS has no equivalent to offer. Those screens stay Android-only. Everything else runs from one codebase on both platforms.

Continue Reading