Skip to content

Commit

Permalink
fix: ignore mention with negative index [WPB-4854] (#2270)
Browse files Browse the repository at this point in the history
  • Loading branch information
Garzas committed Sep 26, 2023
1 parent c2ed958 commit be349f5
Show file tree
Hide file tree
Showing 2 changed files with 109 additions and 10 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -233,20 +233,23 @@ internal fun MessageGenericAsset(
* @param resources: Resources - To be able to get String out of UIText message
* @return Pair<List<DisplayMention>, String>
*/
private fun mapToDisplayMentions(uiText: UIText, resources: Resources): Pair<List<DisplayMention>, String> {
fun mapToDisplayMentions(uiText: UIText, resources: Resources): Pair<List<DisplayMention>, String> {
return if (uiText is UIText.DynamicString) {
val stringBuilder: StringBuilder = StringBuilder(uiText.value)
val mentions = uiText.mentions.sortedBy { it.start }.reversed()
val mentionList = mentions.mapNotNull {
val mentions = uiText.mentions
.filter { it.start >= 0 && it.length > 0 }
.sortedBy { it.start }
.reversed()
val mentionList = mentions.mapNotNull { mention ->
// secured crash for mentions caused by web when text without mentions contains mention data
if (it.start + it.length <= uiText.value.length && uiText.value.elementAt(it.start) == '@') {
val mentionName = uiText.value.substring(it.start, it.start + it.length)
stringBuilder.insert(it.start + it.length, MENTION_MARK)
stringBuilder.insert(it.start, MENTION_MARK)
if (mention.start + mention.length <= uiText.value.length && uiText.value.elementAt(mention.start) == '@') {
val mentionName = uiText.value.substring(mention.start, mention.start + mention.length)
stringBuilder.insert(mention.start + mention.length, MENTION_MARK)
stringBuilder.insert(mention.start, MENTION_MARK)
DisplayMention(
it.userId,
it.length,
it.isSelfMention,
mention.userId,
mention.length,
mention.isSelfMention,
mentionName
)
} else {
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,96 @@
/*
* Wire
* Copyright (C) 2023 Wire Swiss GmbH
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see http://www.gnu.org/licenses/.
*/
package com.wire.android.ui.home.conversations.model

import android.content.res.Resources
import com.wire.android.framework.TestUser
import com.wire.android.ui.markdown.MarkdownConstants
import com.wire.android.util.ui.UIText
import com.wire.kalium.logic.data.message.mention.MessageMention
import io.mockk.MockKAnnotations
import io.mockk.every
import io.mockk.impl.annotations.MockK
import org.amshove.kluent.internal.assertEquals
import org.junit.jupiter.api.Assertions.assertTrue
import org.junit.jupiter.api.Test

class MessageTypesTest {

@MockK
lateinit var mockResources: Resources

init {
MockKAnnotations.init(this, relaxUnitFun = true)

every { mockResources.getString(any()) } returns "mockedString"
}

@Test
fun `Given message with no mentions when mapping then no mentions should be returned`() {
val uiText = UIText.DynamicString("Hello world")
val result = mapToDisplayMentions(uiText, mockResources)
assertTrue(result.first.isEmpty())
assertEquals("Hello world", result.second)
}

@Test
fun `Given message with a valid mention when mapping then the mention should be returned with markers`() {
val mention = MessageMention(0, 6, TestUser.USER_ID, isSelfMention = false)
val uiText = UIText.DynamicString("@Hello world", listOf(mention))
val result = mapToDisplayMentions(uiText, mockResources)
assertEquals(1, result.first.size)
assertEquals("@Hello", result.first.first().mentionUserName)
assertEquals("${MarkdownConstants.MENTION_MARK}@Hello${MarkdownConstants.MENTION_MARK} world", result.second)
}

@Test
fun `Given message with a negative start mention when mapping then no mentions should be returned`() {
val mention = MessageMention(-1, 5, TestUser.USER_ID, isSelfMention = false)
val uiText = UIText.DynamicString("Hello world", listOf(mention))
val result = mapToDisplayMentions(uiText, mockResources)
assertTrue(result.first.isEmpty())
assertEquals("Hello world", result.second)
}

@Test
fun `Given message with a mention exceeding string length when mapping then no mentions should be returned`() {
val mention = MessageMention(10, 20, TestUser.USER_ID, isSelfMention = false)
val uiText = UIText.DynamicString("Hello world", listOf(mention))
val result = mapToDisplayMentions(uiText, mockResources)
assertTrue(result.first.isEmpty())
assertEquals("Hello world", result.second)
}

@Test
fun `Given message where mention's start position doesn't have '@' character when mapping then no mentions should be returned`() {
val mention = MessageMention(6, 5, TestUser.USER_ID, isSelfMention = false)
val uiText = UIText.DynamicString("Hello world", listOf(mention))
val result = mapToDisplayMentions(uiText, mockResources)
assertTrue(result.first.isEmpty())
assertEquals("Hello world", result.second)
}

@Test
fun `Given message with multiple mentions when mapping then only valid mentions should be returned`() {
val validMention = MessageMention(6, 5, TestUser.USER_ID, isSelfMention = false)
val invalidMention = MessageMention(50, 5, TestUser.OTHER_USER.id, isSelfMention = false)
val uiText = UIText.DynamicString("Hello @world", listOf(validMention, invalidMention))
val result = mapToDisplayMentions(uiText, mockResources)
assertEquals(1, result.first.size)
}
}

0 comments on commit be349f5

Please sign in to comment.