diff --git a/crates/matrix-sdk-base/src/client.rs b/crates/matrix-sdk-base/src/client.rs index 7cb4fb0c8..35ec906b8 100644 --- a/crates/matrix-sdk-base/src/client.rs +++ b/crates/matrix-sdk-base/src/client.rs @@ -384,6 +384,7 @@ impl BaseClient { room: &Room, limited: bool, events: Vec>, + ignore_state_events: bool, prev_batch: Option, push_rules: &Ruleset, user_ids: &mut BTreeSet, @@ -402,7 +403,7 @@ impl BaseClient { Ok(e) => { #[allow(clippy::single_match)] match &e { - AnySyncTimelineEvent::State(s) => { + AnySyncTimelineEvent::State(s) if !ignore_state_events => { match s { AnySyncStateEvent::RoomMember(member) => { Box::pin(ambiguity_cache.handle_event( @@ -436,6 +437,8 @@ impl BaseClient { changes.add_state_event(room.room_id(), s.clone(), raw_event); } + AnySyncTimelineEvent::State(_) => { /* do nothing */ } + AnySyncTimelineEvent::MessageLike( AnySyncMessageLikeEvent::RoomRedaction(r), ) => { @@ -981,6 +984,7 @@ impl BaseClient { &room, new_info.timeline.limited, new_info.timeline.events, + false, new_info.timeline.prev_batch, &push_rules, &mut user_ids, @@ -1075,6 +1079,7 @@ impl BaseClient { &room, new_info.timeline.limited, new_info.timeline.events, + false, new_info.timeline.prev_batch, &push_rules, &mut user_ids, diff --git a/crates/matrix-sdk-base/src/sliding_sync/mod.rs b/crates/matrix-sdk-base/src/sliding_sync/mod.rs index 7d227b440..334336e3b 100644 --- a/crates/matrix-sdk-base/src/sliding_sync/mod.rs +++ b/crates/matrix-sdk-base/src/sliding_sync/mod.rs @@ -28,7 +28,7 @@ use ruma::api::client::sync::sync_events::v5; use ruma::events::AnyToDeviceEvent; use ruma::{ api::client::sync::sync_events::v3::{self, InvitedRoom}, - events::{AnyRoomAccountDataEvent, AnySyncStateEvent, AnySyncTimelineEvent}, + events::{AnyRoomAccountDataEvent, AnySyncStateEvent}, serde::Raw, JsOption, OwnedRoomId, RoomId, UInt, }; @@ -453,6 +453,7 @@ impl BaseClient { &room, room_data.limited, room_data.timeline.clone(), + true, room_data.prev_batch.clone(), &push_rules, &mut user_ids, @@ -1135,8 +1136,8 @@ mod tests { let response = response_with_room(room_id, room); client.process_sliding_sync(&response, &(), true).await.expect("Failed to process sync"); - // The room is left. - assert_eq!(client.get_room(room_id).unwrap().state(), RoomState::Left); + // The room is NOT left because state events from `timeline` must be IGNORED! + assert_eq!(client.get_room(room_id).unwrap().state(), RoomState::Joined); } #[async_test] diff --git a/crates/matrix-sdk-ui/src/timeline/event_item/mod.rs b/crates/matrix-sdk-ui/src/timeline/event_item/mod.rs index 3eb331025..723f482d4 100644 --- a/crates/matrix-sdk-ui/src/timeline/event_item/mod.rs +++ b/crates/matrix-sdk-ui/src/timeline/event_item/mod.rs @@ -724,7 +724,7 @@ mod tests { deserialized_responses::SyncTimelineEvent, latest_event::LatestEvent, sliding_sync::http, MinimalStateEvent, OriginalMinimalStateEvent, }; - use matrix_sdk_test::{async_test, sync_timeline_event}; + use matrix_sdk_test::{async_test, sync_state_event, sync_timeline_event}; use ruma::{ event_id, events::{ @@ -732,7 +732,7 @@ mod tests { member::RoomMemberEventContent, message::{MessageFormat, MessageType}, }, - AnySyncTimelineEvent, BundledMessageLikeRelations, + AnySyncStateEvent, AnySyncTimelineEvent, BundledMessageLikeRelations, }, room_id, serde::Raw, @@ -889,7 +889,12 @@ mod tests { let event = message_event(room_id, user_id, "**My M**", "My M", 122344); let client = logged_in_client(None).await; let mut room = http::response::Room::new(); - room.timeline.push(member_event(room_id, user_id, "Alice Margatroid", "mxc://e.org/SEs")); + room.required_state.push(member_event_as_state_event( + room_id, + user_id, + "Alice Margatroid", + "mxc://e.org/SEs", + )); // And the room is stored in the client so it can be extracted when needed let response = response_with_room(room_id, room); @@ -1000,6 +1005,32 @@ mod tests { }) } + fn member_event_as_state_event( + room_id: &RoomId, + user_id: &UserId, + display_name: &str, + avatar_url: &str, + ) -> Raw { + sync_state_event!({ + "type": "m.room.member", + "content": { + "avatar_url": avatar_url, + "displayname": display_name, + "membership": "join", + "reason": "" + }, + "event_id": "$143273582443PhrSn:example.org", + "origin_server_ts": 143273583, + "room_id": room_id, + "sender": "@example:example.org", + "state_key": user_id, + "type": "m.room.member", + "unsigned": { + "age": 1234 + } + }) + } + fn response_with_room(room_id: &RoomId, room: http::response::Room) -> http::Response { let mut response = http::Response::new("6".to_owned()); response.rooms.insert(room_id.to_owned(), room);