The detail destination in Type-Safe Routes looks its book up with books.first { it.id == id }, and first throws when nothing matches. That listing was left as printed so that it crashes here. The deep link (Deep Links) trusts its argument: adb shell am start -a android.intent.action.VIEW -d booknest://book/99 closed the app, and adb logcat -b crash said why:
E/AndroidRuntime( 5125): FATAL EXCEPTION: main
E/AndroidRuntime( 5125): Process: com.example.booknest, PID: 5125
E/AndroidRuntime( 5125): java.util.NoSuchElementException: Collection contains no element
matching
the predicate.
E/AndroidRuntime( 5125): at com.example.booknest.ui.nav.BookNestNavKt.BookNestNav$lambda$5$0$
0$0$0$1
(BookNestNav.kt:169)
E/AndroidRuntime( 5125): at com.example.booknest.ui.nav.BookNestNavKt.$r8$lambda$wqDf-boopIQp
A6Rn
JavLdgl9rG0(Unknown Source:0)
...
E/AndroidRuntime( 5125): at androidx.navigation.compose.NavHostKt.NavHost$lambda$34$1
(NavHost.kt:1020)
...Read it in four steps. The thread: main, so the UI thread threw. The exception: NoSuchElementException. Your first frame: the top line in your package, a lambda nested five deep in BookNestNav, the composable<BookDetail> block. The line: 169, in a 129-line file. A line past the end means inlined code: the standard library's inline first is mapped after the file's own lines. Skip the $r8$lambda frames (D8 desugaring) and the framework; a Caused by: section holds the root cause.
The fix treats the link as untrusted input:
val book = books.firstOrNull { it.id == id } // 5.35.5 a deep link can lie
if (book == null) {
Log.w(TAG, "no book with id=$id")
Text("No book with id $id", Modifier.padding(16.dp))
return@composable
}After it, the same command logged W/BookNestNav( 5992): no book with id=99 and showed the message. An ANR (a main thread blocked for 5 seconds) leaves its stacks in /data/anr/ for adb bugreport. Release-build frames read a.b.c until R8 234 's mapping file restores them (R8 Full Mode).