mirror of
https://github.com/chatmail/core.git
synced 2026-05-07 08:56:30 +03:00
fix: Never send empty To: header (#6663)
fix #6662 by adding "hidden-recipients:" if To: header would be empty
This commit is contained in:
@@ -607,10 +607,7 @@ impl MimeFactory {
|
|||||||
|| to.len() + past_members.len() == self.member_timestamps.len()
|
|| to.len() + past_members.len() == self.member_timestamps.len()
|
||||||
);
|
);
|
||||||
if to.is_empty() {
|
if to.is_empty() {
|
||||||
to.push(Address::new_group(
|
to.push(hidden_recipients());
|
||||||
Some("hidden-recipients".to_string()),
|
|
||||||
Vec::new(),
|
|
||||||
));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Start with Internet Message Format headers in the order of the standard example
|
// Start with Internet Message Format headers in the order of the standard example
|
||||||
@@ -888,21 +885,23 @@ impl MimeFactory {
|
|||||||
} else if header_name == "to" {
|
} else if header_name == "to" {
|
||||||
protected_headers.push(header.clone());
|
protected_headers.push(header.clone());
|
||||||
if is_encrypted {
|
if is_encrypted {
|
||||||
|
let mut to_without_names = to
|
||||||
|
.clone()
|
||||||
|
.into_iter()
|
||||||
|
.filter_map(|header| match header {
|
||||||
|
Address::Address(mb) => Some(Address::Address(EmailAddress {
|
||||||
|
name: None,
|
||||||
|
email: mb.email,
|
||||||
|
})),
|
||||||
|
_ => None,
|
||||||
|
})
|
||||||
|
.collect::<Vec<_>>();
|
||||||
|
if to_without_names.is_empty() {
|
||||||
|
to_without_names.push(hidden_recipients());
|
||||||
|
}
|
||||||
unprotected_headers.push((
|
unprotected_headers.push((
|
||||||
original_header_name,
|
original_header_name,
|
||||||
Address::new_list(
|
Address::new_list(to_without_names).into(),
|
||||||
to.clone()
|
|
||||||
.into_iter()
|
|
||||||
.filter_map(|header| match header {
|
|
||||||
Address::Address(mb) => Some(Address::Address(EmailAddress {
|
|
||||||
name: None,
|
|
||||||
email: mb.email,
|
|
||||||
})),
|
|
||||||
_ => None,
|
|
||||||
})
|
|
||||||
.collect::<Vec<_>>(),
|
|
||||||
)
|
|
||||||
.into(),
|
|
||||||
));
|
));
|
||||||
} else {
|
} else {
|
||||||
unprotected_headers.push(header.clone());
|
unprotected_headers.push(header.clone());
|
||||||
@@ -1633,6 +1632,10 @@ impl MimeFactory {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn hidden_recipients() -> Address<'static> {
|
||||||
|
Address::new_group(Some("hidden-recipients".to_string()), Vec::new())
|
||||||
|
}
|
||||||
|
|
||||||
async fn build_body_file(context: &Context, msg: &Message) -> Result<MimePart<'static>> {
|
async fn build_body_file(context: &Context, msg: &Message) -> Result<MimePart<'static>> {
|
||||||
let file_name = msg.get_filename().context("msg has no file")?;
|
let file_name = msg.get_filename().context("msg has no file")?;
|
||||||
let suffix = Path::new(&file_name)
|
let suffix = Path::new(&file_name)
|
||||||
|
|||||||
@@ -898,3 +898,23 @@ async fn test_dont_remove_self() -> Result<()> {
|
|||||||
|
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Regression test: mimefactory should never create an empty to header,
|
||||||
|
/// also not if the Selftalk parameter is missing
|
||||||
|
#[tokio::test(flavor = "multi_thread", worker_threads = 2)]
|
||||||
|
async fn test_no_empty_to_header() -> Result<()> {
|
||||||
|
let alice = &TestContext::new_alice().await;
|
||||||
|
let mut self_chat = alice.get_self_chat().await;
|
||||||
|
self_chat.param.remove(Param::Selftalk);
|
||||||
|
self_chat.update_param(alice).await?;
|
||||||
|
|
||||||
|
let payload = alice.send_text(self_chat.id, "Hi").await.payload;
|
||||||
|
assert!(
|
||||||
|
// It would be equally fine if the payload contained `To: alice@example.org` or similar,
|
||||||
|
// as long as it's a valid header
|
||||||
|
payload.contains("To: \"hidden-recipients\": ;"),
|
||||||
|
"Payload doesn't contain correct To: header: {payload}"
|
||||||
|
);
|
||||||
|
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user