Implement IDLE #72

Merged
quentin merged 9 commits from feat/idle into main 2024-01-19 14:04:04 +00:00
3 changed files with 42 additions and 2 deletions
Showing only changes of commit 23aa313e11 - Show all commits

View file

@ -30,6 +30,7 @@ impl Default for ServerCapability {
Capability::Enable, Capability::Enable,
Capability::Move, Capability::Move,
Capability::LiteralPlus, Capability::LiteralPlus,
Capability::Idle,
capability_unselect(), capability_unselect(),
capability_condstore(), capability_condstore(),
//capability_qresync(), //capability_qresync(),

View file

@ -11,6 +11,7 @@ fn main() {
rfc6851_imapext_move(); rfc6851_imapext_move();
rfc7888_imapext_literal(); rfc7888_imapext_literal();
rfc4551_imapext_condstore(); rfc4551_imapext_condstore();
rfc2177_imapext_idle();
println!("✅ SUCCESS 🌟🚀🥳🙏🥹"); println!("✅ SUCCESS 🌟🚀🥳🙏🥹");
} }
@ -21,8 +22,6 @@ fn rfc3501_imap4rev1_base() {
capability(imap_socket, Extension::None).context("check server capabilities")?; capability(imap_socket, Extension::None).context("check server capabilities")?;
login(imap_socket, Account::Alice).context("login test")?; login(imap_socket, Account::Alice).context("login test")?;
create_mailbox(imap_socket, Mailbox::Archive).context("created mailbox archive")?; create_mailbox(imap_socket, Mailbox::Archive).context("created mailbox archive")?;
// UNSUBSCRIBE IS NOT IMPLEMENTED YET
//unsubscribe_mailbox(imap_socket).context("unsubscribe from archive")?;
let select_res = let select_res =
select(imap_socket, Mailbox::Inbox, SelectMod::None).context("select inbox")?; select(imap_socket, Mailbox::Inbox, SelectMod::None).context("select inbox")?;
assert!(select_res.contains("* 0 EXISTS")); assert!(select_res.contains("* 0 EXISTS"));
@ -241,3 +240,25 @@ fn rfc4551_imapext_condstore() {
}) })
.expect("test fully run"); .expect("test fully run");
} }
fn rfc2177_imapext_idle() {
println!("🧪 rfc2177_imapext_idle");
common::aerogramme_provider_daemon_dev(|imap_socket, lmtp_socket| {
// Test setup
connect(imap_socket).context("server says hello")?;
capability(imap_socket, Extension::Idle).context("check server capabilities")?;
login(imap_socket, Account::Alice).context("login test")?;
select(imap_socket, Mailbox::Inbox, SelectMod::None).context("select inbox")?;
// Check that new messages from LMTP are correctly detected during idling
start_idle(imap_socket).context("can't start idling")?;
lmtp_handshake(lmtp_socket).context("handshake lmtp done")?;
lmtp_deliver_email(lmtp_socket, Email::Basic).context("mail delivered successfully")?;
let srv_msg = stop_idle(imap_socket).context("stop idling")?;
assert!(srv_msg.contains("* 1 EXISTS"));
Ok(())
})
.expect("test fully run");
}

View file

@ -36,6 +36,7 @@ pub enum Extension {
Move, Move,
Condstore, Condstore,
LiteralPlus, LiteralPlus,
Idle,
} }
pub enum Enable { pub enum Enable {
@ -114,6 +115,7 @@ pub fn capability(imap: &mut TcpStream, ext: Extension) -> Result<()> {
Extension::Move => Some("MOVE"), Extension::Move => Some("MOVE"),
Extension::Condstore => Some("CONDSTORE"), Extension::Condstore => Some("CONDSTORE"),
Extension::LiteralPlus => Some("LITERAL+"), Extension::LiteralPlus => Some("LITERAL+"),
Extension::Idle => Some("IDLE"),
}; };
let mut buffer: [u8; 6000] = [0; 6000]; let mut buffer: [u8; 6000] = [0; 6000];
@ -496,6 +498,22 @@ pub fn enable(imap: &mut TcpStream, ask: Enable, done: Option<Enable>) -> Result
Ok(()) Ok(())
} }
pub fn start_idle(imap: &mut TcpStream) -> Result<()> {
let mut buffer: [u8; 1500] = [0; 1500];
imap.write(&b"98 IDLE\r\n"[..])?;
let read = read_lines(imap, &mut buffer, None)?;
assert_eq!(read[0], b'+');
Ok(())
}
pub fn stop_idle(imap: &mut TcpStream) -> Result<String> {
let mut buffer: [u8; 16536] = [0; 16536];
imap.write(&b"DONE\r\n"[..])?;
let read = read_lines(imap, &mut buffer, Some(&b"98 OK"[..]))?;
let srv_msg = std::str::from_utf8(read)?;
Ok(srv_msg.to_string())
}
pub fn logout(imap: &mut TcpStream) -> Result<()> { pub fn logout(imap: &mut TcpStream) -> Result<()> {
imap.write(&b"99 logout\r\n"[..])?; imap.write(&b"99 logout\r\n"[..])?;
let mut buffer: [u8; 1500] = [0; 1500]; let mut buffer: [u8; 1500] = [0; 1500];