diff --git a/crates/matrix-sdk/src/room/timeline/event_handler.rs b/crates/matrix-sdk/src/room/timeline/event_handler.rs index a19c62dcd..cfeefae28 100644 --- a/crates/matrix-sdk/src/room/timeline/event_handler.rs +++ b/crates/matrix-sdk/src/room/timeline/event_handler.rs @@ -646,6 +646,7 @@ pub(crate) fn update_read_marker( let Some(fully_read_event) = fully_read_event else { return }; let read_marker_idx = find_read_marker(items_lock); let fully_read_event_idx = find_event_by_id(items_lock, fully_read_event).map(|(idx, _)| idx); + match (read_marker_idx, fully_read_event_idx) { (None, None) => {} (None, Some(idx)) => { diff --git a/crates/matrix-sdk/src/room/timeline/inner.rs b/crates/matrix-sdk/src/room/timeline/inner.rs index 887104424..d43e913fb 100644 --- a/crates/matrix-sdk/src/room/timeline/inner.rs +++ b/crates/matrix-sdk/src/room/timeline/inner.rs @@ -45,6 +45,8 @@ pub(super) struct TimelineInnerMetadata { // Reaction event / txn ID => sender and reaction data pub(super) reaction_map: HashMap, pub(super) fully_read_event: Option, + /// Whether the event that the fully-ready event _refers to_ is part of the + /// timeline. pub(super) fully_read_event_in_timeline: bool, } @@ -184,7 +186,7 @@ impl TimelineInner

{ } pub(super) async fn handle_fully_read(&self, raw: Raw) { - let fully_read_event = match raw.deserialize() { + let fully_read_event_id = match raw.deserialize() { Ok(ev) => ev.content.event_id, Err(error) => { error!(?error, "Failed to deserialize `m.fully_read` account data"); @@ -192,12 +194,13 @@ impl TimelineInner

{ } }; - self.set_fully_read_event(fully_read_event).await; + self.set_fully_read_event(fully_read_event_id).await; } pub(super) async fn set_fully_read_event(&self, fully_read_event_id: OwnedEventId) { let mut metadata_lock = self.metadata.lock().await; + // A similar event has been handled already. We can ignore it. if metadata_lock.fully_read_event.as_ref().map_or(false, |id| *id == fully_read_event_id) { return; } diff --git a/crates/matrix-sdk/src/room/timeline/tests.rs b/crates/matrix-sdk/src/room/timeline/tests.rs index 3fe1cfef7..0c6f0a940 100644 --- a/crates/matrix-sdk/src/room/timeline/tests.rs +++ b/crates/matrix-sdk/src/room/timeline/tests.rs @@ -273,11 +273,15 @@ async fn update_read_marker() { timeline.inner.set_fully_read_event(event_id.clone()).await; assert_matches!(stream.next().await, Some(VecDiff::Move { old_index: 2, new_index: 3 })); + // Nothing should happen if the fully read event is set back to the same event + // as before. + timeline.inner.set_fully_read_event(event_id.clone()).await; + // Nothing should happen if the fully read event isn't found. timeline.inner.set_fully_read_event(event_id!("$fake_event_id").to_owned()).await; - // Nothing should happen if the fully read event is set back to the same event - // as before. + // Nothing should happen if the fully read event is referring to an old event + // that has already been marked as fully read. timeline.inner.set_fully_read_event(event_id).await; timeline.handle_live_message_event(&ALICE, RoomMessageEventContent::text_plain("C")).await;