matrix_sdk/room/
member.rs

1use std::ops::Deref;
2
3use ruma::events::room::MediaSource;
4
5use crate::{
6    media::{MediaFormat, MediaRequestParameters},
7    BaseRoomMember, Client, Result,
8};
9
10/// The high-level `RoomMember` representation
11#[derive(Debug, Clone)]
12pub struct RoomMember {
13    inner: BaseRoomMember,
14    pub(crate) client: Client,
15}
16
17impl Deref for RoomMember {
18    type Target = BaseRoomMember;
19
20    fn deref(&self) -> &Self::Target {
21        &self.inner
22    }
23}
24
25impl RoomMember {
26    pub(crate) fn new(client: Client, member: BaseRoomMember) -> Self {
27        Self { inner: member, client }
28    }
29
30    /// Gets the avatar of this member, if set.
31    ///
32    /// Returns the avatar.
33    /// If a thumbnail is requested no guarantee on the size of the image is
34    /// given.
35    ///
36    /// # Arguments
37    ///
38    /// * `format` - The desired format of the avatar.
39    ///
40    /// # Examples
41    ///
42    /// ```no_run
43    /// use matrix_sdk::{
44    ///     media::MediaFormat, room::RoomMember, ruma::room_id, Client,
45    ///     RoomMemberships,
46    /// };
47    /// # use url::Url;
48    /// # let homeserver = Url::parse("http://example.com").unwrap();
49    /// # async {
50    /// # let user = "example";
51    /// let client = Client::new(homeserver).await.unwrap();
52    /// client.matrix_auth().login_username(user, "password").send().await.unwrap();
53    /// let room_id = room_id!("!roomid:example.com");
54    /// let room = client.get_room(&room_id).unwrap();
55    /// let members = room.members(RoomMemberships::empty()).await.unwrap();
56    /// let member = members.first().unwrap();
57    /// if let Some(avatar) = member.avatar(MediaFormat::File).await.unwrap() {
58    ///     std::fs::write("avatar.png", avatar);
59    /// }
60    /// # };
61    /// ```
62    pub async fn avatar(&self, format: MediaFormat) -> Result<Option<Vec<u8>>> {
63        let Some(url) = self.avatar_url() else { return Ok(None) };
64        let request = MediaRequestParameters { source: MediaSource::Plain(url.to_owned()), format };
65        Ok(Some(self.client.media().get_media_content(&request, true).await?))
66    }
67
68    /// Adds the room member to the current account data's ignore list
69    /// which will ignore the user across all rooms.
70    pub async fn ignore(&self) -> Result<()> {
71        self.client.account().ignore_user(self.inner.user_id()).await
72    }
73
74    /// Removes the room member from the current account data's ignore list
75    /// which will unignore the user across all rooms.
76    pub async fn unignore(&self) -> Result<()> {
77        self.client.account().unignore_user(self.inner.user_id()).await
78    }
79
80    /// Returns true if the member of the room is the user of the account
81    pub fn is_account_user(&self) -> bool {
82        match self.client.user_id() {
83            Some(id) => id == self.inner.user_id(),
84            None => false,
85        }
86    }
87
88    /// Get the suggested role of this member based on their power level.
89    pub fn suggested_role_for_power_level(&self) -> RoomMemberRole {
90        RoomMemberRole::suggested_role_for_power_level(self.power_level())
91    }
92}
93
94/// The role of a member in a room.
95#[derive(Clone, Debug, PartialEq)]
96#[cfg_attr(feature = "uniffi", derive(uniffi::Enum))]
97pub enum RoomMemberRole {
98    /// The member is an administrator.
99    Administrator,
100    /// The member is a moderator.
101    Moderator,
102    /// The member is a regular user.
103    User,
104}
105
106impl RoomMemberRole {
107    /// Creates the suggested role for a given power level.
108    pub fn suggested_role_for_power_level(power_level: i64) -> Self {
109        if power_level >= 100 {
110            Self::Administrator
111        } else if power_level >= 50 {
112            Self::Moderator
113        } else {
114            Self::User
115        }
116    }
117
118    /// Get the suggested power level for this role.
119    pub fn suggested_power_level(&self) -> i64 {
120        match self {
121            Self::Administrator => 100,
122            Self::Moderator => 50,
123            Self::User => 0,
124        }
125    }
126}
127
128#[cfg(test)]
129mod tests {
130    use super::*;
131
132    #[test]
133    fn test_suggested_roles() {
134        assert_eq!(
135            RoomMemberRole::Administrator,
136            RoomMemberRole::suggested_role_for_power_level(100)
137        );
138        assert_eq!(RoomMemberRole::Moderator, RoomMemberRole::suggested_role_for_power_level(50));
139        assert_eq!(RoomMemberRole::User, RoomMemberRole::suggested_role_for_power_level(0));
140    }
141
142    #[test]
143    fn test_unexpected_power_levels() {
144        assert_eq!(
145            RoomMemberRole::Administrator,
146            RoomMemberRole::suggested_role_for_power_level(200)
147        );
148        assert_eq!(
149            RoomMemberRole::Administrator,
150            RoomMemberRole::suggested_role_for_power_level(101)
151        );
152        assert_eq!(RoomMemberRole::Moderator, RoomMemberRole::suggested_role_for_power_level(99));
153        assert_eq!(RoomMemberRole::Moderator, RoomMemberRole::suggested_role_for_power_level(51));
154        assert_eq!(RoomMemberRole::User, RoomMemberRole::suggested_role_for_power_level(-1));
155        assert_eq!(RoomMemberRole::User, RoomMemberRole::suggested_role_for_power_level(-100));
156    }
157
158    #[test]
159    fn test_default_power_levels() {
160        assert_eq!(100, RoomMemberRole::Administrator.suggested_power_level());
161        assert_eq!(50, RoomMemberRole::Moderator.suggested_power_level());
162        assert_eq!(0, RoomMemberRole::User.suggested_power_level());
163
164        assert_eq!(
165            RoomMemberRole::Administrator,
166            RoomMemberRole::suggested_role_for_power_level(
167                RoomMemberRole::Administrator.suggested_power_level()
168            )
169        );
170        assert_eq!(
171            RoomMemberRole::Moderator,
172            RoomMemberRole::suggested_role_for_power_level(
173                RoomMemberRole::Moderator.suggested_power_level()
174            )
175        );
176        assert_eq!(
177            RoomMemberRole::User,
178            RoomMemberRole::suggested_role_for_power_level(
179                RoomMemberRole::User.suggested_power_level()
180            )
181        );
182    }
183}