IRC parsing, tokenization, and state handling in C#
at ircrobotsv2 195 lines 6.7 kB view raw
1namespace IRCSharp.Tests.State; 2 3public class Channel 4{ 5 private readonly Server _server = new("test"); 6 7 public Channel() 8 { 9 _server.Parse(new Line("001 nickname")); 10 _server.Parse(new Line(":nickname JOIN #chan")); 11 } 12 13 [Test] 14 public async Task JoinSelf() 15 { 16 await Assert.That(_server.Channels).ContainsKey("#chan"); 17 await Assert.That(_server.Users).ContainsKey("nickname"); 18 await Assert.That(_server.Channels).HasCount(1); 19 await Assert.That(_server.Users).HasCount(1); 20 21 var user = _server.Users["nickname"]; 22 var chan = _server.Channels["#chan"]; 23 await Assert.That(chan.Users).ContainsKey(user.NickNameLower).And.HasCount(1); 24 await Assert.That(user.Channels).Contains(chan.NameLower).And.HasCount(1); 25 } 26 27 [Test] 28 public async Task JoinOther() 29 { 30 _server.Parse(new Line(":other JOIN #chan")); 31 32 await Assert.That(_server.Users).HasCount(2); 33 await Assert.That(_server.Users).ContainsKey("other"); 34 35 var channel = _server.Channels["#chan"]; 36 await Assert.That(channel.Users).HasCount(2); 37 38 var user = _server.Users["other"]; 39 await Assert.That(user.Channels).Contains(channel.NameLower).And.HasCount(1); 40 } 41 42 [Test] 43 public async Task PartSelf() 44 { 45 _server.Parse(new Line(":nickname PART #chan")); 46 47 await Assert.That(_server.Users).IsEmpty(); 48 await Assert.That(_server.Channels).IsEmpty(); 49 } 50 51 [Test] 52 public async Task PartOther() 53 { 54 _server.Parse(new Line(":other JOIN #chan")); 55 _server.Parse(new Line(":other PART #chan")); 56 57 var user = _server.Users["nickname"]; 58 var channel = _server.Channels["#chan"]; 59 var chanUser = channel.Users[user.NickNameLower]; 60 61 await Assert.That(user.Channels).Contains(channel.NameLower).And.HasCount(1); 62 await Assert.That(_server.Users) 63 .IsEquivalentTo(new Dictionary<string, IRCStates.User> { { "nickname", user } }); 64 await Assert.That(_server.Channels) 65 .IsEquivalentTo(new Dictionary<string, IRCStates.Channel> { { "#chan", channel } }); 66 await Assert.That(channel.Users) 67 .IsEquivalentTo(new Dictionary<string, ChannelUser> { { "nickname", chanUser } }); 68 } 69 70 [Test] 71 public async Task KickSelf() 72 { 73 _server.Parse(new Line(":nickname KICK #chan nickname")); 74 75 await Assert.That(_server.Users).IsEmpty(); 76 await Assert.That(_server.Channels).IsEmpty(); 77 } 78 79 [Test] 80 public async Task KickOther() 81 { 82 _server.Parse(new Line(":other JOIN #chan")); 83 _server.Parse(new Line(":nickname KICK #chan other")); 84 85 var user = _server.Users["nickname"]; 86 var channel = _server.Channels["#chan"]; 87 var chanUser = channel.Users[user.NickNameLower]; 88 89 await Assert.That(_server.Users).HasCount(1); 90 await Assert.That(_server.Channels).HasCount(1); 91 await Assert.That(user.Channels).Contains(channel.NameLower).And.HasCount(1); 92 await Assert.That(channel.Users) 93 .IsEquivalentTo(new Dictionary<string, ChannelUser> { { user.NickNameLower, chanUser } }); 94 } 95 96 [Test] 97 public async Task QuitSelf() 98 { 99 _server.Parse(new Line("QUIT :i'm outta here")); 100 await Assert.That(_server.Users).IsEmpty(); 101 await Assert.That(_server.Channels).IsEmpty(); 102 } 103 104 [Test] 105 public async Task QuitSelfWithSource() 106 { 107 _server.Parse(new Line(":nickname QUIT :i'm outta here")); 108 await Assert.That(_server.Users).IsEmpty(); 109 await Assert.That(_server.Channels).IsEmpty(); 110 } 111 112 [Test] 113 public async Task QuitOther() 114 { 115 _server.Parse(new Line(":other JOIN #chan")); 116 _server.Parse(new Line(":other QUIT :see ya")); 117 await Assert.That(_server.Users).DoesNotContainKey("other"); 118 } 119 120 [Test] 121 public async Task TopicText() 122 { 123 _server.Parse(new Line("332 * #chan :test")); 124 await Assert.That(_server.Channels["#chan"].Topic).IsEqualTo("test"); 125 } 126 127 [Test] 128 public async Task TopicSetByAt() 129 { 130 var dt = DateTimeOffset.FromUnixTimeSeconds(1584023277).DateTime; 131 _server.Parse(new Line("333 * #chan other 1584023277")); 132 133 var channel = _server.Channels["#chan"]; 134 135 await Assert.That(channel.TopicSetter).IsEqualTo("other"); 136 await Assert.That(channel.TopicTime).IsEqualTo(dt); 137 } 138 139 [Test] 140 public async Task TopicCommand() 141 { 142 _server.Parse(new Line("TOPIC #chan :hello there")); 143 await Assert.That(_server.Channels["#chan"].Topic).IsEqualTo("hello there"); 144 } 145 146 [Test] 147 public async Task CreationDate() 148 { 149 var dt = DateTimeOffset.FromUnixTimeSeconds(1584041889).DateTime; 150 _server.Parse(new Line("329 * #chan 1584041889")); 151 await Assert.That(_server.Channels["#chan"].Created).IsEqualTo(dt); 152 } 153 154 [Test] 155 public async Task NamesCommand() 156 { 157 _server.Parse(new Line("353 * * #chan :nickname @+other")); 158 await Assert.That(_server.Users).ContainsKey("nickname"); 159 await Assert.That(_server.Users).ContainsKey("other"); 160 161 var user = _server.Users["other"]; 162 var channel = _server.Channels["#chan"]; 163 var chanUser1 = channel.Users[user.NickNameLower]; 164 var chanUser2 = channel.Users[_server.NickNameLower]; 165 166 await Assert.That(channel.Users).HasCount(2); 167 await Assert.That(channel.Users[user.NickNameLower].Modes).IsEqualTo(chanUser1.Modes); 168 await Assert.That(channel.Users[_server.NickNameLower].Modes).IsEqualTo(chanUser2.Modes); 169 await Assert.That(chanUser1.Modes).IsEquivalentTo(["o", "v"]); 170 await Assert.That(user.Channels).Contains(channel.NameLower).And.HasCount(1); 171 } 172 173 [Test] 174 public async Task UserhostInNames() 175 { 176 _server.Parse(new Line("353 * * #chan :nickname!user@host other!user2@host2")); 177 await Assert.That(_server.UserName).IsEqualTo("user"); 178 await Assert.That(_server.HostName).IsEqualTo("host"); 179 180 var user = _server.Users["other"]; 181 await Assert.That(user.UserName).IsEqualTo("user2"); 182 await Assert.That(user.HostName).IsEqualTo("host2"); 183 } 184 185 [Test] 186 public async Task NickAfterJoin() 187 { 188 var user = _server.Users["nickname"]; 189 var channel = _server.Channels["#chan"]; 190 var chanUser = channel.Users[user.NickNameLower]; 191 _server.Parse(new Line(":nickname NICK nickname2")); 192 await Assert.That(channel.Users) 193 .IsEquivalentTo(new Dictionary<string, ChannelUser> { { user.NickNameLower, chanUser } }); 194 } 195}