rename to IrcSharp
continuous-integration/drone/push Build is passing
Details
continuous-integration/drone/push Build is passing
Details
also tidy up formatting with vs tools
This commit is contained in:
parent
338763fde7
commit
933a4f8560
|
@ -0,0 +1,57 @@
|
||||||
|
|
||||||
|
[*.proto]
|
||||||
|
indent_style=tab
|
||||||
|
indent_size=tab
|
||||||
|
tab_width=4
|
||||||
|
|
||||||
|
[*.{asax,ascx,aspx,cs,cshtml,css,htm,html,js,jsx,master,razor,skin,ts,tsx,vb,xaml,xamlx,xoml}]
|
||||||
|
indent_style=space
|
||||||
|
indent_size=4
|
||||||
|
tab_width=4
|
||||||
|
|
||||||
|
[*.{appxmanifest,axml,build,config,csproj,dbml,discomap,dtd,json,jsproj,lsproj,njsproj,nuspec,proj,props,resjson,resw,resx,StyleCop,targets,tasks,vbproj,xml,xsd}]
|
||||||
|
indent_style=space
|
||||||
|
indent_size=2
|
||||||
|
tab_width=2
|
||||||
|
|
||||||
|
[*]
|
||||||
|
|
||||||
|
# Microsoft .NET properties
|
||||||
|
csharp_new_line_before_members_in_object_initializers=true
|
||||||
|
csharp_preferred_modifier_order=public, private, protected, internal, new, abstract, virtual, sealed, override, static, readonly, extern, unsafe, volatile, async:suggestion
|
||||||
|
csharp_style_var_elsewhere=true:suggestion
|
||||||
|
csharp_style_var_for_built_in_types=true:suggestion
|
||||||
|
csharp_style_var_when_type_is_apparent=true:suggestion
|
||||||
|
dotnet_style_parentheses_in_arithmetic_binary_operators=never_if_unnecessary:none
|
||||||
|
dotnet_style_parentheses_in_other_binary_operators=never_if_unnecessary:none
|
||||||
|
dotnet_style_parentheses_in_relational_binary_operators=never_if_unnecessary:none
|
||||||
|
dotnet_style_predefined_type_for_locals_parameters_members=true:suggestion
|
||||||
|
dotnet_style_predefined_type_for_member_access=true:suggestion
|
||||||
|
dotnet_style_qualification_for_event=false:suggestion
|
||||||
|
dotnet_style_qualification_for_field=false:suggestion
|
||||||
|
dotnet_style_qualification_for_method=false:suggestion
|
||||||
|
dotnet_style_qualification_for_property=false:suggestion
|
||||||
|
dotnet_style_require_accessibility_modifiers=for_non_interface_members:suggestion
|
||||||
|
|
||||||
|
# ReSharper inspection severities
|
||||||
|
resharper_arrange_redundant_parentheses_highlighting=hint
|
||||||
|
resharper_arrange_this_qualifier_highlighting=hint
|
||||||
|
resharper_arrange_type_member_modifiers_highlighting=hint
|
||||||
|
resharper_arrange_type_modifiers_highlighting=hint
|
||||||
|
resharper_built_in_type_reference_style_for_member_access_highlighting=hint
|
||||||
|
resharper_built_in_type_reference_style_highlighting=hint
|
||||||
|
resharper_redundant_base_qualifier_highlighting=warning
|
||||||
|
resharper_suggest_var_or_type_built_in_types_highlighting=hint
|
||||||
|
resharper_suggest_var_or_type_elsewhere_highlighting=hint
|
||||||
|
resharper_suggest_var_or_type_simple_types_highlighting=hint
|
||||||
|
|
||||||
|
# ReSharper properties
|
||||||
|
resharper_csharp_insert_final_newline=true
|
||||||
|
resharper_int_align_assignments=true
|
||||||
|
resharper_int_align_switch_expressions=true
|
||||||
|
resharper_int_align_switch_sections=true
|
||||||
|
resharper_int_align_variables=true
|
||||||
|
resharper_keep_existing_embedded_arrangement=false
|
||||||
|
resharper_keep_existing_switch_expression_arrangement=false
|
||||||
|
resharper_place_simple_case_statement_on_same_line=if_owner_is_single_line
|
||||||
|
resharper_xmldoc_max_blank_lines_between_tags=1
|
|
@ -5,7 +5,16 @@ VisualStudioVersion = 16.0.30011.22
|
||||||
MinimumVisualStudioVersion = 10.0.40219.1
|
MinimumVisualStudioVersion = 10.0.40219.1
|
||||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "IrcTokens", "IrcTokens\IrcTokens.csproj", "{9E812F45-B2CD-42D2-8378-EBEBF8697905}"
|
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "IrcTokens", "IrcTokens\IrcTokens.csproj", "{9E812F45-B2CD-42D2-8378-EBEBF8697905}"
|
||||||
EndProject
|
EndProject
|
||||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Sample", "Sample\Sample.csproj", "{A45DA39B-6B47-4713-8049-3B36E0235B67}"
|
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "TokensSample", "Sample\TokensSample.csproj", "{A45DA39B-6B47-4713-8049-3B36E0235B67}"
|
||||||
|
EndProject
|
||||||
|
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "IrcStates", "IrcStates\IrcStates.csproj", "{233E3CB4-61F1-4368-9139-7E9F4A58ED2D}"
|
||||||
|
EndProject
|
||||||
|
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "StatesSample", "StatesSample\StatesSample.csproj", "{BC9F6696-9D83-4F7A-9E15-CE4D3626C1AF}"
|
||||||
|
EndProject
|
||||||
|
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution Items", "{1A85EB22-D7B4-417F-AC3B-DAFD97DDEA08}"
|
||||||
|
ProjectSection(SolutionItems) = preProject
|
||||||
|
.editorconfig = .editorconfig
|
||||||
|
EndProjectSection
|
||||||
EndProject
|
EndProject
|
||||||
Global
|
Global
|
||||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||||
|
@ -21,6 +30,14 @@ Global
|
||||||
{A45DA39B-6B47-4713-8049-3B36E0235B67}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
{A45DA39B-6B47-4713-8049-3B36E0235B67}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||||
{A45DA39B-6B47-4713-8049-3B36E0235B67}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
{A45DA39B-6B47-4713-8049-3B36E0235B67}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||||
{A45DA39B-6B47-4713-8049-3B36E0235B67}.Release|Any CPU.Build.0 = Release|Any CPU
|
{A45DA39B-6B47-4713-8049-3B36E0235B67}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||||
|
{233E3CB4-61F1-4368-9139-7E9F4A58ED2D}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||||
|
{233E3CB4-61F1-4368-9139-7E9F4A58ED2D}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||||
|
{233E3CB4-61F1-4368-9139-7E9F4A58ED2D}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||||
|
{233E3CB4-61F1-4368-9139-7E9F4A58ED2D}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||||
|
{BC9F6696-9D83-4F7A-9E15-CE4D3626C1AF}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||||
|
{BC9F6696-9D83-4F7A-9E15-CE4D3626C1AF}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||||
|
{BC9F6696-9D83-4F7A-9E15-CE4D3626C1AF}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||||
|
{BC9F6696-9D83-4F7A-9E15-CE4D3626C1AF}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||||
EndGlobalSection
|
EndGlobalSection
|
||||||
GlobalSection(SolutionProperties) = preSolution
|
GlobalSection(SolutionProperties) = preSolution
|
||||||
HideSolutionNode = FALSE
|
HideSolutionNode = FALSE
|
|
@ -0,0 +1,43 @@
|
||||||
|
using System;
|
||||||
|
|
||||||
|
namespace IrcStates
|
||||||
|
{
|
||||||
|
public static class Casemap
|
||||||
|
{
|
||||||
|
public enum CaseMapping
|
||||||
|
{
|
||||||
|
Rfc1459,
|
||||||
|
Ascii
|
||||||
|
}
|
||||||
|
|
||||||
|
private const string AsciiUpperChars = "ABCDEFGHIJKLMNOPQRSTUVWXYZ";
|
||||||
|
private const string AsciiLowerChars = "abcdefghijklmnopqrstuvwxyz";
|
||||||
|
private const string Rfc1459UpperChars = AsciiUpperChars + @"[]~\";
|
||||||
|
private const string Rfc1459LowerChars = AsciiLowerChars + @"{}^|";
|
||||||
|
|
||||||
|
private static string Replace(string s, string upper, string lower)
|
||||||
|
{
|
||||||
|
for (var i = 0; i < upper.Length; ++i)
|
||||||
|
{
|
||||||
|
s = s.Replace(upper[i], lower[i]);
|
||||||
|
}
|
||||||
|
|
||||||
|
return s;
|
||||||
|
}
|
||||||
|
|
||||||
|
public static string CaseFold(CaseMapping mapping, string s)
|
||||||
|
{
|
||||||
|
if (s != null)
|
||||||
|
{
|
||||||
|
return mapping switch
|
||||||
|
{
|
||||||
|
CaseMapping.Rfc1459 => Replace(s, Rfc1459UpperChars, Rfc1459LowerChars),
|
||||||
|
CaseMapping.Ascii => Replace(s, AsciiUpperChars, AsciiLowerChars),
|
||||||
|
_ => throw new ArgumentOutOfRangeException(nameof(mapping), mapping, null)
|
||||||
|
};
|
||||||
|
}
|
||||||
|
|
||||||
|
return string.Empty;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,69 @@
|
||||||
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
|
using System.Linq;
|
||||||
|
|
||||||
|
namespace IrcStates
|
||||||
|
{
|
||||||
|
public class Channel
|
||||||
|
{
|
||||||
|
public string Name { get; set; }
|
||||||
|
public string NameLower { get; set; }
|
||||||
|
public Dictionary<string, User> Users { get; set; }
|
||||||
|
public string Topic { get; set; }
|
||||||
|
public string TopicSetter { get; set; }
|
||||||
|
public DateTime TopicTime { get; set; }
|
||||||
|
public DateTime Created { get; set; }
|
||||||
|
public Dictionary<string, List<string>> ListModes { get; set; }
|
||||||
|
public Dictionary<string, string> Modes { get; set; }
|
||||||
|
|
||||||
|
public override string ToString()
|
||||||
|
{
|
||||||
|
return $"Channel(name={Name})";
|
||||||
|
}
|
||||||
|
|
||||||
|
public void SetName(string name, string nameLower)
|
||||||
|
{
|
||||||
|
Name = name;
|
||||||
|
NameLower = nameLower;
|
||||||
|
}
|
||||||
|
|
||||||
|
public void AddMode(string ch, string param, bool listMode)
|
||||||
|
{
|
||||||
|
if (listMode)
|
||||||
|
{
|
||||||
|
if (!ListModes.ContainsKey(ch))
|
||||||
|
{
|
||||||
|
ListModes[ch] = new List<string>();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (ListModes[ch].Contains(param))
|
||||||
|
{
|
||||||
|
ListModes[ch].Add(param ?? string.Empty);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Modes[ch] = param;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void RemoveMode(string ch, string param)
|
||||||
|
{
|
||||||
|
if (ListModes.ContainsKey(ch))
|
||||||
|
{
|
||||||
|
if (ListModes[ch].Contains(param))
|
||||||
|
{
|
||||||
|
ListModes[ch].Remove(param);
|
||||||
|
if (!ListModes[ch].Any())
|
||||||
|
{
|
||||||
|
ListModes.Remove(ch);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if (Modes.ContainsKey(ch))
|
||||||
|
{
|
||||||
|
Modes.Remove(ch);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,6 @@
|
||||||
|
namespace IrcStates
|
||||||
|
{
|
||||||
|
public class Emit
|
||||||
|
{
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,7 @@
|
||||||
|
// ReSharper disable InconsistentNaming
|
||||||
|
namespace IrcStates
|
||||||
|
{
|
||||||
|
public class ISupport
|
||||||
|
{
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,21 @@
|
||||||
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
|
<PropertyGroup>
|
||||||
|
<TargetFramework>netcoreapp3.1</TargetFramework>
|
||||||
|
</PropertyGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<PackageReference Include="Microsoft.CodeAnalysis.FxCopAnalyzers" Version="2.9.8">
|
||||||
|
<PrivateAssets>all</PrivateAssets>
|
||||||
|
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
|
||||||
|
</PackageReference>
|
||||||
|
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="16.6.0" />
|
||||||
|
<PackageReference Include="MSTest.TestAdapter" Version="2.1.1" />
|
||||||
|
<PackageReference Include="MSTest.TestFramework" Version="2.1.1" />
|
||||||
|
</ItemGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<ProjectReference Include="..\IrcTokens\IrcTokens.csproj" />
|
||||||
|
</ItemGroup>
|
||||||
|
|
||||||
|
</Project>
|
|
@ -0,0 +1,49 @@
|
||||||
|
// ReSharper disable InconsistentNaming
|
||||||
|
namespace IrcStates
|
||||||
|
{
|
||||||
|
public static class Numeric
|
||||||
|
{
|
||||||
|
public const string RPL_WELCOME = "001";
|
||||||
|
public const string RPL_ISUPPORT = "005";
|
||||||
|
public const string RPL_MOTD = "372";
|
||||||
|
public const string RPL_MOTDSTART = "375";
|
||||||
|
public const string RPL_UMODEIS = "221";
|
||||||
|
public const string RPL_VISIBLEHOST = "396";
|
||||||
|
|
||||||
|
public const string RPL_CHANNELMODEIS = "324";
|
||||||
|
public const string RPL_CREATIONTIME = "329";
|
||||||
|
public const string RPL_TOPIC = "332";
|
||||||
|
public const string RPL_TOPICWHOTIME = "333";
|
||||||
|
|
||||||
|
public const string RPL_WHOREPLY = "352";
|
||||||
|
public const string RPL_WHOSPCRPL = "354";
|
||||||
|
public const string RPL_ENDOFWHO = "315";
|
||||||
|
public const string RPL_NAMREPLY = "353";
|
||||||
|
public const string RPL_ENDOFNAMES = "366";
|
||||||
|
|
||||||
|
public const string RPL_BANLIST = "367";
|
||||||
|
public const string RPL_ENDOFBANLIST = "368";
|
||||||
|
public const string RPL_QUIETLIST = "728";
|
||||||
|
public const string RPL_ENDOFQUIETLIST = "729";
|
||||||
|
|
||||||
|
public const string RPL_SASLSUCCESS = "903";
|
||||||
|
public const string ERR_SASLFAIL = "904";
|
||||||
|
public const string ERR_SASLTOOLONG = "905";
|
||||||
|
public const string ERR_SASLABORTED = "906";
|
||||||
|
public const string ERR_SASLALREADY = "907";
|
||||||
|
public const string RPL_SASLMECHS = "908";
|
||||||
|
|
||||||
|
public const string RPL_WHOISUSER = "311";
|
||||||
|
public const string RPL_WHOISSERVER = "312";
|
||||||
|
public const string RPL_WHOISOPERATOR = "313";
|
||||||
|
public const string RPL_WHOISIDLE = "317";
|
||||||
|
public const string RPL_WHOISCHANNELS = "319";
|
||||||
|
public const string RPL_WHOISACCOUNT = "330";
|
||||||
|
public const string RPL_WHOISHOST = "378";
|
||||||
|
public const string RPL_WHOISMODES = "379";
|
||||||
|
public const string RPL_WHOISSECURE = "671";
|
||||||
|
public const string RPL_ENDOFWHOIS = "318";
|
||||||
|
|
||||||
|
public const string ERR_NOSUCHCHANNEL = "403";
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,6 @@
|
||||||
|
namespace IrcStates
|
||||||
|
{
|
||||||
|
public class Server
|
||||||
|
{
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,9 @@
|
||||||
|
using Microsoft.VisualStudio.TestTools.UnitTesting;
|
||||||
|
|
||||||
|
namespace IrcStates.Tests
|
||||||
|
{
|
||||||
|
[TestClass]
|
||||||
|
public class Cap
|
||||||
|
{
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,9 @@
|
||||||
|
using Microsoft.VisualStudio.TestTools.UnitTesting;
|
||||||
|
|
||||||
|
namespace IrcStates.Tests
|
||||||
|
{
|
||||||
|
[TestClass]
|
||||||
|
public class Casemap
|
||||||
|
{
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,9 @@
|
||||||
|
using Microsoft.VisualStudio.TestTools.UnitTesting;
|
||||||
|
|
||||||
|
namespace IrcStates.Tests
|
||||||
|
{
|
||||||
|
[TestClass]
|
||||||
|
public class Channel
|
||||||
|
{
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,9 @@
|
||||||
|
using Microsoft.VisualStudio.TestTools.UnitTesting;
|
||||||
|
|
||||||
|
namespace IrcStates.Tests
|
||||||
|
{
|
||||||
|
[TestClass]
|
||||||
|
public class Emit
|
||||||
|
{
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,10 @@
|
||||||
|
using Microsoft.VisualStudio.TestTools.UnitTesting;
|
||||||
|
// ReSharper disable InconsistentNaming
|
||||||
|
|
||||||
|
namespace IrcStates.Tests
|
||||||
|
{
|
||||||
|
[TestClass]
|
||||||
|
public class ISupport
|
||||||
|
{
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,9 @@
|
||||||
|
using Microsoft.VisualStudio.TestTools.UnitTesting;
|
||||||
|
|
||||||
|
namespace IrcStates.Tests
|
||||||
|
{
|
||||||
|
[TestClass]
|
||||||
|
public class Mode
|
||||||
|
{
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,9 @@
|
||||||
|
using Microsoft.VisualStudio.TestTools.UnitTesting;
|
||||||
|
|
||||||
|
namespace IrcStates.Tests
|
||||||
|
{
|
||||||
|
[TestClass]
|
||||||
|
public class Motd
|
||||||
|
{
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,9 @@
|
||||||
|
using Microsoft.VisualStudio.TestTools.UnitTesting;
|
||||||
|
|
||||||
|
namespace IrcStates.Tests
|
||||||
|
{
|
||||||
|
[TestClass]
|
||||||
|
public class User
|
||||||
|
{
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,9 @@
|
||||||
|
using Microsoft.VisualStudio.TestTools.UnitTesting;
|
||||||
|
|
||||||
|
namespace IrcStates.Tests
|
||||||
|
{
|
||||||
|
[TestClass]
|
||||||
|
public class Who
|
||||||
|
{
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,28 @@
|
||||||
|
using System.Collections.Generic;
|
||||||
|
|
||||||
|
namespace IrcStates
|
||||||
|
{
|
||||||
|
public class User
|
||||||
|
{
|
||||||
|
private string NickName;
|
||||||
|
private string NickNameLower;
|
||||||
|
|
||||||
|
public string UserName { get; set; }
|
||||||
|
public string HostName { get; set; }
|
||||||
|
public string RealName { get; set; }
|
||||||
|
public string Account { get; set; }
|
||||||
|
public string Away { get; set; }
|
||||||
|
public HashSet<string> Channels { get; set; }
|
||||||
|
|
||||||
|
public override string ToString()
|
||||||
|
{
|
||||||
|
return $"User(nickname={NickName})";
|
||||||
|
}
|
||||||
|
|
||||||
|
public void SetNickName(string nick, string nickLower)
|
||||||
|
{
|
||||||
|
NickName = nick;
|
||||||
|
NickNameLower = nickLower;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -5,29 +5,45 @@ namespace IrcTokens
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Represents the three parts of a hostmask. Parse with the constructor.
|
/// Represents the three parts of a hostmask. Parse with the constructor.
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public class Hostmask
|
public class Hostmask : IEquatable<Hostmask>
|
||||||
{
|
{
|
||||||
public string NickName { get; set; }
|
public string NickName { get; set; }
|
||||||
public string UserName { get; set; }
|
public string UserName { get; set; }
|
||||||
public string HostName { get; set; }
|
public string HostName { get; set; }
|
||||||
|
|
||||||
public override string ToString() => _source;
|
public override string ToString()
|
||||||
|
{
|
||||||
|
return _source;
|
||||||
|
}
|
||||||
|
|
||||||
public override int GetHashCode() => _source.GetHashCode(StringComparison.Ordinal);
|
public override int GetHashCode()
|
||||||
|
{
|
||||||
|
return _source.GetHashCode(StringComparison.Ordinal);
|
||||||
|
}
|
||||||
|
|
||||||
|
public bool Equals(Hostmask other)
|
||||||
|
{
|
||||||
|
if (other == null)
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
return _source == other._source;
|
||||||
|
}
|
||||||
|
|
||||||
public override bool Equals(object obj)
|
public override bool Equals(object obj)
|
||||||
{
|
{
|
||||||
if (obj == null || GetType() != obj.GetType())
|
return Equals(obj as Hostmask);
|
||||||
return false;
|
|
||||||
|
|
||||||
return _source == ((Hostmask) obj)._source;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private readonly string _source;
|
private readonly string _source;
|
||||||
|
|
||||||
public Hostmask(string source)
|
public Hostmask(string source)
|
||||||
{
|
{
|
||||||
if (source == null) return;
|
if (source == null)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
_source = source;
|
_source = source;
|
||||||
|
|
||||||
|
|
|
@ -8,7 +8,7 @@ namespace IrcTokens
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Tools to represent, parse, and format IRC lines
|
/// Tools to represent, parse, and format IRC lines
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public class Line
|
public class Line : IEquatable<Line>
|
||||||
{
|
{
|
||||||
public Dictionary<string, string> Tags { get; set; }
|
public Dictionary<string, string> Tags { get; set; }
|
||||||
public string Source { get; set; }
|
public string Source { get; set; }
|
||||||
|
@ -16,32 +16,52 @@ namespace IrcTokens
|
||||||
public List<string> Params { get; set; }
|
public List<string> Params { get; set; }
|
||||||
|
|
||||||
private Hostmask _hostmask;
|
private Hostmask _hostmask;
|
||||||
private readonly string _rawLine;
|
|
||||||
|
|
||||||
public override string ToString()
|
public override string ToString()
|
||||||
{
|
{
|
||||||
var vars = new List<string>();
|
var vars = new List<string>();
|
||||||
|
|
||||||
if (Command != null)
|
if (Command != null)
|
||||||
|
{
|
||||||
vars.Add($"command={Command}");
|
vars.Add($"command={Command}");
|
||||||
|
}
|
||||||
|
|
||||||
if (Source != null)
|
if (Source != null)
|
||||||
|
{
|
||||||
vars.Add($"source={Source}");
|
vars.Add($"source={Source}");
|
||||||
|
}
|
||||||
|
|
||||||
if (Params != null && Params.Any())
|
if (Params != null && Params.Any())
|
||||||
|
{
|
||||||
vars.Add($"params=[{string.Join(",", Params)}]");
|
vars.Add($"params=[{string.Join(",", Params)}]");
|
||||||
|
}
|
||||||
|
|
||||||
if (Tags != null && Tags.Any())
|
if (Tags != null && Tags.Any())
|
||||||
|
{
|
||||||
vars.Add($"tags=[{string.Join(";", Tags.Select(kvp => $"{kvp.Key}={kvp.Value}"))}]");
|
vars.Add($"tags=[{string.Join(";", Tags.Select(kvp => $"{kvp.Key}={kvp.Value}"))}]");
|
||||||
|
}
|
||||||
|
|
||||||
return $"Line({string.Join(", ", vars)})";
|
return $"Line({string.Join(", ", vars)})";
|
||||||
}
|
}
|
||||||
|
|
||||||
public override int GetHashCode() => Format().GetHashCode(StringComparison.Ordinal);
|
public override int GetHashCode()
|
||||||
|
{
|
||||||
|
return Format().GetHashCode(StringComparison.Ordinal);
|
||||||
|
}
|
||||||
|
|
||||||
|
public bool Equals(Line other)
|
||||||
|
{
|
||||||
|
if (other == null)
|
||||||
|
{
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
return Format() == other.Format();
|
||||||
|
}
|
||||||
|
|
||||||
public override bool Equals(object obj)
|
public override bool Equals(object obj)
|
||||||
{
|
{
|
||||||
if (obj == null || GetType() != obj.GetType())
|
return Equals(obj as Line);
|
||||||
return false;
|
|
||||||
|
|
||||||
return Format() == ((Line) obj).Format();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public Hostmask Hostmask =>
|
public Hostmask Hostmask =>
|
||||||
|
@ -56,9 +76,10 @@ namespace IrcTokens
|
||||||
public Line(string line)
|
public Line(string line)
|
||||||
{
|
{
|
||||||
if (string.IsNullOrWhiteSpace(line))
|
if (string.IsNullOrWhiteSpace(line))
|
||||||
|
{
|
||||||
throw new ArgumentNullException(nameof(line));
|
throw new ArgumentNullException(nameof(line));
|
||||||
|
}
|
||||||
|
|
||||||
_rawLine = line;
|
|
||||||
string[] split;
|
string[] split;
|
||||||
|
|
||||||
if (line.StartsWith('@'))
|
if (line.StartsWith('@'))
|
||||||
|
@ -97,7 +118,7 @@ namespace IrcTokens
|
||||||
|
|
||||||
Params = line.Contains(' ', StringComparison.Ordinal)
|
Params = line.Contains(' ', StringComparison.Ordinal)
|
||||||
? line.Split(' ', StringSplitOptions.RemoveEmptyEntries).ToList()
|
? line.Split(' ', StringSplitOptions.RemoveEmptyEntries).ToList()
|
||||||
: new List<string> {line};
|
: new List<string> { line };
|
||||||
|
|
||||||
if (Params[0].StartsWith(':'))
|
if (Params[0].StartsWith(':'))
|
||||||
{
|
{
|
||||||
|
@ -135,7 +156,9 @@ namespace IrcTokens
|
||||||
}
|
}
|
||||||
|
|
||||||
if (Source != null)
|
if (Source != null)
|
||||||
|
{
|
||||||
outs.Add($":{Source}");
|
outs.Add($":{Source}");
|
||||||
|
}
|
||||||
|
|
||||||
outs.Add(Command);
|
outs.Add(Command);
|
||||||
|
|
||||||
|
@ -147,14 +170,22 @@ namespace IrcTokens
|
||||||
foreach (var p in Params)
|
foreach (var p in Params)
|
||||||
{
|
{
|
||||||
if (p.Contains(' ', StringComparison.Ordinal))
|
if (p.Contains(' ', StringComparison.Ordinal))
|
||||||
|
{
|
||||||
throw new ArgumentException(@"non-last parameters cannot have spaces", p);
|
throw new ArgumentException(@"non-last parameters cannot have spaces", p);
|
||||||
|
}
|
||||||
|
|
||||||
if (p.StartsWith(':'))
|
if (p.StartsWith(':'))
|
||||||
|
{
|
||||||
throw new ArgumentException(@"non-last parameters cannot start with colon", p);
|
throw new ArgumentException(@"non-last parameters cannot start with colon", p);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
outs.AddRange(Params);
|
outs.AddRange(Params);
|
||||||
|
|
||||||
if (string.IsNullOrWhiteSpace(last) || last.Contains(' ', StringComparison.Ordinal) || last.StartsWith(':'))
|
if (string.IsNullOrWhiteSpace(last) || last.Contains(' ', StringComparison.Ordinal) || last.StartsWith(':'))
|
||||||
|
{
|
||||||
last = $":{last}";
|
last = $":{last}";
|
||||||
|
}
|
||||||
|
|
||||||
outs.Add(last);
|
outs.Add(last);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -50,7 +50,9 @@ namespace IrcTokens
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
{
|
||||||
unescaped.Append(current);
|
unescaped.Append(current);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return unescaped.ToString();
|
return unescaped.ToString();
|
||||||
|
|
|
@ -18,8 +18,10 @@ namespace IrcTokens
|
||||||
set
|
set
|
||||||
{
|
{
|
||||||
if (value != null)
|
if (value != null)
|
||||||
|
{
|
||||||
_encoding = Encoding.GetEncoding(value.CodePage, EncoderFallback.ExceptionFallback,
|
_encoding = Encoding.GetEncoding(value.CodePage, EncoderFallback.ExceptionFallback,
|
||||||
DecoderFallback.ReplacementFallback);
|
DecoderFallback.ReplacementFallback);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -30,8 +32,10 @@ namespace IrcTokens
|
||||||
set
|
set
|
||||||
{
|
{
|
||||||
if (value != null)
|
if (value != null)
|
||||||
_encoding = Encoding.GetEncoding(value.CodePage, EncoderFallback.ReplacementFallback,
|
{
|
||||||
|
_fallback = Encoding.GetEncoding(value.CodePage, EncoderFallback.ReplacementFallback,
|
||||||
DecoderFallback.ReplacementFallback);
|
DecoderFallback.ReplacementFallback);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -55,7 +59,9 @@ namespace IrcTokens
|
||||||
public List<Line> Push(byte[] data)
|
public List<Line> Push(byte[] data)
|
||||||
{
|
{
|
||||||
if (data == null || data.Length == 0)
|
if (data == null || data.Length == 0)
|
||||||
|
{
|
||||||
return null;
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
_buffer = _buffer.Concat(data).ToArray();
|
_buffer = _buffer.Concat(data).ToArray();
|
||||||
|
|
||||||
|
|
|
@ -16,8 +16,10 @@ namespace IrcTokens
|
||||||
set
|
set
|
||||||
{
|
{
|
||||||
if (value != null)
|
if (value != null)
|
||||||
|
{
|
||||||
_encoding = Encoding.GetEncoding(value.CodePage, EncoderFallback.ExceptionFallback,
|
_encoding = Encoding.GetEncoding(value.CodePage, EncoderFallback.ExceptionFallback,
|
||||||
DecoderFallback.ExceptionFallback);
|
DecoderFallback.ExceptionFallback);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -52,7 +54,9 @@ namespace IrcTokens
|
||||||
public void Push(Line line)
|
public void Push(Line line)
|
||||||
{
|
{
|
||||||
if (line == null)
|
if (line == null)
|
||||||
|
{
|
||||||
throw new ArgumentNullException(nameof(line));
|
throw new ArgumentNullException(nameof(line));
|
||||||
|
}
|
||||||
|
|
||||||
PendingBytes = PendingBytes.Concat(Encoding.GetBytes($"{line.Format()}\r\n")).ToArray();
|
PendingBytes = PendingBytes.Concat(Encoding.GetBytes($"{line.Format()}\r\n")).ToArray();
|
||||||
_bufferedLines.Enqueue(line);
|
_bufferedLines.Enqueue(line);
|
||||||
|
|
|
@ -5,16 +5,16 @@ using System.Collections.Generic;
|
||||||
namespace IrcTokens.Tests
|
namespace IrcTokens.Tests
|
||||||
{
|
{
|
||||||
[TestClass]
|
[TestClass]
|
||||||
public class FormatTests
|
public class Format
|
||||||
{
|
{
|
||||||
[TestMethod]
|
[TestMethod]
|
||||||
public void TestTags()
|
public void TestTags()
|
||||||
{
|
{
|
||||||
var line = new Line
|
var line = new Line
|
||||||
{
|
{
|
||||||
Command = "PRIVMSG",
|
Command = "PRIVMSG",
|
||||||
Params = new List<string> {"#channel", "hello"},
|
Params = new List<string> { "#channel", "hello" },
|
||||||
Tags = new Dictionary<string, string> {{"id", "\\" + " " + ";" + "\r\n"}}
|
Tags = new Dictionary<string, string> { { "id", "\\" + " " + ";" + "\r\n" } }
|
||||||
}.Format();
|
}.Format();
|
||||||
|
|
||||||
Assert.AreEqual("@id=\\\\\\s\\:\\r\\n PRIVMSG #channel hello", line);
|
Assert.AreEqual("@id=\\\\\\s\\:\\r\\n PRIVMSG #channel hello", line);
|
||||||
|
@ -25,8 +25,8 @@ namespace IrcTokens.Tests
|
||||||
{
|
{
|
||||||
var line = new Line
|
var line = new Line
|
||||||
{
|
{
|
||||||
Command = "PRIVMSG",
|
Command = "PRIVMSG",
|
||||||
Params = new List<string> {"#channel", "hello"}
|
Params = new List<string> { "#channel", "hello" }
|
||||||
}.Format();
|
}.Format();
|
||||||
|
|
||||||
Assert.AreEqual("PRIVMSG #channel hello", line);
|
Assert.AreEqual("PRIVMSG #channel hello", line);
|
||||||
|
@ -38,8 +38,8 @@ namespace IrcTokens.Tests
|
||||||
var line = new Line
|
var line = new Line
|
||||||
{
|
{
|
||||||
Command = "PRIVMSG",
|
Command = "PRIVMSG",
|
||||||
Params = new List<string> {"#channel", "hello"},
|
Params = new List<string> { "#channel", "hello" },
|
||||||
Tags = new Dictionary<string, string> {{"a", null}}
|
Tags = new Dictionary<string, string> { { "a", null } }
|
||||||
}.Format();
|
}.Format();
|
||||||
|
|
||||||
Assert.AreEqual("@a PRIVMSG #channel hello", line);
|
Assert.AreEqual("@a PRIVMSG #channel hello", line);
|
||||||
|
@ -51,8 +51,8 @@ namespace IrcTokens.Tests
|
||||||
var line = new Line
|
var line = new Line
|
||||||
{
|
{
|
||||||
Command = "PRIVMSG",
|
Command = "PRIVMSG",
|
||||||
Params = new List<string> {"#channel", "hello"},
|
Params = new List<string> { "#channel", "hello" },
|
||||||
Tags = new Dictionary<string, string> {{"a", ""}}
|
Tags = new Dictionary<string, string> { { "a", "" } }
|
||||||
}.Format();
|
}.Format();
|
||||||
|
|
||||||
Assert.AreEqual("@a PRIVMSG #channel hello", line);
|
Assert.AreEqual("@a PRIVMSG #channel hello", line);
|
||||||
|
@ -64,7 +64,7 @@ namespace IrcTokens.Tests
|
||||||
var line = new Line
|
var line = new Line
|
||||||
{
|
{
|
||||||
Command = "PRIVMSG",
|
Command = "PRIVMSG",
|
||||||
Params = new List<string> {"#channel", "hello"},
|
Params = new List<string> { "#channel", "hello" },
|
||||||
Source = "nick!user@host"
|
Source = "nick!user@host"
|
||||||
}.Format();
|
}.Format();
|
||||||
|
|
||||||
|
@ -74,14 +74,14 @@ namespace IrcTokens.Tests
|
||||||
[TestMethod]
|
[TestMethod]
|
||||||
public void TestCommandLowercase()
|
public void TestCommandLowercase()
|
||||||
{
|
{
|
||||||
var line = new Line {Command = "privmsg"}.Format();
|
var line = new Line { Command = "privmsg" }.Format();
|
||||||
Assert.AreEqual("privmsg", line);
|
Assert.AreEqual("privmsg", line);
|
||||||
}
|
}
|
||||||
|
|
||||||
[TestMethod]
|
[TestMethod]
|
||||||
public void TestCommandUppercase()
|
public void TestCommandUppercase()
|
||||||
{
|
{
|
||||||
var line = new Line {Command = "PRIVMSG"}.Format();
|
var line = new Line { Command = "PRIVMSG" }.Format();
|
||||||
Assert.AreEqual("PRIVMSG", line);
|
Assert.AreEqual("PRIVMSG", line);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -91,7 +91,7 @@ namespace IrcTokens.Tests
|
||||||
var line = new Line
|
var line = new Line
|
||||||
{
|
{
|
||||||
Command = "PRIVMSG",
|
Command = "PRIVMSG",
|
||||||
Params = new List<string> {"#channel", "hello world"}
|
Params = new List<string> { "#channel", "hello world" }
|
||||||
}.Format();
|
}.Format();
|
||||||
|
|
||||||
Assert.AreEqual("PRIVMSG #channel :hello world", line);
|
Assert.AreEqual("PRIVMSG #channel :hello world", line);
|
||||||
|
@ -103,7 +103,7 @@ namespace IrcTokens.Tests
|
||||||
var line = new Line
|
var line = new Line
|
||||||
{
|
{
|
||||||
Command = "PRIVMSG",
|
Command = "PRIVMSG",
|
||||||
Params = new List<string> {"#channel", "helloworld"}
|
Params = new List<string> { "#channel", "helloworld" }
|
||||||
}.Format();
|
}.Format();
|
||||||
|
|
||||||
Assert.AreEqual("PRIVMSG #channel helloworld", line);
|
Assert.AreEqual("PRIVMSG #channel helloworld", line);
|
||||||
|
@ -115,7 +115,7 @@ namespace IrcTokens.Tests
|
||||||
var line = new Line
|
var line = new Line
|
||||||
{
|
{
|
||||||
Command = "PRIVMSG",
|
Command = "PRIVMSG",
|
||||||
Params = new List<string> {"#channel", ":helloworld"}
|
Params = new List<string> { "#channel", ":helloworld" }
|
||||||
}.Format();
|
}.Format();
|
||||||
|
|
||||||
Assert.AreEqual("PRIVMSG #channel ::helloworld", line);
|
Assert.AreEqual("PRIVMSG #channel ::helloworld", line);
|
||||||
|
@ -129,7 +129,7 @@ namespace IrcTokens.Tests
|
||||||
new Line
|
new Line
|
||||||
{
|
{
|
||||||
Command = "USER",
|
Command = "USER",
|
||||||
Params = new List<string> {"user", "0 *", "real name"}
|
Params = new List<string> { "user", "0 *", "real name" }
|
||||||
}.Format();
|
}.Format();
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
@ -142,7 +142,7 @@ namespace IrcTokens.Tests
|
||||||
new Line
|
new Line
|
||||||
{
|
{
|
||||||
Command = "PRIVMSG",
|
Command = "PRIVMSG",
|
||||||
Params = new List<string> {":#channel", "hello"}
|
Params = new List<string> { ":#channel", "hello" }
|
||||||
}.Format();
|
}.Format();
|
||||||
});
|
});
|
||||||
}
|
}
|
|
@ -3,12 +3,12 @@
|
||||||
namespace IrcTokens.Tests
|
namespace IrcTokens.Tests
|
||||||
{
|
{
|
||||||
[TestClass]
|
[TestClass]
|
||||||
public class HostmaskTests
|
public class Hostmask
|
||||||
{
|
{
|
||||||
[TestMethod]
|
[TestMethod]
|
||||||
public void TestHostmask()
|
public void TestHostmask()
|
||||||
{
|
{
|
||||||
var hostmask = new Hostmask("nick!user@host");
|
var hostmask = new IrcTokens.Hostmask("nick!user@host");
|
||||||
Assert.AreEqual("nick", hostmask.NickName);
|
Assert.AreEqual("nick", hostmask.NickName);
|
||||||
Assert.AreEqual("user", hostmask.UserName);
|
Assert.AreEqual("user", hostmask.UserName);
|
||||||
Assert.AreEqual("host", hostmask.HostName);
|
Assert.AreEqual("host", hostmask.HostName);
|
||||||
|
@ -17,7 +17,7 @@ namespace IrcTokens.Tests
|
||||||
[TestMethod]
|
[TestMethod]
|
||||||
public void TestNoHostName()
|
public void TestNoHostName()
|
||||||
{
|
{
|
||||||
var hostmask = new Hostmask("nick!user");
|
var hostmask = new IrcTokens.Hostmask("nick!user");
|
||||||
Assert.AreEqual("nick", hostmask.NickName);
|
Assert.AreEqual("nick", hostmask.NickName);
|
||||||
Assert.AreEqual("user", hostmask.UserName);
|
Assert.AreEqual("user", hostmask.UserName);
|
||||||
Assert.IsNull(hostmask.HostName);
|
Assert.IsNull(hostmask.HostName);
|
||||||
|
@ -26,7 +26,7 @@ namespace IrcTokens.Tests
|
||||||
[TestMethod]
|
[TestMethod]
|
||||||
public void TestNoUserName()
|
public void TestNoUserName()
|
||||||
{
|
{
|
||||||
var hostmask = new Hostmask("nick@host");
|
var hostmask = new IrcTokens.Hostmask("nick@host");
|
||||||
Assert.AreEqual("nick", hostmask.NickName);
|
Assert.AreEqual("nick", hostmask.NickName);
|
||||||
Assert.IsNull(hostmask.UserName);
|
Assert.IsNull(hostmask.UserName);
|
||||||
Assert.AreEqual("host", hostmask.HostName);
|
Assert.AreEqual("host", hostmask.HostName);
|
||||||
|
@ -35,7 +35,7 @@ namespace IrcTokens.Tests
|
||||||
[TestMethod]
|
[TestMethod]
|
||||||
public void TestOnlyNickName()
|
public void TestOnlyNickName()
|
||||||
{
|
{
|
||||||
var hostmask = new Hostmask("nick");
|
var hostmask = new IrcTokens.Hostmask("nick");
|
||||||
Assert.AreEqual("nick", hostmask.NickName);
|
Assert.AreEqual("nick", hostmask.NickName);
|
||||||
Assert.IsNull(hostmask.UserName);
|
Assert.IsNull(hostmask.UserName);
|
||||||
Assert.IsNull(hostmask.HostName);
|
Assert.IsNull(hostmask.HostName);
|
||||||
|
@ -45,7 +45,7 @@ namespace IrcTokens.Tests
|
||||||
public void TestHostmaskFromLine()
|
public void TestHostmaskFromLine()
|
||||||
{
|
{
|
||||||
var line = new Line(":nick!user@host PRIVMSG #channel hello");
|
var line = new Line(":nick!user@host PRIVMSG #channel hello");
|
||||||
var hostmask = new Hostmask("nick!user@host");
|
var hostmask = new IrcTokens.Hostmask("nick!user@host");
|
||||||
Assert.AreEqual(hostmask.ToString(), line.Hostmask.ToString());
|
Assert.AreEqual(hostmask.ToString(), line.Hostmask.ToString());
|
||||||
Assert.AreEqual("nick", line.Hostmask.NickName);
|
Assert.AreEqual("nick", line.Hostmask.NickName);
|
||||||
Assert.AreEqual("user", line.Hostmask.UserName);
|
Assert.AreEqual("user", line.Hostmask.UserName);
|
|
@ -1,15 +1,15 @@
|
||||||
using System.Collections.Generic;
|
using IrcTokens.Tests.Data;
|
||||||
|
using Microsoft.VisualStudio.TestTools.UnitTesting;
|
||||||
|
using System.Collections.Generic;
|
||||||
using System.Globalization;
|
using System.Globalization;
|
||||||
using System.IO;
|
using System.IO;
|
||||||
using IrcTokens.Tests.Data;
|
|
||||||
using Microsoft.VisualStudio.TestTools.UnitTesting;
|
|
||||||
using YamlDotNet.Serialization;
|
using YamlDotNet.Serialization;
|
||||||
using YamlDotNet.Serialization.NamingConventions;
|
using YamlDotNet.Serialization.NamingConventions;
|
||||||
|
|
||||||
namespace IrcTokens.Tests
|
namespace IrcTokens.Tests
|
||||||
{
|
{
|
||||||
[TestClass]
|
[TestClass]
|
||||||
public class ParserTests
|
public class Parser
|
||||||
{
|
{
|
||||||
private static T LoadYaml<T>(string path)
|
private static T LoadYaml<T>(string path)
|
||||||
{
|
{
|
||||||
|
@ -46,7 +46,7 @@ namespace IrcTokens.Tests
|
||||||
{
|
{
|
||||||
Command = atoms.Verb,
|
Command = atoms.Verb,
|
||||||
Params = atoms.Params,
|
Params = atoms.Params,
|
||||||
Source = atoms.Source ?? null,
|
Source = atoms.Source,
|
||||||
Tags = atoms.Tags
|
Tags = atoms.Tags
|
||||||
}.Format();
|
}.Format();
|
||||||
|
|
|
@ -1,19 +1,18 @@
|
||||||
using System.Collections.Generic;
|
using Microsoft.VisualStudio.TestTools.UnitTesting;
|
||||||
using System.Linq;
|
using System.Collections.Generic;
|
||||||
using System.Text;
|
using System.Text;
|
||||||
using Microsoft.VisualStudio.TestTools.UnitTesting;
|
|
||||||
|
|
||||||
namespace IrcTokens.Tests
|
namespace IrcTokens.Tests
|
||||||
{
|
{
|
||||||
[TestClass]
|
[TestClass]
|
||||||
public class StatefulDecoderTests
|
public class StatefulDecoder
|
||||||
{
|
{
|
||||||
private StatefulDecoder _decoder;
|
private IrcTokens.StatefulDecoder _decoder;
|
||||||
|
|
||||||
[TestInitialize]
|
[TestInitialize]
|
||||||
public void TestInitialize()
|
public void TestInitialize()
|
||||||
{
|
{
|
||||||
_decoder = new StatefulDecoder();
|
_decoder = new IrcTokens.StatefulDecoder();
|
||||||
}
|
}
|
||||||
|
|
||||||
[TestMethod]
|
[TestMethod]
|
||||||
|
@ -26,7 +25,7 @@ namespace IrcTokens.Tests
|
||||||
Assert.AreEqual(1, lines.Count);
|
Assert.AreEqual(1, lines.Count);
|
||||||
|
|
||||||
var line = new Line("PRIVMSG #channel hello");
|
var line = new Line("PRIVMSG #channel hello");
|
||||||
CollectionAssert.AreEqual(new List<Line> {line}, lines);
|
CollectionAssert.AreEqual(new List<Line> { line }, lines);
|
||||||
}
|
}
|
||||||
|
|
||||||
[TestMethod]
|
[TestMethod]
|
||||||
|
@ -45,7 +44,7 @@ namespace IrcTokens.Tests
|
||||||
public void TestEncoding()
|
public void TestEncoding()
|
||||||
{
|
{
|
||||||
var iso8859 = Encoding.GetEncoding("iso-8859-1");
|
var iso8859 = Encoding.GetEncoding("iso-8859-1");
|
||||||
_decoder = new StatefulDecoder {Encoding = iso8859};
|
_decoder = new IrcTokens.StatefulDecoder { Encoding = iso8859 };
|
||||||
var lines = _decoder.Push(iso8859.GetBytes("PRIVMSG #channel :hello Ç\r\n"));
|
var lines = _decoder.Push(iso8859.GetBytes("PRIVMSG #channel :hello Ç\r\n"));
|
||||||
var line = new Line("PRIVMSG #channel :hello Ç");
|
var line = new Line("PRIVMSG #channel :hello Ç");
|
||||||
Assert.IsTrue(line.Equals(lines[0]));
|
Assert.IsTrue(line.Equals(lines[0]));
|
||||||
|
@ -55,7 +54,7 @@ namespace IrcTokens.Tests
|
||||||
public void TestEncodingFallback()
|
public void TestEncodingFallback()
|
||||||
{
|
{
|
||||||
var latin1 = Encoding.GetEncoding("iso-8859-1");
|
var latin1 = Encoding.GetEncoding("iso-8859-1");
|
||||||
_decoder = new StatefulDecoder {Encoding = null, Fallback = latin1};
|
_decoder = new IrcTokens.StatefulDecoder { Encoding = null, Fallback = latin1 };
|
||||||
var lines = _decoder.Push(latin1.GetBytes("PRIVMSG #channel hélló\r\n"));
|
var lines = _decoder.Push(latin1.GetBytes("PRIVMSG #channel hélló\r\n"));
|
||||||
Assert.AreEqual(1, lines.Count);
|
Assert.AreEqual(1, lines.Count);
|
||||||
Assert.IsTrue(new Line("PRIVMSG #channel hélló").Equals(lines[0]));
|
Assert.IsTrue(new Line("PRIVMSG #channel hélló").Equals(lines[0]));
|
|
@ -1,18 +1,17 @@
|
||||||
using System.Linq;
|
using Microsoft.VisualStudio.TestTools.UnitTesting;
|
||||||
using System.Text;
|
using System.Text;
|
||||||
using Microsoft.VisualStudio.TestTools.UnitTesting;
|
|
||||||
|
|
||||||
namespace IrcTokens.Tests
|
namespace IrcTokens.Tests
|
||||||
{
|
{
|
||||||
[TestClass]
|
[TestClass]
|
||||||
public class StatefulEncoderTests
|
public class StatefulEncoder
|
||||||
{
|
{
|
||||||
private StatefulEncoder _encoder;
|
private IrcTokens.StatefulEncoder _encoder;
|
||||||
|
|
||||||
[TestInitialize]
|
[TestInitialize]
|
||||||
public void TestInitialize()
|
public void TestInitialize()
|
||||||
{
|
{
|
||||||
_encoder = new StatefulEncoder();
|
_encoder = new IrcTokens.StatefulEncoder();
|
||||||
}
|
}
|
||||||
|
|
||||||
[TestMethod]
|
[TestMethod]
|
||||||
|
@ -64,7 +63,7 @@ namespace IrcTokens.Tests
|
||||||
public void TestEncoding()
|
public void TestEncoding()
|
||||||
{
|
{
|
||||||
var iso8859 = Encoding.GetEncoding("iso-8859-1");
|
var iso8859 = Encoding.GetEncoding("iso-8859-1");
|
||||||
_encoder = new StatefulEncoder {Encoding = iso8859};
|
_encoder = new IrcTokens.StatefulEncoder { Encoding = iso8859 };
|
||||||
_encoder.Push(new Line("PRIVMSG #channel :hello Ç"));
|
_encoder.Push(new Line("PRIVMSG #channel :hello Ç"));
|
||||||
CollectionAssert.AreEqual(iso8859.GetBytes("PRIVMSG #channel :hello Ç\r\n"), _encoder.PendingBytes);
|
CollectionAssert.AreEqual(iso8859.GetBytes("PRIVMSG #channel :hello Ç\r\n"), _encoder.PendingBytes);
|
||||||
}
|
}
|
|
@ -1,10 +1,10 @@
|
||||||
using System.Collections.Generic;
|
using Microsoft.VisualStudio.TestTools.UnitTesting;
|
||||||
using Microsoft.VisualStudio.TestTools.UnitTesting;
|
using System.Collections.Generic;
|
||||||
|
|
||||||
namespace IrcTokens.Tests
|
namespace IrcTokens.Tests
|
||||||
{
|
{
|
||||||
[TestClass]
|
[TestClass]
|
||||||
public class TokenizationTests
|
public class Tokenization
|
||||||
{
|
{
|
||||||
[TestMethod]
|
[TestMethod]
|
||||||
public void TestTagsMissing()
|
public void TestTagsMissing()
|
||||||
|
@ -87,14 +87,14 @@ namespace IrcTokens.Tests
|
||||||
public void TestParamsTrailing()
|
public void TestParamsTrailing()
|
||||||
{
|
{
|
||||||
var line = new Line("PRIVMSG #channel :hello world");
|
var line = new Line("PRIVMSG #channel :hello world");
|
||||||
CollectionAssert.AreEqual(new List<string> {"#channel", "hello world"}, line.Params);
|
CollectionAssert.AreEqual(new List<string> { "#channel", "hello world" }, line.Params);
|
||||||
}
|
}
|
||||||
|
|
||||||
[TestMethod]
|
[TestMethod]
|
||||||
public void TestParamsOnlyTrailing()
|
public void TestParamsOnlyTrailing()
|
||||||
{
|
{
|
||||||
var line = new Line("PRIVMSG :hello world");
|
var line = new Line("PRIVMSG :hello world");
|
||||||
CollectionAssert.AreEqual(new List<string> {"hello world"}, line.Params);
|
CollectionAssert.AreEqual(new List<string> { "hello world" }, line.Params);
|
||||||
}
|
}
|
||||||
|
|
||||||
[TestMethod]
|
[TestMethod]
|
||||||
|
@ -109,10 +109,10 @@ namespace IrcTokens.Tests
|
||||||
public void TestAllTokens()
|
public void TestAllTokens()
|
||||||
{
|
{
|
||||||
var line = new Line("@id=123 :nick!user@host PRIVMSG #channel :hello world");
|
var line = new Line("@id=123 :nick!user@host PRIVMSG #channel :hello world");
|
||||||
CollectionAssert.AreEqual(new Dictionary<string, string> {{"id", "123"}}, line.Tags);
|
CollectionAssert.AreEqual(new Dictionary<string, string> { { "id", "123" } }, line.Tags);
|
||||||
Assert.AreEqual("nick!user@host", line.Source);
|
Assert.AreEqual("nick!user@host", line.Source);
|
||||||
Assert.AreEqual("PRIVMSG", line.Command);
|
Assert.AreEqual("PRIVMSG", line.Command);
|
||||||
CollectionAssert.AreEqual(new List<string> {"#channel", "hello world"}, line.Params);
|
CollectionAssert.AreEqual(new List<string> { "#channel", "hello world" }, line.Params);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
|
@ -1,10 +1,9 @@
|
||||||
using System;
|
using IrcTokens;
|
||||||
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Net.Sockets;
|
using System.Net.Sockets;
|
||||||
using System.Text;
|
|
||||||
using IrcTokens;
|
|
||||||
|
|
||||||
namespace Sample
|
namespace TokensSample
|
||||||
{
|
{
|
||||||
public class Client
|
public class Client
|
||||||
{
|
{
|
||||||
|
@ -25,15 +24,15 @@ namespace Sample
|
||||||
{
|
{
|
||||||
_socket.Connect("127.0.0.1", 6667);
|
_socket.Connect("127.0.0.1", 6667);
|
||||||
|
|
||||||
Send(new Line {Command = "USER", Params = new List<string> {"username", "0", "*", "real name"}});
|
Send(new Line { Command = "USER", Params = new List<string> { "username", "0", "*", "real name" } });
|
||||||
Send(new Line {Command = "NICK", Params = new List<string> {"statefulbot"}});
|
Send(new Line { Command = "NICK", Params = new List<string> { "tokensbot" } });
|
||||||
|
|
||||||
while (true)
|
while (true)
|
||||||
{
|
{
|
||||||
var bytesReceived = _socket.Receive(_bytes);
|
var bytesReceived = _socket.Receive(_bytes);
|
||||||
var lines = _decoder.Push(_bytes);
|
var lines = _decoder.Push(_bytes);
|
||||||
|
|
||||||
if (lines.Count == 0)
|
if (bytesReceived == 0)
|
||||||
{
|
{
|
||||||
Console.WriteLine("! disconnected");
|
Console.WriteLine("! disconnected");
|
||||||
_socket.Shutdown(SocketShutdown.Both);
|
_socket.Shutdown(SocketShutdown.Both);
|
||||||
|
@ -47,10 +46,10 @@ namespace Sample
|
||||||
switch (line.Command)
|
switch (line.Command)
|
||||||
{
|
{
|
||||||
case "PING":
|
case "PING":
|
||||||
Send(new Line {Command = "PONG", Params = line.Params});
|
Send(new Line { Command = "PONG", Params = line.Params });
|
||||||
break;
|
break;
|
||||||
case "001":
|
case "001":
|
||||||
Send(new Line {Command = "JOIN", Params = new List<string> {"#channel"}});
|
Send(new Line { Command = "JOIN", Params = new List<string> { "#channel" } });
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -62,7 +61,9 @@ namespace Sample
|
||||||
Console.WriteLine($"> {line.Format()}");
|
Console.WriteLine($"> {line.Format()}");
|
||||||
_encoder.Push(line);
|
_encoder.Push(line);
|
||||||
while (_encoder.PendingBytes.Length > 0)
|
while (_encoder.PendingBytes.Length > 0)
|
||||||
|
{
|
||||||
_encoder.Pop(_socket.Send(_encoder.PendingBytes));
|
_encoder.Pop(_socket.Send(_encoder.PendingBytes));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,8 +1,8 @@
|
||||||
using System;
|
using IrcTokens;
|
||||||
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using IrcTokens;
|
|
||||||
|
|
||||||
namespace Sample
|
namespace TokensSample
|
||||||
{
|
{
|
||||||
public class Program
|
public class Program
|
||||||
{
|
{
|
||||||
|
@ -17,7 +17,7 @@ namespace Sample
|
||||||
var line2 = new Line
|
var line2 = new Line
|
||||||
{
|
{
|
||||||
Command = "USER",
|
Command = "USER",
|
||||||
Params = new List<string> {"user", "0", "*", "real name"}
|
Params = new List<string> { "user", "0", "*", "real name" }
|
||||||
};
|
};
|
||||||
Console.WriteLine(line2);
|
Console.WriteLine(line2);
|
||||||
Console.WriteLine(line2.Format());
|
Console.WriteLine(line2.Format());
|
||||||
|
|
|
@ -0,0 +1,12 @@
|
||||||
|
using System;
|
||||||
|
|
||||||
|
namespace StatesSample
|
||||||
|
{
|
||||||
|
public static class Program
|
||||||
|
{
|
||||||
|
private static void Main(string[] args)
|
||||||
|
{
|
||||||
|
Console.WriteLine("Hello World!");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,12 @@
|
||||||
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
|
<PropertyGroup>
|
||||||
|
<OutputType>Exe</OutputType>
|
||||||
|
<TargetFramework>netcoreapp3.1</TargetFramework>
|
||||||
|
</PropertyGroup>
|
||||||
|
|
||||||
|
<ItemGroup>
|
||||||
|
<ProjectReference Include="..\IrcStates\IrcStates.csproj" />
|
||||||
|
</ItemGroup>
|
||||||
|
|
||||||
|
</Project>
|
Loading…
Reference in New Issue