Compare commits
5 commits
main
...
nex/fed-im
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
ed65377f8d | ||
|
|
44943626d9 | ||
|
|
cc9cdd3129 | ||
|
|
92a3e5918e | ||
|
|
244eaf2e0c |
3 changed files with 81 additions and 26 deletions
|
|
@ -5,7 +5,7 @@ use axum_client_ip::InsecureClientIp;
|
||||||
use conduwuit::{
|
use conduwuit::{
|
||||||
Err, Error, Result, debug,
|
Err, Error, Result, debug,
|
||||||
debug::INFO_SPAN_LEVEL,
|
debug::INFO_SPAN_LEVEL,
|
||||||
debug_warn, err, error,
|
debug_warn, err, error, info,
|
||||||
result::LogErr,
|
result::LogErr,
|
||||||
trace,
|
trace,
|
||||||
utils::{
|
utils::{
|
||||||
|
|
@ -79,13 +79,11 @@ pub(crate) async fn send_transaction_message_route(
|
||||||
}
|
}
|
||||||
|
|
||||||
let txn_start_time = Instant::now();
|
let txn_start_time = Instant::now();
|
||||||
trace!(
|
info!(
|
||||||
pdus = body.pdus.len(),
|
pdus = body.pdus.len(),
|
||||||
edus = body.edus.len(),
|
edus = body.edus.len(),
|
||||||
elapsed = ?txn_start_time.elapsed(),
|
|
||||||
id = ?body.transaction_id,
|
id = ?body.transaction_id,
|
||||||
origin =?body.origin(),
|
"Processing transaction",
|
||||||
"Starting txn",
|
|
||||||
);
|
);
|
||||||
|
|
||||||
let pdus = body
|
let pdus = body
|
||||||
|
|
@ -104,14 +102,21 @@ pub(crate) async fn send_transaction_message_route(
|
||||||
.filter_map(Result::ok)
|
.filter_map(Result::ok)
|
||||||
.stream();
|
.stream();
|
||||||
|
|
||||||
let results = handle(&services, &client, body.origin(), txn_start_time, pdus, edus).await?;
|
info!(
|
||||||
|
pdus = body.pdus.len(),
|
||||||
debug!(
|
edus = body.edus.len(),
|
||||||
|
elapsed = ?txn_start_time.elapsed(),
|
||||||
|
id = ?body.transaction_id,
|
||||||
|
"Validated transaction",
|
||||||
|
);
|
||||||
|
|
||||||
|
let results = handle(&services, &client, body.origin(), txn_start_time, pdus, edus).await?;
|
||||||
|
|
||||||
|
info!(
|
||||||
pdus = body.pdus.len(),
|
pdus = body.pdus.len(),
|
||||||
edus = body.edus.len(),
|
edus = body.edus.len(),
|
||||||
elapsed = ?txn_start_time.elapsed(),
|
elapsed = ?txn_start_time.elapsed(),
|
||||||
id = ?body.transaction_id,
|
id = ?body.transaction_id,
|
||||||
origin =?body.origin(),
|
|
||||||
"Finished txn",
|
"Finished txn",
|
||||||
);
|
);
|
||||||
for (id, result) in &results {
|
for (id, result) in &results {
|
||||||
|
|
@ -138,6 +143,10 @@ async fn handle(
|
||||||
pdus: impl Stream<Item = Pdu> + Send,
|
pdus: impl Stream<Item = Pdu> + Send,
|
||||||
edus: impl Stream<Item = Edu> + Send,
|
edus: impl Stream<Item = Edu> + Send,
|
||||||
) -> Result<ResolvedMap> {
|
) -> Result<ResolvedMap> {
|
||||||
|
edus.for_each_concurrent(automatic_width(), |edu| handle_edu(services, client, origin, edu))
|
||||||
|
.boxed()
|
||||||
|
.await;
|
||||||
|
|
||||||
// group pdus by room
|
// group pdus by room
|
||||||
let pdus = pdus
|
let pdus = pdus
|
||||||
.collect()
|
.collect()
|
||||||
|
|
@ -154,7 +163,8 @@ async fn handle(
|
||||||
.into_iter()
|
.into_iter()
|
||||||
.try_stream()
|
.try_stream()
|
||||||
.broad_and_then(|(room_id, pdus): (_, Vec<_>)| {
|
.broad_and_then(|(room_id, pdus): (_, Vec<_>)| {
|
||||||
handle_room(services, client, origin, started, room_id, pdus.into_iter())
|
let count = pdus.len();
|
||||||
|
handle_room(services, client, origin, started, room_id, pdus.into_iter(), count)
|
||||||
.map_ok(Vec::into_iter)
|
.map_ok(Vec::into_iter)
|
||||||
.map_ok(IterStream::try_stream)
|
.map_ok(IterStream::try_stream)
|
||||||
})
|
})
|
||||||
|
|
@ -163,11 +173,6 @@ async fn handle(
|
||||||
.boxed()
|
.boxed()
|
||||||
.await?;
|
.await?;
|
||||||
|
|
||||||
// evaluate edus after pdus, at least for now.
|
|
||||||
edus.for_each_concurrent(automatic_width(), |edu| handle_edu(services, client, origin, edu))
|
|
||||||
.boxed()
|
|
||||||
.await;
|
|
||||||
|
|
||||||
Ok(results)
|
Ok(results)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -178,6 +183,7 @@ async fn handle_room(
|
||||||
txn_start_time: Instant,
|
txn_start_time: Instant,
|
||||||
room_id: OwnedRoomId,
|
room_id: OwnedRoomId,
|
||||||
pdus: impl Iterator<Item = Pdu> + Send,
|
pdus: impl Iterator<Item = Pdu> + Send,
|
||||||
|
count: usize,
|
||||||
) -> Result<Vec<(OwnedEventId, Result)>> {
|
) -> Result<Vec<(OwnedEventId, Result)>> {
|
||||||
let _room_lock = services
|
let _room_lock = services
|
||||||
.rooms
|
.rooms
|
||||||
|
|
@ -187,10 +193,20 @@ async fn handle_room(
|
||||||
.await;
|
.await;
|
||||||
|
|
||||||
let room_id = &room_id;
|
let room_id = &room_id;
|
||||||
|
let mut n = 0;
|
||||||
pdus.try_stream()
|
pdus.try_stream()
|
||||||
.and_then(|(_, event_id, value)| async move {
|
.and_then(|(_, event_id, value)| async move {
|
||||||
services.server.check_running()?;
|
services.server.check_running()?;
|
||||||
let pdu_start_time = Instant::now();
|
let pdu_start_time = Instant::now();
|
||||||
|
info!(
|
||||||
|
%room_id,
|
||||||
|
%event_id,
|
||||||
|
pdu = n + 1,
|
||||||
|
total = count,
|
||||||
|
pdu_elapsed = ?pdu_start_time.elapsed(),
|
||||||
|
txn_elapsed = ?txn_start_time.elapsed(),
|
||||||
|
"Handling PDU",
|
||||||
|
);
|
||||||
let result = services
|
let result = services
|
||||||
.rooms
|
.rooms
|
||||||
.event_handler
|
.event_handler
|
||||||
|
|
@ -198,11 +214,16 @@ async fn handle_room(
|
||||||
.await
|
.await
|
||||||
.map(|_| ());
|
.map(|_| ());
|
||||||
|
|
||||||
debug!(
|
info!(
|
||||||
|
%room_id,
|
||||||
|
%event_id,
|
||||||
|
pdu = n + 1,
|
||||||
|
total = count,
|
||||||
pdu_elapsed = ?pdu_start_time.elapsed(),
|
pdu_elapsed = ?pdu_start_time.elapsed(),
|
||||||
txn_elapsed = ?txn_start_time.elapsed(),
|
txn_elapsed = ?txn_start_time.elapsed(),
|
||||||
"Finished PDU {event_id}",
|
"Finished handling PDU {event_id}",
|
||||||
);
|
);
|
||||||
|
n += 1;
|
||||||
|
|
||||||
Ok((event_id, result))
|
Ok((event_id, result))
|
||||||
})
|
})
|
||||||
|
|
|
||||||
|
|
@ -1,9 +1,13 @@
|
||||||
use std::{fmt::Debug, mem};
|
use std::{
|
||||||
|
error::Error as _,
|
||||||
|
fmt::{Debug, Write},
|
||||||
|
mem,
|
||||||
|
};
|
||||||
|
|
||||||
use bytes::Bytes;
|
use bytes::Bytes;
|
||||||
use conduwuit::{
|
use conduwuit::{
|
||||||
Err, Error, Result, debug, debug::INFO_SPAN_LEVEL, debug_error, debug_warn, err,
|
Err, Error, Result, debug, debug::INFO_SPAN_LEVEL, debug_error, debug_warn, err,
|
||||||
error::inspect_debug_log, implement, trace, utils::string::EMPTY,
|
error::inspect_debug_log, implement, trace, utils::string::EMPTY, warn,
|
||||||
};
|
};
|
||||||
use http::{HeaderValue, header::AUTHORIZATION};
|
use http::{HeaderValue, header::AUTHORIZATION};
|
||||||
use ipaddress::IPAddress;
|
use ipaddress::IPAddress;
|
||||||
|
|
@ -193,9 +197,9 @@ fn handle_error(
|
||||||
) -> Result {
|
) -> Result {
|
||||||
if e.is_timeout() || e.is_connect() {
|
if e.is_timeout() || e.is_connect() {
|
||||||
e = e.without_url();
|
e = e.without_url();
|
||||||
debug_warn!("{e:?}");
|
warn!(?url, "network error while sending federation request: {e:?}");
|
||||||
} else if e.is_redirect() {
|
} else if e.is_redirect() {
|
||||||
debug_error!(
|
warn!(
|
||||||
method = ?method,
|
method = ?method,
|
||||||
url = ?url,
|
url = ?url,
|
||||||
final_url = ?e.url(),
|
final_url = ?e.url(),
|
||||||
|
|
@ -204,9 +208,17 @@ fn handle_error(
|
||||||
e,
|
e,
|
||||||
);
|
);
|
||||||
} else {
|
} else {
|
||||||
debug_error!("{e:?}");
|
warn!(?url, "failed to send federation request: {e:?}");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
let mut nice_error = "Request failed".to_owned();
|
||||||
|
let mut src = e.source();
|
||||||
|
while let Some(source) = src {
|
||||||
|
write!(nice_error, ": {source:?}").expect("writing to string should not fail");
|
||||||
|
src = source.source();
|
||||||
|
}
|
||||||
|
warn!(nice_error, "Federation request error");
|
||||||
|
|
||||||
Err(e.into())
|
Err(e.into())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -10,7 +10,7 @@ use std::{
|
||||||
|
|
||||||
use base64::{Engine as _, engine::general_purpose::URL_SAFE_NO_PAD};
|
use base64::{Engine as _, engine::general_purpose::URL_SAFE_NO_PAD};
|
||||||
use conduwuit_core::{
|
use conduwuit_core::{
|
||||||
Error, Event, Result, debug, err, error,
|
Error, Event, Result, debug, err, error, info,
|
||||||
result::LogErr,
|
result::LogErr,
|
||||||
trace,
|
trace,
|
||||||
utils::{
|
utils::{
|
||||||
|
|
@ -142,7 +142,7 @@ impl Service {
|
||||||
}
|
}
|
||||||
|
|
||||||
fn handle_response_err(dest: Destination, statuses: &mut CurTransactionStatus, e: &Error) {
|
fn handle_response_err(dest: Destination, statuses: &mut CurTransactionStatus, e: &Error) {
|
||||||
debug!(dest = ?dest, "{e:?}");
|
debug!(dest = ?dest, "error response: {e:?}");
|
||||||
statuses.entry(dest).and_modify(|e| {
|
statuses.entry(dest).and_modify(|e| {
|
||||||
*e = match e {
|
*e = match e {
|
||||||
| TransactionStatus::Running => TransactionStatus::Failed(1, Instant::now()),
|
| TransactionStatus::Running => TransactionStatus::Failed(1, Instant::now()),
|
||||||
|
|
@ -177,7 +177,21 @@ impl Service {
|
||||||
if !new_events.is_empty() {
|
if !new_events.is_empty() {
|
||||||
self.db.mark_as_active(new_events.iter());
|
self.db.mark_as_active(new_events.iter());
|
||||||
|
|
||||||
let new_events_vec = new_events.into_iter().map(|(_, event)| event).collect();
|
let new_events_vec: Vec<SendingEvent> =
|
||||||
|
new_events.into_iter().map(|(_, event)| event).collect();
|
||||||
|
|
||||||
|
if let Some(status) = statuses.get(&dest.clone()) {
|
||||||
|
if matches!(status, TransactionStatus::Running) {
|
||||||
|
// If the server is in backoff, clear it
|
||||||
|
info!(
|
||||||
|
?dest,
|
||||||
|
"Catching up previously failed destination with {}+ new events",
|
||||||
|
new_events_vec.len()
|
||||||
|
);
|
||||||
|
statuses.insert(dest.clone(), TransactionStatus::Running);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
futures.push(self.send_events(dest.clone(), new_events_vec));
|
futures.push(self.send_events(dest.clone(), new_events_vec));
|
||||||
} else {
|
} else {
|
||||||
statuses.remove(dest);
|
statuses.remove(dest);
|
||||||
|
|
@ -859,12 +873,20 @@ impl Service {
|
||||||
pdus,
|
pdus,
|
||||||
edus,
|
edus,
|
||||||
};
|
};
|
||||||
|
let pdu_count = request.pdus.len();
|
||||||
|
let edu_count = request.edus.len();
|
||||||
|
|
||||||
let result = self
|
let result = self
|
||||||
.services
|
.services
|
||||||
.federation
|
.federation
|
||||||
.execute_on(&self.services.client.sender, &server, request)
|
.execute_on(&self.services.client.sender, &server, request)
|
||||||
.await;
|
.await
|
||||||
|
.inspect(|_| {
|
||||||
|
info!(%txn_id, %server, "Sent {} PDUs, {} EDUs", pdu_count, edu_count);
|
||||||
|
})
|
||||||
|
.inspect_err(|e| {
|
||||||
|
info!(%txn_id, %server, "Failed to send transaction ({} PDUs, {} EDUs): {e:?}", pdu_count, edu_count);
|
||||||
|
});
|
||||||
|
|
||||||
for (event_id, result) in result.iter().flat_map(|resp| resp.pdus.iter()) {
|
for (event_id, result) in result.iter().flat_map(|resp| resp.pdus.iter()) {
|
||||||
if let Err(e) = result {
|
if let Err(e) = result {
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue