fix: Don't allow set_unsigned to panic

While an error in this function is probably bad, detonating a metric tonne of TNT on the call tree is probably worse
This commit is contained in:
timedout committed 2026-09-27 17:32:47 +01:00
1 parent 90793eaaf4
commit 4812837d13
12 files changed
+73 -67

No files matched your search

+2 -2
View File
@@ -74,7 +74,7 @@ fn redaction_removes_stickiness() {
fn sticky_ttl_is_added_to_unsigned() {
let mut pdu = sticky_pdu(&serde_json::json!({ "duration_ms": 300_000 }));
pdu.origin_server_ts = ruma::MilliSecondsSinceUnixEpoch::now().get();
pdu.set_unsigned(None, None, None, None);
pdu.set_unsigned(None, None, None, None).unwrap();
let unsigned: serde_json::Value =
serde_json::from_str(pdu.unsigned.as_deref().expect("unsigned is set").get())
@@ -99,7 +99,7 @@ fn set_unsigned_adds_the_sticky_ttl() {
// section
let mut pdu = sticky_pdu(&serde_json::json!({ "duration_ms": 300_000 }));
pdu.origin_server_ts = ruma::MilliSecondsSinceUnixEpoch::now().get();
pdu.set_unsigned(None, None, None, None);
pdu.set_unsigned(None, None, None, None).unwrap();
let unsigned: serde_json::Value =
serde_json::from_str(pdu.unsigned.as_deref().expect("unsigned is set").get())
+11 -22
View File
@@ -34,40 +34,29 @@ impl Pdu {
membership: Option<MembershipState>,
prev_content: Option<Box<RawJsonValue>>,
redacted_because: Option<Raw<AnyTimelineEvent>>,
) {
) -> crate::Result<Unsigned> {
// See: https://spec.matrix.org/v1.19/client-server-api/#definition-clientevent_unsigneddata
let Some(mut unsigned) = self.unsigned().map_or_else(
|| Some(Unsigned::new()),
|u| serde_json::from_str::<Unsigned>(u.get()).ok(),
) else {
return;
};
let mut unsigned = self
.unsigned()
.map_or_else(|| Ok(Unsigned::new()), |u| serde_json::from_str::<Unsigned>(u.get()))?;
let now = MilliSecondsSinceUnixEpoch::now().get();
let now_i: ruma::Int = now.into();
unsigned.insert(
"age".to_owned(),
to_raw_value(&now_i.saturating_sub(self.origin_server_ts.into())).unwrap(),
to_raw_value(&now_i.saturating_sub(self.origin_server_ts.into()))?,
);
if let Some(membership) = membership {
unsigned.insert("membership".to_owned(), to_raw_value(&membership).unwrap());
unsigned.insert("membership".to_owned(), to_raw_value(&membership)?);
}
if let Some(prev_content) = prev_content {
unsigned.insert(
"prev_content".to_owned(),
to_raw_value(&prev_content)
.expect("prev_content must be a valid JSON value for unsigned"),
);
unsigned.insert("prev_content".to_owned(), to_raw_value(&prev_content)?);
}
if let Some(redacted_because) = redacted_because {
unsigned.remove("org.continuwuity.redacted_by");
unsigned.insert(
"redacted_because".to_owned(),
to_raw_value(&redacted_because)
.expect("redacted_because must be a valid JSON value for unsigned"),
);
unsigned.insert("redacted_because".to_owned(), to_raw_value(&redacted_because)?);
}
// Remove transaction_id unless the user is the sender
@@ -82,11 +71,11 @@ impl Pdu {
{
unsigned.insert(
sticky::TTL_UNSIGNED_KEY.to_owned(),
to_raw_value(&expires_at.saturating_sub(u64::from(now)))
.expect("sticky event TTL must be a valid JSON value for unsigned"),
to_raw_value(&expires_at.saturating_sub(u64::from(now)))?,
);
}
self.unsigned = Some(to_raw_value(&unsigned).unwrap());
self.unsigned = Some(to_raw_value(&unsigned)?);
Ok(unsigned)
}
}