Member-only story
Fan-Out With a Seatbelt: Six Ways flatMapMerge Bites Android Apps in Production
flatMapMerge Bites Android Apps in ProductionNot a Medium Member? “Read For Free”
flatMapMerge looks like a one-line upgrade from "sequential" to "fast". It is also one of the few Flow operators where a harmless-looking change quietly alters ordering, error semantics, resource usage and lifecycle behaviour all at once. This post walks through what the operator guarantees, when you should not reach for it at all, and six failure modes I would check for in any code review.
🧠 TL;DR (Too Long; Didn’t Read)
- The official docs describe
flatMapMergeasmap(transform).flattenMerge(concurrency), and they explicitly discourage it in ordinary application flows. A suspendingmapis usually enough. transformis invoked sequentially. Only the returned inner flows are collected concurrently.- Output order is the order in which items are emitted, not the order of the source.
- The operator is still marked
@ExperimentalCoroutinesApi, so you need an opt-in and should expect the API surface to move.
1. What the operator actually does
@ExperimentalCoroutinesApi
fun <T, R> Flow<T>.flatMapMerge(
concurrency: Int = DEFAULT_CONCURRENCY,
transform: suspend (value: T) ->…









