AsyncTcpSocket使用实例
AsyncTcpSocket是一个非常好的异步tcp封装类,比较原始的封装,缺少丢包和粘包处理,我在这个实例中把它加上了,我用.net core 3.1 重新编译了AsyncTcpSocket类库,完全可以使用,并用.net core 3.1下的winform搭了一个服务端和客户端,用作Demo,在这里分享一下。
1. 源代码下载
2. 粘包丢包处理
原理挺简单,就是发送时先计算待发送字符串的字节长度,然后把长度值放在待发送字节的头部,接收消息的时候,先计算所接收的消息头部的长度,再截取该长度的数据,就OK了。
/// <summary>
/// 待发送字符串加长度头后转字节数组
/// </summary>
/// <param name="sendMsg">待转换字符串</param>
/// <returns></returns>
public static byte[] ConvertToByteData(string sendMsg)
{
byte[] data = Encoding.UTF8.GetBytes(sendMsg);
byte[] sendData = new byte[sizeof(int)+ data.Length];
byte[] dataLen = BitConverter.GetBytes(data.Length);
sendData = dataLen.Concat(data).ToArray();
return sendData;
}
/// <summary>
/// 收到的字节数组还原成消息字符串
/// </summary>
/// <param name="receiveData">待转换消息字节数组</param>
/// <returns></returns>
public static string ConvertToStrData(byte[] receiveData)
{
string receiveStr = string.Empty;
byte[] dataLen = receiveData.Take(sizeof(int)).ToArray();
int msgLen = BitConverter.ToInt32(dataLen);
byte[] receiveMsg = receiveData.Skip(sizeof(int)).Take(msgLen).ToArray();
receiveStr = Encoding.UTF8.GetString(receiveMsg);
return receiveStr;
}
3. 服务端代码
很简单,基本就是连接事件,断开事件,发送事件,接收事件
AsyncTcpServer server;
TcpClient client;
// 连接事件
void server_ClientConnected(object sender, TcpClientConnectedEventArgs e)
{
client = e.TcpClient;
}
// 断开事件
void server_ClientDisconnected(object sender, TcpClientDisconnectedEventArgs e)
{
}
// 接收数据事件
void server_DatagramReceived(object sender, TcpDatagramReceivedEventArgs<byte[]> e)
{
string receiveMsg = NetworkHelp.ConvertToStrData(e.Datagram);
server.Send(e.TcpClient,
ConvertToByteData("Server has received you text : "+
System.Environment.NewLine +
receiveMsg));
}
server = new AsyncTcpServer(ServerPort);
server.Encoding = Encoding.UTF8;
server.ClientConnected +=
new EventHandler<TcpClientConnectedEventArgs>(server_ClientConnected);
server.ClientDisconnected +=
new EventHandler<TcpClientDisconnectedEventArgs>(server_ClientDisconnected);
server.DatagramReceived +=
new EventHandler<TcpDatagramReceivedEventArgs<byte[]>>(server_DatagramReceived);
// 开启服务
server.Start();
// 关闭服务
server.Stop();
// 发送数据
byte[] sendData = ConvertToByteData(this.tbSend.Text);
server.Send(client,sendData);
4. 客户端代码
AsyncTcpClient client;
// 异常发生事件
void client_ServerExceptionOccurred(object sender, TcpServerExceptionOccurredEventArgs e)
{
string msg=string.Format(CultureInfo.InvariantCulture,
"TCP server {0} exception occurred, {1}." +
System.Environment.NewLine, e.ToString(),
e.Exception.Message);
}
// 连接事件
void client_ServerConnected(object sender, TcpServerConnectedEventArgs e)
{
}
// 断开事件
void client_ServerDisconnected( object sender, TcpServerDisconnectedEventArgs e)
{
}
// 接收事件
void client_DatagramReceived(object sender, TcpDatagramReceivedEventArgs<byte[]> e)
{
string receiveMsg = NetworkHelp.ConvertToStrData(e.Datagram);
}
client = new AsyncTcpClient(remoteEP);
client.Encoding = Encoding.UTF8;
client.ServerExceptionOccurred +=
new EventHandler<TcpServerExceptionOccurredEventArgs>(client_ServerExceptionOccurred);
client.ServerConnected +=
new EventHandler<TcpServerConnectedEventArgs>(client_ServerConnected);
client.ServerDisconnected +=
new EventHandler<TcpServerDisconnectedEventArgs>(client_ServerDisconnected);
client.DatagramReceived +=
new EventHandler<TcpDatagramReceivedEventArgs<byte[]>>(client_DatagramReceived);
// 连接
client.Connect();
// 关闭连接
client.Close();
// 发送数据
byte[] sendData=ConvertToByteData(this.tbSend.Text);
client.Send(sendData);