Skip to content

Commit dd871ef

Browse files
zecakehHywan
authored andcommitted
refactor(base): Store RoomPowerLevels in RoomMember
Avoids to carry around the event content only to convert it when we want to use it. Avoids also to carry around the room creator when we might not need it. Signed-off-by: Kévin Commaille <zecakeh@tedomum.fr>
1 parent 8a29f17 commit dd871ef

File tree

2 files changed

+31
-34
lines changed

2 files changed

+31
-34
lines changed

crates/matrix-sdk-base/src/room/members.rs

Lines changed: 10 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -25,7 +25,7 @@ use ruma::{
2525
presence::PresenceEvent,
2626
room::{
2727
member::{MembershipState, RoomMemberEventContent},
28-
power_levels::{PowerLevelAction, RoomPowerLevels, RoomPowerLevelsEventContent},
28+
power_levels::{PowerLevelAction, RoomPowerLevels},
2929
},
3030
MessageLikeEventType, StateEventType,
3131
},
@@ -35,7 +35,7 @@ use tracing::debug;
3535

3636
use super::Room;
3737
use crate::{
38-
deserialized_responses::{DisplayName, MemberEvent, SyncOrStrippedState},
38+
deserialized_responses::{DisplayName, MemberEvent},
3939
store::{ambiguity_map::is_display_name_ambiguous, Result as StoreResult, StateStoreExt},
4040
MinimalRoomMemberEvent,
4141
};
@@ -166,13 +166,7 @@ impl Room {
166166
display_names: &'a [DisplayName],
167167
) -> StoreResult<MemberRoomInfo<'a>> {
168168
let max_power_level = self.max_power_level();
169-
let room_creator = self.inner.read().creator().map(ToOwned::to_owned);
170-
171-
let power_levels = self
172-
.store
173-
.get_state_event_static(self.room_id())
174-
.await?
175-
.and_then(|e| e.deserialize().ok());
169+
let power_levels = self.power_levels_or_default().await;
176170

177171
let users_display_names =
178172
self.store.get_users_with_display_names(self.room_id(), display_names).await?;
@@ -188,7 +182,6 @@ impl Room {
188182
Ok(MemberRoomInfo {
189183
power_levels: power_levels.into(),
190184
max_power_level,
191-
room_creator,
192185
users_display_names,
193186
ignored_users,
194187
})
@@ -205,9 +198,8 @@ pub struct RoomMember {
205198
pub(crate) profile: Arc<Option<MinimalRoomMemberEvent>>,
206199
#[allow(dead_code)]
207200
pub(crate) presence: Arc<Option<PresenceEvent>>,
208-
pub(crate) power_levels: Arc<Option<SyncOrStrippedState<RoomPowerLevelsEventContent>>>,
201+
pub(crate) power_levels: Arc<RoomPowerLevels>,
209202
pub(crate) max_power_level: i64,
210-
pub(crate) is_room_creator: bool,
211203
pub(crate) display_name_ambiguous: bool,
212204
pub(crate) is_ignored: bool,
213205
}
@@ -219,15 +211,9 @@ impl RoomMember {
219211
presence: Option<PresenceEvent>,
220212
room_info: &MemberRoomInfo<'_>,
221213
) -> Self {
222-
let MemberRoomInfo {
223-
power_levels,
224-
max_power_level,
225-
room_creator,
226-
users_display_names,
227-
ignored_users,
228-
} = room_info;
214+
let MemberRoomInfo { power_levels, max_power_level, users_display_names, ignored_users } =
215+
room_info;
229216

230-
let is_room_creator = room_creator.as_deref() == Some(event.user_id());
231217
let display_name = event.display_name();
232218
let display_name_ambiguous = users_display_names
233219
.get(&display_name)
@@ -240,7 +226,6 @@ impl RoomMember {
240226
presence: presence.into(),
241227
power_levels: power_levels.clone(),
242228
max_power_level: *max_power_level,
243-
is_room_creator,
244229
display_name_ambiguous,
245230
is_ignored,
246231
}
@@ -301,10 +286,7 @@ impl RoomMember {
301286

302287
/// Get the power level of this member.
303288
pub fn power_level(&self) -> i64 {
304-
(*self.power_levels)
305-
.as_ref()
306-
.map(|e| e.power_levels().for_user(self.user_id()).into())
307-
.unwrap_or_else(|| if self.is_room_creator { 100 } else { 0 })
289+
self.power_levels.for_user(self.user_id()).into()
308290
}
309291

310292
/// Whether this user can ban other users based on the power levels.
@@ -377,11 +359,8 @@ impl RoomMember {
377359
self.can_do_impl(|pls| pls.user_can_do(self.user_id(), action))
378360
}
379361

380-
fn can_do_impl(&self, f: impl FnOnce(RoomPowerLevels) -> bool) -> bool {
381-
match &*self.power_levels {
382-
Some(event) => f(event.power_levels()),
383-
None => self.is_room_creator,
384-
}
362+
fn can_do_impl(&self, f: impl FnOnce(&RoomPowerLevels) -> bool) -> bool {
363+
f(&self.power_levels)
385364
}
386365

387366
/// Is the name that the member uses ambiguous in the room.
@@ -405,9 +384,8 @@ impl RoomMember {
405384

406385
// Information about the room a member is in.
407386
pub(crate) struct MemberRoomInfo<'a> {
408-
pub(crate) power_levels: Arc<Option<SyncOrStrippedState<RoomPowerLevelsEventContent>>>,
387+
pub(crate) power_levels: Arc<RoomPowerLevels>,
409388
pub(crate) max_power_level: i64,
410-
pub(crate) room_creator: Option<OwnedUserId>,
411389
pub(crate) users_display_names: HashMap<&'a DisplayName, BTreeSet<OwnedUserId>>,
412390
pub(crate) ignored_users: Option<BTreeSet<OwnedUserId>>,
413391
}

crates/matrix-sdk-base/src/room/mod.rs

Lines changed: 21 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -47,9 +47,8 @@ pub use room_info::{
4747
apply_redaction, BaseRoomInfo, InviteAcceptanceDetails, RoomInfo, RoomInfoNotableUpdate,
4848
RoomInfoNotableUpdateReasons,
4949
};
50-
#[cfg(feature = "e2e-encryption")]
51-
use ruma::{events::AnySyncTimelineEvent, serde::Raw};
5250
use ruma::{
51+
assign,
5352
events::{
5453
direct::OwnedDirectUserIdentifier,
5554
receipt::{Receipt, ReceiptThread, ReceiptType},
@@ -61,9 +60,12 @@ use ruma::{
6160
power_levels::{RoomPowerLevels, RoomPowerLevelsEventContent},
6261
},
6362
},
63+
int,
6464
room::RoomType,
6565
EventId, OwnedEventId, OwnedMxcUri, OwnedRoomAliasId, OwnedRoomId, OwnedUserId, RoomId, UserId,
6666
};
67+
#[cfg(feature = "e2e-encryption")]
68+
use ruma::{events::AnySyncTimelineEvent, serde::Raw};
6769
use serde::{Deserialize, Serialize};
6870
pub use state::{RoomState, RoomStateFilter};
6971
pub(crate) use tags::RoomNotableTags;
@@ -371,6 +373,23 @@ impl Room {
371373
.power_levels())
372374
}
373375

376+
/// Get the current power levels of this room, or a sensible default if they
377+
/// are not known.
378+
pub async fn power_levels_or_default(&self) -> RoomPowerLevels {
379+
if let Ok(power_levels) = self.power_levels().await {
380+
return power_levels;
381+
}
382+
383+
// As a fallback, create the default power levels of a room, with the creator at
384+
// level 100.
385+
let creator = self.creator();
386+
assign!(
387+
RoomPowerLevelsEventContent::new(),
388+
{ users: creator.into_iter().map(|user_id| (user_id, int!(100))).collect() }
389+
)
390+
.into()
391+
}
392+
374393
/// Get the `m.room.name` of this room.
375394
///
376395
/// The returned string may be empty if the event has been redacted, or it's

0 commit comments

Comments
 (0)