using SuperSocket.ClientEngine; using System.Net; using System.Text; using Vbdsm.Gen; using Vbdsm.Settings; namespace Vbdsm.SocketClients { public class TpcClient { private Dictionary Clients { get; } private int MaxErrorCount { get; } private int MinuteInterval => 5; private long LastRequestTime { get; set; } private int ErrorCount { get; set; } private string? ClientId { get; } private string TerminalIds { get; } public TpcClient(string? clientId, string terminalIds) { Clients = GenClients(); MaxErrorCount = AppSetting.Instance.MaxErrorCount; ClientId = clientId; TerminalIds = terminalIds; //LastRequestTime = CalcCurrentTime(); } private Dictionary GenClients() { var clients = new Dictionary(); foreach (var server in AppSetting.Instance.Servers) { var key = $"{server.Ip}:{server.Port}"; if (!clients.ContainsKey(key)) { var client = InitClient(key); clients.Add(key, client); } } return clients; } private AsyncTcpSession InitClient(string key, AsyncTcpSession? client = null) { if (client != null) client.Close(); client = new AsyncTcpSession(); try { var arr = key.Split(':'); var ip = arr[0]; var port = arr[1]; if (arr.Length < 2) { return client; } // 连接断开事件 client.Closed += (sender, _) => { client = sender as AsyncTcpSession; string message = $"[{DateTime.Now}] :客户端【{ClientId}】【{ip}:{port}】连接断开。"; Console.WriteLine(message); }; // 收到服务器数据事件 client.DataReceived += (_, e) => { string msg = Encoding.Default.GetString(e.Data, 0, e.Length).ToString().Replace("\r\n", ""); string message = $"[{DateTime.Now}] 客户端【{ClientId}】【{ip}:{port}】接受消息 => {msg}。"; Console.WriteLine(message); }; // 连接到服务器事件 client.Connected += (_, _) => { string message = $"[{DateTime.Now}] 客户端【{ClientId}】【{ip}:{port}】连接成功。"; Console.WriteLine(message); }; // 发生错误的处理 client.Error += (_, e) => { string message = $"[{DateTime.Now}] 客户端【{ClientId}】【{ip}:{port}】错误 => {e.Exception.Message}"; Console.WriteLine(message); }; client.Connect(new IPEndPoint(IPAddress.Parse(ip), Convert.ToInt16(port))); } catch (Exception e) { Console.WriteLine(e.Message); } return client; } public void Run() { try { Console.WriteLine($"[{DateTime.Now}] 客户端【{ClientId}@{TerminalIds}】开始运行"); // 创建连接 Thread.Sleep(2000); while (true) { Console.Write("."); Send(); Thread.Sleep(2 * 1000); } } catch (Exception e) { Console.WriteLine(e.Message); } } public void ReSend() { Console.WriteLine($"[{DateTime.Now}] 客户端【{ClientId}】 手动触发 ==>"); Send(false); } private void Send(bool needCheck = true) { if (ErrorCount >= MaxErrorCount || needCheck && !CheckSend()) { return; } try { LastRequestTime = CalcCurrentTime(); string str = new GenData(TerminalIds, ClientId).GenTerminals(LastRequestTime); if (string.IsNullOrEmpty(str)) { Console.WriteLine($"\r\n[{DateTime.Now}] 客户端【{ClientId}】[{LastRequestTime}] 已发送过数据! "); return; } Console.WriteLine($"\r\n[{DateTime.Now}] 客户端【{ClientId}】发送数据[{LastRequestTime}] ==> {str}"); byte[] bytes = Encoding.UTF8.GetBytes(str); foreach (var kv in Clients) { ErrorCount = 0; Send(kv, bytes); } } catch (Exception e) { ErrorCount++; Console.WriteLine(e); } } private void Send(KeyValuePair keyValue, byte[] bytes) { var client = keyValue.Value; if (client.IsConnected) { Console.WriteLine($"[{DateTime.Now}] 客户端【{ClientId}】【{keyValue.Key}】发送数据"); client.Send(bytes, 0, bytes.Length); } else { client = InitClient(keyValue.Key, client); Clients.Remove(keyValue.Key); Clients.Add(keyValue.Key, client); ErrorCount++; Console.WriteLine($"[{DateTime.Now}] 客户端【{ClientId}】【{keyValue.Key}】连接失败 ==> {ErrorCount}/{MaxErrorCount}"); Thread.Sleep(2 * 1000); if (ErrorCount <= MaxErrorCount) { Send(keyValue, bytes); } } } private bool CheckSend() { var time = CalcCurrentTime() - LastRequestTime; return time > 0; } private long CalcCurrentTime() { //long time = Convert.ToInt64($"{DateTime.Now:yyyyMMddHH}{(DateTime.Now.Minute - DateTime.Now.Minute % minuteInterval):D2}00"); long time = Convert.ToInt64($"{DateTime.Now:yyyyMMddHHmm00}"); time -= (time - (time / 10000) * 10000) % (MinuteInterval * 100); return time; } } }