123 lines
4.1 KiB
Rust
123 lines
4.1 KiB
Rust
mod common;
|
||
|
||
pub use common::*;
|
||
|
||
use indymilter_test::*;
|
||
use spamassassin_milter::*;
|
||
|
||
/// ‘Happy path’ processing of a spam message.
|
||
#[tokio::test]
|
||
async fn spam_message() {
|
||
let config = configure_spamc(Config::builder())
|
||
.spamc_args([format!("--port={SPAMD_PORT}")])
|
||
.build();
|
||
|
||
let server = spawn_mock_spamd_server(SPAMD_PORT, |spam| {
|
||
let mut spam = spam
|
||
.replacen("X-Spam-Checker-Version: BogusChecker 1.0.0\r\n", "", 1)
|
||
.replacen("X-Spam-Report: Bogus report\r\n", "", 1)
|
||
.replacen(
|
||
"\r\n\r\n",
|
||
"\r\n\
|
||
X-Spam-Checker-Version: MyChecker 1.0.0\r\n\
|
||
X-Spam-Flag: YES\r\n\
|
||
X-Spam-Custom: Custom-Value\r\n\
|
||
Content-Type: multipart/mixed; ...\r\n\
|
||
\r\n",
|
||
1,
|
||
)
|
||
.replacen(
|
||
"Subject: Test message\r\n",
|
||
"Subject: [SPAM] Test message\r\n",
|
||
1,
|
||
);
|
||
|
||
// Replace the message body with the SpamAssassin ‘report’.
|
||
spam.replace_range(
|
||
(spam.find("\r\n\r\n").unwrap() + 4)..,
|
||
"Spam detection software has identified ...",
|
||
);
|
||
|
||
Err(spam)
|
||
})
|
||
.await
|
||
.unwrap();
|
||
|
||
let milter = SpamAssassinMilter::spawn(LOCALHOST, config).await.unwrap();
|
||
|
||
let mut conn = TestConnection::open(milter.addr()).await.unwrap();
|
||
|
||
let status = conn.connect("client.gluet.ch", [123, 123, 123, 123]).await.unwrap();
|
||
assert_eq!(status, Status::Continue);
|
||
|
||
let status = conn.helo("mail.gluet.ch").await.unwrap();
|
||
assert_eq!(status, Status::Continue);
|
||
|
||
let status = conn.mail(["<from@gluet.ch>"]).await.unwrap();
|
||
assert_eq!(status, Status::Continue);
|
||
|
||
let status = conn.rcpt(["<to@gluet.ch>"]).await.unwrap();
|
||
assert_eq!(status, Status::Continue);
|
||
|
||
conn.macros(
|
||
MacroStage::Data,
|
||
[
|
||
("i", "1234567ABC"),
|
||
("j", "localhost"),
|
||
("_", "client.gluet.ch [123.123.123.123]"),
|
||
("{tls_version}", "TLSv1.2"),
|
||
("v", "Postfix 3.3.0"),
|
||
],
|
||
)
|
||
.await
|
||
.unwrap();
|
||
|
||
let status = conn.data().await.unwrap();
|
||
assert_eq!(status, Status::Continue);
|
||
|
||
let status = conn.header("From", "from@gluet.ch").await.unwrap();
|
||
assert_eq!(status, Status::Continue);
|
||
|
||
let status = conn.header("To", "to@gluet.ch").await.unwrap();
|
||
assert_eq!(status, Status::Continue);
|
||
|
||
let status = conn.header("Subject", "Test message").await.unwrap();
|
||
assert_eq!(status, Status::Continue);
|
||
|
||
let status = conn.header("Message-ID", rand_msg_id()).await.unwrap();
|
||
assert_eq!(status, Status::Continue);
|
||
|
||
let status = conn.header("Date", current_date()).await.unwrap();
|
||
assert_eq!(status, Status::Continue);
|
||
|
||
// Incoming foreign SpamAssassin headers, to be replaced or deleted.
|
||
let status = conn.header("X-Spam-Checker-Version", "BogusChecker 1.0.0").await.unwrap();
|
||
assert_eq!(status, Status::Continue);
|
||
|
||
let status = conn.header("X-Spam-Report", "Bogus report").await.unwrap();
|
||
assert_eq!(status, Status::Continue);
|
||
|
||
let status = conn.eoh().await.unwrap();
|
||
assert_eq!(status, Status::Continue);
|
||
|
||
let status = conn.body(&b"HI!!! You have won a BILLION dollars!!!!"[..]).await.unwrap();
|
||
assert_eq!(status, Status::Continue);
|
||
|
||
let (actions, status) = conn.eom().await.unwrap();
|
||
assert_eq!(status, Status::Continue);
|
||
|
||
assert!(actions.has_delete_header("X-Spam-Checker-Version", any()));
|
||
assert!(actions.has_add_header("X-Spam-Checker-Version", " MyChecker 1.0.0"));
|
||
assert!(actions.has_add_header("X-Spam-Flag", " YES"));
|
||
assert!(actions.has_add_header("X-Spam-Custom", " Custom-Value"));
|
||
assert!(actions.has_delete_header("X-Spam-Report", any()));
|
||
assert!(actions.has_change_header("Subject", 1, " [SPAM] Test message"));
|
||
assert!(actions.has_add_header("Content-Type", " multipart/mixed; ..."));
|
||
assert!(actions.has_replaced_body(b"Spam detection software has identified ..."));
|
||
|
||
conn.close().await.unwrap();
|
||
|
||
milter.shutdown().await.unwrap();
|
||
|
||
server.await.unwrap().unwrap();
|
||
}
|