fix: sending slowness
parent
0b263208e3
commit
b7ab57897b
|
@ -1831,7 +1831,7 @@ checksum = "7345c971d1ef21ffdbd103a75990a15eb03604fc8b8852ca8cb418ee1a099028"
|
||||||
[[package]]
|
[[package]]
|
||||||
name = "state-res"
|
name = "state-res"
|
||||||
version = "0.1.0"
|
version = "0.1.0"
|
||||||
source = "git+https://github.com/timokoesters/state-res?branch=spec-comp#a9186476b748c901fbf4356414247a0b3ac01b5f"
|
source = "git+https://github.com/timokoesters/state-res?branch=spec-comp#1d01b6e65b6afd50e65085fb40f1e7d2782f519e"
|
||||||
dependencies = [
|
dependencies = [
|
||||||
"itertools",
|
"itertools",
|
||||||
"js_int",
|
"js_int",
|
||||||
|
|
|
@ -354,19 +354,23 @@ pub async fn deactivate_route(
|
||||||
third_party_invite: None,
|
third_party_invite: None,
|
||||||
};
|
};
|
||||||
|
|
||||||
db.rooms.build_and_append_pdu(
|
db.rooms
|
||||||
PduBuilder {
|
.build_and_append_pdu(
|
||||||
event_type: EventType::RoomMember,
|
PduBuilder {
|
||||||
content: serde_json::to_value(event).expect("event is valid, we just created it"),
|
event_type: EventType::RoomMember,
|
||||||
unsigned: None,
|
content: serde_json::to_value(event)
|
||||||
state_key: Some(sender_id.to_string()),
|
.expect("event is valid, we just created it"),
|
||||||
redacts: None,
|
unsigned: None,
|
||||||
},
|
state_key: Some(sender_id.to_string()),
|
||||||
&sender_id,
|
redacts: None,
|
||||||
&room_id,
|
},
|
||||||
&db.globals,
|
&sender_id,
|
||||||
&db.account_data,
|
&room_id,
|
||||||
).await?;
|
&db.globals,
|
||||||
|
&db.sending,
|
||||||
|
&db.account_data,
|
||||||
|
)
|
||||||
|
.await?;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Remove devices and mark account as deactivated
|
// Remove devices and mark account as deactivated
|
||||||
|
|
|
@ -120,6 +120,7 @@ pub async fn leave_room_route(
|
||||||
&sender_id,
|
&sender_id,
|
||||||
&body.room_id,
|
&body.room_id,
|
||||||
&db.globals,
|
&db.globals,
|
||||||
|
&db.sending,
|
||||||
&db.account_data,
|
&db.account_data,
|
||||||
)
|
)
|
||||||
.await?;
|
.await?;
|
||||||
|
@ -157,6 +158,7 @@ pub async fn invite_user_route(
|
||||||
&sender_id,
|
&sender_id,
|
||||||
&body.room_id,
|
&body.room_id,
|
||||||
&db.globals,
|
&db.globals,
|
||||||
|
&db.sending,
|
||||||
&db.account_data,
|
&db.account_data,
|
||||||
)
|
)
|
||||||
.await?;
|
.await?;
|
||||||
|
@ -209,6 +211,7 @@ pub async fn kick_user_route(
|
||||||
&sender_id,
|
&sender_id,
|
||||||
&body.room_id,
|
&body.room_id,
|
||||||
&db.globals,
|
&db.globals,
|
||||||
|
&db.sending,
|
||||||
&db.account_data,
|
&db.account_data,
|
||||||
)
|
)
|
||||||
.await?;
|
.await?;
|
||||||
|
@ -266,6 +269,7 @@ pub async fn ban_user_route(
|
||||||
&sender_id,
|
&sender_id,
|
||||||
&body.room_id,
|
&body.room_id,
|
||||||
&db.globals,
|
&db.globals,
|
||||||
|
&db.sending,
|
||||||
&db.account_data,
|
&db.account_data,
|
||||||
)
|
)
|
||||||
.await?;
|
.await?;
|
||||||
|
@ -314,6 +318,7 @@ pub async fn unban_user_route(
|
||||||
&sender_id,
|
&sender_id,
|
||||||
&body.room_id,
|
&body.room_id,
|
||||||
&db.globals,
|
&db.globals,
|
||||||
|
&db.sending,
|
||||||
&db.account_data,
|
&db.account_data,
|
||||||
)
|
)
|
||||||
.await?;
|
.await?;
|
||||||
|
@ -672,6 +677,7 @@ async fn join_room_by_id_helper(
|
||||||
&sender_id,
|
&sender_id,
|
||||||
&room_id,
|
&room_id,
|
||||||
&db.globals,
|
&db.globals,
|
||||||
|
&db.sending,
|
||||||
&db.account_data,
|
&db.account_data,
|
||||||
)
|
)
|
||||||
.await?;
|
.await?;
|
||||||
|
|
|
@ -49,25 +49,29 @@ pub async fn send_message_event_route(
|
||||||
let mut unsigned = serde_json::Map::new();
|
let mut unsigned = serde_json::Map::new();
|
||||||
unsigned.insert("transaction_id".to_owned(), body.txn_id.clone().into());
|
unsigned.insert("transaction_id".to_owned(), body.txn_id.clone().into());
|
||||||
|
|
||||||
let event_id = db.rooms.build_and_append_pdu(
|
let event_id = db
|
||||||
PduBuilder {
|
.rooms
|
||||||
event_type: body.content.event_type().into(),
|
.build_and_append_pdu(
|
||||||
content: serde_json::from_str(
|
PduBuilder {
|
||||||
body.json_body
|
event_type: body.content.event_type().into(),
|
||||||
.as_ref()
|
content: serde_json::from_str(
|
||||||
.ok_or(Error::BadRequest(ErrorKind::BadJson, "Invalid JSON body."))?
|
body.json_body
|
||||||
.get(),
|
.as_ref()
|
||||||
)
|
.ok_or(Error::BadRequest(ErrorKind::BadJson, "Invalid JSON body."))?
|
||||||
.map_err(|_| Error::BadRequest(ErrorKind::BadJson, "Invalid JSON body."))?,
|
.get(),
|
||||||
unsigned: Some(unsigned),
|
)
|
||||||
state_key: None,
|
.map_err(|_| Error::BadRequest(ErrorKind::BadJson, "Invalid JSON body."))?,
|
||||||
redacts: None,
|
unsigned: Some(unsigned),
|
||||||
},
|
state_key: None,
|
||||||
&sender_id,
|
redacts: None,
|
||||||
&body.room_id,
|
},
|
||||||
&db.globals,
|
&sender_id,
|
||||||
&db.account_data,
|
&body.room_id,
|
||||||
).await?;
|
&db.globals,
|
||||||
|
&db.sending,
|
||||||
|
&db.account_data,
|
||||||
|
)
|
||||||
|
.await?;
|
||||||
|
|
||||||
db.transaction_ids
|
db.transaction_ids
|
||||||
.add_txnid(sender_id, device_id, &body.txn_id, event_id.as_bytes())?;
|
.add_txnid(sender_id, device_id, &body.txn_id, event_id.as_bytes())?;
|
||||||
|
|
|
@ -31,40 +31,43 @@ pub async fn set_displayname_route(
|
||||||
// Send a new membership event and presence update into all joined rooms
|
// Send a new membership event and presence update into all joined rooms
|
||||||
for room_id in db.rooms.rooms_joined(&sender_id) {
|
for room_id in db.rooms.rooms_joined(&sender_id) {
|
||||||
let room_id = room_id?;
|
let room_id = room_id?;
|
||||||
db.rooms.build_and_append_pdu(
|
db.rooms
|
||||||
PduBuilder {
|
.build_and_append_pdu(
|
||||||
event_type: EventType::RoomMember,
|
PduBuilder {
|
||||||
content: serde_json::to_value(ruma::events::room::member::MemberEventContent {
|
event_type: EventType::RoomMember,
|
||||||
displayname: body.displayname.clone(),
|
content: serde_json::to_value(ruma::events::room::member::MemberEventContent {
|
||||||
..serde_json::from_value::<Raw<_>>(
|
displayname: body.displayname.clone(),
|
||||||
db.rooms
|
..serde_json::from_value::<Raw<_>>(
|
||||||
.room_state_get(
|
db.rooms
|
||||||
&room_id,
|
.room_state_get(
|
||||||
&EventType::RoomMember,
|
&room_id,
|
||||||
&sender_id.to_string(),
|
&EventType::RoomMember,
|
||||||
)?
|
&sender_id.to_string(),
|
||||||
.ok_or_else(|| {
|
)?
|
||||||
Error::bad_database(
|
.ok_or_else(|| {
|
||||||
|
Error::bad_database(
|
||||||
"Tried to send displayname update for user not in the room.",
|
"Tried to send displayname update for user not in the room.",
|
||||||
)
|
)
|
||||||
})?
|
})?
|
||||||
.content
|
.content
|
||||||
.clone(),
|
.clone(),
|
||||||
)
|
)
|
||||||
.expect("from_value::<Raw<..>> can never fail")
|
.expect("from_value::<Raw<..>> can never fail")
|
||||||
.deserialize()
|
.deserialize()
|
||||||
.map_err(|_| Error::bad_database("Database contains invalid PDU."))?
|
.map_err(|_| Error::bad_database("Database contains invalid PDU."))?
|
||||||
})
|
})
|
||||||
.expect("event is valid, we just created it"),
|
.expect("event is valid, we just created it"),
|
||||||
unsigned: None,
|
unsigned: None,
|
||||||
state_key: Some(sender_id.to_string()),
|
state_key: Some(sender_id.to_string()),
|
||||||
redacts: None,
|
redacts: None,
|
||||||
},
|
},
|
||||||
&sender_id,
|
&sender_id,
|
||||||
&room_id,
|
&room_id,
|
||||||
&db.globals,
|
&db.globals,
|
||||||
&db.account_data,
|
&db.sending,
|
||||||
).await?;
|
&db.account_data,
|
||||||
|
)
|
||||||
|
.await?;
|
||||||
|
|
||||||
// Presence update
|
// Presence update
|
||||||
db.rooms.edus.update_presence(
|
db.rooms.edus.update_presence(
|
||||||
|
@ -134,40 +137,43 @@ pub async fn set_avatar_url_route(
|
||||||
// Send a new membership event and presence update into all joined rooms
|
// Send a new membership event and presence update into all joined rooms
|
||||||
for room_id in db.rooms.rooms_joined(&sender_id) {
|
for room_id in db.rooms.rooms_joined(&sender_id) {
|
||||||
let room_id = room_id?;
|
let room_id = room_id?;
|
||||||
db.rooms.build_and_append_pdu(
|
db.rooms
|
||||||
PduBuilder {
|
.build_and_append_pdu(
|
||||||
event_type: EventType::RoomMember,
|
PduBuilder {
|
||||||
content: serde_json::to_value(ruma::events::room::member::MemberEventContent {
|
event_type: EventType::RoomMember,
|
||||||
avatar_url: body.avatar_url.clone(),
|
content: serde_json::to_value(ruma::events::room::member::MemberEventContent {
|
||||||
..serde_json::from_value::<Raw<_>>(
|
avatar_url: body.avatar_url.clone(),
|
||||||
db.rooms
|
..serde_json::from_value::<Raw<_>>(
|
||||||
.room_state_get(
|
db.rooms
|
||||||
&room_id,
|
.room_state_get(
|
||||||
&EventType::RoomMember,
|
&room_id,
|
||||||
&sender_id.to_string(),
|
&EventType::RoomMember,
|
||||||
)?
|
&sender_id.to_string(),
|
||||||
.ok_or_else(|| {
|
)?
|
||||||
Error::bad_database(
|
.ok_or_else(|| {
|
||||||
"Tried to send avatar url update for user not in the room.",
|
Error::bad_database(
|
||||||
)
|
"Tried to send avatar url update for user not in the room.",
|
||||||
})?
|
)
|
||||||
.content
|
})?
|
||||||
.clone(),
|
.content
|
||||||
)
|
.clone(),
|
||||||
.expect("from_value::<Raw<..>> can never fail")
|
)
|
||||||
.deserialize()
|
.expect("from_value::<Raw<..>> can never fail")
|
||||||
.map_err(|_| Error::bad_database("Database contains invalid PDU."))?
|
.deserialize()
|
||||||
})
|
.map_err(|_| Error::bad_database("Database contains invalid PDU."))?
|
||||||
.expect("event is valid, we just created it"),
|
})
|
||||||
unsigned: None,
|
.expect("event is valid, we just created it"),
|
||||||
state_key: Some(sender_id.to_string()),
|
unsigned: None,
|
||||||
redacts: None,
|
state_key: Some(sender_id.to_string()),
|
||||||
},
|
redacts: None,
|
||||||
&sender_id,
|
},
|
||||||
&room_id,
|
&sender_id,
|
||||||
&db.globals,
|
&room_id,
|
||||||
&db.account_data,
|
&db.globals,
|
||||||
).await?;
|
&db.sending,
|
||||||
|
&db.account_data,
|
||||||
|
)
|
||||||
|
.await?;
|
||||||
|
|
||||||
// Presence update
|
// Presence update
|
||||||
db.rooms.edus.update_presence(
|
db.rooms.edus.update_presence(
|
||||||
|
|
|
@ -18,22 +18,26 @@ pub async fn redact_event_route(
|
||||||
) -> ConduitResult<redact_event::Response> {
|
) -> ConduitResult<redact_event::Response> {
|
||||||
let sender_id = body.sender_id.as_ref().expect("user is authenticated");
|
let sender_id = body.sender_id.as_ref().expect("user is authenticated");
|
||||||
|
|
||||||
let event_id = db.rooms.build_and_append_pdu(
|
let event_id = db
|
||||||
PduBuilder {
|
.rooms
|
||||||
event_type: EventType::RoomRedaction,
|
.build_and_append_pdu(
|
||||||
content: serde_json::to_value(redaction::RedactionEventContent {
|
PduBuilder {
|
||||||
reason: body.reason.clone(),
|
event_type: EventType::RoomRedaction,
|
||||||
})
|
content: serde_json::to_value(redaction::RedactionEventContent {
|
||||||
.expect("event is valid, we just created it"),
|
reason: body.reason.clone(),
|
||||||
unsigned: None,
|
})
|
||||||
state_key: None,
|
.expect("event is valid, we just created it"),
|
||||||
redacts: Some(body.event_id.clone()),
|
unsigned: None,
|
||||||
},
|
state_key: None,
|
||||||
&sender_id,
|
redacts: Some(body.event_id.clone()),
|
||||||
&body.room_id,
|
},
|
||||||
&db.globals,
|
&sender_id,
|
||||||
&db.account_data,
|
&body.room_id,
|
||||||
).await?;
|
&db.globals,
|
||||||
|
&db.sending,
|
||||||
|
&db.account_data,
|
||||||
|
)
|
||||||
|
.await?;
|
||||||
|
|
||||||
Ok(redact_event::Response { event_id }.into())
|
Ok(redact_event::Response { event_id }.into())
|
||||||
}
|
}
|
||||||
|
|
|
@ -53,41 +53,47 @@ pub async fn create_room_route(
|
||||||
content.room_version = RoomVersionId::Version6;
|
content.room_version = RoomVersionId::Version6;
|
||||||
|
|
||||||
// 1. The room create event
|
// 1. The room create event
|
||||||
db.rooms.build_and_append_pdu(
|
db.rooms
|
||||||
PduBuilder {
|
.build_and_append_pdu(
|
||||||
event_type: EventType::RoomCreate,
|
PduBuilder {
|
||||||
content: serde_json::to_value(content).expect("event is valid, we just created it"),
|
event_type: EventType::RoomCreate,
|
||||||
unsigned: None,
|
content: serde_json::to_value(content).expect("event is valid, we just created it"),
|
||||||
state_key: Some("".to_owned()),
|
unsigned: None,
|
||||||
redacts: None,
|
state_key: Some("".to_owned()),
|
||||||
},
|
redacts: None,
|
||||||
&sender_id,
|
},
|
||||||
&room_id,
|
&sender_id,
|
||||||
&db.globals,
|
&room_id,
|
||||||
&db.account_data,
|
&db.globals,
|
||||||
).await?;
|
&db.sending,
|
||||||
|
&db.account_data,
|
||||||
|
)
|
||||||
|
.await?;
|
||||||
|
|
||||||
// 2. Let the room creator join
|
// 2. Let the room creator join
|
||||||
db.rooms.build_and_append_pdu(
|
db.rooms
|
||||||
PduBuilder {
|
.build_and_append_pdu(
|
||||||
event_type: EventType::RoomMember,
|
PduBuilder {
|
||||||
content: serde_json::to_value(member::MemberEventContent {
|
event_type: EventType::RoomMember,
|
||||||
membership: member::MembershipState::Join,
|
content: serde_json::to_value(member::MemberEventContent {
|
||||||
displayname: db.users.displayname(&sender_id)?,
|
membership: member::MembershipState::Join,
|
||||||
avatar_url: db.users.avatar_url(&sender_id)?,
|
displayname: db.users.displayname(&sender_id)?,
|
||||||
is_direct: Some(body.is_direct),
|
avatar_url: db.users.avatar_url(&sender_id)?,
|
||||||
third_party_invite: None,
|
is_direct: Some(body.is_direct),
|
||||||
})
|
third_party_invite: None,
|
||||||
.expect("event is valid, we just created it"),
|
})
|
||||||
unsigned: None,
|
.expect("event is valid, we just created it"),
|
||||||
state_key: Some(sender_id.to_string()),
|
unsigned: None,
|
||||||
redacts: None,
|
state_key: Some(sender_id.to_string()),
|
||||||
},
|
redacts: None,
|
||||||
&sender_id,
|
},
|
||||||
&room_id,
|
&sender_id,
|
||||||
&db.globals,
|
&room_id,
|
||||||
&db.account_data,
|
&db.globals,
|
||||||
).await?;
|
&db.sending,
|
||||||
|
&db.account_data,
|
||||||
|
)
|
||||||
|
.await?;
|
||||||
|
|
||||||
// 3. Power levels
|
// 3. Power levels
|
||||||
let mut users = BTreeMap::new();
|
let mut users = BTreeMap::new();
|
||||||
|
@ -117,19 +123,22 @@ pub async fn create_room_route(
|
||||||
})
|
})
|
||||||
.expect("event is valid, we just created it")
|
.expect("event is valid, we just created it")
|
||||||
};
|
};
|
||||||
db.rooms.build_and_append_pdu(
|
db.rooms
|
||||||
PduBuilder {
|
.build_and_append_pdu(
|
||||||
event_type: EventType::RoomPowerLevels,
|
PduBuilder {
|
||||||
content: power_levels_content,
|
event_type: EventType::RoomPowerLevels,
|
||||||
unsigned: None,
|
content: power_levels_content,
|
||||||
state_key: Some("".to_owned()),
|
unsigned: None,
|
||||||
redacts: None,
|
state_key: Some("".to_owned()),
|
||||||
},
|
redacts: None,
|
||||||
&sender_id,
|
},
|
||||||
&room_id,
|
&sender_id,
|
||||||
&db.globals,
|
&room_id,
|
||||||
&db.account_data,
|
&db.globals,
|
||||||
).await?;
|
&db.sending,
|
||||||
|
&db.account_data,
|
||||||
|
)
|
||||||
|
.await?;
|
||||||
|
|
||||||
// 4. Events set by preset
|
// 4. Events set by preset
|
||||||
|
|
||||||
|
@ -140,73 +149,84 @@ pub async fn create_room_route(
|
||||||
});
|
});
|
||||||
|
|
||||||
// 4.1 Join Rules
|
// 4.1 Join Rules
|
||||||
db.rooms.build_and_append_pdu(
|
db.rooms
|
||||||
PduBuilder {
|
.build_and_append_pdu(
|
||||||
event_type: EventType::RoomJoinRules,
|
PduBuilder {
|
||||||
content: match preset {
|
event_type: EventType::RoomJoinRules,
|
||||||
create_room::RoomPreset::PublicChat => serde_json::to_value(
|
content: match preset {
|
||||||
join_rules::JoinRulesEventContent::new(join_rules::JoinRule::Public),
|
create_room::RoomPreset::PublicChat => serde_json::to_value(
|
||||||
)
|
join_rules::JoinRulesEventContent::new(join_rules::JoinRule::Public),
|
||||||
.expect("event is valid, we just created it"),
|
)
|
||||||
// according to spec "invite" is the default
|
.expect("event is valid, we just created it"),
|
||||||
_ => serde_json::to_value(join_rules::JoinRulesEventContent::new(
|
// according to spec "invite" is the default
|
||||||
join_rules::JoinRule::Invite,
|
_ => serde_json::to_value(join_rules::JoinRulesEventContent::new(
|
||||||
))
|
join_rules::JoinRule::Invite,
|
||||||
.expect("event is valid, we just created it"),
|
))
|
||||||
|
.expect("event is valid, we just created it"),
|
||||||
|
},
|
||||||
|
unsigned: None,
|
||||||
|
state_key: Some("".to_owned()),
|
||||||
|
redacts: None,
|
||||||
},
|
},
|
||||||
unsigned: None,
|
&sender_id,
|
||||||
state_key: Some("".to_owned()),
|
&room_id,
|
||||||
redacts: None,
|
&db.globals,
|
||||||
},
|
&db.sending,
|
||||||
&sender_id,
|
&db.account_data,
|
||||||
&room_id,
|
)
|
||||||
&db.globals,
|
.await?;
|
||||||
&db.account_data,
|
|
||||||
).await?;
|
|
||||||
|
|
||||||
// 4.2 History Visibility
|
// 4.2 History Visibility
|
||||||
db.rooms.build_and_append_pdu(
|
db.rooms
|
||||||
PduBuilder {
|
.build_and_append_pdu(
|
||||||
event_type: EventType::RoomHistoryVisibility,
|
PduBuilder {
|
||||||
content: serde_json::to_value(history_visibility::HistoryVisibilityEventContent::new(
|
event_type: EventType::RoomHistoryVisibility,
|
||||||
history_visibility::HistoryVisibility::Shared,
|
content: serde_json::to_value(
|
||||||
))
|
history_visibility::HistoryVisibilityEventContent::new(
|
||||||
.expect("event is valid, we just created it"),
|
history_visibility::HistoryVisibility::Shared,
|
||||||
unsigned: None,
|
),
|
||||||
state_key: Some("".to_owned()),
|
)
|
||||||
redacts: None,
|
.expect("event is valid, we just created it"),
|
||||||
},
|
unsigned: None,
|
||||||
&sender_id,
|
state_key: Some("".to_owned()),
|
||||||
&room_id,
|
redacts: None,
|
||||||
&db.globals,
|
},
|
||||||
&db.account_data,
|
&sender_id,
|
||||||
).await?;
|
&room_id,
|
||||||
|
&db.globals,
|
||||||
|
&db.sending,
|
||||||
|
&db.account_data,
|
||||||
|
)
|
||||||
|
.await?;
|
||||||
|
|
||||||
// 4.3 Guest Access
|
// 4.3 Guest Access
|
||||||
db.rooms.build_and_append_pdu(
|
db.rooms
|
||||||
PduBuilder {
|
.build_and_append_pdu(
|
||||||
event_type: EventType::RoomGuestAccess,
|
PduBuilder {
|
||||||
content: match preset {
|
event_type: EventType::RoomGuestAccess,
|
||||||
create_room::RoomPreset::PublicChat => {
|
content: match preset {
|
||||||
serde_json::to_value(guest_access::GuestAccessEventContent::new(
|
create_room::RoomPreset::PublicChat => {
|
||||||
guest_access::GuestAccess::Forbidden,
|
serde_json::to_value(guest_access::GuestAccessEventContent::new(
|
||||||
|
guest_access::GuestAccess::Forbidden,
|
||||||
|
))
|
||||||
|
.expect("event is valid, we just created it")
|
||||||
|
}
|
||||||
|
_ => serde_json::to_value(guest_access::GuestAccessEventContent::new(
|
||||||
|
guest_access::GuestAccess::CanJoin,
|
||||||
))
|
))
|
||||||
.expect("event is valid, we just created it")
|
.expect("event is valid, we just created it"),
|
||||||
}
|
},
|
||||||
_ => serde_json::to_value(guest_access::GuestAccessEventContent::new(
|
unsigned: None,
|
||||||
guest_access::GuestAccess::CanJoin,
|
state_key: Some("".to_owned()),
|
||||||
))
|
redacts: None,
|
||||||
.expect("event is valid, we just created it"),
|
|
||||||
},
|
},
|
||||||
unsigned: None,
|
&sender_id,
|
||||||
state_key: Some("".to_owned()),
|
&room_id,
|
||||||
redacts: None,
|
&db.globals,
|
||||||
},
|
&db.sending,
|
||||||
&sender_id,
|
&db.account_data,
|
||||||
&room_id,
|
)
|
||||||
&db.globals,
|
.await?;
|
||||||
&db.account_data,
|
|
||||||
).await?;
|
|
||||||
|
|
||||||
// 5. Events listed in initial_state
|
// 5. Events listed in initial_state
|
||||||
for event in &body.initial_state {
|
for event in &body.initial_state {
|
||||||
|
@ -220,78 +240,90 @@ pub async fn create_room_route(
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
db.rooms.build_and_append_pdu(
|
db.rooms
|
||||||
pdu_builder,
|
.build_and_append_pdu(
|
||||||
&sender_id,
|
pdu_builder,
|
||||||
&room_id,
|
&sender_id,
|
||||||
&db.globals,
|
&room_id,
|
||||||
&db.account_data,
|
&db.globals,
|
||||||
).await?;
|
&db.sending,
|
||||||
|
&db.account_data,
|
||||||
|
)
|
||||||
|
.await?;
|
||||||
}
|
}
|
||||||
|
|
||||||
// 6. Events implied by name and topic
|
// 6. Events implied by name and topic
|
||||||
if let Some(name) = &body.name {
|
if let Some(name) = &body.name {
|
||||||
db.rooms.build_and_append_pdu(
|
db.rooms
|
||||||
PduBuilder {
|
.build_and_append_pdu(
|
||||||
event_type: EventType::RoomName,
|
PduBuilder {
|
||||||
content: serde_json::to_value(
|
event_type: EventType::RoomName,
|
||||||
name::NameEventContent::new(name.clone()).map_err(|_| {
|
content: serde_json::to_value(
|
||||||
Error::BadRequest(ErrorKind::InvalidParam, "Name is invalid.")
|
name::NameEventContent::new(name.clone()).map_err(|_| {
|
||||||
})?,
|
Error::BadRequest(ErrorKind::InvalidParam, "Name is invalid.")
|
||||||
)
|
})?,
|
||||||
.expect("event is valid, we just created it"),
|
)
|
||||||
unsigned: None,
|
.expect("event is valid, we just created it"),
|
||||||
state_key: Some("".to_owned()),
|
unsigned: None,
|
||||||
redacts: None,
|
state_key: Some("".to_owned()),
|
||||||
},
|
redacts: None,
|
||||||
&sender_id,
|
},
|
||||||
&room_id,
|
&sender_id,
|
||||||
&db.globals,
|
&room_id,
|
||||||
&db.account_data,
|
&db.globals,
|
||||||
).await?;
|
&db.sending,
|
||||||
|
&db.account_data,
|
||||||
|
)
|
||||||
|
.await?;
|
||||||
}
|
}
|
||||||
|
|
||||||
if let Some(topic) = &body.topic {
|
if let Some(topic) = &body.topic {
|
||||||
db.rooms.build_and_append_pdu(
|
db.rooms
|
||||||
PduBuilder {
|
.build_and_append_pdu(
|
||||||
event_type: EventType::RoomTopic,
|
PduBuilder {
|
||||||
content: serde_json::to_value(topic::TopicEventContent {
|
event_type: EventType::RoomTopic,
|
||||||
topic: topic.clone(),
|
content: serde_json::to_value(topic::TopicEventContent {
|
||||||
})
|
topic: topic.clone(),
|
||||||
.expect("event is valid, we just created it"),
|
})
|
||||||
unsigned: None,
|
.expect("event is valid, we just created it"),
|
||||||
state_key: Some("".to_owned()),
|
unsigned: None,
|
||||||
redacts: None,
|
state_key: Some("".to_owned()),
|
||||||
},
|
redacts: None,
|
||||||
&sender_id,
|
},
|
||||||
&room_id,
|
&sender_id,
|
||||||
&db.globals,
|
&room_id,
|
||||||
&db.account_data,
|
&db.globals,
|
||||||
).await?;
|
&db.sending,
|
||||||
|
&db.account_data,
|
||||||
|
)
|
||||||
|
.await?;
|
||||||
}
|
}
|
||||||
|
|
||||||
// 7. Events implied by invite (and TODO: invite_3pid)
|
// 7. Events implied by invite (and TODO: invite_3pid)
|
||||||
for user in &body.invite {
|
for user in &body.invite {
|
||||||
db.rooms.build_and_append_pdu(
|
db.rooms
|
||||||
PduBuilder {
|
.build_and_append_pdu(
|
||||||
event_type: EventType::RoomMember,
|
PduBuilder {
|
||||||
content: serde_json::to_value(member::MemberEventContent {
|
event_type: EventType::RoomMember,
|
||||||
membership: member::MembershipState::Invite,
|
content: serde_json::to_value(member::MemberEventContent {
|
||||||
displayname: db.users.displayname(&user)?,
|
membership: member::MembershipState::Invite,
|
||||||
avatar_url: db.users.avatar_url(&user)?,
|
displayname: db.users.displayname(&user)?,
|
||||||
is_direct: Some(body.is_direct),
|
avatar_url: db.users.avatar_url(&user)?,
|
||||||
third_party_invite: None,
|
is_direct: Some(body.is_direct),
|
||||||
})
|
third_party_invite: None,
|
||||||
.expect("event is valid, we just created it"),
|
})
|
||||||
unsigned: None,
|
.expect("event is valid, we just created it"),
|
||||||
state_key: Some(user.to_string()),
|
unsigned: None,
|
||||||
redacts: None,
|
state_key: Some(user.to_string()),
|
||||||
},
|
redacts: None,
|
||||||
&sender_id,
|
},
|
||||||
&room_id,
|
&sender_id,
|
||||||
&db.globals,
|
&room_id,
|
||||||
&db.account_data,
|
&db.globals,
|
||||||
).await?;
|
&db.sending,
|
||||||
|
&db.account_data,
|
||||||
|
)
|
||||||
|
.await?;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Homeserver specific stuff
|
// Homeserver specific stuff
|
||||||
|
@ -363,23 +395,29 @@ pub async fn upgrade_room_route(
|
||||||
|
|
||||||
// Send a m.room.tombstone event to the old room to indicate that it is not intended to be used any further
|
// Send a m.room.tombstone event to the old room to indicate that it is not intended to be used any further
|
||||||
// Fail if the sender does not have the required permissions
|
// Fail if the sender does not have the required permissions
|
||||||
let tombstone_event_id = db.rooms.build_and_append_pdu(
|
let tombstone_event_id = db
|
||||||
PduBuilder {
|
.rooms
|
||||||
event_type: EventType::RoomTombstone,
|
.build_and_append_pdu(
|
||||||
content: serde_json::to_value(ruma::events::room::tombstone::TombstoneEventContent {
|
PduBuilder {
|
||||||
body: "This room has been replaced".to_string(),
|
event_type: EventType::RoomTombstone,
|
||||||
replacement_room: replacement_room.clone(),
|
content: serde_json::to_value(
|
||||||
})
|
ruma::events::room::tombstone::TombstoneEventContent {
|
||||||
.expect("event is valid, we just created it"),
|
body: "This room has been replaced".to_string(),
|
||||||
unsigned: None,
|
replacement_room: replacement_room.clone(),
|
||||||
state_key: Some("".to_owned()),
|
},
|
||||||
redacts: None,
|
)
|
||||||
},
|
.expect("event is valid, we just created it"),
|
||||||
sender_id,
|
unsigned: None,
|
||||||
&body.room_id,
|
state_key: Some("".to_owned()),
|
||||||
&db.globals,
|
redacts: None,
|
||||||
&db.account_data,
|
},
|
||||||
).await?;
|
sender_id,
|
||||||
|
&body.room_id,
|
||||||
|
&db.globals,
|
||||||
|
&db.sending,
|
||||||
|
&db.account_data,
|
||||||
|
)
|
||||||
|
.await?;
|
||||||
|
|
||||||
// Get the old room federations status
|
// Get the old room federations status
|
||||||
let federate = serde_json::from_value::<Raw<ruma::events::room::create::CreateEventContent>>(
|
let federate = serde_json::from_value::<Raw<ruma::events::room::create::CreateEventContent>>(
|
||||||
|
@ -406,42 +444,48 @@ pub async fn upgrade_room_route(
|
||||||
create_event_content.room_version = new_version;
|
create_event_content.room_version = new_version;
|
||||||
create_event_content.predecessor = predecessor;
|
create_event_content.predecessor = predecessor;
|
||||||
|
|
||||||
db.rooms.build_and_append_pdu(
|
db.rooms
|
||||||
PduBuilder {
|
.build_and_append_pdu(
|
||||||
event_type: EventType::RoomCreate,
|
PduBuilder {
|
||||||
content: serde_json::to_value(create_event_content)
|
event_type: EventType::RoomCreate,
|
||||||
.expect("event is valid, we just created it"),
|
content: serde_json::to_value(create_event_content)
|
||||||
unsigned: None,
|
.expect("event is valid, we just created it"),
|
||||||
state_key: Some("".to_owned()),
|
unsigned: None,
|
||||||
redacts: None,
|
state_key: Some("".to_owned()),
|
||||||
},
|
redacts: None,
|
||||||
sender_id,
|
},
|
||||||
&replacement_room,
|
sender_id,
|
||||||
&db.globals,
|
&replacement_room,
|
||||||
&db.account_data,
|
&db.globals,
|
||||||
).await?;
|
&db.sending,
|
||||||
|
&db.account_data,
|
||||||
|
)
|
||||||
|
.await?;
|
||||||
|
|
||||||
// Join the new room
|
// Join the new room
|
||||||
db.rooms.build_and_append_pdu(
|
db.rooms
|
||||||
PduBuilder {
|
.build_and_append_pdu(
|
||||||
event_type: EventType::RoomMember,
|
PduBuilder {
|
||||||
content: serde_json::to_value(member::MemberEventContent {
|
event_type: EventType::RoomMember,
|
||||||
membership: member::MembershipState::Join,
|
content: serde_json::to_value(member::MemberEventContent {
|
||||||
displayname: db.users.displayname(&sender_id)?,
|
membership: member::MembershipState::Join,
|
||||||
avatar_url: db.users.avatar_url(&sender_id)?,
|
displayname: db.users.displayname(&sender_id)?,
|
||||||
is_direct: None,
|
avatar_url: db.users.avatar_url(&sender_id)?,
|
||||||
third_party_invite: None,
|
is_direct: None,
|
||||||
})
|
third_party_invite: None,
|
||||||
.expect("event is valid, we just created it"),
|
})
|
||||||
unsigned: None,
|
.expect("event is valid, we just created it"),
|
||||||
state_key: Some(sender_id.to_string()),
|
unsigned: None,
|
||||||
redacts: None,
|
state_key: Some(sender_id.to_string()),
|
||||||
},
|
redacts: None,
|
||||||
sender_id,
|
},
|
||||||
&replacement_room,
|
sender_id,
|
||||||
&db.globals,
|
&replacement_room,
|
||||||
&db.account_data,
|
&db.globals,
|
||||||
).await?;
|
&db.sending,
|
||||||
|
&db.account_data,
|
||||||
|
)
|
||||||
|
.await?;
|
||||||
|
|
||||||
// Recommended transferable state events list from the specs
|
// Recommended transferable state events list from the specs
|
||||||
let transferable_state_events = vec![
|
let transferable_state_events = vec![
|
||||||
|
@ -463,19 +507,22 @@ pub async fn upgrade_room_route(
|
||||||
None => continue, // Skipping missing events.
|
None => continue, // Skipping missing events.
|
||||||
};
|
};
|
||||||
|
|
||||||
db.rooms.build_and_append_pdu(
|
db.rooms
|
||||||
PduBuilder {
|
.build_and_append_pdu(
|
||||||
event_type,
|
PduBuilder {
|
||||||
content: event_content,
|
event_type,
|
||||||
unsigned: None,
|
content: event_content,
|
||||||
state_key: Some("".to_owned()),
|
unsigned: None,
|
||||||
redacts: None,
|
state_key: Some("".to_owned()),
|
||||||
},
|
redacts: None,
|
||||||
sender_id,
|
},
|
||||||
&replacement_room,
|
sender_id,
|
||||||
&db.globals,
|
&replacement_room,
|
||||||
&db.account_data,
|
&db.globals,
|
||||||
).await?;
|
&db.sending,
|
||||||
|
&db.account_data,
|
||||||
|
)
|
||||||
|
.await?;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Moves any local aliases to the new room
|
// Moves any local aliases to the new room
|
||||||
|
@ -505,7 +552,8 @@ pub async fn upgrade_room_route(
|
||||||
power_levels_event_content.invite = new_level;
|
power_levels_event_content.invite = new_level;
|
||||||
|
|
||||||
// Modify the power levels in the old room to prevent sending of events and inviting new users
|
// Modify the power levels in the old room to prevent sending of events and inviting new users
|
||||||
let _ = db.rooms
|
let _ = db
|
||||||
|
.rooms
|
||||||
.build_and_append_pdu(
|
.build_and_append_pdu(
|
||||||
PduBuilder {
|
PduBuilder {
|
||||||
event_type: EventType::RoomPowerLevels,
|
event_type: EventType::RoomPowerLevels,
|
||||||
|
@ -518,8 +566,10 @@ pub async fn upgrade_room_route(
|
||||||
sender_id,
|
sender_id,
|
||||||
&body.room_id,
|
&body.room_id,
|
||||||
&db.globals,
|
&db.globals,
|
||||||
|
&db.sending,
|
||||||
&db.account_data,
|
&db.account_data,
|
||||||
).await;
|
)
|
||||||
|
.await;
|
||||||
|
|
||||||
// Return the replacement room id
|
// Return the replacement room id
|
||||||
Ok(upgrade_room::Response { replacement_room }.into())
|
Ok(upgrade_room::Response { replacement_room }.into())
|
||||||
|
|
|
@ -33,17 +33,18 @@ pub async fn send_state_event_for_key_route(
|
||||||
)
|
)
|
||||||
.map_err(|_| Error::BadRequest(ErrorKind::BadJson, "Invalid JSON body."))?;
|
.map_err(|_| Error::BadRequest(ErrorKind::BadJson, "Invalid JSON body."))?;
|
||||||
|
|
||||||
Ok(
|
Ok(send_state_event_for_key::Response::new(
|
||||||
send_state_event_for_key::Response::new(send_state_event_for_key_helper(
|
send_state_event_for_key_helper(
|
||||||
&db,
|
&db,
|
||||||
sender_id,
|
sender_id,
|
||||||
&body.content,
|
&body.content,
|
||||||
content,
|
content,
|
||||||
&body.room_id,
|
&body.room_id,
|
||||||
Some(body.state_key.to_owned()),
|
Some(body.state_key.to_owned()),
|
||||||
).await?)
|
)
|
||||||
.into(),
|
.await?,
|
||||||
)
|
)
|
||||||
|
.into())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg_attr(
|
#[cfg_attr(
|
||||||
|
@ -70,8 +71,8 @@ pub async fn send_state_event_for_empty_key_route(
|
||||||
)
|
)
|
||||||
.map_err(|_| Error::BadRequest(ErrorKind::BadJson, "Invalid JSON body."))?;
|
.map_err(|_| Error::BadRequest(ErrorKind::BadJson, "Invalid JSON body."))?;
|
||||||
|
|
||||||
Ok(
|
Ok(send_state_event_for_empty_key::Response::new(
|
||||||
send_state_event_for_empty_key::Response::new(send_state_event_for_key_helper(
|
send_state_event_for_key_helper(
|
||||||
&db,
|
&db,
|
||||||
sender_id
|
sender_id
|
||||||
.as_ref()
|
.as_ref()
|
||||||
|
@ -80,9 +81,10 @@ pub async fn send_state_event_for_empty_key_route(
|
||||||
json,
|
json,
|
||||||
&body.room_id,
|
&body.room_id,
|
||||||
Some("".into()),
|
Some("".into()),
|
||||||
).await?)
|
)
|
||||||
.into(),
|
.await?,
|
||||||
)
|
)
|
||||||
|
.into())
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg_attr(
|
#[cfg_attr(
|
||||||
|
@ -211,19 +213,23 @@ pub async fn send_state_event_for_key_helper(
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
let event_id = db.rooms.build_and_append_pdu(
|
let event_id = db
|
||||||
PduBuilder {
|
.rooms
|
||||||
event_type: content.event_type().into(),
|
.build_and_append_pdu(
|
||||||
content: json,
|
PduBuilder {
|
||||||
unsigned: None,
|
event_type: content.event_type().into(),
|
||||||
state_key,
|
content: json,
|
||||||
redacts: None,
|
unsigned: None,
|
||||||
},
|
state_key,
|
||||||
&sender_id,
|
redacts: None,
|
||||||
&room_id,
|
},
|
||||||
&db.globals,
|
&sender_id,
|
||||||
&db.account_data,
|
&room_id,
|
||||||
).await?;
|
&db.globals,
|
||||||
|
&db.sending,
|
||||||
|
&db.account_data,
|
||||||
|
)
|
||||||
|
.await?;
|
||||||
|
|
||||||
Ok(event_id)
|
Ok(event_id)
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,6 +3,7 @@ pub mod globals;
|
||||||
pub mod key_backups;
|
pub mod key_backups;
|
||||||
pub mod media;
|
pub mod media;
|
||||||
pub mod rooms;
|
pub mod rooms;
|
||||||
|
pub mod sending;
|
||||||
pub mod transaction_ids;
|
pub mod transaction_ids;
|
||||||
pub mod uiaa;
|
pub mod uiaa;
|
||||||
pub mod users;
|
pub mod users;
|
||||||
|
@ -25,6 +26,7 @@ pub struct Database {
|
||||||
pub media: media::Media,
|
pub media: media::Media,
|
||||||
pub key_backups: key_backups::KeyBackups,
|
pub key_backups: key_backups::KeyBackups,
|
||||||
pub transaction_ids: transaction_ids::TransactionIds,
|
pub transaction_ids: transaction_ids::TransactionIds,
|
||||||
|
pub sending: sending::Sending,
|
||||||
pub _db: sled::Db,
|
pub _db: sled::Db,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -135,6 +137,9 @@ impl Database {
|
||||||
transaction_ids: transaction_ids::TransactionIds {
|
transaction_ids: transaction_ids::TransactionIds {
|
||||||
userdevicetxnid_response: db.open_tree("userdevicetxnid_response")?,
|
userdevicetxnid_response: db.open_tree("userdevicetxnid_response")?,
|
||||||
},
|
},
|
||||||
|
sending: sending::Sending {
|
||||||
|
serverpduids: db.open_tree("serverpduids")?,
|
||||||
|
},
|
||||||
_db: db,
|
_db: db,
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,12 +1,13 @@
|
||||||
use crate::{utils, Error, Result};
|
use crate::{utils, Error, Result};
|
||||||
use ruma::ServerName;
|
use ruma::ServerName;
|
||||||
use std::convert::TryInto;
|
use std::{convert::TryInto, sync::Arc};
|
||||||
|
|
||||||
pub const COUNTER: &str = "c";
|
pub const COUNTER: &str = "c";
|
||||||
|
|
||||||
|
#[derive(Clone)]
|
||||||
pub struct Globals {
|
pub struct Globals {
|
||||||
pub(super) globals: sled::Tree,
|
pub(super) globals: sled::Tree,
|
||||||
keypair: ruma::signatures::Ed25519KeyPair,
|
keypair: Arc<ruma::signatures::Ed25519KeyPair>,
|
||||||
reqwest_client: reqwest::Client,
|
reqwest_client: reqwest::Client,
|
||||||
server_name: Box<ServerName>,
|
server_name: Box<ServerName>,
|
||||||
max_request_size: u32,
|
max_request_size: u32,
|
||||||
|
@ -16,13 +17,15 @@ pub struct Globals {
|
||||||
|
|
||||||
impl Globals {
|
impl Globals {
|
||||||
pub fn load(globals: sled::Tree, config: &rocket::Config) -> Result<Self> {
|
pub fn load(globals: sled::Tree, config: &rocket::Config) -> Result<Self> {
|
||||||
let keypair = ruma::signatures::Ed25519KeyPair::new(
|
let keypair = Arc::new(
|
||||||
&*globals
|
ruma::signatures::Ed25519KeyPair::new(
|
||||||
.update_and_fetch("keypair", utils::generate_keypair)?
|
&*globals
|
||||||
.expect("utils::generate_keypair always returns Some"),
|
.update_and_fetch("keypair", utils::generate_keypair)?
|
||||||
"key1".to_owned(),
|
.expect("utils::generate_keypair always returns Some"),
|
||||||
)
|
"key1".to_owned(),
|
||||||
.map_err(|_| Error::bad_database("Private or public keys are invalid."))?;
|
)
|
||||||
|
.map_err(|_| Error::bad_database("Private or public keys are invalid."))?,
|
||||||
|
);
|
||||||
|
|
||||||
Ok(Self {
|
Ok(Self {
|
||||||
globals,
|
globals,
|
||||||
|
|
|
@ -1,14 +1,12 @@
|
||||||
mod edus;
|
mod edus;
|
||||||
|
|
||||||
pub use edus::RoomEdus;
|
pub use edus::RoomEdus;
|
||||||
use rocket::futures;
|
|
||||||
|
|
||||||
use crate::{pdu::PduBuilder, server_server, utils, Error, PduEvent, Result};
|
use crate::{pdu::PduBuilder, utils, Error, PduEvent, Result};
|
||||||
use log::{error, warn};
|
use log::error;
|
||||||
use ring::digest;
|
use ring::digest;
|
||||||
use ruma::{
|
use ruma::{
|
||||||
api::client::error::ErrorKind,
|
api::client::error::ErrorKind,
|
||||||
api::federation,
|
|
||||||
events::{
|
events::{
|
||||||
ignored_user_list,
|
ignored_user_list,
|
||||||
room::{
|
room::{
|
||||||
|
@ -27,7 +25,6 @@ use std::{
|
||||||
convert::{TryFrom, TryInto},
|
convert::{TryFrom, TryInto},
|
||||||
mem,
|
mem,
|
||||||
sync::Arc,
|
sync::Arc,
|
||||||
time::SystemTime,
|
|
||||||
};
|
};
|
||||||
|
|
||||||
/// The unique identifier of each state group.
|
/// The unique identifier of each state group.
|
||||||
|
@ -36,6 +33,7 @@ use std::{
|
||||||
/// hashing the entire state.
|
/// hashing the entire state.
|
||||||
pub type StateHashId = Vec<u8>;
|
pub type StateHashId = Vec<u8>;
|
||||||
|
|
||||||
|
#[derive(Clone)]
|
||||||
pub struct Rooms {
|
pub struct Rooms {
|
||||||
pub edus: edus::RoomEdus,
|
pub edus: edus::RoomEdus,
|
||||||
pub(super) pduid_pdu: sled::Tree, // PduId = RoomId + Count
|
pub(super) pduid_pdu: sled::Tree, // PduId = RoomId + Count
|
||||||
|
@ -415,6 +413,16 @@ impl Rooms {
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Returns the pdu.
|
||||||
|
pub fn get_pdu_json_from_id(&self, pdu_id: &IVec) -> Result<Option<serde_json::Value>> {
|
||||||
|
self.pduid_pdu.get(pdu_id)?.map_or(Ok(None), |pdu| {
|
||||||
|
Ok(Some(
|
||||||
|
serde_json::from_slice(&pdu)
|
||||||
|
.map_err(|_| Error::bad_database("Invalid PDU in db."))?,
|
||||||
|
))
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
/// Removes a pdu and creates a new one with the same id.
|
/// Removes a pdu and creates a new one with the same id.
|
||||||
fn replace_pdu(&self, pdu_id: &IVec, pdu: &PduEvent) -> Result<()> {
|
fn replace_pdu(&self, pdu_id: &IVec, pdu: &PduEvent) -> Result<()> {
|
||||||
if self.pduid_pdu.get(&pdu_id)?.is_some() {
|
if self.pduid_pdu.get(&pdu_id)?.is_some() {
|
||||||
|
@ -613,6 +621,7 @@ impl Rooms {
|
||||||
sender: &UserId,
|
sender: &UserId,
|
||||||
room_id: &RoomId,
|
room_id: &RoomId,
|
||||||
globals: &super::globals::Globals,
|
globals: &super::globals::Globals,
|
||||||
|
sending: &super::sending::Sending,
|
||||||
account_data: &super::account_data::AccountData,
|
account_data: &super::account_data::AccountData,
|
||||||
) -> Result<EventId> {
|
) -> Result<EventId> {
|
||||||
let PduBuilder {
|
let PduBuilder {
|
||||||
|
@ -829,39 +838,12 @@ impl Rooms {
|
||||||
self.append_to_state(&pdu_id, &pdu)?;
|
self.append_to_state(&pdu_id, &pdu)?;
|
||||||
}
|
}
|
||||||
|
|
||||||
pdu_json
|
for server in self
|
||||||
.as_object_mut()
|
.room_servers(room_id)
|
||||||
.expect("json is object")
|
.filter_map(|r| r.ok())
|
||||||
.remove("event_id");
|
.filter(|server| &**server != globals.server_name())
|
||||||
|
{
|
||||||
let raw_json =
|
sending.send_pdu(server, &pdu_id)?;
|
||||||
serde_json::from_value::<Raw<_>>(pdu_json).expect("Raw::from_value always works");
|
|
||||||
|
|
||||||
let pdus = &[raw_json];
|
|
||||||
let transaction_id = utils::random_string(16);
|
|
||||||
|
|
||||||
for result in futures::future::join_all(
|
|
||||||
self.room_servers(room_id)
|
|
||||||
.filter_map(|r| r.ok())
|
|
||||||
.filter(|server| &**server != globals.server_name())
|
|
||||||
.map(|server| {
|
|
||||||
server_server::send_request(
|
|
||||||
&globals,
|
|
||||||
server,
|
|
||||||
federation::transactions::send_transaction_message::v1::Request {
|
|
||||||
origin: globals.server_name(),
|
|
||||||
pdus,
|
|
||||||
edus: &[],
|
|
||||||
origin_server_ts: SystemTime::now(),
|
|
||||||
transaction_id: &transaction_id,
|
|
||||||
},
|
|
||||||
)
|
|
||||||
}),
|
|
||||||
)
|
|
||||||
.await {
|
|
||||||
if let Err(e) = result {
|
|
||||||
warn!("{}", e);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
Ok(pdu.event_id)
|
Ok(pdu.event_id)
|
||||||
|
|
|
@ -13,6 +13,7 @@ use std::{
|
||||||
convert::{TryFrom, TryInto},
|
convert::{TryFrom, TryInto},
|
||||||
};
|
};
|
||||||
|
|
||||||
|
#[derive(Clone)]
|
||||||
pub struct RoomEdus {
|
pub struct RoomEdus {
|
||||||
pub(in super::super) readreceiptid_readreceipt: sled::Tree, // ReadReceiptId = RoomId + Count + UserId
|
pub(in super::super) readreceiptid_readreceipt: sled::Tree, // ReadReceiptId = RoomId + Count + UserId
|
||||||
pub(in super::super) roomuserid_privateread: sled::Tree, // RoomUserId = Room + User, PrivateRead = Count
|
pub(in super::super) roomuserid_privateread: sled::Tree, // RoomUserId = Room + User, PrivateRead = Count
|
||||||
|
|
|
@ -0,0 +1,83 @@
|
||||||
|
use std::{convert::TryFrom, time::SystemTime};
|
||||||
|
|
||||||
|
use crate::{server_server, utils, Error, Result};
|
||||||
|
use rocket::futures::stream::{FuturesUnordered, StreamExt};
|
||||||
|
use ruma::{api::federation, Raw, ServerName};
|
||||||
|
use tokio::select;
|
||||||
|
|
||||||
|
pub struct Sending {
|
||||||
|
/// The state for a given state hash.
|
||||||
|
pub(super) serverpduids: sled::Tree, // ServerPduId = ServerName + PduId
|
||||||
|
}
|
||||||
|
|
||||||
|
impl Sending {
|
||||||
|
pub fn start_handler(&self, globals: &super::globals::Globals, rooms: &super::rooms::Rooms) {
|
||||||
|
let serverpduids = self.serverpduids.clone();
|
||||||
|
let rooms = rooms.clone();
|
||||||
|
let globals = globals.clone();
|
||||||
|
|
||||||
|
tokio::spawn(async move {
|
||||||
|
let mut futures = FuturesUnordered::new();
|
||||||
|
let mut subscriber = serverpduids.watch_prefix(b"");
|
||||||
|
loop {
|
||||||
|
select! {
|
||||||
|
Some(_) = futures.next() => {},
|
||||||
|
Some(event) = &mut subscriber => {
|
||||||
|
let serverpduid = if let sled::Event::Insert {key, ..} = event {
|
||||||
|
key
|
||||||
|
} else
|
||||||
|
{ return Err::<(), Error>(Error::bad_database("")); };
|
||||||
|
let mut parts = serverpduid.splitn(2, |&b| b == 0xff);
|
||||||
|
let server = Box::<ServerName>::try_from(
|
||||||
|
utils::string_from_bytes(parts.next().expect("splitn will always return 1 or more elements"))
|
||||||
|
.map_err(|_| Error::bad_database("ServerName in serverpduid bytes are invalid."))?
|
||||||
|
).map_err(|_| Error::bad_database("ServerName in serverpduid is invalid."))?;
|
||||||
|
|
||||||
|
let pdu_id = parts.next().ok_or_else(|| Error::bad_database("Invalid serverpduid in db."))?;
|
||||||
|
let mut pdu_json = rooms.get_pdu_json_from_id(&pdu_id.into())?.ok_or_else(|| Error::bad_database("Event in serverpduids not found in db."))?;
|
||||||
|
|
||||||
|
pdu_json
|
||||||
|
.as_object_mut()
|
||||||
|
.expect("json is object")
|
||||||
|
.remove("event_id");
|
||||||
|
|
||||||
|
let raw_json =
|
||||||
|
serde_json::from_value::<Raw<_>>(pdu_json).expect("Raw::from_value always works");
|
||||||
|
|
||||||
|
let globals = &globals;
|
||||||
|
|
||||||
|
futures.push(
|
||||||
|
async move {
|
||||||
|
let pdus = vec![raw_json];
|
||||||
|
let transaction_id = utils::random_string(16);
|
||||||
|
|
||||||
|
server_server::send_request(
|
||||||
|
&globals,
|
||||||
|
server,
|
||||||
|
federation::transactions::send_transaction_message::v1::Request {
|
||||||
|
origin: globals.server_name(),
|
||||||
|
pdus: &pdus,
|
||||||
|
edus: &[],
|
||||||
|
origin_server_ts: SystemTime::now(),
|
||||||
|
transaction_id: &transaction_id,
|
||||||
|
},
|
||||||
|
).await
|
||||||
|
}
|
||||||
|
);
|
||||||
|
},
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
/*
|
||||||
|
*/
|
||||||
|
|
||||||
|
pub fn send_pdu(&self, server: Box<ServerName>, pdu_id: &[u8]) -> Result<()> {
|
||||||
|
let mut key = server.as_bytes().to_vec();
|
||||||
|
key.push(0xff);
|
||||||
|
key.extend_from_slice(pdu_id);
|
||||||
|
self.serverpduids.insert(key, b"")?;
|
||||||
|
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
}
|
|
@ -130,6 +130,8 @@ fn setup_rocket() -> rocket::Rocket {
|
||||||
.attach(AdHoc::on_attach("Config", |mut rocket| async {
|
.attach(AdHoc::on_attach("Config", |mut rocket| async {
|
||||||
let data = Database::load_or_create(rocket.config().await).expect("valid config");
|
let data = Database::load_or_create(rocket.config().await).expect("valid config");
|
||||||
|
|
||||||
|
data.sending.start_handler(&data.globals, &data.rooms);
|
||||||
|
|
||||||
Ok(rocket.manage(data))
|
Ok(rocket.manage(data))
|
||||||
}))
|
}))
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,12 +1,13 @@
|
||||||
use crate::{Error, Result};
|
use crate::{Error, Result};
|
||||||
use js_int::UInt;
|
use js_int::UInt;
|
||||||
use ruma::{
|
use ruma::{
|
||||||
|
events::pdu::PduStub,
|
||||||
events::{
|
events::{
|
||||||
pdu::EventHash, room::member::MemberEventContent, AnyEvent, AnyRoomEvent, AnyStateEvent,
|
pdu::EventHash, room::member::MemberEventContent, AnyEvent, AnyRoomEvent, AnyStateEvent,
|
||||||
AnyStrippedStateEvent, AnySyncRoomEvent, AnySyncStateEvent, EventType, StateEvent,
|
AnyStrippedStateEvent, AnySyncRoomEvent, AnySyncStateEvent, EventType, StateEvent,
|
||||||
},
|
},
|
||||||
EventId, Raw, RoomId, ServerKeyId, ServerName, UserId,
|
EventId, Raw, RoomId, ServerKeyId, ServerName, UserId,
|
||||||
events::pdu::PduStub};
|
};
|
||||||
use serde::{Deserialize, Serialize};
|
use serde::{Deserialize, Serialize};
|
||||||
use serde_json::json;
|
use serde_json::json;
|
||||||
use std::{collections::BTreeMap, convert::TryInto, sync::Arc, time::UNIX_EPOCH};
|
use std::{collections::BTreeMap, convert::TryInto, sync::Arc, time::UNIX_EPOCH};
|
||||||
|
|
Loading…
Reference in New Issue