Browse Source

event: Compare raw sources rather than pretty-printed ones

Should be more performant.
fractal-6
Kévin Commaille 2 years ago
parent
commit
4908bc84bc
No known key found for this signature in database
GPG Key ID: 29A48C1F03620416
  1. 30
      src/session/model/room/event/mod.rs
  2. 15
      src/utils/matrix.rs

30
src/session/model/room/event/mod.rs

@ -22,7 +22,10 @@ use super::{
timeline::{TimelineItem, TimelineItemImpl},
Member, Room,
};
use crate::{spawn_tokio, utils::matrix::get_media_content};
use crate::{
spawn_tokio,
utils::matrix::{get_media_content, raw_eq},
};
/// The unique key to identify an event in a room.
#[derive(Clone, Debug, PartialEq, Eq, Hash)]
@ -226,17 +229,17 @@ mod imp {
pub fn set_item(&self, item: EventTimelineItem) {
let obj = self.obj();
let prev_source = self.source();
let prev_raw = self.raw();
let was_edited = self.is_edited();
let was_highlighted = self.is_highlighted();
let prev_latest_edit_source = self.latest_edit_source();
let prev_latest_edit_raw = self.latest_edit_raw();
self.reactions.update(item.reactions().clone());
obj.update_read_receipts(item.read_receipts());
self.item.replace(Some(item));
if self.source() != prev_source {
if !raw_eq(prev_raw.as_ref(), self.raw().as_ref()) {
obj.notify_source();
}
if self.is_edited() != was_edited {
@ -245,7 +248,10 @@ mod imp {
if self.is_highlighted() != was_highlighted {
obj.notify_is_highlighted();
}
if self.latest_edit_source() != prev_latest_edit_source {
if !raw_eq(
prev_latest_edit_raw.as_ref(),
self.latest_edit_raw().as_ref(),
) {
obj.notify_latest_edit_source();
obj.notify_latest_edit_event_id_string();
obj.notify_latest_edit_timestamp();
@ -255,6 +261,12 @@ mod imp {
obj.update_state();
}
/// The raw JSON source for this `Event`, if it has been echoed back
/// by the server.
pub fn raw(&self) -> Option<Raw<AnySyncTimelineEvent>> {
self.item.borrow().as_ref()?.original_json().cloned()
}
/// The pretty-formatted JSON source for this `Event`, if it has
/// been echoed back by the server.
fn source(&self) -> Option<String> {
@ -440,13 +452,7 @@ impl Event {
/// The raw JSON source for this `Event`, if it has been echoed back
/// by the server.
pub fn raw(&self) -> Option<Raw<AnySyncTimelineEvent>> {
self.imp()
.item
.borrow()
.as_ref()
.unwrap()
.original_json()
.cloned()
self.imp().raw()
}
/// The unique of this `Event` in the timeline.

15
src/utils/matrix.rs

@ -9,6 +9,7 @@ use matrix_sdk::{config::RequestConfig, Client, ClientBuildError};
use ruma::{
events::{room::message::MessageType, AnyMessageLikeEventContent, AnySyncTimelineEvent},
matrix_uri::MatrixId,
serde::Raw,
MatrixToUri, MatrixUri,
};
use thiserror::Error;
@ -391,3 +392,17 @@ fn parse_pill(s: &str, room: &Room, session: &Session) -> Option<Pill> {
_ => None,
}
}
/// Compare two raw JSON sources.
pub fn raw_eq<T, U>(lhs: Option<&Raw<T>>, rhs: Option<&Raw<U>>) -> bool {
let Some(lhs) = lhs else {
// They are equal only if both are `None`.
return rhs.is_none();
};
let Some(rhs) = rhs else {
// They cannot be equal.
return false;
};
lhs.json().get() == rhs.json().get()
}

Loading…
Cancel
Save