From 2a0eeed55fabba04ce5caa2d323b43c114b671fe Mon Sep 17 00:00:00 2001 From: davotoula Date: Mon, 15 Dec 2025 18:55:34 +0100 Subject: [PATCH] code review: remove unsafe casting to avoid app crash if a non-voice reply context leaks through lint fixes --- .../ui/actions/uploads/VoiceMessagePreview.kt | 5 ++--- .../ui/screen/loggedIn/home/ShortNotePostScreen.kt | 8 ++------ .../ui/screen/loggedIn/home/ShortNotePostViewModel.kt | 11 ++++++----- 3 files changed, 10 insertions(+), 14 deletions(-) diff --git a/amethyst/src/main/java/com/vitorpamplona/amethyst/ui/actions/uploads/VoiceMessagePreview.kt b/amethyst/src/main/java/com/vitorpamplona/amethyst/ui/actions/uploads/VoiceMessagePreview.kt index 7a2fb1759..a601837be 100644 --- a/amethyst/src/main/java/com/vitorpamplona/amethyst/ui/actions/uploads/VoiceMessagePreview.kt +++ b/amethyst/src/main/java/com/vitorpamplona/amethyst/ui/actions/uploads/VoiceMessagePreview.kt @@ -20,7 +20,6 @@ */ package com.vitorpamplona.amethyst.ui.actions.uploads -import android.content.Context import android.media.MediaPlayer import android.util.Log import androidx.compose.foundation.background @@ -77,7 +76,7 @@ fun VoiceMessagePreview( // Initialize MediaPlayer DisposableEffect(voiceMetadata.url, localFile) { - val player = createMediaPlayer(context, voiceMetadata.url, localFile) + val player = createMediaPlayer(voiceMetadata.url, localFile) player?.setOnCompletionListener { isPlaying = false progress = 0f @@ -242,7 +241,6 @@ fun VoiceMessagePreview( } private fun createMediaPlayer( - context: Context, url: String, localFile: File?, ): MediaPlayer? = @@ -256,5 +254,6 @@ private fun createMediaPlayer( prepare() } } catch (e: Exception) { + Log.w("VoiceMessagePreview", "Failed to create MediaPlayer", e) null } diff --git a/amethyst/src/main/java/com/vitorpamplona/amethyst/ui/screen/loggedIn/home/ShortNotePostScreen.kt b/amethyst/src/main/java/com/vitorpamplona/amethyst/ui/screen/loggedIn/home/ShortNotePostScreen.kt index 09b288a3b..b347e68b3 100644 --- a/amethyst/src/main/java/com/vitorpamplona/amethyst/ui/screen/loggedIn/home/ShortNotePostScreen.kt +++ b/amethyst/src/main/java/com/vitorpamplona/amethyst/ui/screen/loggedIn/home/ShortNotePostScreen.kt @@ -479,16 +479,12 @@ private fun NewPostScreenBody( ) } - BottomRowActions(postViewModel, accountViewModel) + BottomRowActions(postViewModel) } } @Composable -private fun BottomRowActions( - postViewModel: ShortNotePostViewModel, - accountViewModel: AccountViewModel, -) { - val context = LocalContext.current +private fun BottomRowActions(postViewModel: ShortNotePostViewModel) { val scrollState = rememberScrollState() Row( modifier = diff --git a/amethyst/src/main/java/com/vitorpamplona/amethyst/ui/screen/loggedIn/home/ShortNotePostViewModel.kt b/amethyst/src/main/java/com/vitorpamplona/amethyst/ui/screen/loggedIn/home/ShortNotePostViewModel.kt index 2a243073b..8915803d6 100644 --- a/amethyst/src/main/java/com/vitorpamplona/amethyst/ui/screen/loggedIn/home/ShortNotePostViewModel.kt +++ b/amethyst/src/main/java/com/vitorpamplona/amethyst/ui/screen/loggedIn/home/ShortNotePostViewModel.kt @@ -235,7 +235,7 @@ open class ShortNotePostViewModel : fun hasLnAddress(): Boolean = account.userProfile().info?.lnAddress() != null - fun user(): User? = account.userProfile() + fun user(): User = account.userProfile() open fun init(accountVM: AccountViewModel) { this.accountViewModel = accountVM @@ -534,15 +534,16 @@ open class ShortNotePostViewModel : private suspend fun createTemplate(): EventTemplate? { // Check if this is a voice message voiceMetadata?.let { audioMeta -> - return if (originalNote != null) { + // Only create voice reply if original note is also a VoiceEvent + val originalVoiceHint = originalNote?.toEventHint() + return if (originalVoiceHint != null) { // Create voice reply event - @Suppress("UNCHECKED_CAST") VoiceReplyEvent.build( voiceMessage = audioMeta, - replyingTo = originalNote!!.toEventHint() as com.vitorpamplona.quartz.nip01Core.hints.EventHintBundle, + replyingTo = originalVoiceHint, ) } else { - // Create root voice event + // Create root voice event (no reply or original is not a voice message) VoiceEvent.build( voiceMessage = audioMeta, )