fix: rare state races

next
Timo Kösters 2020-12-31 14:52:08 +01:00
parent 2cf6fd57b7
commit df16b2ba98
No known key found for this signature in database
GPG Key ID: 24DA7517711A2BA4
2 changed files with 19 additions and 12 deletions

View File

@ -678,9 +678,6 @@ impl Rooms {
self.stateid_pduid.insert(&state_id, &short_pdu_id)?; self.stateid_pduid.insert(&state_id, &short_pdu_id)?;
} }
self.roomid_statehash
.insert(new_pdu.room_id.as_bytes(), &*new_state_hash)?;
Ok(new_state_hash) Ok(new_state_hash)
} else { } else {
Err(Error::bad_database( Err(Error::bad_database(
@ -689,6 +686,13 @@ impl Rooms {
} }
} }
pub fn set_room_state(&self, room_id: &RoomId, state_hash: &StateHashId) -> Result<()> {
self.roomid_statehash
.insert(room_id.as_bytes(), state_hash)?;
Ok(())
}
/// Creates a new persisted data unit and adds it to a room. /// Creates a new persisted data unit and adds it to a room.
#[allow(clippy::too_many_arguments)] #[allow(clippy::too_many_arguments)]
pub fn build_and_append_pdu( pub fn build_and_append_pdu(
@ -929,7 +933,7 @@ impl Rooms {
// We append to state before appending the pdu, so we don't have a moment in time with the // We append to state before appending the pdu, so we don't have a moment in time with the
// pdu without it's state. This is okay because append_pdu can't fail. // pdu without it's state. This is okay because append_pdu can't fail.
self.append_to_state(&pdu_id, &pdu, &globals)?; let statehashid = self.append_to_state(&pdu_id, &pdu, &globals)?;
self.append_pdu( self.append_pdu(
&pdu, &pdu,
@ -941,6 +945,10 @@ impl Rooms {
admin, admin,
)?; )?;
// We set the room state after inserting the pdu, so that we never have a moment in time
// where events in the current room state do not exist
self.set_room_state(&room_id, &statehashid)?;
for server in self for server in self
.room_servers(room_id) .room_servers(room_id)
.filter_map(|r| r.ok()) .filter_map(|r| r.ok())
@ -991,13 +999,12 @@ impl Rooms {
if bridge_user_id.map_or(false, |bridge_user_id| { if bridge_user_id.map_or(false, |bridge_user_id| {
self.is_joined(&bridge_user_id, room_id).unwrap_or(false) self.is_joined(&bridge_user_id, room_id).unwrap_or(false)
}) || users.iter().any(|users| { }) || users.iter().any(|users| {
dbg!( users.is_match(pdu.sender.as_str())
users.is_match(pdu.sender.as_str()) || pdu.kind == EventType::RoomMember
|| pdu.kind == EventType::RoomMember && pdu
&& pdu.state_key.as_ref().map_or(false, |state_key| dbg!( .state_key
users.is_match(dbg!(&state_key)) .as_ref()
)) .map_or(false, |state_key| users.is_match(&state_key))
)
}) || aliases.map_or(false, |aliases| { }) || aliases.map_or(false, |aliases| {
room_aliases room_aliases
.filter_map(|r| r.ok()) .filter_map(|r| r.ok())

View File

@ -95,7 +95,7 @@ where
ruma::signatures::sign_json( ruma::signatures::sign_json(
globals.server_name().as_str(), globals.server_name().as_str(),
globals.keypair(), globals.keypair(),
&mut request_json, dbg!(&mut request_json),
) )
.expect("our request json is what ruma expects"); .expect("our request json is what ruma expects");