forked from lavina/lavina
1
0
Fork 0

fix irc integration tests

This commit is contained in:
Nikita Vilunov 2023-02-17 22:12:29 +01:00
parent 266eafe6e6
commit 49a975e66e
3 changed files with 84 additions and 56 deletions

View File

@ -22,6 +22,13 @@ impl<'a> TestScope<'a> {
self.buffer.clear();
Ok(())
}
async fn assert(&mut self, f: impl FnOnce(&str) -> Result<()>) -> Result<()> {
let len = self.reader.read_until(b'\n', &mut self.buffer).await?;
let res = f(std::str::from_utf8(&self.buffer[0..len])?);
self.buffer.clear();
res
}
}
async fn init_client(stream: &mut TcpStream) -> Result<TestScope> {
@ -47,45 +54,28 @@ macro_rules! expect {
}};
}
const SERVER_HOSTNAME: &'static str = "irc.localhost";
#[rustfmt::skip]
async fn registration(scope: &mut TestScope<'_>, nickname: &str) -> Result<()> {
expect!(scope, ":irc.localhost NOTICE * :Welcome to my server!\n");
send!(scope, "NICK {nickname}\n");
send!(scope, "USER UserName 0 * :Real Name\n");
expect!(
scope,
":irc.localhost 001 {nickname} :Welcome to Kek Server\n"
);
expect!(
scope,
":irc.localhost 002 {nickname} :Welcome to Kek Server\n"
);
expect!(
scope,
":irc.localhost 003 {nickname} :Welcome to Kek Server\n"
);
expect!(scope, ":irc.localhost 004 {nickname} irc.localhost kek-0.1.alpha.3 DGMQRSZagiloswz CFILPQbcefgijklmnopqrstvz bkloveqjfI\n");
expect!(
scope,
":irc.localhost 005 {nickname} CHANTYPES=# :are supported by this server\n"
);
expect!(scope, ":irc.localhost 001 {nickname} :Welcome to Kek Server\n");
expect!(scope, ":irc.localhost 002 {nickname} :Welcome to Kek Server\n");
expect!(scope, ":irc.localhost 003 {nickname} :Welcome to Kek Server\n");
expect!(scope, ":irc.localhost 004 {nickname} irc.localhost kek-0.1.alpha.3 r CFILPQbcefgijklmnopqrstvz\n");
expect!(scope, ":irc.localhost 005 {nickname} CHANTYPES=# :are supported by this server\n");
Ok(())
}
async fn join(scope: &mut TestScope<'_>, nickname: &str) -> Result<()> {
send!(scope, "JOIN #channol\n");
expect!(scope, ":{nickname} JOIN #channol\n");
expect!(
scope,
":irc.localhost 332 {nickname} #channol :chan topic lol\n"
);
expect!(
scope,
":irc.localhost 353 {nickname} = #channol :{nickname}\n"
);
expect!(
scope,
":irc.localhost 366 {nickname} #channol :End of /NAMES list\n"
);
#[rustfmt::skip]
async fn join(scope: &mut TestScope<'_>, nickname: &str, chan: &str) -> Result<()> {
send!(scope, "JOIN #{chan}\n");
expect!(scope, ":{nickname} JOIN #{chan}\n");
expect!(scope, ":irc.localhost 332 {nickname} #{chan} :New room\n");
expect!(scope, ":irc.localhost 353 {nickname} = #{chan} :{nickname}\n");
expect!(scope, ":irc.localhost 366 {nickname} #{chan} :End of /NAMES list\n");
Ok(())
}
@ -94,11 +84,12 @@ async fn test_registration() -> Result<()> {
let mut stream = TcpStream::connect("127.0.0.1:6667").await?;
let mut scope = init_client(&mut stream).await?;
registration(&mut scope, "NickName").await?;
join(&mut scope, "NickName").await?;
registration(&mut scope, "NickName1").await?;
join(&mut scope, "NickName1", "chan1").await?;
Ok(())
}
#[rustfmt::skip]
#[tokio::test]
async fn test_two_connections_one_player() -> Result<()> {
let mut stream1 = TcpStream::connect("127.0.0.1:6667").await?;
@ -106,21 +97,39 @@ async fn test_two_connections_one_player() -> Result<()> {
let mut stream2 = TcpStream::connect("127.0.0.1:6667").await?;
let mut scope2 = init_client(&mut stream2).await?;
registration(&mut scope1, "NickName").await?;
registration(&mut scope2, "NickName").await?;
join(&mut scope1, "NickName").await?;
join(&mut scope2, "NickName").await?;
send!(scope1, "PRIVMSG #channol :Chmoki vsem v etam chati!\n");
expect!(
scope2,
":NickName PRIVMSG #channol :Chmoki vsem v etam chati!\n"
);
send!(scope2, "PRIVMSG #channol :I tebe privetiki\n");
expect!(scope1, ":NickName PRIVMSG #channol :I tebe privetiki\n");
let nickname = "NickName2";
let chan = "chan2";
registration(&mut scope1, nickname).await?;
registration(&mut scope2, nickname).await?;
join(&mut scope1, nickname, chan).await?;
// force join on second connection when the other one joins a room
expect!(scope2, ":{nickname} JOIN #{chan}\n");
expect!(scope2, ":{SERVER_HOSTNAME} 332 {nickname} #{chan} :New room\n");
expect!(scope2, ":{SERVER_HOSTNAME} 353 {nickname} = #{chan} :{nickname}\n");
expect!(scope2, ":{SERVER_HOSTNAME} 366 {nickname} #{chan} :End of /NAMES list\n");
// force send PRIVMSG to other connections
send!(scope1, "PRIVMSG #{chan} :Chmoki vsem v etam chati!\n");
expect!(scope2, ":{nickname} PRIVMSG #{chan} :Chmoki vsem v etam chati!\n");
send!(scope2, "PRIVMSG #{chan} :I tebe privetiki\n");
expect!(scope1, ":{nickname} PRIVMSG #{chan} :I tebe privetiki\n");
let mut stream3 = TcpStream::connect("127.0.0.1:6667").await?;
let mut scope3 = init_client(&mut stream3).await?;
registration(&mut scope3, nickname).await?;
// force join on registration
expect!(scope3, ":{nickname} JOIN #{chan}\n");
expect!(scope3, ":{SERVER_HOSTNAME} 332 {nickname} #{chan} :New room\n");
expect!(scope3, ":{SERVER_HOSTNAME} 353 {nickname} = #{chan} :{nickname}\n");
expect!(scope3, ":{SERVER_HOSTNAME} 366 {nickname} #{chan} :End of /NAMES list\n");
Ok(())
}
#[rustfmt::skip]
#[tokio::test]
async fn test_two_players() -> Result<()> {
let mut stream1 = TcpStream::connect("127.0.0.1:6667").await?;
@ -128,17 +137,30 @@ async fn test_two_players() -> Result<()> {
let mut stream2 = TcpStream::connect("127.0.0.1:6667").await?;
let mut scope2 = init_client(&mut stream2).await?;
registration(&mut scope1, "NickName1").await?;
registration(&mut scope2, "NickName2").await?;
join(&mut scope1, "NickName1").await?;
join(&mut scope2, "NickName2").await?;
send!(scope1, "PRIVMSG #channol :Chmoki vsem v etam chati!\n");
expect!(
scope2,
":NickName1 PRIVMSG #channol :Chmoki vsem v etam chati!\n"
);
send!(scope2, "PRIVMSG #channol :I tebe privetiki\n");
expect!(scope1, ":NickName2 PRIVMSG #channol :I tebe privetiki\n");
let nickname1 = "NickName3";
let nickname2 = "NickName4";
let chan = "chan3";
registration(&mut scope1, "NickName3").await?;
registration(&mut scope2, "NickName4").await?;
join(&mut scope1, nickname1, "chan3").await?;
send!(scope2, "JOIN #{chan}\n");
expect!(scope2, ":{nickname2} JOIN #{chan}\n");
expect!(scope2, ":irc.localhost 332 {nickname2} #{chan} :New room\n");
scope2.assert(|line| {
if line == format!(":irc.localhost 353 {nickname2} = #{chan} :{nickname1} {nickname2}\n") { return Ok(()) }
if line == format!(":irc.localhost 353 {nickname2} = #{chan} :{nickname2} {nickname1}\n") { return Ok(()) }
panic!("incorrect chan member list received: {line}");
}).await?;
expect!(scope2, ":irc.localhost 366 {nickname2} #{chan} :End of /NAMES list\n");
expect!(scope1, ":{nickname2} JOIN #{chan}\n");
send!(scope1, "PRIVMSG #chan3 :Chmoki vsem v etam chati!\n");
expect!(scope2, ":{nickname1} PRIVMSG #chan3 :Chmoki vsem v etam chati!\n");
send!(scope2, "PRIVMSG #chan3 :I tebe privetiki\n");
expect!(scope1, ":{nickname2} PRIVMSG #chan3 :I tebe privetiki\n");
Ok(())
}

1
test/.gitignore vendored Normal file
View File

@ -0,0 +1 @@
*.log

5
test/run.sh Executable file
View File

@ -0,0 +1,5 @@
#!/bin/sh
cargo build
./target/debug/lavina 1>test/lavina.stdout.log 2>test/lavina.stderr.log &
cargo test
kill %1