This commit is contained in:
CortexCore
2024-06-20 17:28:56 +08:00
parent 554af9ca4e
commit 0423dc7c48
6 changed files with 213 additions and 73 deletions

View File

@@ -22,6 +22,7 @@ namespace BITKit.Net
public event Action OnDisconnected;
public event Action OnConnectedFailed;
public bool IsConnected => _isConnected;
public bool IsConnecting { get; private set; }
public float2 Traffic { get; set; }
public bool ManualTick { get; set; }
@@ -51,6 +52,7 @@ namespace BITKit.Net
private DateTime _now = DateTime.Now;
private TimeSpan _interval = TimeSpan.FromMilliseconds(100);
private readonly byte[] _heartBeat = new byte[] { (byte)NetCommandType.Heartbeat };
public KcpNetClient()
{
client = new KcpClient(
@@ -80,7 +82,7 @@ namespace BITKit.Net
else
{
OnDisconnected?.Invoke();
BIT4Log.Warning<KcpNetClient>("连接已断开");
BIT4Log.Log<KcpNetClient>("连接已断开");
}
}
@@ -105,6 +107,9 @@ namespace BITKit.Net
public async UniTask<bool> Connect(string address = "127.0.0.1", ushort port = 27014)
{
if (IsConnecting) return false;
IsConnecting = true;
if (client.connected) return false;
if (BITApp.SynchronizationContext is not null)
await UniTask.SwitchToSynchronizationContext(BITApp.SynchronizationContext, BITApp.CancellationToken);
OnStartConnect?.Invoke();
@@ -120,29 +125,39 @@ namespace BITKit.Net
// client.Tick();
// await Task.Delay(100);
// }
//_commandQueue.Enqueue(new []{(byte)NetCommandType.Heartbeat });
_commandQueue.Enqueue(new []{(byte)NetCommandType.Heartbeat });
//client.Send(new []{(byte)NetCommandType.Heartbeat }, KcpChannel.Reliable);
HandShake();
if (BITApp.SynchronizationContext is not null)
await UniTask.SwitchToSynchronizationContext(BITApp.SynchronizationContext);
if (client.connected)
{
SendServerMessage(Environment.MachineName);
Traffic+=new float2(1,0);
_commandQueue.Enqueue(new []{(byte)NetCommandType.Heartbeat});
}
Traffic += new float2(1, 0);
//_commandQueue.Enqueue(new []{(byte)NetCommandType.Heartbeat});
for (var i = 0; i < 5; i++)
{
client.Send(new []{(byte)NetCommandType.Heartbeat }, KcpChannel.Reliable);
client.Tick();
await Task.Delay(100);
}
if (client.connected is false)
if (client.connected)
{
OnConnectedFailed?.Invoke();
Disconnect();
return false;
SendServerMessage(Environment.MachineName);
IsConnecting = false;
return client.connected;
}
return client.connected;
OnConnectedFailed?.Invoke();
Disconnect();
IsConnecting = false;
return false;
}
catch (Exception e)
{
@@ -151,6 +166,8 @@ namespace BITKit.Net
await UniTask.SwitchToSynchronizationContext(BITApp.SynchronizationContext);
OnConnectedFailed?.Invoke();
_timer.Stop();
IsConnecting = false;
return false;
}
}
@@ -201,8 +218,10 @@ namespace BITKit.Net
break;
case NetCommandType.Heartbeat:
_commandQueue.Enqueue(new []{(byte)NetCommandType.Heartbeat });
_isConnected.AddElement(this);
if (Id is not -1)
{
_isConnected.AddElement(this);
}
_lastHeartbeat = DateTime.Now;
break;
case NetCommandType.Ping:
@@ -299,6 +318,21 @@ namespace BITKit.Net
BIT4Log.LogException(e);
}
break;
case NetCommandType.AllRpc:
case NetCommandType.TargetRpc:
{
var rpcName = reader.ReadString();
if (_rpcMethods.TryGetValue(rpcName, out var methodInfo))
{
var pars = BITBinary.Read(reader).As<object[]>();
methodInfo.Invoke(_rpcHandles[rpcName], pars);
}
else
{
BIT4Log.Warning<KcpClient>($"未找到对应的Rpc方法:{rpcName}");
}
}
break;
default:
BIT4Log.Log<KcpClient>($"未知消息类型:{type},字节:{(byte)type}");
if (bytes.Array != null)
@@ -318,7 +352,7 @@ namespace BITKit.Net
private async void OnDisconnectInternal()
{
BIT4Log.Log<KcpNetClient>("连接被断开");
//BIT4Log.Log<KcpNetClient>("连接被断开");
Disconnect();
}
private void OnError(ErrorCode errorCode, string message)
@@ -357,10 +391,10 @@ namespace BITKit.Net
public async UniTask<T> GetFromServer<T>(string path = default,params object[] pars)
{
await UniTask.SwitchToThreadPool();
//await UniTask.SwitchToThreadPool();
var id = _index++;
using var ms = new MemoryStream();
await using var writer = new BinaryWriter(ms);
var ms = new MemoryStream();
var writer = new BinaryWriter(ms);
writer.Write((byte)NetCommandType.GetFromServer);
writer.Write(id);
if (string.IsNullOrEmpty(path))
@@ -375,14 +409,27 @@ namespace BITKit.Net
BITBinary.Write(writer,pars);
var bytes = ms.ToArray();
await ms.DisposeAsync();
await writer.DisposeAsync();
_commandQueue.Enqueue(bytes);
var startTime = _now;
while (true)
{
if((_now-startTime).TotalSeconds>5 || IsConnected is false)
throw new TimeoutException("请求超时或已断开连接");
if ((_now - startTime).TotalSeconds > 5 || IsConnected is false)
{
//await BITApp.SwitchToMainThread();
if (string.IsNullOrEmpty(path))
{
throw new TimeoutException("请求超时或已断开连接");
}
throw new TimeoutException($"请求超时或已断开连接,请求为{path}");
}
if (_p2p.TryRemove(id, out var value))
{
@@ -493,19 +540,29 @@ namespace BITKit.Net
try
{
_now = DateTime.UtcNow;
if (IsConnected)
if (client.connected)
{
if (DateTime.Now - _lastHeartbeat > TimeSpan.FromSeconds(5))
{
BIT4Log.Warning<KcpNetClient>("心跳超时,自动断开");
Disconnect();
_commandQueue.Clear();
return;
}
while (_commandQueue.TryDequeue(out var bytes))
{
Traffic += new float2(bytes.Length, 0);
client.Send(bytes, KcpChannel.Reliable);
}
client.Send(_heartBeat, KcpChannel.Unreliable);
}
while (_commandQueue.TryDequeue(out var bytes))
else
{
Traffic+=new float2(bytes.Length,0);
client.Send(bytes, KcpChannel.Reliable);
if (_commandQueue.Count > 0)
{
_commandQueue.Clear();
//BIT4Log.Warning<KcpNetClient>("连接已断开,清空指令队列");
}
}
#if UNITY_EDITOR