Compare commits

..

No commits in common. "ruma-update" and "main" have entirely different histories.

7 changed files with 748 additions and 1244 deletions

1903
Cargo.lock generated

File diff suppressed because it is too large Load diff

View file

@ -8,15 +8,15 @@ resolver = "2"
[dependencies] [dependencies]
crossbeam-channel = "0.5" crossbeam-channel = "0.5"
eframe = { version = "0.17", features = ["persistence"] } eframe = { version = "0.16", features = ["persistence"] }
futures = "0.3" futures = "0.3"
ron = "0.7" ron = "0.6"
serde = { version = "1.0", features = ["derive"] } serde = { version = "1.0", features = ["derive"] }
tokio = { version = "1.15", features = ["full"] } tokio = { version = "1.15", features = ["full"] }
url = { version = "2.2", features = ["serde"] } url = { version = "2.2", features = ["serde"] }
[dependencies.matrix-sdk] [dependencies.matrix-sdk]
git = "https://github.com/matrix-org/matrix-rust-sdk/" git = "https://github.com/matrix-org/matrix-rust-sdk/"
rev = "6dff065" rev = "2e04a37"
default-features = false default-features = false
features = ["encryption", "qrcode", "sled_cryptostore", "sled_state_store", "rustls-tls"] features = ["encryption", "qrcode", "sled_cryptostore", "sled_state_store", "rustls-tls"]

View file

@ -8,7 +8,7 @@ use std::{
use matrix_sdk::{ use matrix_sdk::{
config::ClientConfig, config::ClientConfig,
reqwest::Url, reqwest::Url,
ruma::{UserId, DeviceId}, ruma::{DeviceIdBox, UserId},
Client, Client,
}; };
use ron::ser::PrettyConfig; use ron::ser::PrettyConfig;
@ -21,9 +21,9 @@ pub struct Session {
/// Access token for authentication /// Access token for authentication
pub access_token: String, pub access_token: String,
/// The user's mxid. /// The user's mxid.
pub user_id: Box<UserId>, pub user_id: UserId,
/// The user's device ID. /// The user's device ID.
pub device_id: Box<DeviceId>, pub device_id: DeviceIdBox,
} }
impl Session { impl Session {
@ -42,7 +42,7 @@ impl Session {
user_id: self.user_id, user_id: self.user_id,
device_id: self.device_id, device_id: self.device_id,
}; };
let client = Client::builder().homeserver_url(self.homeserver)?; let client = Client::new(self.homeserver)?;
let runtime = tokio::runtime::Runtime::new().unwrap(); let runtime = tokio::runtime::Runtime::new().unwrap();
runtime.block_on(client.restore_login(session))?; runtime.block_on(client.restore_login(session))?;
Ok(client) Ok(client)

View file

@ -26,19 +26,19 @@ pub enum Request {
/// Restore session /// Restore session
Restore(matrix_sdk::Session), Restore(matrix_sdk::Session),
/// Get the calculated name for a room. /// Get the calculated name for a room.
RoomName(Box<RoomId>), RoomName(RoomId),
/// Send a message to a room. /// Send a message to a room.
Message(Joined, String), Message(Joined, String),
/// Get a member from a joined room /// Get a member from a joined room
JoinedMember(Joined, Box<UserId>), JoinedMember(Joined, UserId),
/// Get the verification request with the flow id. /// Get the verification request with the flow id.
VerifyRequest(Box<UserId>, String), VerifyRequest(UserId, String),
/// Cancel a verification attempt. /// Cancel a verification attempt.
VerifyCancel(VerificationRequest), VerifyCancel(VerificationRequest),
/// Accept a verification request. /// Accept a verification request.
VerifyAccept(VerificationRequest), VerifyAccept(VerificationRequest),
/// Find an active verification with the flow id. /// Find an active verification with the flow id.
VerifyStart(Box<UserId>, String), VerifyStart(UserId, String),
/// Start SAS verification flow. /// Start SAS verification flow.
VerifyStartSas(VerificationRequest), VerifyStartSas(VerificationRequest),
VerifySasConfirm(SasVerification), VerifySasConfirm(SasVerification),
@ -53,9 +53,9 @@ pub enum Response {
/// Response from the synchronization loop /// Response from the synchronization loop
Sync(matrix_sdk::deserialized_responses::SyncResponse), Sync(matrix_sdk::deserialized_responses::SyncResponse),
/// Calculated the name for a room /// Calculated the name for a room
RoomName(Box<RoomId>, String), RoomName(RoomId, String),
/// Retrived a member frmo a joined room. /// Retrived a member frmo a joined room.
JoinedMember(Box<RoomId>, RoomMember), JoinedMember(RoomId, RoomMember),
/// Got a verification request. /// Got a verification request.
VerifyRequest(VerificationRequest), VerifyRequest(VerificationRequest),
/// Started SAS verification. /// Started SAS verification.
@ -123,7 +123,7 @@ async fn handle_request(
}, },
Request::JoinedMember(room, user) => { Request::JoinedMember(room, user) => {
if let Some(member) = room.get_member(&user).await? { if let Some(member) = room.get_member(&user).await? {
response.send(Response::JoinedMember(room.room_id().to_owned(), member))?; response.send(Response::JoinedMember(room.room_id().clone(), member))?;
} }
} }
Request::Message(room, message) => { Request::Message(room, message) => {

View file

@ -21,7 +21,7 @@ impl epi::App for App {
fn setup( fn setup(
&mut self, &mut self,
_ctx: &egui::Context, _ctx: &egui::CtxRef,
_frame: &epi::Frame, _frame: &epi::Frame,
storage: Option<&dyn epi::Storage>, storage: Option<&dyn epi::Storage>,
) { ) {
@ -70,7 +70,7 @@ impl epi::App for App {
}; };
} }
fn update(&mut self, ctx: &egui::Context, _frame: &epi::Frame) { fn update(&mut self, ctx: &egui::CtxRef, _frame: &epi::Frame) {
match self.view { match self.view {
View::Login(ref mut login) => { View::Login(ref mut login) => {
if login.update(ctx) { if login.update(ctx) {
@ -107,7 +107,7 @@ impl View {
}); });
let view = session::App::new(client, req_tx, res_rx, handle); let view = session::App::new(client, req_tx, res_rx, handle);
for room in view.client.rooms() { for room in view.client.rooms() {
view.request.room_name(room.room_id().to_owned()); view.request.room_name(room.room_id().clone());
} }
*self = View::Main(view); *self = View::Main(view);

View file

@ -12,7 +12,7 @@ pub struct Login {
} }
impl Login { impl Login {
pub fn update(&mut self, ctx: &egui::Context) -> bool { pub fn update(&mut self, ctx: &egui::CtxRef) -> bool {
let mut update = false; let mut update = false;
egui::CentralPanel::default().show(ctx, |ui| { egui::CentralPanel::default().show(ctx, |ui| {
ui.add_space(ui.available_height() / 3.0); ui.add_space(ui.available_height() / 3.0);

View file

@ -46,34 +46,34 @@ pub struct App {
/// Data for the room list /// Data for the room list
pub room_list: RoomList, pub room_list: RoomList,
/// Data for storing a timeline /// Data for storing a timeline
pub timelines: HashMap<Box<RoomId>, Timeline>, pub timelines: HashMap<RoomId, Timeline>,
/// Message entry /// Message entry
pub entry: MessageEntry, pub entry: MessageEntry,
} }
#[derive(Debug, Default, Clone, Serialize, Deserialize)] #[derive(Debug, Default, Clone, Serialize, Deserialize)]
pub struct RoomList { pub struct RoomList {
pub selected_room: Option<Box<RoomId>>, pub selected_room: Option<matrix_sdk::ruma::identifiers::RoomId>,
pub room_name: HashMap<Box<RoomId>, String>, pub room_name: HashMap<RoomId, String>,
} }
#[derive(Debug, Default, Clone, Serialize, Deserialize)] #[derive(Debug, Default, Clone, Serialize, Deserialize)]
pub struct Timeline { pub struct Timeline {
messages: Vec<AnyRoomEvent>, messages: Vec<AnyRoomEvent>,
#[serde(skip)] #[serde(skip)]
member: HashMap<Box<UserId>, RoomMember>, member: HashMap<UserId, RoomMember>,
#[serde(skip)] #[serde(skip)]
member_pending: HashSet<Box<UserId>>, member_pending: HashSet<UserId>,
} }
#[derive(Debug, Default, Clone, Serialize, Deserialize)] #[derive(Debug, Default, Clone, Serialize, Deserialize)]
pub struct MessageEntry { pub struct MessageEntry {
text: HashMap<Box<RoomId>, String>, text: HashMap<RoomId, String>,
} }
impl MessageEntry { impl MessageEntry {
pub fn get(&mut self, room: &RoomId) -> &mut String { pub fn get(&mut self, room: &RoomId) -> &mut String {
self.text.entry(room.to_owned()).or_default() self.text.entry(room.clone()).or_default()
} }
} }
@ -126,7 +126,7 @@ impl App {
} }
} }
pub fn update(&mut self, ctx: &egui::Context) { pub fn update(&mut self, ctx: &egui::CtxRef) {
if let Ok(response) = self.response.try_recv() { if let Ok(response) = self.response.try_recv() {
self.handle_response(response); self.handle_response(response);
} }
@ -138,7 +138,7 @@ impl App {
ui.add(Label::new(RichText::new("Joined").strong())); ui.add(Label::new(RichText::new("Joined").strong()));
let mut joined = self.client.joined_rooms(); let mut joined = self.client.joined_rooms();
joined.sort_by_key(|room| self.room_list.room_name(room).to_uppercase()); joined.sort_by_key(|room| self.room_list.room_name(&room).to_uppercase());
joined.retain(|room| { joined.retain(|room| {
room.create_content() room.create_content()
.and_then(|c| c.room_type) .and_then(|c| c.room_type)
@ -158,7 +158,7 @@ impl App {
}); });
let response = response.response.interact(Sense::click()); let response = response.response.interact(Sense::click());
if response.clicked() { if response.clicked() {
self.room_list.selected_room = Some(room.room_id().to_owned()); self.room_list.selected_room = Some(room.room_id().clone());
} }
} }
}); });
@ -184,7 +184,7 @@ impl App {
egui::SidePanel::right(Id::MemberList).show(ctx, |ui| { egui::SidePanel::right(Id::MemberList).show(ctx, |ui| {
ui.heading("Members"); ui.heading("Members");
let timeline = self.timelines.entry(room.room_id().to_owned()).or_default(); let timeline = self.timelines.entry(room.room_id().clone()).or_default();
for member in timeline.member.values() { for member in timeline.member.values() {
ui.group(|ui| { ui.group(|ui| {
ui.set_width(ui.available_width()); ui.set_width(ui.available_width());
@ -216,14 +216,18 @@ impl App {
} }
if verify_req.we_started() { if verify_req.we_started() {
ui.label("Waiting for other user to accept verification."); ui.label("Waiting for other user to accept verification.");
} else if ui.button("Accept").clicked() { } else {
self.request.verify_accept(verify_req.clone()) if ui.button("Accept").clicked() {
self.request.verify_accept(verify_req.clone())
}
} }
if verify_req.is_ready() { if verify_req.is_ready() {
let methods = verify_req.their_supported_methods().unwrap(); let methods = verify_req.their_supported_methods().unwrap();
for method in methods { for method in methods {
if method == VerificationMethod::SasV1 && ui.button("Verify with emoji").clicked() { if method == VerificationMethod::SasV1 {
self.request.verify_start_sas(verify_req.clone()); if ui.button("Verify with emoji").clicked() {
self.request.verify_start_sas(verify_req.clone());
}
} }
} }
} }
@ -284,19 +288,18 @@ impl App {
// Main panel with the timeline // Main panel with the timeline
egui::CentralPanel::default().show(ctx, |ui| { egui::CentralPanel::default().show(ctx, |ui| {
ScrollArea::vertical().show(ui, |ui| { ScrollArea::vertical().show(ui, |ui| {
let timeline = self.timelines.entry(room.room_id().to_owned()).or_default(); let timeline = self.timelines.entry(room.room_id().clone()).or_default();
for event in timeline.messages.iter() { for event in timeline.messages.iter() {
let sender = event.sender(); let sender = event.sender();
let name = match timeline.member.get(sender) { let name = match timeline.member.get(sender) {
Some(member) => member.name(), Some(member) => member.name(),
None => { None => {
if !timeline.member_pending.contains(sender) { if !timeline.member_pending.contains(sender) {
self.request.joined_member(joined.clone(), sender.to_owned()); self.request.joined_member(joined.clone(), sender.clone());
} }
sender.localpart() sender.localpart()
} }
}; };
#[allow(clippy::single_match)]
match event { match event {
AnyRoomEvent::Message(AnyMessageEvent::RoomMessage(msg)) => { AnyRoomEvent::Message(AnyMessageEvent::RoomMessage(msg)) => {
match &msg.content.msgtype { match &msg.content.msgtype {
@ -360,7 +363,7 @@ impl App {
.entry(room) .entry(room)
.or_default() .or_default()
.member .member
.insert(member.user_id().to_owned(), member); .insert(member.user_id().clone(), member);
} }
Response::VerifyRequest(verification) => { Response::VerifyRequest(verification) => {
self.verify_req = Some(verification); self.verify_req = Some(verification);
@ -399,12 +402,12 @@ impl App {
match to_device { match to_device {
AnyToDeviceEvent::KeyVerificationRequest(req) => { AnyToDeviceEvent::KeyVerificationRequest(req) => {
self.request self.request
.verify_request(req.sender, req.content.transaction_id.to_string()); .verify_request(req.sender, req.content.transaction_id);
} }
AnyToDeviceEvent::KeyVerificationStart(start) => { AnyToDeviceEvent::KeyVerificationStart(start) => {
if self.verify_req.is_none() { if self.verify_req.is_none() {
self.request self.request
.verify_start(start.sender, start.content.transaction_id.to_string()) .verify_start(start.sender, start.content.transaction_id)
} }
} }
_ => (), _ => (),
@ -417,11 +420,11 @@ impl App {
pub struct RequestSender(UnboundedSender<sync::Request>); pub struct RequestSender(UnboundedSender<sync::Request>);
impl RequestSender { impl RequestSender {
pub fn room_name(&self, name: Box<RoomId>) { pub fn room_name(&self, name: RoomId) {
self.0.send(sync::Request::RoomName(name)).ok(); self.0.send(sync::Request::RoomName(name)).ok();
} }
pub fn joined_member(&self, room: Joined, id: Box<UserId>) { pub fn joined_member(&self, room: Joined, id: UserId) {
self.0.send(sync::Request::JoinedMember(room, id)).ok(); self.0.send(sync::Request::JoinedMember(room, id)).ok();
} }
@ -429,7 +432,7 @@ impl RequestSender {
self.0.send(sync::Request::Message(room, message)).ok(); self.0.send(sync::Request::Message(room, message)).ok();
} }
pub fn verify_request(&self, user: Box<UserId>, flow_id: String) { pub fn verify_request(&self, user: UserId, flow_id: String) {
self.0 self.0
.send(sync::Request::VerifyRequest(user, flow_id)) .send(sync::Request::VerifyRequest(user, flow_id))
.ok(); .ok();
@ -443,7 +446,7 @@ impl RequestSender {
self.0.send(sync::Request::VerifyAccept(verify)).ok(); self.0.send(sync::Request::VerifyAccept(verify)).ok();
} }
pub fn verify_start(&self, user: Box<UserId>, flow_id: String) { pub fn verify_start(&self, user: UserId, flow_id: String) {
self.0.send(sync::Request::VerifyStart(user, flow_id)).ok(); self.0.send(sync::Request::VerifyStart(user, flow_id)).ok();
} }