mirror of
https://forgejo.ellis.link/continuwuation/continuwuity/
synced 2026-10-06 02:37:25 +00:00
56 lines
1.5 KiB
Rust
56 lines
1.5 KiB
Rust
use std::{sync::Arc, time::Duration};
|
|
|
|
use axum::extract::State;
|
|
use conduwuit::{
|
|
Result, info,
|
|
utils::{random_string, time::jitter},
|
|
warn,
|
|
};
|
|
use ruma::{OwnedServerName, api::error::ErrorKind};
|
|
use ruminuwuity::api::federation::{
|
|
ping::unstable::{Request, Response},
|
|
pong,
|
|
};
|
|
|
|
use crate::Ruma;
|
|
|
|
/// # `GET /_matrix/federation/unstable/uk.timedout.msc0000.tabletennis/ping`
|
|
///
|
|
/// Initiates a ping
|
|
pub(crate) async fn ping(
|
|
State(services): State<crate::State>,
|
|
body: Ruma<Request>,
|
|
) -> Result<Response> {
|
|
// TODO: rate-limiting
|
|
// TODO: make answer stable based on question
|
|
let answer = random_string(64);
|
|
services.federation.register_ping_answer(answer.clone())?;
|
|
services
|
|
.server
|
|
.runtime()
|
|
.spawn(send_ping(Arc::new(services), body.identity, answer.clone()));
|
|
Ok(Response::new(answer))
|
|
}
|
|
|
|
async fn send_ping(services: Arc<crate::State>, target: OwnedServerName, answer: String) {
|
|
tokio::time::sleep(jitter(Duration::from_secs(1), 1.0..=10.0)).await;
|
|
info!(%answer, "Sending a federation pong to {target}");
|
|
match services
|
|
.sending
|
|
.send_federation_request(&target, pong::unstable::Request::new(answer))
|
|
.await
|
|
{
|
|
| Ok(_) => info!(%target, "Federation pong succeeded"),
|
|
| Err(e) =>
|
|
if e.is_not_found() {
|
|
if e.kind() == ErrorKind::Unrecognized {
|
|
warn!(%target, "Remote requested a ping but does not recognize the pong.");
|
|
} else {
|
|
info!(%target, "Ping expired by the time we ponged.");
|
|
}
|
|
} else {
|
|
warn!(%target, "Pong failed");
|
|
},
|
|
}
|
|
}
|