Allow internal shares as long as they originate from our process.

This commit is contained in:
Greyson Parrelli
2026-04-10 16:17:41 -04:00
committed by Cody Henthorne
parent 773d6c36dc
commit c449f72786
5 changed files with 27 additions and 7 deletions

View File

@@ -2,10 +2,12 @@ package org.thoughtcrime.securesms.mediapreview
import android.annotation.SuppressLint
import android.content.ActivityNotFoundException
import android.content.ComponentName
import android.content.Context
import android.content.Intent
import android.graphics.PorterDuff
import android.graphics.PorterDuffColorFilter
import android.os.Build
import android.os.Bundle
import android.text.Annotation
import android.text.SpannableString
@@ -67,6 +69,7 @@ import org.thoughtcrime.securesms.mediapreview.mediarail.MediaRailAdapter.ImageL
import org.thoughtcrime.securesms.mediasend.v2.MediaSelectionActivity
import org.thoughtcrime.securesms.mms.PartAuthority
import org.thoughtcrime.securesms.recipients.Recipient
import org.thoughtcrime.securesms.sharing.v2.ShareActivity
import org.thoughtcrime.securesms.util.ContextUtil
import org.thoughtcrime.securesms.util.DateUtils
import org.thoughtcrime.securesms.util.Debouncer
@@ -578,6 +581,10 @@ class MediaPreviewV2Fragment :
.createChooserIntent()
.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION)
if (Build.VERSION.SDK_INT < 34) {
shareIntent.putExtra(Intent.EXTRA_EXCLUDE_COMPONENTS, arrayOf(ComponentName(requireContext(), ShareActivity::class.java)))
}
try {
startActivity(shareIntent)
} catch (e: ActivityNotFoundException) {

View File

@@ -4,7 +4,9 @@ import android.app.Activity
import android.content.Context
import android.content.Intent
import android.net.Uri
import android.os.Build
import android.os.Bundle
import android.os.Process
import android.view.ViewGroup
import android.widget.Toast
import androidx.activity.result.ActivityResultLauncher
@@ -194,12 +196,14 @@ class ShareActivity : PassphraseRequiredActivity(), MultiselectForwardFragment.C
override fun getDialogBackgroundColor(): Int = ContextCompat.getColor(this, R.color.signal_background_primary)
private fun getUnresolvedShareData(): Result<UnresolvedShareData, IntentError> {
val isInternalShare = Build.VERSION.SDK_INT >= 34 && getLaunchedFromUid() == Process.myUid()
return when (intent.action) {
Intent.ACTION_SEND_MULTIPLE if intent.hasExtra(Intent.EXTRA_STREAM) -> {
intent.getParcelableArrayListExtraCompat(Intent.EXTRA_STREAM, Uri::class.java)?.let { uris ->
val text: CharSequence? = intent.getCharSequenceArrayListExtra(Intent.EXTRA_TEXT)
?.let { textExtras -> combineTextExtras(textExtras) }
Result.success(UnresolvedShareData.ExternalMultiShare(uris, text))
Result.success(UnresolvedShareData.ExternalMultiShare(uris, text, isInternalShare))
} ?: Result.failure(IntentError.SEND_MULTIPLE_STREAM)
}
@@ -215,7 +219,7 @@ class ShareActivity : PassphraseRequiredActivity(), MultiselectForwardFragment.C
extractSingleExtraTextFromIntent(IntentError.SEND_STREAM)
} else {
val text: CharSequence? = if (intent.hasExtra(Intent.EXTRA_TEXT)) intent.getCharSequenceExtra(Intent.EXTRA_TEXT) else null
Result.success(UnresolvedShareData.ExternalSingleShare(uri, intent.type, text))
Result.success(UnresolvedShareData.ExternalSingleShare(uri, intent.type, text, isInternalShare))
}
}

View File

@@ -32,7 +32,7 @@ class ShareRepository(context: Context) {
@WorkerThread
@Throws(IOException::class)
private fun resolve(multiShareExternal: UnresolvedShareData.ExternalSingleShare): ResolvedShareData {
if (!UriUtil.isValidExternalUri(appContext, multiShareExternal.uri)) {
if (!multiShareExternal.isInternalShare && !UriUtil.isValidExternalUri(appContext, multiShareExternal.uri)) {
return ResolvedShareData.Failure
}
@@ -70,7 +70,7 @@ class ShareRepository(context: Context) {
@WorkerThread
private fun resolve(externalMultiShare: UnresolvedShareData.ExternalMultiShare): ResolvedShareData {
val mimeTypes: Map<Uri, String> = externalMultiShare.uris
.filter { UriUtil.isValidExternalUri(appContext, it) }
.filter { externalMultiShare.isInternalShare || UriUtil.isValidExternalUri(appContext, it) }
.associateWith { uri -> getMimeType(appContext, uri, null) }
.filterValues {
MediaUtil.isImageType(it) || MediaUtil.isVideoType(it)

View File

@@ -3,7 +3,7 @@ package org.thoughtcrime.securesms.sharing.v2
import android.net.Uri
sealed class UnresolvedShareData {
data class ExternalMultiShare(val uris: List<Uri>, val text: CharSequence?) : UnresolvedShareData()
data class ExternalSingleShare(val uri: Uri, val mimeType: String?, val text: CharSequence?) : UnresolvedShareData()
data class ExternalMultiShare(val uris: List<Uri>, val text: CharSequence?, val isInternalShare: Boolean = false) : UnresolvedShareData()
data class ExternalSingleShare(val uri: Uri, val mimeType: String?, val text: CharSequence?, val isInternalShare: Boolean = false) : UnresolvedShareData()
data class ExternalPrimitiveShare(val text: CharSequence) : UnresolvedShareData()
}

View File

@@ -1,9 +1,11 @@
package org.thoughtcrime.securesms.stories.dialogs
import android.content.ActivityNotFoundException
import android.content.ComponentName
import android.content.Context
import android.content.Intent
import android.net.Uri
import android.os.Build
import android.view.View
import android.view.ViewGroup
import android.widget.Toast
@@ -26,6 +28,7 @@ import org.thoughtcrime.securesms.database.model.MessageRecord
import org.thoughtcrime.securesms.database.model.MmsMessageRecord
import org.thoughtcrime.securesms.database.model.databaseprotos.StoryTextPost
import org.thoughtcrime.securesms.providers.BlobProvider
import org.thoughtcrime.securesms.sharing.v2.ShareActivity
import org.thoughtcrime.securesms.stories.StoryTextPostModel
import org.thoughtcrime.securesms.stories.landing.StoriesLandingItem
import org.thoughtcrime.securesms.stories.viewer.page.StoryPost
@@ -118,11 +121,17 @@ object StoryContextMenu {
} else {
val attachment: Attachment = messageRecord.slideDeck.firstSlide!!.asAttachment()
ShareCompat.IntentBuilder(fragment.requireContext())
val chooserIntent = ShareCompat.IntentBuilder(fragment.requireContext())
.setStream(attachment.publicUri)
.setType(attachment.contentType)
.createChooserIntent()
.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION)
if (Build.VERSION.SDK_INT < 34) {
chooserIntent.putExtra(Intent.EXTRA_EXCLUDE_COMPONENTS, arrayOf(ComponentName(fragment.requireContext(), ShareActivity::class.java)))
}
chooserIntent
}
try {