use ferogram_mtproto::{
Session,
transport::{AbridgedTransport, Transport},
};
#[test]
fn session_seq_no_increments() {
let mut s = Session::new();
let a = s.next_seq_no();
let b = s.next_seq_no();
assert!(a & 1 == 1, "content-related seq_no must be odd");
assert!(b & 1 == 1);
assert!(b > a, "seq_no must increase");
}
#[test]
fn session_unrelated_seq_no_is_even() {
let mut s = Session::new();
let n = s.next_seq_no_unrelated();
assert_eq!(n & 1, 0, "unrelated seq_no must be even");
}
#[test]
fn message_plaintext_bytes_layout() {
let mut s = Session::new();
use ferogram_mtproto::Message;
let id = s.next_msg_id();
let msg = Message::plaintext(id, 1, vec![0xAA, 0xBB]);
let wire = msg.to_plaintext_bytes();
assert_eq!(wire.len(), 8 + 8 + 4 + 2);
assert_eq!(&wire[..8], &[0u8; 8]);
assert_eq!(u32::from_le_bytes(wire[16..20].try_into().unwrap()), 2);
assert_eq!(&wire[20..], &[0xAA, 0xBB]);
}
struct MemTransport {
inbox: Vec<u8>,
outbox: Vec<u8>,
}
impl Transport for MemTransport {
type Error = std::io::Error;
fn send(&mut self, data: &[u8]) -> Result<(), Self::Error> {
self.outbox.extend_from_slice(data);
Ok(())
}
fn recv(&mut self) -> Result<Vec<u8>, Self::Error> {
Ok(std::mem::take(&mut self.inbox))
}
}
#[test]
fn abridged_sends_init_byte_once() {
let inner = MemTransport {
inbox: vec![],
outbox: vec![],
};
let mut t = AbridgedTransport::new(inner);
let payload = vec![0u8; 4]; t.send_message(&payload).unwrap();
assert_eq!(t.inner_mut().outbox[0], 0xef);
let prev_len = t.inner_mut().outbox.len();
t.send_message(&payload).unwrap();
let second_byte = t.inner_mut().outbox[prev_len];
assert_ne!(second_byte, 0xef, "init byte must only be sent once");
}