diff --git a/src/session/content/room_details/invite_subpage/invitee_list.rs b/src/session/content/room_details/invite_subpage/invitee_list.rs index ccc31e5b..ac6f4195 100644 --- a/src/session/content/room_details/invite_subpage/invitee_list.rs +++ b/src/session/content/room_details/invite_subpage/invitee_list.rs @@ -2,6 +2,7 @@ use gtk::{gio, glib, glib::clone, prelude::*, subclass::prelude::*}; use log::error; use matrix_sdk::ruma::{api::client::r0::user_directory::search_users, identifiers::UserId}; use matrix_sdk::HttpError; +use std::sync::Arc; use crate::session::user::UserExt; use crate::{session::Room, spawn, spawn_tokio}; @@ -40,7 +41,7 @@ mod imp { pub room: OnceCell, pub state: Cell, pub search_term: RefCell>, - pub invitee_list: RefCell, Invitee>>, + pub invitee_list: RefCell, Invitee>>, pub abort_handle: RefCell>, } @@ -244,7 +245,7 @@ impl InviteeList { .filter_map(|item| { // Skip over users that are already in the room if member_list.contains(&item.user_id) { - self.remove_invitee(&item.user_id); + self.remove_invitee(item.user_id.into()); None } else if let Some(user) = self.get_invitee(&item.user_id) { // The avatar or the display name may have changed in the mean time @@ -333,7 +334,7 @@ impl InviteeList { priv_ .invitee_list .borrow_mut() - .insert(user.user_id().to_owned(), user.clone()); + .insert(user.user_id(), user.clone()); self.emit_by_name("invitee-added", &[&user]).unwrap(); self.notify("has-selected"); } @@ -348,9 +349,9 @@ impl InviteeList { .collect() } - fn remove_invitee(&self, user_id: &UserId) { + fn remove_invitee(&self, user_id: Arc) { let priv_ = imp::InviteeList::from_instance(self); - let removed = priv_.invitee_list.borrow_mut().remove(user_id); + let removed = priv_.invitee_list.borrow_mut().remove(&user_id); if let Some(user) = removed { user.set_invited(false); self.emit_by_name("invitee-removed", &[&user]).unwrap(); diff --git a/src/session/mod.rs b/src/session/mod.rs index 1304430e..32e6ba06 100644 --- a/src/session/mod.rs +++ b/src/session/mod.rs @@ -397,7 +397,7 @@ impl Session { match handle.await.unwrap() { Ok((display_name, avatar_url)) => { user.set_display_name(display_name); - user.set_avatar_url(avatar_url) + user.set_avatar_url(avatar_url); } Err(error) => error!("Couldn’t fetch account metadata: {}", error), } @@ -500,7 +500,7 @@ impl Session { fn mark_ready(&self) { let priv_ = imp::Session::from_instance(self); let client = self.client(); - let user_id = self.user().unwrap().user_id().to_owned(); + let user_id = self.user().unwrap().user_id(); priv_.is_ready.set(true); diff --git a/src/session/room/event.rs b/src/session/room/event.rs index df466648..105f46df 100644 --- a/src/session/room/event.rs +++ b/src/session/room/event.rs @@ -15,6 +15,7 @@ use matrix_sdk::{ }, Error as MatrixError, }; +use std::sync::Arc; use crate::{ session::{room::Member, Room}, @@ -174,7 +175,7 @@ impl Event { } pub fn sender(&self) -> Member { - self.room().members().member_by_id(&self.matrix_sender()) + self.room().members().member_by_id(self.matrix_sender()) } pub fn room(&self) -> Room { @@ -210,11 +211,11 @@ impl Event { self.notify("can-view-media"); } - pub fn matrix_sender(&self) -> Box { + pub fn matrix_sender(&self) -> Arc { let priv_ = imp::Event::from_instance(self); if let Some(event) = priv_.event.borrow().as_ref() { - event.sender().to_owned() + event.sender().into() } else { priv_ .pure_event @@ -222,7 +223,7 @@ impl Event { .as_ref() .unwrap() .event - .get_field::>("sender") + .get_field::>("sender") .unwrap() .unwrap() } diff --git a/src/session/room/item.rs b/src/session/room/item.rs index 9359c715..46ca8449 100644 --- a/src/session/room/item.rs +++ b/src/session/room/item.rs @@ -3,6 +3,7 @@ use matrix_sdk::ruma::{ events::AnySyncRoomEvent, identifiers::{EventId, UserId}, }; +use std::sync::Arc; use crate::session::room::Event; @@ -182,7 +183,7 @@ impl Item { } } - pub fn matrix_sender(&self) -> Option> { + pub fn matrix_sender(&self) -> Option> { let priv_ = imp::Item::from_instance(self); if let ItemType::Event(event) = priv_.type_.get().unwrap() { Some(event.matrix_sender()) diff --git a/src/session/room/member.rs b/src/session/room/member.rs index dfc3f73a..1af7a0f8 100644 --- a/src/session/room/member.rs +++ b/src/session/room/member.rs @@ -98,7 +98,7 @@ impl Member { /// Update the user based on the the room member state event pub fn update_from_room_member(&self, member: &RoomMember) { - if member.user_id() != self.user_id() { + if member.user_id() != &*self.user_id() { log::error!("Tried Member update from RoomMember with wrong user ID."); return; }; @@ -111,7 +111,7 @@ impl Member { /// Update the user based on the the room member state event pub fn update_from_member_event(&self, event: &impl MemberEvent) { - if event.sender() != self.user_id() { + if event.sender() != &*self.user_id() { log::error!("Tried Member update from MemberEvent with wrong user ID."); return; }; diff --git a/src/session/room/member_list.rs b/src/session/room/member_list.rs index 5158eb1a..756d9f3f 100644 --- a/src/session/room/member_list.rs +++ b/src/session/room/member_list.rs @@ -1,7 +1,7 @@ +use crate::session::room::{Member, Room, UserId}; use gtk::{gio, glib, prelude::*, subclass::prelude::*}; use indexmap::IndexMap; - -use crate::session::room::{Member, Room, UserId}; +use std::sync::Arc; use matrix_sdk::ruma::events::{room::member::RoomMemberEventContent, SyncStateEvent}; @@ -13,7 +13,7 @@ mod imp { #[derive(Debug, Default)] pub struct MemberList { - pub members: RefCell, Member>>, + pub members: RefCell, Member>>, pub room: OnceCell>, } @@ -108,8 +108,8 @@ impl MemberList { let prev_len = members.len(); for member in new_members { members - .entry(member.user_id().to_owned()) - .or_insert_with(|| Member::new(&self.room(), member.user_id())) + .entry(member.user_id().into()) + .or_insert_with_key(|user_id| Member::new(&self.room(), user_id)) .update_from_room_member(&member); } let num_members_added = members.len().saturating_sub(prev_len); @@ -126,13 +126,13 @@ impl MemberList { /// Returns the member with the given ID. /// /// Creates a new member first if there is no member with the given ID. - pub fn member_by_id(&self, user_id: &UserId) -> Member { + pub fn member_by_id(&self, user_id: Arc) -> Member { let mut members = imp::MemberList::from_instance(self).members.borrow_mut(); let mut was_member_added = false; let prev_len = members.len(); let member = members - .entry(user_id.to_owned()) - .or_insert_with(|| { + .entry(user_id) + .or_insert_with_key(|user_id| { was_member_added = true; Member::new(&self.room(), user_id) }) @@ -153,7 +153,7 @@ impl MemberList { /// /// Creates a new member first if there is no member matching the given event. pub fn update_member_for_member_event(&self, event: &SyncStateEvent) { - self.member_by_id(&event.sender) + self.member_by_id(event.sender.clone().into()) .update_from_member_event(event); } diff --git a/src/session/room/mod.rs b/src/session/room/mod.rs index 3dd37614..a17b3e8d 100644 --- a/src/session/room/mod.rs +++ b/src/session/room/mod.rs @@ -51,6 +51,7 @@ use serde_json::value::RawValue; use std::cell::RefCell; use std::convert::TryInto; use std::path::PathBuf; +use std::sync::Arc; use crate::components::{LabelWithWidgets, Pill}; use crate::prelude::*; @@ -851,7 +852,7 @@ impl Room { let event = AnySyncMessageEvent::RoomMessage(SyncMessageEvent { content: content.clone(), event_id: EventId::parse(format!("${}:fractal.gnome.org", txn_id).as_str()).unwrap(), - sender: self.session().user().unwrap().user_id().to_owned(), + sender: self.session().user().unwrap().user_id().as_ref().to_owned(), origin_server_ts: MilliSecondsSinceUnixEpoch::now(), unsigned: Unsigned::default(), }); @@ -1075,8 +1076,7 @@ impl Room { pub async fn invite(&self, users: &[User]) { let matrix_room = self.matrix_room(); - let user_ids: Vec> = - users.iter().map(|user| user.user_id().to_owned()).collect(); + let user_ids: Vec> = users.iter().map(|user| user.user_id()).collect(); if let MatrixRoom::Joined(matrix_room) = matrix_room { let handle = spawn_tokio!(async move { diff --git a/src/session/room/timeline.rs b/src/session/room/timeline.rs index 67ffada1..7c757995 100644 --- a/src/session/room/timeline.rs +++ b/src/session/room/timeline.rs @@ -714,12 +714,12 @@ impl Timeline { let user = session.user().unwrap(); - let user_to_verify = if &request.to == user.user_id() { + let user_to_verify = if &*request.to == &*user.user_id() { // The request was sent by another user to verify us event.sender() - } else if &message.sender == user.user_id() { + } else if &*message.sender == &*user.user_id() { // The request was sent by us to verify another user - self.room().members().member_by_id(&request.to) + self.room().members().member_by_id(request.to.into()) } else { // Ignore the request when it doesn't verify us or wasn't set by us return; @@ -745,25 +745,25 @@ impl Timeline { return; } AnySyncMessageEvent::KeyVerificationReady(e) => { - FlowId::new(e.sender, e.content.relates_to.event_id.to_string()) + FlowId::new(e.sender.into(), e.content.relates_to.event_id.to_string()) } AnySyncMessageEvent::KeyVerificationStart(e) => { - FlowId::new(e.sender, e.content.relates_to.event_id.to_string()) + FlowId::new(e.sender.into(), e.content.relates_to.event_id.to_string()) } AnySyncMessageEvent::KeyVerificationCancel(e) => { - FlowId::new(e.sender, e.content.relates_to.event_id.to_string()) + FlowId::new(e.sender.into(), e.content.relates_to.event_id.to_string()) } AnySyncMessageEvent::KeyVerificationAccept(e) => { - FlowId::new(e.sender, e.content.relates_to.event_id.to_string()) + FlowId::new(e.sender.into(), e.content.relates_to.event_id.to_string()) } AnySyncMessageEvent::KeyVerificationKey(e) => { - FlowId::new(e.sender, e.content.relates_to.event_id.to_string()) + FlowId::new(e.sender.into(), e.content.relates_to.event_id.to_string()) } AnySyncMessageEvent::KeyVerificationMac(e) => { - FlowId::new(e.sender, e.content.relates_to.event_id.to_string()) + FlowId::new(e.sender.into(), e.content.relates_to.event_id.to_string()) } AnySyncMessageEvent::KeyVerificationDone(e) => { - FlowId::new(e.sender, e.content.relates_to.event_id.to_string()) + FlowId::new(e.sender.into(), e.content.relates_to.event_id.to_string()) } _ => { return; diff --git a/src/session/user.rs b/src/session/user.rs index 94aaae0a..1a53bb3e 100644 --- a/src/session/user.rs +++ b/src/session/user.rs @@ -4,6 +4,7 @@ use matrix_sdk::ruma::identifiers::{MxcUri, UserId}; use crate::session::{Avatar, Session}; use crate::spawn_tokio; use matrix_sdk::encryption::identities::UserIdentity; +use std::sync::Arc; use log::error; @@ -11,11 +12,11 @@ mod imp { use super::*; use glib::object::WeakRef; use once_cell::{sync::Lazy, unsync::OnceCell}; - use std::{cell::RefCell, convert::TryInto}; + use std::cell::RefCell; #[derive(Debug, Default)] pub struct User { - pub user_id: OnceCell>, + pub user_id: OnceCell>, pub display_name: RefCell>, pub session: OnceCell>, pub avatar: OnceCell, @@ -75,8 +76,9 @@ mod imp { ) { match pspec.name() { "user-id" => { - let user_id = value.get::<&str>().unwrap().try_into().unwrap(); - self.user_id.set(user_id).unwrap(); + self.user_id + .set(UserId::parse_arc(value.get::<&str>().unwrap()).unwrap()) + .unwrap(); } "display-name" => { obj.set_display_name(value.get::>().unwrap()); @@ -126,7 +128,7 @@ impl User { pub async fn crypto_identity(&self) -> Option { let client = self.session().client(); - let user_id = self.user_id().to_owned(); + let user_id = self.user_id(); let handle = spawn_tokio!(async move { client.get_user_identity(&user_id).await }); match handle.await.unwrap() { @@ -145,9 +147,9 @@ pub trait UserExt: IsA { priv_.session.get().unwrap().upgrade().unwrap() } - fn user_id(&self) -> &UserId { + fn user_id(&self) -> Arc { let priv_ = imp::User::from_instance(self.upcast_ref()); - priv_.user_id.get().unwrap() + priv_.user_id.get().unwrap().clone() } fn display_name(&self) -> String { diff --git a/src/session/verification/identity_verification.rs b/src/session/verification/identity_verification.rs index d74a7c65..e188ee91 100644 --- a/src/session/verification/identity_verification.rs +++ b/src/session/verification/identity_verification.rs @@ -400,7 +400,7 @@ impl IdentityVerification { }; let client = self.session().client(); - let user_id = self.user().user_id().to_owned(); + let user_id = self.user().user_id(); let flow_id = self.flow_id().to_owned(); let (sync_sender, sync_receiver) = mpsc::channel(100); diff --git a/src/session/verification/verification_list.rs b/src/session/verification/verification_list.rs index ce07d0a7..22984e2a 100644 --- a/src/session/verification/verification_list.rs +++ b/src/session/verification/verification_list.rs @@ -8,15 +8,16 @@ use log::{debug, warn}; use matrix_sdk::ruma::{ api::client::r0::sync::sync_events::ToDevice, events::AnyToDeviceEvent, identifiers::UserId, }; +use std::sync::Arc; #[derive(Hash, PartialEq, Eq, Debug)] pub struct FlowId { - user_id: Box, + user_id: Arc, flow_id: String, } impl FlowId { - pub fn new(user_id: Box, flow_id: String) -> Self { + pub fn new(user_id: Arc, flow_id: String) -> Self { Self { user_id, flow_id } } } @@ -118,14 +119,14 @@ impl VerificationList { debug!("Received verification event: {:?}", event); let request = match event { AnyToDeviceEvent::KeyVerificationRequest(e) => { - let flow_id = FlowId::new(e.sender, e.content.transaction_id); + let flow_id = FlowId::new(e.sender.into(), e.content.transaction_id); if let Some(request) = self.get_by_id(&flow_id) { Some(request) } else { let session = self.session(); let user = session.user().unwrap(); // ToDevice verifications can only be send by us - if &flow_id.user_id != user.user_id() { + if flow_id.user_id != user.user_id() { warn!("Received a device verification event from a different user, which isn't allowed"); continue; } @@ -168,25 +169,25 @@ impl VerificationList { } } AnyToDeviceEvent::KeyVerificationReady(e) => { - self.get_by_id(&FlowId::new(e.sender, e.content.transaction_id)) + self.get_by_id(&FlowId::new(e.sender.into(), e.content.transaction_id)) } AnyToDeviceEvent::KeyVerificationStart(e) => { - self.get_by_id(&FlowId::new(e.sender, e.content.transaction_id)) + self.get_by_id(&FlowId::new(e.sender.into(), e.content.transaction_id)) } AnyToDeviceEvent::KeyVerificationCancel(e) => { - self.get_by_id(&FlowId::new(e.sender, e.content.transaction_id)) + self.get_by_id(&FlowId::new(e.sender.into(), e.content.transaction_id)) } AnyToDeviceEvent::KeyVerificationAccept(e) => { - self.get_by_id(&FlowId::new(e.sender, e.content.transaction_id)) + self.get_by_id(&FlowId::new(e.sender.into(), e.content.transaction_id)) } AnyToDeviceEvent::KeyVerificationMac(e) => { - self.get_by_id(&FlowId::new(e.sender, e.content.transaction_id)) + self.get_by_id(&FlowId::new(e.sender.into(), e.content.transaction_id)) } AnyToDeviceEvent::KeyVerificationKey(e) => { - self.get_by_id(&FlowId::new(e.sender, e.content.transaction_id)) + self.get_by_id(&FlowId::new(e.sender.into(), e.content.transaction_id)) } AnyToDeviceEvent::KeyVerificationDone(e) => { - self.get_by_id(&FlowId::new(e.sender, e.content.transaction_id)) + self.get_by_id(&FlowId::new(e.sender.into(), e.content.transaction_id)) } _ => continue, }; @@ -220,10 +221,7 @@ impl VerificationList { ); list.insert( - FlowId::new( - request.user().user_id().to_owned(), - request.flow_id().to_owned(), - ), + FlowId::new(request.user().user_id(), request.flow_id().to_owned()), request, ); length as u32 @@ -234,11 +232,9 @@ impl VerificationList { pub fn remove(&self, request: &IdentityVerification) { let priv_ = imp::VerificationList::from_instance(self); - let position = if let Some((position, _, _)) = - priv_.list.borrow_mut().shift_remove_full(&FlowId::new( - request.user().user_id().to_owned(), - request.flow_id().to_owned(), - )) { + let position = if let Some((position, _, _)) = priv_.list.borrow_mut().shift_remove_full( + &FlowId::new(request.user().user_id(), request.flow_id().to_owned()), + ) { position } else { return;