From 9d1660270272180cd71147d6ddd53d1382643d2e Mon Sep 17 00:00:00 2001
From: wenxiangchao <wenxiangchao@ihengxin.com.cn>
Date: 星期一, 02 十一月 2026 18:00:14 +0800
Subject: [PATCH] merge: 并入远程 Initial commit 作为历史根节点

---
 ConnectionUtil/TcpClient.cs |  254 ++++++++++++++++++++++++++++++++++++++++++++++++++
 1 files changed, 254 insertions(+), 0 deletions(-)

diff --git a/ConnectionUtil/TcpClient.cs b/ConnectionUtil/TcpClient.cs
new file mode 100644
index 0000000..33d6f72
--- /dev/null
+++ b/ConnectionUtil/TcpClient.cs
@@ -0,0 +1,254 @@
+锘縰sing System;
+using System.Net.Sockets;
+using System.Text;
+using System.Threading;
+using System.Threading.Tasks;
+
+namespace ConnectionUtil
+{
+    /// <summary>
+    /// TCP瀹㈡埛绔寘瑁呯被
+    /// </summary>
+    /// <summary>
+    /// TCP瀹㈡埛绔寘瑁呯被
+    /// </summary>
+    public class TcpClientWrapper : IDisposable
+    {
+        private System.Net.Sockets.TcpClient _client;
+        private NetworkStream _stream;
+        private readonly string _host;
+        private readonly int _port;
+        private bool _isConnected;
+        private readonly CancellationTokenSource _cts;
+        private Task _heartbeatTask;
+        private readonly SemaphoreSlim _sendReceiveLock;
+
+        /// <summary>
+        /// 鍒濆鍖朤CP瀹㈡埛绔�
+        /// </summary>
+        /// <param name="host">鏈嶅姟鍣ㄥ湴鍧�</param>
+        /// <param name="port">鏈嶅姟鍣ㄧ鍙�</param>
+        public TcpClientWrapper(string host = "127.0.0.1", int port = 6543)
+        {
+            _host = host;
+            _port = port;
+            _cts = new CancellationTokenSource();
+            _sendReceiveLock = new SemaphoreSlim(1, 1);
+        }
+
+        /// <summary>
+        /// 寮傛杩炴帴鍒版湇鍔″櫒
+        /// </summary>
+        /// <returns>杩炴帴鏄惁鎴愬姛</returns>
+        public async Task<bool> ConnectAsync()
+        {
+            try
+            {
+                _client = new System.Net.Sockets.TcpClient();
+                await _client.ConnectAsync(_host, _port);
+                _stream = _client.GetStream();
+                _isConnected = true;
+
+                // 鍚姩蹇冭烦浠诲姟
+                _heartbeatTask = StartHeartbeatAsync(_cts.Token);
+
+                Console.WriteLine($"鎴愬姛杩炴帴鍒版湇鍔″櫒 {_host}:{_port}");
+                return true;
+            }
+            catch (Exception ex)
+            {
+                Console.WriteLine($"杩炴帴鏈嶅姟鍣ㄥけ璐ワ細{ex.Message}");
+                return false;
+            }
+        }
+
+        /// <summary>
+        /// 鍚屾杩炴帴鍒版湇鍔″櫒
+        /// </summary>
+        /// <returns>杩炴帴鏄惁鎴愬姛</returns>
+        public bool Connect()
+        {
+            try
+            {
+                _client = new System.Net.Sockets.TcpClient();
+                _client.Connect(_host, _port);
+                _stream = _client.GetStream();
+                _isConnected = true;
+
+                // 鍚姩蹇冭烦浠诲姟
+                _heartbeatTask = StartHeartbeatAsync(_cts.Token);
+                return true;
+            }
+            catch (Exception ex)
+            {
+                Console.WriteLine($"杩炴帴鏈嶅姟鍣ㄥけ璐ワ細{ex.Message}");
+                return false;
+            }
+        }
+
+        /// <summary>
+        /// 鍚姩蹇冭烦妫�娴�
+        /// </summary>
+        private async Task StartHeartbeatAsync(CancellationToken token)
+        {
+            while (!token.IsCancellationRequested && _isConnected)
+            {
+                try
+                {
+                    await Task.Delay(20000, token); // 20绉掑彂閫佷竴娆″績璺�
+                    if (_isConnected)
+                    {
+                        await SendMessageAsync("ping");
+                    }
+                }
+                catch (OperationCanceledException)
+                {
+                    break;
+                }
+                catch (Exception)
+                {
+                    _isConnected = false;
+                    break;
+                }
+            }
+        }
+
+        /// <summary>
+        /// 鍙戦�佹秷鎭苟鎺ユ敹鍝嶅簲
+        /// </summary>
+        /// <typeparam name="T">鍝嶅簲鏁版嵁绫诲瀷</typeparam>
+        /// <param name="data">瑕佸彂閫佺殑鏁版嵁瀵硅薄</param>
+        /// <param name="timeout">瓒呮椂鏃堕棿</param>
+        /// <returns>鏈嶅姟鍣ㄥ搷搴旀暟鎹�</returns>
+        public async Task<string> SendMessageAsync(string message, TimeSpan? timeout = null)
+        {
+            if (!_isConnected)
+            {
+                throw new InvalidOperationException("鏈繛鎺ュ埌鏈嶅姟鍣�");
+            }
+
+            TimeSpan actualTimeout = timeout ?? TimeSpan.FromSeconds(30);
+
+            if (!await _sendReceiveLock.WaitAsync(actualTimeout))
+            {
+                throw new TimeoutException("绛夊緟鍙戦�佽秴鏃�");
+            }
+
+            try
+            {
+                byte[] messageBytes = Encoding.UTF8.GetBytes(message + "\r\n");
+
+                // 鍙戦�佹秷鎭�
+                await _stream.WriteAsync(messageBytes, 0, messageBytes.Length);
+
+                // 鎺ユ敹鍝嶅簲
+                byte[] buffer = new byte[1024];
+                StringBuilder response = new StringBuilder();
+                int bytesRead;
+
+                CancellationTokenSource cts = new CancellationTokenSource(actualTimeout);
+
+                try
+                {
+                    // 璇诲彇鐩村埌閬囧埌鎹㈣绗�
+                    while ((bytesRead = await _stream.ReadAsync(buffer, 0, buffer.Length)) > 0)
+                    {
+                        string received = Encoding.UTF8.GetString(buffer, 0, bytesRead);
+                        response.Append(received);
+
+                        if (received.EndsWith("\r\n"))
+                        {
+                            break;
+                        }
+
+                        if (cts.Token.IsCancellationRequested)
+                        {
+                            throw new TimeoutException("鎺ユ敹鍝嶅簲瓒呮椂");
+                        }
+                    }
+                }
+                finally
+                {
+                    cts.Dispose();
+                }
+
+                string jsonResponse = response.ToString().TrimEnd('\r', '\n');
+                Console.WriteLine($"鏀跺埌鏈嶅姟鍣ㄥ搷搴旓細{jsonResponse}");
+
+                // 鍙嶅簭鍒楀寲鍝嶅簲
+                return jsonResponse;
+            }
+            catch (Exception ex)
+            {
+                Console.WriteLine($"鍙戦�佹秷鎭け璐ワ細{ex.Message}");
+                _isConnected = false;
+                throw;
+            }
+            finally
+            {
+                _sendReceiveLock.Release();
+            }
+        }
+
+        /// <summary>
+        /// 鍚屾鍙戦�佹秷鎭苟鎺ユ敹鍝嶅簲
+        /// </summary>
+        /// <typeparam name="T">鍝嶅簲鏁版嵁绫诲瀷</typeparam>
+        /// <param name="data">瑕佸彂閫佺殑鏁版嵁瀵硅薄</param>
+        /// <param name="timeout">瓒呮椂鏃堕棿</param>
+        /// <returns>鏈嶅姟鍣ㄥ搷搴旀暟鎹�</returns>
+        public string SendMessage(string message, TimeSpan? timeout = null)
+        {
+            timeout = timeout ?? TimeSpan.FromSeconds(30);
+
+            try
+            {
+                // 浣跨敤 Task.Run 鏉ユ墽琛屽紓姝ユ搷浣滐紝骞剁瓑寰呯粨鏋�
+                return Task.Run(() => SendMessageAsync(message, timeout)).Result;
+            }
+            catch (AggregateException ae)
+            {
+                // 瑙e寘寮傚父
+                throw ae.InnerException;
+            }
+        }
+
+        /// <summary>
+        /// 妫�鏌ユ槸鍚﹀凡杩炴帴
+        /// </summary>
+        public bool IsConnected
+        {
+            get { return _isConnected; }
+        }
+
+        /// <summary>
+        /// 閲婃斁璧勬簮
+        /// </summary>
+        public void Dispose()
+        {
+            _cts.Cancel();
+            _isConnected = false;
+            if (_stream != null)
+            {
+                _stream.Dispose();
+            }
+            if (_client != null)
+            {
+                _client.Dispose();
+            }
+            _cts.Dispose();
+            if (_sendReceiveLock != null)
+            {
+                _sendReceiveLock.Dispose();
+            }
+        }
+
+        /// <summary>
+        /// 鍏抽棴杩炴帴
+        /// </summary>
+        public void Close()
+        {
+            Dispose();
+        }
+    }
+}

--
Gitblit v1.9.1