Add recent search results to global search (#7742)

* Add global search results history: keep the latest 25 items used in the global search, save them to an encrypted file store.

* Integrate the search history in the global search feature

* Add `MatrixClient.getRoomInfo` and use it in `GlobalSearchPresenter`

---------

Co-authored-by: ElementBot <android@element.io>
This commit is contained in:
Jorge Martin Espinosa
2026-09-22 17:17:57 +02:00
committed by GitHub
parent 51fe66cd88
commit 8b1b5560d9
153 changed files with 1537 additions and 401 deletions
@@ -25,7 +25,7 @@ import java.io.FileOutputStream
*
* It uses hardcoded constants that are used in that library, for backwards compatibility reasons.
*/
internal class EncryptedFile(
class EncryptedFile(
private val context: Context,
private val file: File
) {
@@ -326,6 +326,11 @@ interface MatrixClient : ClientUrlContentFetcher {
*/
suspend fun uploadMedia(mimeType: String, data: ByteArray): Result<String>
/**
* Returns the latest [RoomInfo] of a room, if known to the client, or `null` if the room is unknown.
*/
suspend fun getRoomInfo(roomId: RoomId): Result<RoomInfo?>
/**
* Get a room info flow for a given room ID.
* The flow will emit a new value whenever the room info is updated, skipping duplicates, and an empty [Optional] if the room is not found.
@@ -11,6 +11,7 @@ package io.element.android.libraries.matrix.api.core
import io.element.android.libraries.androidutils.metadata.isInDebug
import java.io.Serializable
@kotlinx.serialization.Serializable
@JvmInline
value class RoomId(val value: String) : Serializable {
init {
@@ -779,6 +779,14 @@ class RustMatrixClient(
}
}
override suspend fun getRoomInfo(roomId: RoomId): Result<RoomInfo?> = withContext(sessionDispatcher) {
runCatchingExceptions {
innerRoomListService.roomOrNull(roomId.value)?.use { room ->
roomInfoMapper.map(room.roomInfo())
}
}
}
override fun getRoomInfoFlow(roomId: RoomId): Flow<Optional<RoomInfo>> {
return mxCallbackFlow {
val roomNotFound = innerRoomListService.roomOrNull(roomId.value).use { it == null }
@@ -74,6 +74,7 @@ import kotlinx.coroutines.flow.flowOf
import kotlinx.coroutines.test.TestScope
import java.io.File
import java.util.Optional
import kotlin.jvm.optionals.getOrNull
class FakeMatrixClient(
override val sessionId: SessionId = A_SESSION_ID,
@@ -173,6 +174,7 @@ class FakeMatrixClient(
var knockRoomLambda: (RoomIdOrAlias, String, List<String>) -> Result<RoomInfo?> = { _, _, _ ->
Result.success(null)
}
var getRoomInfoLambda = { _: RoomId -> Result.success<RoomInfo?>(null) }
var getRoomInfoFlowLambda = { _: RoomId ->
flowOf<Optional<RoomInfo>>(Optional.empty())
}
@@ -379,6 +381,8 @@ class FakeMatrixClient(
return Result.success(visitedRoomsId)
}
override suspend fun getRoomInfo(roomId: RoomId): Result<RoomInfo?> = getRoomInfoLambda(roomId)
override fun getRoomInfoFlow(roomId: RoomId) = getRoomInfoFlowLambda(roomId)
var setAllSendQueuesEnabledLambda = lambdaRecorder(ensureNeverCalled = true) { _: Boolean ->