Skip to main content

tuwunel_api/client/room/
timestamp.rs

1use axum::extract::State;
2use ruma::api::client::room::get_event_by_timestamp::v1;
3use tuwunel_core::{Err, Result, utils::result::NotFound};
4
5use crate::router::Ruma;
6
7/// # `GET /_matrix/client/v1/rooms/{roomId}/timestamp_to_event`
8///
9/// Get the ID of the event closest to the given timestamp.
10pub(crate) async fn get_event_by_timestamp_route(
11	State(services): State<crate::State>,
12	body: Ruma<v1::Request>,
13) -> Result<v1::Response> {
14	let sender_user = body.sender_user();
15	let room_id = &body.room_id;
16
17	if !services
18		.state_accessor
19		.user_can_see_state_events(sender_user, room_id)
20		.await
21	{
22		return Err!(Request(Forbidden("You don't have permission to view this room.")));
23	}
24
25	let (origin_server_ts, event_id) = services
26		.timeline
27		.get_event_id_near_ts_with_fallback(room_id, body.ts, body.dir)
28		.await?;
29
30	// An event this server does not hold has no recorded state, which the
31	// visibility check would allow as well.
32	if let Some(pdu) = services
33		.timeline
34		.get_pdu(&event_id)
35		.await
36		.optional()?
37		&& !services
38			.state_accessor
39			.user_can_see_event(sender_user, &pdu)
40			.await
41	{
42		return Err!(Request(Forbidden("You don't have permission to view this event.")));
43	}
44
45	Ok(v1::Response::new(event_id, origin_server_ts))
46}