2024-05-07 07:42:10 +02:00
|
|
|
use std::collections::HashSet;
|
2024-04-29 20:59:02 +02:00
|
|
|
|
2024-05-07 07:42:10 +02:00
|
|
|
use ruma::{
|
|
|
|
api::client::filter::{LazyLoadOptions, RoomEventFilter},
|
|
|
|
events::AnyTimelineEvent,
|
|
|
|
serde::Raw,
|
|
|
|
DeviceId, OwnedEventId, OwnedRoomId, OwnedUserId, RoomId, UserId,
|
|
|
|
};
|
|
|
|
|
|
|
|
use crate::services;
|
|
|
|
|
|
|
|
pub fn filter_room_events<'i, I: Iterator<Item = &'i Raw<AnyTimelineEvent>>>(
|
2024-04-29 20:59:02 +02:00
|
|
|
events: I,
|
2024-05-07 07:42:10 +02:00
|
|
|
sender_user: &UserId,
|
|
|
|
sender_device: &DeviceId,
|
|
|
|
room_id: Option<&RoomId>,
|
2024-04-29 20:59:02 +02:00
|
|
|
filter: RoomEventFilter,
|
2024-05-07 07:42:10 +02:00
|
|
|
) -> crate::Result<Box<dyn Iterator<Item = &'i Raw<AnyTimelineEvent>>>> {
|
|
|
|
let (lazy_load_enabled, lazy_load_send_redundant) = match &filter.lazy_load_options {
|
|
|
|
LazyLoadOptions::Enabled {
|
|
|
|
include_redundant_members,
|
|
|
|
} => (true, *include_redundant_members),
|
|
|
|
_ => (false, false),
|
|
|
|
};
|
|
|
|
|
|
|
|
let it = Box::new(
|
|
|
|
events
|
|
|
|
.filter(|event| match &filter.rooms {
|
|
|
|
None => true,
|
|
|
|
Some(rooms) => rooms.iter().any(|r| {
|
|
|
|
r.as_str()
|
|
|
|
== event
|
|
|
|
.get_field::<String>("room_id")
|
|
|
|
.expect("room events should deserialize")
|
|
|
|
.expect("room events should have a room_id")
|
|
|
|
}),
|
|
|
|
})
|
|
|
|
.filter(|event| match &filter.not_rooms[..] {
|
|
|
|
[] => true,
|
|
|
|
not_rooms => not_rooms.iter().all(|r| {
|
|
|
|
r.as_str()
|
|
|
|
!= event
|
|
|
|
.get_field::<String>("room_id")
|
|
|
|
.expect("room events should deserialize")
|
|
|
|
.expect("room events should have a room_id")
|
|
|
|
}),
|
|
|
|
})
|
|
|
|
.filter(|event| match &filter.senders {
|
|
|
|
None => true,
|
|
|
|
Some(rooms) => rooms.iter().any(|r| {
|
|
|
|
r.as_str()
|
|
|
|
== event
|
|
|
|
.get_field::<String>("sender")
|
|
|
|
.expect("room events should deserialize")
|
|
|
|
.expect("room events should have a sender")
|
|
|
|
}),
|
|
|
|
})
|
|
|
|
.filter(|event| match &filter.not_senders[..] {
|
|
|
|
[] => true,
|
|
|
|
not_senders => not_senders.iter().all(|r| {
|
|
|
|
r.as_str()
|
|
|
|
!= event
|
|
|
|
.get_field::<String>("sender")
|
|
|
|
.expect("room events should deserialize")
|
|
|
|
.expect("room events should have a sender")
|
|
|
|
}),
|
|
|
|
})
|
|
|
|
.filter(|event| match &filter.types {
|
|
|
|
None => true,
|
|
|
|
Some(types) => types.iter().any(|t| {
|
|
|
|
t.as_str()
|
|
|
|
== event
|
|
|
|
.get_field::<String>("type")
|
|
|
|
.expect("room events should deserialize")
|
|
|
|
.expect("room events should have a type")
|
|
|
|
}),
|
|
|
|
})
|
|
|
|
.filter(|event| match &filter.not_types[..] {
|
|
|
|
[] => true,
|
|
|
|
not_types => not_types.iter().all(|t| {
|
|
|
|
t.as_str()
|
|
|
|
!= event
|
|
|
|
.get_field::<String>("type")
|
|
|
|
.expect("room events should deserialize")
|
|
|
|
.expect("room events should have a type")
|
|
|
|
}),
|
|
|
|
})
|
|
|
|
.filter(|event| {
|
|
|
|
let room_id = event
|
|
|
|
.get_field::<OwnedRoomId>("room_id")
|
|
|
|
.expect("room events should deserialize")
|
|
|
|
.expect("room events should have a room_id");
|
|
|
|
let event_id = event
|
|
|
|
.get_field::<OwnedEventId>("event_id")
|
|
|
|
.expect("room events should deserialize")
|
|
|
|
.expect("room events should have an event_id");
|
|
|
|
|
|
|
|
services()
|
|
|
|
.rooms
|
|
|
|
.state_accessor
|
|
|
|
.user_can_see_event(sender_user, &room_id, &event_id)
|
|
|
|
.unwrap_or(false)
|
2024-04-29 20:59:02 +02:00
|
|
|
}),
|
2024-05-07 07:42:10 +02:00
|
|
|
);
|
|
|
|
|
|
|
|
let memberships = it
|
|
|
|
.map(|event| {
|
|
|
|
let room_id = event
|
|
|
|
.get_field::<OwnedRoomId>("room_id")
|
|
|
|
.expect("room events should deserialize")
|
|
|
|
.expect("room events should have a room_id");
|
|
|
|
let sender = event
|
|
|
|
.get_field::<OwnedUserId>("sender")
|
|
|
|
.expect("room events should deserialize")
|
|
|
|
.expect("room events should have a sender");
|
|
|
|
|
|
|
|
(room_id, sender)
|
2024-04-29 20:59:02 +02:00
|
|
|
})
|
2024-05-07 07:42:10 +02:00
|
|
|
.flat_map(|(room_id, sender)| {
|
|
|
|
services()
|
|
|
|
.rooms
|
|
|
|
.lazy_loading
|
|
|
|
.lazy_load_was_sent_before(sender_user, sender_device, &room_id, &sender)
|
|
|
|
.map(|b| {
|
|
|
|
if !b || lazy_load_send_redundant {
|
|
|
|
Some(sender)
|
|
|
|
} else {
|
|
|
|
None
|
|
|
|
}
|
|
|
|
})
|
|
|
|
.transpose()
|
2024-04-29 20:59:02 +02:00
|
|
|
})
|
2024-05-07 07:42:10 +02:00
|
|
|
.collect::<crate::Result<HashSet<_>>>()?;
|
|
|
|
|
|
|
|
Ok(it)
|
2024-04-29 20:59:02 +02:00
|
|
|
}
|