daydream

A small matrix web client written in rust
git clone git://archive.git.mtrnord.blog/daydream-mx/daydream.git
Log | Files | Refs | README | LICENSE

commit b557df96506d072dfdf1a511e70ac2f20db5e26d
parent 024552abb7fad7766ac403152d69dde59921f6e8
Author: Marcel <mtrnord1@gmail.com>
Date:   Fri,  3 Jul 2020 19:51:08 +0200

Fix Room change performance, fix worker

Took 58 minutes

Diffstat:
MCargo.toml | 7++++---
Msrc/app/components/event_list.rs | 4++--
Msrc/app/components/events/image.rs | 2+-
Msrc/app/components/events/notice.rs | 2+-
Msrc/app/components/events/text.rs | 2+-
Msrc/app/components/events/video.rs | 2+-
Msrc/app/components/room_list/item.rs | 23++++++-----------------
Msrc/app/components/room_list/mod.rs | 1+
Msrc/app/matrix/mod.rs | 21+++++++--------------
Msrc/app/matrix/sync.rs | 59++++++++++++++++++++++++++---------------------------------
Msrc/app/mod.rs | 9+++++----
Msrc/lib.rs | 3++-
Msrc/utils/notifications.rs | 13++-----------
Mwebpack.config.js | 6++++--
14 files changed, 63 insertions(+), 91 deletions(-)

diff --git a/Cargo.toml b/Cargo.toml @@ -23,9 +23,9 @@ wasm-logger = "0.2" lazy_static = "1.4.0" # Yew -yew = { git = "https://github.com/daydream-mx/yew.git", branch = "fix-webpack-worker", features = ["webpack"] } -yew-router = { git = "https://github.com/daydream-mx/yew.git", branch = "fix-webpack-worker" } -yewtil = { git = "https://github.com/daydream-mx/yew.git", branch = "fix-webpack-worker" } +yew = { git = "https://github.com/daydream-mx/yew.git", branch = "MTRNord/daydream-no-bincode", features = ["webpack"] } +yew-router = { git = "https://github.com/daydream-mx/yew.git", branch = "MTRNord/daydream-no-bincode" } +yewtil = { git = "https://github.com/daydream-mx/yew.git", branch = "MTRNord/daydream-no-bincode" } # Matrix matrix-sdk = { version = "0.1.0", git = "https://github.com/MTRNord/matrix-rust-sdk", branch = "daydream", default-features = false, features = ["messages"]}# features = ["encryption"]} @@ -63,6 +63,7 @@ features = [ olm-sys = { git = "https://gitlab.gnome.org/stoically/olm-sys", branch = "wasm-target" } cjson = { git = "https://github.com/engineerd/cjson" } ruma-events = { git = "https://github.com/ruma/ruma-events", rev="3f74ba327093d4f32e11c2741aaa649e4ab733d9" } +reqwest = { git = "https://github.com/daydream-mx/reqwest.git", branch = "MTRNord/wasm-worker-support"} [profile.release] # less code to include into binary diff --git a/src/app/components/event_list.rs b/src/app/components/event_list.rs @@ -84,7 +84,7 @@ impl Component for EventList { false } } else { - let mut msgs = vec![msg]; + let msgs = vec![msg]; self.state.events.insert(room_id.clone(), msgs); room_id == self.props.current_room.clone().unwrap().room_id } @@ -92,7 +92,7 @@ impl Component for EventList { false } } - Response::OldMessages((room_id, mut messages)) => { + Response::OldMessages((room_id, messages)) => { let mut deserialized_messages: Vec<MessageEvent> = messages .iter() .map(|x| x.deserialize()) diff --git a/src/app/components/events/image.rs b/src/app/components/events/image.rs @@ -36,7 +36,7 @@ impl Component for Image { fn change(&mut self, props: Self::Properties) -> bool { // TODO fix the PartialEq hack - if format!("{:#?}", self.props) != format!("{:#?}", props) { + if format!("{:?}", self.props) != format!("{:?}", props) { self.props = props; true } else { diff --git a/src/app/components/events/notice.rs b/src/app/components/events/notice.rs @@ -39,7 +39,7 @@ impl Component for Notice { fn change(&mut self, props: Self::Properties) -> bool { // TODO fix the PartialEq hack - if format!("{:#?}", self.props) != format!("{:#?}", props) { + if format!("{:?}", self.props) != format!("{:?}", props) { self.props = props; true } else { diff --git a/src/app/components/events/text.rs b/src/app/components/events/text.rs @@ -38,7 +38,7 @@ impl Component for Text { fn change(&mut self, props: Self::Properties) -> bool { // TODO fix the PartialEq hack - if format!("{:#?}", self.props) != format!("{:#?}", props) { + if format!("{:?}", self.props) != format!("{:?}", props) { self.props = props; true } else { diff --git a/src/app/components/events/video.rs b/src/app/components/events/video.rs @@ -36,7 +36,7 @@ impl Component for Video { fn change(&mut self, props: Self::Properties) -> bool { // TODO fix the PartialEq hack - if format!("{:#?}", self.props) != format!("{:#?}", props) { + if format!("{:?}", self.props) != format!("{:?}", props) { self.props = props; true } else { diff --git a/src/app/components/room_list/item.rs b/src/app/components/room_list/item.rs @@ -1,10 +1,6 @@ -use matrix_sdk::{events::room::message::MessageEventContent, js_int::UInt, Room}; -use rand::random; +use matrix_sdk::{events::room::message::MessageEventContent, Room}; use yew::prelude::*; - -use crate::app::components::events::{get_sender_avatar, get_sender_displayname, is_new_user}; -use crate::app::matrix::types::get_media_download_url; -use url::Url; +use yewtil::NeqAssign; pub(crate) struct RoomItem { props: Props, @@ -15,7 +11,7 @@ pub enum Msg { ChangeRoom(Room), } -#[derive(Clone, Properties, Debug)] +#[derive(Clone, Properties, Debug, PartialEq)] pub struct Props { #[prop_or_default] pub room: Option<Room>, @@ -42,13 +38,7 @@ impl Component for RoomItem { } fn change(&mut self, props: Self::Properties) -> bool { - // TODO fix the PartialEq hack - if format!("{:#?}", self.props) != format!("{:#?}", props) { - self.props = props; - true - } else { - false - } + self.props.neq_assign(props) } //noinspection RsTypeCheck @@ -68,9 +58,8 @@ impl Component for RoomItem { { None => "".to_string(), Some(m) => { - let content = m.content.clone(); - if let MessageEventContent::Text(text_event) = content { - text_event.body + if let MessageEventContent::Text(text_event) = &m.content { + text_event.clone().body } else { "".to_string() } diff --git a/src/app/components/room_list/mod.rs b/src/app/components/room_list/mod.rs @@ -84,6 +84,7 @@ impl Component for RoomList { false } Response::JoinedRoom((room_id, room)) => { + info!("Got JoinedRoom"); self.state.rooms.insert(room_id, room); if self.state.loading { self.state.loading = false; diff --git a/src/app/matrix/mod.rs b/src/app/matrix/mod.rs @@ -1,6 +1,6 @@ -use std::collections::{HashMap, HashSet}; +use std::collections::{HashSet}; use std::convert::TryFrom; -use std::sync::{Arc, Mutex}; +use std::sync::{Arc}; use log::*; use matrix_sdk::{ @@ -22,12 +22,9 @@ use pulldown_cmark::{html, Options, Parser}; use serde::{Deserialize, Serialize}; use url::Url; use wasm_bindgen_futures::spawn_local; -use yew::format::Json; -use yew::worker::*; use yew::worker::*; use crate::app::matrix::types::{get_media_download_url, get_video_media_download_url}; -use crate::constants::AUTH_KEY; use crate::errors::{Field, MatrixError}; mod sync; @@ -83,7 +80,7 @@ pub enum Response { SyncPing, OldMessages((RoomId, Vec<EventJson<MessageEvent>>)), JoinedRoom((RoomId, Room)), - SaveSession(SessionStore) + SaveSession(SessionStore), } #[derive(Debug, Clone)] @@ -224,14 +221,7 @@ impl Agent for MatrixAgent { }); } Request::GetLoggedIn => { - let login_client = self.login(); - if login_client.is_none() { - for sub in self.subscribers.iter() { - let resp = Response::Error(MatrixError::MissingClient); - self.link.respond(*sub, resp); - } - return; - } + self.login(); // Always clone agent after having tried to login! let agent = self.clone(); @@ -442,6 +432,9 @@ impl MatrixAgent { fn login(&mut self) -> Option<Client> { info!("preparing client"); + if self.session.is_none() { + return None; + } if self.session.is_some() { info!("restoring login"); let homeserver = self.session.clone().unwrap().homeserver_url; diff --git a/src/app/matrix/sync.rs b/src/app/matrix/sync.rs @@ -23,7 +23,6 @@ use crate::app::components::events::{get_sender_avatar, get_sender_displayname}; use crate::app::matrix::types::{get_media_download_url, get_video_media_download_url}; use crate::app::matrix::Response; use crate::utils::notifications::Notifications; -use serde::Serialize; lazy_static! { static ref SYNC_NUMBER: Mutex<i32> = Mutex::new(0); @@ -72,7 +71,7 @@ impl Sync { } async fn on_state_event(&self, room_id: &RoomId, event: StateEvent) { - if let StateEvent::RoomCreate(event) = event { + if let StateEvent::RoomCreate(_event) = event { info!("Sent JoinedRoomSync State"); let resp = Response::JoinedRoomSync(room_id.clone()); self.callback.emit(resp); @@ -98,36 +97,30 @@ impl Sync { let sync_number = SYNC_NUMBER.lock().unwrap(); if *sync_number == 1 { spawn_local(async move { - if Notifications::browser_support() { - let room: Arc<RwLock<Room>> = client - .clone() - .get_joined_room(&local_room_id.clone()) - .await - .unwrap(); - let read_clone = room.read().await; - let clean_room = (*read_clone).clone(); - let avatar_url = get_sender_avatar( - homeserver_url, - clean_room.clone(), - cloned_event.clone(), - ); - let room_name = clean_room.display_name(); - let displayname = - get_sender_displayname(clean_room, cloned_event.clone()); - - let mut title = "".to_string(); - if displayname == room_name { - title = displayname; - } else { - title = format!("{} ({})", displayname, room_name); - } - - /* - TODO fix by moving it out of the worker - let notification = - Notifications::new(avatar_url, title, text_event.body.clone()); - notification.show();*/ - } + let room: Arc<RwLock<Room>> = client + .clone() + .get_joined_room(&local_room_id.clone()) + .await + .unwrap(); + let read_clone = room.read().await; + let clean_room = (*read_clone).clone(); + let avatar_url = get_sender_avatar( + homeserver_url, + clean_room.clone(), + cloned_event.clone(), + ); + let room_name = clean_room.display_name(); + let displayname = get_sender_displayname(clean_room, cloned_event.clone()); + + let title = if displayname == room_name { + displayname + } else { + format!("{} ({})", displayname, room_name) + }; + + let notification = + Notifications::new(avatar_url, title, text_event.body.clone()); + notification.show(); }); } } @@ -176,7 +169,7 @@ impl Sync { let serialized_event = EventJson::from(event.clone()); let resp = Response::Sync((room_id.clone(), serialized_event)); - self.callback.emit(resp); + //self.callback.emit(resp); } } } diff --git a/src/app/mod.rs b/src/app/mod.rs @@ -4,12 +4,12 @@ use yew_router::{prelude::*, Switch}; use crate::app::matrix::{MatrixAgent, Response, SessionStore}; use crate::app::views::{login::Login, main_view::MainView}; +use crate::constants::AUTH_KEY; use log::*; use std::sync::{Arc, Mutex}; -use yew::services::StorageService; -use yew::services::storage::Area; -use crate::constants::AUTH_KEY; use yew::format::Json; +use yew::services::storage::Area; +use yew::services::StorageService; pub mod components; pub mod matrix; @@ -88,7 +88,8 @@ impl Component for App { Response::Error(_) => {} Response::LoggedIn(logged_in) => { if !logged_in && self.session.is_some() { - self.matrix_agent.send(matrix::Request::SetSession(self.session.clone().unwrap())); + self.matrix_agent + .send(matrix::Request::SetSession(self.session.clone().unwrap())); self.matrix_agent.send(matrix::Request::GetLoggedIn); return false; } diff --git a/src/lib.rs b/src/lib.rs @@ -21,7 +21,6 @@ language_loader!(DaydreamLanguageLoader); //#[global_allocator] //static ALLOC: wee_alloc::WeeAlloc = wee_alloc::WeeAlloc::INIT; - //====== Running the primary frontend ======// #[wasm_bindgen] pub fn run_app() -> Result<(), JsValue> { @@ -49,6 +48,8 @@ use yew::agent::Threaded; /// We need to wrap it in wasm_bindgen so the worker knows the spin the the yew worker instance #[wasm_bindgen] pub fn init_worker() { + wasm_logger::init(wasm_logger::Config::default()); + // Spawning a yew component without StartApp requires initializing yew::initialize(); diff --git a/src/utils/notifications.rs b/src/utils/notifications.rs @@ -1,6 +1,6 @@ -use wasm_bindgen::prelude::*; use wasm_bindgen::JsCast; -use web_sys::{window, Notification, NotificationOptions, NotificationPermission}; +use wasm_bindgen::prelude::*; +use web_sys::{Notification, NotificationOptions, NotificationPermission}; #[derive(Clone)] pub(crate) struct Notifications { @@ -17,15 +17,6 @@ impl Notifications { content, } } - pub fn browser_support() -> bool { - match window() { - Some(v) => match v.get("Notification") { - Some(_) => true, - _ => false, - }, - _ => false, - } - } fn notifications_allowed(&self) -> bool { match Notification::permission() { diff --git a/webpack.config.js b/webpack.config.js @@ -80,7 +80,8 @@ const appConfig = (env, argv) => { watch: process.env.WEBPACK_MODE !== 'production', watchOptions: { poll: true - } + }, + devtool: 'inline-source-map' }; }; @@ -95,7 +96,8 @@ const workerConfig = { output: { path: distPath, filename: "worker.js" - } + }, + devtool: 'inline-source-map' }; module.exports = (env, argv) => {