diff --git a/matrix-sdk-android/src/main/java/org/matrix/android/sdk/internal/database/mapper/ContentMapper.kt b/matrix-sdk-android/src/main/java/org/matrix/android/sdk/internal/database/mapper/ContentMapper.kt index ab094e94b8..5002a1b225 100644 --- a/matrix-sdk-android/src/main/java/org/matrix/android/sdk/internal/database/mapper/ContentMapper.kt +++ b/matrix-sdk-android/src/main/java/org/matrix/android/sdk/internal/database/mapper/ContentMapper.kt @@ -20,21 +20,34 @@ package org.matrix.android.sdk.internal.database.mapper import org.matrix.android.sdk.api.session.events.model.Content import org.matrix.android.sdk.api.util.JSON_DICT_PARAMETERIZED_TYPE import org.matrix.android.sdk.internal.di.MoshiProvider +import org.matrix.android.sdk.internal.network.parsing.CheckNumberType internal object ContentMapper { private val moshi = MoshiProvider.providesMoshi() - private val adapter = moshi.adapter(JSON_DICT_PARAMETERIZED_TYPE) + private val castJsonNumberMoshi by lazy { + // We are adding the CheckNumberType as we are serializing/deserializing multiple time in a row + // and we lost typing information doing so. + // We don't want this check to be done on all adapters, so we create a new moshi just for that. + MoshiProvider.providesMoshi() + .newBuilder() + .add(CheckNumberType.JSON_ADAPTER_FACTORY) + .build() + } - fun map(content: String?): Content? { + fun map(content: String?, castJsonNumbers: Boolean = false): Content? { return content?.let { - adapter.fromJson(it) + if (castJsonNumbers) { + castJsonNumberMoshi + } else { + moshi + }.adapter(JSON_DICT_PARAMETERIZED_TYPE).fromJson(it) } } fun map(content: Content?): String? { return content?.let { - adapter.toJson(it) + moshi.adapter(JSON_DICT_PARAMETERIZED_TYPE).toJson(it) } } } diff --git a/matrix-sdk-android/src/main/java/org/matrix/android/sdk/internal/database/mapper/EventMapper.kt b/matrix-sdk-android/src/main/java/org/matrix/android/sdk/internal/database/mapper/EventMapper.kt index 61f09dcece..d7226a2a0b 100644 --- a/matrix-sdk-android/src/main/java/org/matrix/android/sdk/internal/database/mapper/EventMapper.kt +++ b/matrix-sdk-android/src/main/java/org/matrix/android/sdk/internal/database/mapper/EventMapper.kt @@ -54,7 +54,7 @@ internal object EventMapper { return eventEntity } - fun map(eventEntity: EventEntity): Event { + fun map(eventEntity: EventEntity, castJsonNumbers: Boolean = false): Event { val ud = eventEntity.unsignedData ?.takeIf { it.isNotBlank() } ?.let { @@ -69,8 +69,8 @@ internal object EventMapper { return Event( type = eventEntity.type, eventId = eventEntity.eventId, - content = ContentMapper.map(eventEntity.content), - prevContent = ContentMapper.map(eventEntity.prevContent), + content = ContentMapper.map(eventEntity.content, castJsonNumbers), + prevContent = ContentMapper.map(eventEntity.prevContent, castJsonNumbers), originServerTs = eventEntity.originServerTs, senderId = eventEntity.sender, stateKey = eventEntity.stateKey, @@ -96,8 +96,8 @@ internal object EventMapper { } } -internal fun EventEntity.asDomain(): Event { - return EventMapper.map(this) +internal fun EventEntity.asDomain(castJsonNumbers: Boolean = false): Event { + return EventMapper.map(this, castJsonNumbers) } internal fun Event.toEntity(roomId: String, sendState: SendState, ageLocalTs: Long?): EventEntity { diff --git a/matrix-sdk-android/src/main/java/org/matrix/android/sdk/internal/network/parsing/CheckNumberType.kt b/matrix-sdk-android/src/main/java/org/matrix/android/sdk/internal/network/parsing/CheckNumberType.kt index d4ceca2006..40ba02ef6d 100644 --- a/matrix-sdk-android/src/main/java/org/matrix/android/sdk/internal/network/parsing/CheckNumberType.kt +++ b/matrix-sdk-android/src/main/java/org/matrix/android/sdk/internal/network/parsing/CheckNumberType.kt @@ -49,7 +49,7 @@ interface CheckNumberType { val numberAsString = reader.nextString() val decimal = BigDecimal(numberAsString) if (decimal.scale() <= 0) { - decimal.intValueExact() + decimal.longValueExact() } else { decimal.toDouble() } diff --git a/matrix-sdk-android/src/main/java/org/matrix/android/sdk/internal/session/room/send/LocalEchoRepository.kt b/matrix-sdk-android/src/main/java/org/matrix/android/sdk/internal/session/room/send/LocalEchoRepository.kt index dc0f7ec5bd..50f5e13980 100644 --- a/matrix-sdk-android/src/main/java/org/matrix/android/sdk/internal/session/room/send/LocalEchoRepository.kt +++ b/matrix-sdk-android/src/main/java/org/matrix/android/sdk/internal/session/room/send/LocalEchoRepository.kt @@ -122,7 +122,7 @@ internal class LocalEchoRepository @Inject constructor(@SessionDatabase private suspend fun getUpToDateEcho(eventId: String): Event? { // We are using awaitTransaction here to make sure this executes after other transactions return monarchy.awaitTransaction { realm -> - EventEntity.where(realm, eventId).findFirst()?.asDomain() + EventEntity.where(realm, eventId).findFirst()?.asDomain(castJsonNumbers = true) } }