mirror of
https://gitee.com/ThingsGateway/ThingsGateway.git
synced 2025-10-21 03:01:28 +08:00
Compare commits
8 Commits
Author | SHA1 | Date | |
---|---|---|---|
![]() |
c27dde085e | ||
![]() |
d26cc308c0 | ||
![]() |
fb1efdf290 | ||
![]() |
3c99f2a472 | ||
![]() |
affe9a44e0 | ||
![]() |
43730fa519 | ||
![]() |
d39aa22b09 | ||
![]() |
e232a6b6ea |
@@ -1,6 +1,6 @@
|
||||
<Project>
|
||||
<PropertyGroup>
|
||||
<Version>3.0.0.20</Version>
|
||||
<Version>3.0.0.23</Version>
|
||||
<LangVersion>latest</LangVersion>
|
||||
<TargetFrameworks>net6.0;net7.0</TargetFrameworks>
|
||||
<Authors>Diego</Authors>
|
||||
|
@@ -1,6 +1,6 @@
|
||||
<Project>
|
||||
<PropertyGroup>
|
||||
<Version>3.0.0.20</Version>
|
||||
<Version>3.0.0.23</Version>
|
||||
<GenerateDocumentationFile>True</GenerateDocumentationFile>
|
||||
<LangVersion>latest</LangVersion>
|
||||
<TargetFrameworks>net45;netstandard2.0;net6.0;net7.0</TargetFrameworks>
|
||||
|
@@ -101,62 +101,76 @@ public class ModbusSerialServer : ReadWriteDevicesSerialSessionBase
|
||||
return PackHelper.LoadSourceRead<T, T2>(this, deviceVariables, maxPack);
|
||||
|
||||
}
|
||||
|
||||
EasyLock easyLock = new();
|
||||
|
||||
|
||||
/// <inheritdoc/>
|
||||
public override OperResult<byte[]> Read(string address, int length, CancellationToken cancellationToken = default)
|
||||
{
|
||||
ModbusAddress mAddress;
|
||||
try
|
||||
{
|
||||
mAddress = ModbusAddress.ParseFrom(address, Station);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
return new OperResult<byte[]>(ex);
|
||||
}
|
||||
if (MulStation)
|
||||
{
|
||||
Init(mAddress);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (Station != mAddress.Station)
|
||||
easyLock.Wait();
|
||||
|
||||
ModbusAddress mAddress;
|
||||
try
|
||||
{
|
||||
return new OperResult<byte[]>("地址错误");
|
||||
mAddress = ModbusAddress.ParseFrom(address, Station);
|
||||
}
|
||||
Init(mAddress);
|
||||
catch (Exception ex)
|
||||
{
|
||||
return new OperResult<byte[]>(ex);
|
||||
}
|
||||
if (MulStation)
|
||||
{
|
||||
Init(mAddress);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (Station != mAddress.Station)
|
||||
{
|
||||
return new OperResult<byte[]>("地址错误");
|
||||
}
|
||||
Init(mAddress);
|
||||
|
||||
}
|
||||
|
||||
var ModbusServer01ByteBlock = ModbusServer01ByteBlocks[mAddress.Station];
|
||||
var ModbusServer02ByteBlock = ModbusServer02ByteBlocks[mAddress.Station];
|
||||
var ModbusServer03ByteBlock = ModbusServer03ByteBlocks[mAddress.Station];
|
||||
var ModbusServer04ByteBlock = ModbusServer04ByteBlocks[mAddress.Station];
|
||||
int len = mAddress.ReadFunction == 2 || mAddress.ReadFunction == 1 ? length : length * RegisterByteLength;
|
||||
switch (mAddress.ReadFunction)
|
||||
{
|
||||
case 1:
|
||||
byte[] bytes0 = new byte[len];
|
||||
ModbusServer01ByteBlock.Pos = mAddress.AddressStart;
|
||||
ModbusServer01ByteBlock.Read(bytes0);
|
||||
return OperResult.CreateSuccessResult(bytes0);
|
||||
case 2:
|
||||
byte[] bytes1 = new byte[len];
|
||||
ModbusServer02ByteBlock.Pos = mAddress.AddressStart;
|
||||
ModbusServer02ByteBlock.Read(bytes1);
|
||||
return OperResult.CreateSuccessResult(bytes1);
|
||||
case 3:
|
||||
|
||||
byte[] bytes3 = new byte[len];
|
||||
ModbusServer03ByteBlock.Pos = mAddress.AddressStart * RegisterByteLength;
|
||||
ModbusServer03ByteBlock.Read(bytes3);
|
||||
return OperResult.CreateSuccessResult(bytes3);
|
||||
case 4:
|
||||
byte[] bytes4 = new byte[len];
|
||||
ModbusServer04ByteBlock.Pos = mAddress.AddressStart * RegisterByteLength;
|
||||
ModbusServer04ByteBlock.Read(bytes4);
|
||||
return OperResult.CreateSuccessResult(bytes4);
|
||||
}
|
||||
return new OperResult<byte[]>("功能码错误");
|
||||
}
|
||||
|
||||
var ModbusServer01ByteBlock = ModbusServer01ByteBlocks[mAddress.Station];
|
||||
var ModbusServer02ByteBlock = ModbusServer02ByteBlocks[mAddress.Station];
|
||||
var ModbusServer03ByteBlock = ModbusServer03ByteBlocks[mAddress.Station];
|
||||
var ModbusServer04ByteBlock = ModbusServer04ByteBlocks[mAddress.Station];
|
||||
int len = mAddress.ReadFunction == 2 || mAddress.ReadFunction == 1 ? length : length * RegisterByteLength;
|
||||
switch (mAddress.ReadFunction)
|
||||
finally
|
||||
{
|
||||
case 1:
|
||||
byte[] bytes0 = new byte[len];
|
||||
ModbusServer01ByteBlock.Pos = mAddress.AddressStart;
|
||||
ModbusServer01ByteBlock.Read(bytes0);
|
||||
return OperResult.CreateSuccessResult(bytes0);
|
||||
case 2:
|
||||
byte[] bytes1 = new byte[len];
|
||||
ModbusServer02ByteBlock.Pos = mAddress.AddressStart;
|
||||
ModbusServer02ByteBlock.Read(bytes1);
|
||||
return OperResult.CreateSuccessResult(bytes1);
|
||||
case 3:
|
||||
|
||||
byte[] bytes3 = new byte[len];
|
||||
ModbusServer03ByteBlock.Pos = mAddress.AddressStart * RegisterByteLength;
|
||||
ModbusServer03ByteBlock.Read(bytes3);
|
||||
return OperResult.CreateSuccessResult(bytes3);
|
||||
case 4:
|
||||
byte[] bytes4 = new byte[len];
|
||||
ModbusServer04ByteBlock.Pos = mAddress.AddressStart * RegisterByteLength;
|
||||
ModbusServer04ByteBlock.Read(bytes4);
|
||||
return OperResult.CreateSuccessResult(bytes4);
|
||||
easyLock.Release();
|
||||
}
|
||||
return new OperResult<byte[]>("功能码错误");
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
@@ -173,87 +187,108 @@ public class ModbusSerialServer : ReadWriteDevicesSerialSessionBase
|
||||
SerialSession.SetDataHandlingAdapter(dataHandleAdapter);
|
||||
}
|
||||
|
||||
|
||||
/// <inheritdoc/>
|
||||
public override OperResult Write(string address, byte[] value, CancellationToken cancellationToken = default)
|
||||
{
|
||||
ModbusAddress mAddress;
|
||||
try
|
||||
{
|
||||
mAddress = ModbusAddress.ParseFrom(address, Station);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
return new OperResult(ex);
|
||||
}
|
||||
if (MulStation)
|
||||
{
|
||||
Init(mAddress);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (Station != mAddress.Station)
|
||||
easyLock.Wait();
|
||||
ModbusAddress mAddress;
|
||||
try
|
||||
{
|
||||
return new OperResult("地址错误");
|
||||
mAddress = ModbusAddress.ParseFrom(address, Station);
|
||||
}
|
||||
Init(mAddress);
|
||||
catch (Exception ex)
|
||||
{
|
||||
return new OperResult(ex);
|
||||
}
|
||||
if (MulStation)
|
||||
{
|
||||
Init(mAddress);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (Station != mAddress.Station)
|
||||
{
|
||||
return new OperResult("地址错误");
|
||||
}
|
||||
Init(mAddress);
|
||||
}
|
||||
var ModbusServer03ByteBlock = ModbusServer03ByteBlocks[mAddress.Station];
|
||||
var ModbusServer04ByteBlock = ModbusServer04ByteBlocks[mAddress.Station];
|
||||
switch (mAddress.ReadFunction)
|
||||
{
|
||||
case 3:
|
||||
ModbusServer03ByteBlock.Pos = mAddress.AddressStart * RegisterByteLength;
|
||||
ModbusServer03ByteBlock.Write(value);
|
||||
return OperResult.CreateSuccessResult();
|
||||
case 4:
|
||||
ModbusServer04ByteBlock.Pos = mAddress.AddressStart * RegisterByteLength;
|
||||
ModbusServer04ByteBlock.Write(value);
|
||||
return OperResult.CreateSuccessResult();
|
||||
}
|
||||
return new OperResult("功能码错误");
|
||||
|
||||
}
|
||||
var ModbusServer03ByteBlock = ModbusServer03ByteBlocks[mAddress.Station];
|
||||
var ModbusServer04ByteBlock = ModbusServer04ByteBlocks[mAddress.Station];
|
||||
switch (mAddress.ReadFunction)
|
||||
finally
|
||||
{
|
||||
case 3:
|
||||
ModbusServer03ByteBlock.Pos = mAddress.AddressStart * RegisterByteLength;
|
||||
ModbusServer03ByteBlock.Write(value);
|
||||
return OperResult.CreateSuccessResult();
|
||||
case 4:
|
||||
ModbusServer04ByteBlock.Pos = mAddress.AddressStart * RegisterByteLength;
|
||||
ModbusServer04ByteBlock.Write(value);
|
||||
return OperResult.CreateSuccessResult();
|
||||
|
||||
easyLock.Release();
|
||||
}
|
||||
return new OperResult("功能码错误");
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
public override OperResult Write(string address, bool[] value, CancellationToken cancellationToken = default)
|
||||
{
|
||||
ModbusAddress mAddress;
|
||||
try
|
||||
{
|
||||
mAddress = ModbusAddress.ParseFrom(address, Station);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
return (new OperResult(ex));
|
||||
}
|
||||
if (MulStation)
|
||||
{
|
||||
Init(mAddress);
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
if (Station != mAddress.Station)
|
||||
easyLock.Wait();
|
||||
ModbusAddress mAddress;
|
||||
try
|
||||
{
|
||||
return (new OperResult("地址错误"));
|
||||
mAddress = ModbusAddress.ParseFrom(address, Station);
|
||||
}
|
||||
Init(mAddress);
|
||||
catch (Exception ex)
|
||||
{
|
||||
return (new OperResult(ex));
|
||||
}
|
||||
if (MulStation)
|
||||
{
|
||||
Init(mAddress);
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
if (Station != mAddress.Station)
|
||||
{
|
||||
return (new OperResult("地址错误"));
|
||||
}
|
||||
Init(mAddress);
|
||||
|
||||
}
|
||||
|
||||
var ModbusServer01ByteBlock = ModbusServer01ByteBlocks[mAddress.Station];
|
||||
var ModbusServer02ByteBlock = ModbusServer02ByteBlocks[mAddress.Station];
|
||||
switch (mAddress.ReadFunction)
|
||||
{
|
||||
case 1:
|
||||
ModbusServer01ByteBlock.Pos = mAddress.AddressStart;
|
||||
ModbusServer01ByteBlock.Write(value.BoolArrayToByte());
|
||||
return (OperResult.CreateSuccessResult());
|
||||
case 2:
|
||||
ModbusServer02ByteBlock.Pos = mAddress.AddressStart;
|
||||
ModbusServer02ByteBlock.Write(value.BoolArrayToByte());
|
||||
return (OperResult.CreateSuccessResult());
|
||||
}
|
||||
return new OperResult("功能码错误");
|
||||
|
||||
}
|
||||
|
||||
var ModbusServer01ByteBlock = ModbusServer01ByteBlocks[mAddress.Station];
|
||||
var ModbusServer02ByteBlock = ModbusServer02ByteBlocks[mAddress.Station];
|
||||
switch (mAddress.ReadFunction)
|
||||
finally
|
||||
{
|
||||
case 1:
|
||||
ModbusServer01ByteBlock.Pos = mAddress.AddressStart;
|
||||
ModbusServer01ByteBlock.Write(value.BoolArrayToByte());
|
||||
return (OperResult.CreateSuccessResult());
|
||||
case 2:
|
||||
ModbusServer02ByteBlock.Pos = mAddress.AddressStart;
|
||||
ModbusServer02ByteBlock.Write(value.BoolArrayToByte());
|
||||
return (OperResult.CreateSuccessResult());
|
||||
|
||||
easyLock.Release();
|
||||
}
|
||||
return new OperResult("功能码错误");
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
|
@@ -186,7 +186,7 @@ public class ModbusTcpDtu : ReadWriteDevicesTcpServerBase
|
||||
var item = commandResult.Content;
|
||||
if (FrameTime != 0)
|
||||
Thread.Sleep(FrameTime);
|
||||
var WaitingClientEx = client.CreateWaitingClient(new() { ThrowBreakException = true });
|
||||
var WaitingClientEx = client.CreateWaitingClient(new() { });
|
||||
var result = WaitingClientEx.SendThenResponse(item, TimeOut, cancellationToken);
|
||||
return (MessageBase)result.RequestInfo;
|
||||
}
|
||||
@@ -213,7 +213,7 @@ public class ModbusTcpDtu : ReadWriteDevicesTcpServerBase
|
||||
|
||||
var item = commandResult.Content;
|
||||
await Task.Delay(FrameTime, cancellationToken);
|
||||
var WaitingClientEx = client.CreateWaitingClient(new() { ThrowBreakException = true });
|
||||
var WaitingClientEx = client.CreateWaitingClient(new() { });
|
||||
var result = await WaitingClientEx.SendThenResponseAsync(item, TimeOut, cancellationToken);
|
||||
return (MessageBase)result.RequestInfo;
|
||||
}
|
||||
|
@@ -104,62 +104,75 @@ public class ModbusTcpServer : ReadWriteDevicesTcpServerBase
|
||||
return PackHelper.LoadSourceRead<T, T2>(this, deviceVariables, maxPack);
|
||||
|
||||
}
|
||||
|
||||
EasyLock easyLock = new();
|
||||
|
||||
/// <inheritdoc/>
|
||||
public override OperResult<byte[]> Read(string address, int length, CancellationToken cancellationToken = default)
|
||||
{
|
||||
ModbusAddress mAddress;
|
||||
try
|
||||
{
|
||||
mAddress = ModbusAddress.ParseFrom(address, Station);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
return new OperResult<byte[]>(ex);
|
||||
}
|
||||
if (MulStation)
|
||||
{
|
||||
Init(mAddress);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (Station != mAddress.Station)
|
||||
easyLock.Wait();
|
||||
|
||||
ModbusAddress mAddress;
|
||||
try
|
||||
{
|
||||
return new OperResult<byte[]>("地址错误");
|
||||
mAddress = ModbusAddress.ParseFrom(address, Station);
|
||||
}
|
||||
Init(mAddress);
|
||||
catch (Exception ex)
|
||||
{
|
||||
return new OperResult<byte[]>(ex);
|
||||
}
|
||||
if (MulStation)
|
||||
{
|
||||
Init(mAddress);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (Station != mAddress.Station)
|
||||
{
|
||||
return new OperResult<byte[]>("地址错误");
|
||||
}
|
||||
Init(mAddress);
|
||||
|
||||
}
|
||||
|
||||
var ModbusServer01ByteBlock = ModbusServer01ByteBlocks[mAddress.Station];
|
||||
var ModbusServer02ByteBlock = ModbusServer02ByteBlocks[mAddress.Station];
|
||||
var ModbusServer03ByteBlock = ModbusServer03ByteBlocks[mAddress.Station];
|
||||
var ModbusServer04ByteBlock = ModbusServer04ByteBlocks[mAddress.Station];
|
||||
int len = mAddress.ReadFunction == 2 || mAddress.ReadFunction == 1 ? length : length * RegisterByteLength;
|
||||
switch (mAddress.ReadFunction)
|
||||
{
|
||||
case 1:
|
||||
byte[] bytes0 = new byte[len];
|
||||
ModbusServer01ByteBlock.Pos = mAddress.AddressStart;
|
||||
ModbusServer01ByteBlock.Read(bytes0);
|
||||
return OperResult.CreateSuccessResult(bytes0);
|
||||
case 2:
|
||||
byte[] bytes1 = new byte[len];
|
||||
ModbusServer02ByteBlock.Pos = mAddress.AddressStart;
|
||||
ModbusServer02ByteBlock.Read(bytes1);
|
||||
return OperResult.CreateSuccessResult(bytes1);
|
||||
case 3:
|
||||
|
||||
byte[] bytes3 = new byte[len];
|
||||
ModbusServer03ByteBlock.Pos = mAddress.AddressStart * RegisterByteLength;
|
||||
ModbusServer03ByteBlock.Read(bytes3);
|
||||
return OperResult.CreateSuccessResult(bytes3);
|
||||
case 4:
|
||||
byte[] bytes4 = new byte[len];
|
||||
ModbusServer04ByteBlock.Pos = mAddress.AddressStart * RegisterByteLength;
|
||||
ModbusServer04ByteBlock.Read(bytes4);
|
||||
return OperResult.CreateSuccessResult(bytes4);
|
||||
}
|
||||
return new OperResult<byte[]>("功能码错误");
|
||||
}
|
||||
|
||||
var ModbusServer01ByteBlock = ModbusServer01ByteBlocks[mAddress.Station];
|
||||
var ModbusServer02ByteBlock = ModbusServer02ByteBlocks[mAddress.Station];
|
||||
var ModbusServer03ByteBlock = ModbusServer03ByteBlocks[mAddress.Station];
|
||||
var ModbusServer04ByteBlock = ModbusServer04ByteBlocks[mAddress.Station];
|
||||
int len = mAddress.ReadFunction == 2 || mAddress.ReadFunction == 1 ? length : length * RegisterByteLength;
|
||||
switch (mAddress.ReadFunction)
|
||||
finally
|
||||
{
|
||||
case 1:
|
||||
byte[] bytes0 = new byte[len];
|
||||
ModbusServer01ByteBlock.Pos = mAddress.AddressStart;
|
||||
ModbusServer01ByteBlock.Read(bytes0);
|
||||
return OperResult.CreateSuccessResult(bytes0);
|
||||
case 2:
|
||||
byte[] bytes1 = new byte[len];
|
||||
ModbusServer02ByteBlock.Pos = mAddress.AddressStart;
|
||||
ModbusServer02ByteBlock.Read(bytes1);
|
||||
return OperResult.CreateSuccessResult(bytes1);
|
||||
case 3:
|
||||
|
||||
byte[] bytes3 = new byte[len];
|
||||
ModbusServer03ByteBlock.Pos = mAddress.AddressStart * RegisterByteLength;
|
||||
ModbusServer03ByteBlock.Read(bytes3);
|
||||
return OperResult.CreateSuccessResult(bytes3);
|
||||
case 4:
|
||||
byte[] bytes4 = new byte[len];
|
||||
ModbusServer04ByteBlock.Pos = mAddress.AddressStart * RegisterByteLength;
|
||||
ModbusServer04ByteBlock.Read(bytes4);
|
||||
return OperResult.CreateSuccessResult(bytes4);
|
||||
easyLock.Release();
|
||||
}
|
||||
return new OperResult<byte[]>("功能码错误");
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
@@ -193,84 +206,104 @@ public class ModbusTcpServer : ReadWriteDevicesTcpServerBase
|
||||
/// <inheritdoc/>
|
||||
public override OperResult Write(string address, byte[] value, CancellationToken cancellationToken = default)
|
||||
{
|
||||
ModbusAddress mAddress;
|
||||
try
|
||||
{
|
||||
mAddress = ModbusAddress.ParseFrom(address, Station);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
return new OperResult(ex);
|
||||
}
|
||||
if (MulStation)
|
||||
{
|
||||
Init(mAddress);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (Station != mAddress.Station)
|
||||
easyLock.Wait();
|
||||
ModbusAddress mAddress;
|
||||
try
|
||||
{
|
||||
return new OperResult("地址错误");
|
||||
mAddress = ModbusAddress.ParseFrom(address, Station);
|
||||
}
|
||||
Init(mAddress);
|
||||
catch (Exception ex)
|
||||
{
|
||||
return new OperResult(ex);
|
||||
}
|
||||
if (MulStation)
|
||||
{
|
||||
Init(mAddress);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (Station != mAddress.Station)
|
||||
{
|
||||
return new OperResult("地址错误");
|
||||
}
|
||||
Init(mAddress);
|
||||
}
|
||||
var ModbusServer03ByteBlock = ModbusServer03ByteBlocks[mAddress.Station];
|
||||
var ModbusServer04ByteBlock = ModbusServer04ByteBlocks[mAddress.Station];
|
||||
switch (mAddress.ReadFunction)
|
||||
{
|
||||
case 3:
|
||||
ModbusServer03ByteBlock.Pos = mAddress.AddressStart * RegisterByteLength;
|
||||
ModbusServer03ByteBlock.Write(value);
|
||||
return OperResult.CreateSuccessResult();
|
||||
case 4:
|
||||
ModbusServer04ByteBlock.Pos = mAddress.AddressStart * RegisterByteLength;
|
||||
ModbusServer04ByteBlock.Write(value);
|
||||
return OperResult.CreateSuccessResult();
|
||||
}
|
||||
return new OperResult("功能码错误");
|
||||
|
||||
}
|
||||
var ModbusServer03ByteBlock = ModbusServer03ByteBlocks[mAddress.Station];
|
||||
var ModbusServer04ByteBlock = ModbusServer04ByteBlocks[mAddress.Station];
|
||||
switch (mAddress.ReadFunction)
|
||||
finally
|
||||
{
|
||||
case 3:
|
||||
ModbusServer03ByteBlock.Pos = mAddress.AddressStart * RegisterByteLength;
|
||||
ModbusServer03ByteBlock.Write(value);
|
||||
return OperResult.CreateSuccessResult();
|
||||
case 4:
|
||||
ModbusServer04ByteBlock.Pos = mAddress.AddressStart * RegisterByteLength;
|
||||
ModbusServer04ByteBlock.Write(value);
|
||||
return OperResult.CreateSuccessResult();
|
||||
|
||||
easyLock.Release();
|
||||
}
|
||||
return new OperResult("功能码错误");
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
public override OperResult Write(string address, bool[] value, CancellationToken cancellationToken = default)
|
||||
{
|
||||
ModbusAddress mAddress;
|
||||
try
|
||||
{
|
||||
mAddress = ModbusAddress.ParseFrom(address, Station);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
return (new OperResult(ex));
|
||||
}
|
||||
if (MulStation)
|
||||
{
|
||||
Init(mAddress);
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
if (Station != mAddress.Station)
|
||||
easyLock.Wait();
|
||||
ModbusAddress mAddress;
|
||||
try
|
||||
{
|
||||
return (new OperResult("地址错误"));
|
||||
mAddress = ModbusAddress.ParseFrom(address, Station);
|
||||
}
|
||||
Init(mAddress);
|
||||
catch (Exception ex)
|
||||
{
|
||||
return (new OperResult(ex));
|
||||
}
|
||||
if (MulStation)
|
||||
{
|
||||
Init(mAddress);
|
||||
|
||||
}
|
||||
else
|
||||
{
|
||||
if (Station != mAddress.Station)
|
||||
{
|
||||
return (new OperResult("地址错误"));
|
||||
}
|
||||
Init(mAddress);
|
||||
|
||||
}
|
||||
|
||||
var ModbusServer01ByteBlock = ModbusServer01ByteBlocks[mAddress.Station];
|
||||
var ModbusServer02ByteBlock = ModbusServer02ByteBlocks[mAddress.Station];
|
||||
switch (mAddress.ReadFunction)
|
||||
{
|
||||
case 1:
|
||||
ModbusServer01ByteBlock.Pos = mAddress.AddressStart;
|
||||
ModbusServer01ByteBlock.Write(value.BoolArrayToByte());
|
||||
return (OperResult.CreateSuccessResult());
|
||||
case 2:
|
||||
ModbusServer02ByteBlock.Pos = mAddress.AddressStart;
|
||||
ModbusServer02ByteBlock.Write(value.BoolArrayToByte());
|
||||
return (OperResult.CreateSuccessResult());
|
||||
}
|
||||
return new OperResult("功能码错误");
|
||||
|
||||
}
|
||||
|
||||
var ModbusServer01ByteBlock = ModbusServer01ByteBlocks[mAddress.Station];
|
||||
var ModbusServer02ByteBlock = ModbusServer02ByteBlocks[mAddress.Station];
|
||||
switch (mAddress.ReadFunction)
|
||||
finally
|
||||
{
|
||||
case 1:
|
||||
ModbusServer01ByteBlock.Pos = mAddress.AddressStart;
|
||||
ModbusServer01ByteBlock.Write(value.BoolArrayToByte());
|
||||
return (OperResult.CreateSuccessResult());
|
||||
case 2:
|
||||
ModbusServer02ByteBlock.Pos = mAddress.AddressStart;
|
||||
ModbusServer02ByteBlock.Write(value.BoolArrayToByte());
|
||||
return (OperResult.CreateSuccessResult());
|
||||
|
||||
easyLock.Release();
|
||||
}
|
||||
return new OperResult("功能码错误");
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
|
@@ -11,5 +11,4 @@
|
||||
<PackageReference Include="OPCFoundation.NetStandard.Opc.Ua.Client.ComplexTypes" Version="1.4.372.56" />
|
||||
</ItemGroup>
|
||||
|
||||
|
||||
</Project>
|
||||
|
@@ -24,7 +24,7 @@ public abstract class ReadWriteDevicesSerialSessionBase : ReadWriteDevicesBase
|
||||
public ReadWriteDevicesSerialSessionBase(SerialSession serialSession)
|
||||
{
|
||||
SerialSession = serialSession;
|
||||
WaitingClientEx = SerialSession.CreateWaitingClient(new() { ThrowBreakException = true });
|
||||
WaitingClientEx = SerialSession.CreateWaitingClient(new() { });
|
||||
SerialSession.Received -= Received;
|
||||
SerialSession.Connecting -= Connecting;
|
||||
SerialSession.Connected -= Connected;
|
||||
@@ -96,7 +96,7 @@ public abstract class ReadWriteDevicesSerialSessionBase : ReadWriteDevicesBase
|
||||
{
|
||||
try
|
||||
{
|
||||
waitingOptions ??= new WaitingOptions { ThrowBreakException = true };
|
||||
waitingOptions ??= new WaitingOptions { };
|
||||
ResponsedData result = SerialSession.CreateWaitingClient(waitingOptions).SendThenResponse(data, TimeOut, cancellationToken);
|
||||
return OperResult.CreateSuccessResult(result.Data);
|
||||
}
|
||||
@@ -111,7 +111,7 @@ public abstract class ReadWriteDevicesSerialSessionBase : ReadWriteDevicesBase
|
||||
{
|
||||
try
|
||||
{
|
||||
waitingOptions ??= new WaitingOptions { ThrowBreakException = true };
|
||||
waitingOptions ??= new WaitingOptions { };
|
||||
ResponsedData result = await SerialSession.CreateWaitingClient(waitingOptions).SendThenResponseAsync(data, TimeOut, cancellationToken);
|
||||
return OperResult.CreateSuccessResult(result.Data);
|
||||
}
|
||||
|
@@ -23,7 +23,7 @@ public abstract class ReadWriteDevicesTcpClientBase : ReadWriteDevicesBase
|
||||
public ReadWriteDevicesTcpClientBase(TcpClient tcpClient)
|
||||
{
|
||||
TcpClient = tcpClient;
|
||||
WaitingClientEx = TcpClient.CreateWaitingClient(new() { ThrowBreakException = true });
|
||||
WaitingClientEx = TcpClient.CreateWaitingClient(new() { });
|
||||
TcpClient.Connecting -= Connecting;
|
||||
TcpClient.Connected -= Connected;
|
||||
TcpClient.Disconnecting -= Disconnecting;
|
||||
@@ -86,7 +86,7 @@ public abstract class ReadWriteDevicesTcpClientBase : ReadWriteDevicesBase
|
||||
{
|
||||
try
|
||||
{
|
||||
waitingOptions ??= new WaitingOptions { ThrowBreakException = true, };
|
||||
waitingOptions ??= new WaitingOptions { };
|
||||
ResponsedData result = TcpClient.CreateWaitingClient(waitingOptions).SendThenResponse(data, TimeOut, cancellationToken);
|
||||
return OperResult.CreateSuccessResult(result.Data);
|
||||
}
|
||||
@@ -101,7 +101,7 @@ public abstract class ReadWriteDevicesTcpClientBase : ReadWriteDevicesBase
|
||||
{
|
||||
try
|
||||
{
|
||||
waitingOptions ??= new WaitingOptions { ThrowBreakException = true };
|
||||
waitingOptions ??= new WaitingOptions { };
|
||||
ResponsedData result = await TcpClient.CreateWaitingClient(waitingOptions).SendThenResponseAsync(data, TimeOut, cancellationToken);
|
||||
return OperResult.CreateSuccessResult(result.Data);
|
||||
}
|
||||
|
@@ -22,7 +22,7 @@ public abstract class ReadWriteDevicesUdpSessionBase : ReadWriteDevicesBase
|
||||
{
|
||||
UdpSession = udpSession;
|
||||
SetDataAdapter();
|
||||
WaitingClientEx = UdpSession.CreateWaitingClient(new() { ThrowBreakException = true });
|
||||
WaitingClientEx = UdpSession.CreateWaitingClient(new() { });
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -64,7 +64,7 @@ public abstract class ReadWriteDevicesUdpSessionBase : ReadWriteDevicesBase
|
||||
{
|
||||
try
|
||||
{
|
||||
waitingOptions ??= new WaitingOptions { ThrowBreakException = true };
|
||||
waitingOptions ??= new WaitingOptions { };
|
||||
ResponsedData result = UdpSession.CreateWaitingClient(waitingOptions).SendThenResponse(data, TimeOut, cancellationToken);
|
||||
return OperResult.CreateSuccessResult(result.Data);
|
||||
}
|
||||
@@ -79,7 +79,7 @@ public abstract class ReadWriteDevicesUdpSessionBase : ReadWriteDevicesBase
|
||||
{
|
||||
try
|
||||
{
|
||||
waitingOptions ??= new WaitingOptions { ThrowBreakException = true };
|
||||
waitingOptions ??= new WaitingOptions { };
|
||||
ResponsedData result = await UdpSession.CreateWaitingClient(waitingOptions).SendThenResponseAsync(data, TimeOut, cancellationToken);
|
||||
return OperResult.CreateSuccessResult(result.Data);
|
||||
}
|
||||
|
@@ -51,10 +51,10 @@ public sealed class EasyLock
|
||||
/// <summary>
|
||||
/// 进入锁
|
||||
/// </summary>
|
||||
public void Wait()
|
||||
public void Wait(CancellationToken cancellationToken = default)
|
||||
{
|
||||
Interlocked.Increment(ref lockWaitCount);
|
||||
m_waiterLock.Wait();
|
||||
m_waiterLock.Wait(cancellationToken);
|
||||
Interlocked.Decrement(ref lockWaitCount);
|
||||
}
|
||||
/// <summary>
|
||||
@@ -71,10 +71,10 @@ public sealed class EasyLock
|
||||
/// <summary>
|
||||
/// 进入锁
|
||||
/// </summary>
|
||||
public async Task WaitAsync()
|
||||
public async Task WaitAsync(CancellationToken cancellationToken = default)
|
||||
{
|
||||
Interlocked.Increment(ref lockWaitCount);
|
||||
await m_waiterLock.WaitAsync();
|
||||
await m_waiterLock.WaitAsync(cancellationToken);
|
||||
Interlocked.Decrement(ref lockWaitCount);
|
||||
}
|
||||
/// <summary>
|
||||
|
@@ -23,6 +23,8 @@
|
||||
//------------------------------------------------------------------------------
|
||||
//------------------------------------------------------------------------------
|
||||
|
||||
using System.Runtime.CompilerServices;
|
||||
|
||||
namespace ThingsGateway.Foundation.Core
|
||||
{
|
||||
/// <summary>
|
||||
@@ -49,5 +51,27 @@ namespace ThingsGateway.Foundation.Core
|
||||
{
|
||||
task.ConfigureAwait(false).GetAwaiter().GetResult();
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// 配置ConfigureAwait为false。
|
||||
/// </summary>
|
||||
/// <typeparam name="T"></typeparam>
|
||||
/// <param name="task"></param>
|
||||
/// <returns></returns>
|
||||
public static ConfiguredTaskAwaitable<T> ConfigureFalseAwait<T>(this Task<T> task)
|
||||
{
|
||||
return task.ConfigureAwait(false);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 配置ConfigureAwait为false。
|
||||
/// </summary>
|
||||
/// <param name="task"></param>
|
||||
public static ConfiguredTaskAwaitable ConfigureFalseAwait(this Task task)
|
||||
{
|
||||
return task.ConfigureAwait(false);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
@@ -27,43 +27,48 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
/// <summary>
|
||||
/// 请求关闭
|
||||
/// </summary>
|
||||
public Action<DmtpActor, string> OnClose { get; set; }
|
||||
public Func<DmtpActor, string, Task> Closed { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// 当创建通道时
|
||||
/// </summary>
|
||||
public Action<DmtpActor, CreateChannelEventArgs> OnCreateChannel { get; set; }
|
||||
public Func<DmtpActor, CreateChannelEventArgs, Task> CreatedChannel { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// 查找其他IDmtpActor
|
||||
/// </summary>
|
||||
public Func<string, IDmtpActor> OnFindDmtpActor { get; set; }
|
||||
public Func<string, Task<IDmtpActor>> FindDmtpActor { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// 在完成握手连接时
|
||||
/// </summary>
|
||||
public Action<DmtpActor, DmtpVerifyEventArgs> OnHandshaked { get; set; }
|
||||
public Func<DmtpActor, DmtpVerifyEventArgs, Task> Handshaked { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// 握手
|
||||
/// </summary>
|
||||
public Action<DmtpActor, DmtpVerifyEventArgs> OnHandshaking { get; set; }
|
||||
public Func<DmtpActor, DmtpVerifyEventArgs, Task> Handshaking { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// 重设Id
|
||||
/// </summary>
|
||||
public Action<DmtpActor, WaitSetId> OnResetId { get; set; }
|
||||
public Func<DmtpActor, IdChangedEventArgs, Task> IdChanged { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// 当需要路由的时候
|
||||
/// </summary>
|
||||
public Action<DmtpActor, PackageRouterEventArgs> OnRouting { get; set; }
|
||||
public Func<DmtpActor, PackageRouterEventArgs, Task> Routing { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// 发送数据接口
|
||||
/// </summary>
|
||||
public Action<DmtpActor, ArraySegment<byte>[]> OutputSend { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// 异步发送数据接口
|
||||
/// </summary>
|
||||
public Func<DmtpActor, ArraySegment<byte>[], Task> OutputSendAsync { get; set; }
|
||||
|
||||
#endregion 委托
|
||||
|
||||
#region 属性
|
||||
@@ -119,29 +124,22 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
public virtual void Close(bool sendClose, string message)
|
||||
public void Close(string msg)
|
||||
{
|
||||
this.OnClosed(true, msg);
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
public bool SendClose(string msg)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (this.IsHandshaked)
|
||||
{
|
||||
try
|
||||
{
|
||||
if (sendClose)
|
||||
{
|
||||
this.SendString(0, message);
|
||||
}
|
||||
}
|
||||
catch
|
||||
{
|
||||
}
|
||||
this.IsHandshaked = false;
|
||||
this.WaitHandlePool.CancelAll();
|
||||
this.OnClose?.Invoke(this, message);
|
||||
}
|
||||
this.SendString(0, msg);
|
||||
return true;
|
||||
}
|
||||
catch
|
||||
{
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -165,7 +163,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
Metadata = metadata
|
||||
};
|
||||
|
||||
this.OnHandshaking?.Invoke(this, args);
|
||||
this.OnHandshaking(args).GetFalseAwaitResult();
|
||||
|
||||
var waitVerify = new WaitVerify()
|
||||
{
|
||||
@@ -189,7 +187,8 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
this.Id = verifyResult.Id;
|
||||
this.IsHandshaked = true;
|
||||
this.PrivateHandshaked(new DmtpVerifyEventArgs()
|
||||
|
||||
Task.Factory.StartNew(this.PrivateOnHandshaked, new DmtpVerifyEventArgs()
|
||||
{
|
||||
Id = verifyResult.Id,
|
||||
Metadata = verifyResult.Metadata,
|
||||
@@ -201,18 +200,15 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
else
|
||||
{
|
||||
verifyResult.Handle = true;
|
||||
this.Close(false, verifyResult.Message);
|
||||
throw new TokenVerifyException(verifyResult.Message);
|
||||
}
|
||||
}
|
||||
case WaitDataStatus.Overtime:
|
||||
this.Close(false, TouchSocketDmtpStatus.Overtime.GetDescription());
|
||||
throw new TimeoutException(TouchSocketDmtpStatus.Overtime.GetDescription());
|
||||
case WaitDataStatus.Canceled:
|
||||
case WaitDataStatus.Disposed:
|
||||
default:
|
||||
this.Close(false, null);
|
||||
return;
|
||||
throw new OperationCanceledException();
|
||||
}
|
||||
}
|
||||
finally
|
||||
@@ -240,7 +236,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
Metadata = metadata
|
||||
};
|
||||
|
||||
this.OnHandshaking?.Invoke(this, args);
|
||||
await this.OnHandshaking(args).ConfigureFalseAwait();
|
||||
|
||||
var waitVerify = new WaitVerify()
|
||||
{
|
||||
@@ -253,8 +249,8 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
|
||||
try
|
||||
{
|
||||
this.SendJsonObject(P1_Handshake_Request, waitVerify);
|
||||
switch (await waitData.WaitAsync(timeout))
|
||||
await this.SendJsonObjectAsync(P1_Handshake_Request, waitVerify).ConfigureFalseAwait();
|
||||
switch (await waitData.WaitAsync(timeout).ConfigureFalseAwait())
|
||||
{
|
||||
case WaitDataStatus.SetRunning:
|
||||
{
|
||||
@@ -263,7 +259,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
this.Id = verifyResult.Id;
|
||||
this.IsHandshaked = true;
|
||||
this.PrivateHandshaked(new DmtpVerifyEventArgs()
|
||||
_ = Task.Factory.StartNew(this.PrivateOnHandshaked, new DmtpVerifyEventArgs()
|
||||
{
|
||||
Id = verifyResult.Id,
|
||||
Metadata = verifyResult.Metadata,
|
||||
@@ -275,18 +271,15 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
else
|
||||
{
|
||||
verifyResult.Handle = true;
|
||||
this.Close(false, verifyResult.Message);
|
||||
throw new TokenVerifyException(verifyResult.Message);
|
||||
}
|
||||
}
|
||||
case WaitDataStatus.Overtime:
|
||||
this.Close(false, TouchSocketDmtpStatus.Overtime.GetDescription());
|
||||
throw new TimeoutException(TouchSocketDmtpStatus.Overtime.GetDescription());
|
||||
case WaitDataStatus.Canceled:
|
||||
case WaitDataStatus.Disposed:
|
||||
default:
|
||||
this.Close(false, null);
|
||||
return;
|
||||
throw new OperationCanceledException();
|
||||
}
|
||||
}
|
||||
finally
|
||||
@@ -295,6 +288,100 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
}
|
||||
}
|
||||
|
||||
#region 委托触发
|
||||
|
||||
/// <summary>
|
||||
/// 当关闭后
|
||||
/// </summary>
|
||||
/// <param name="manual"></param>
|
||||
/// <param name="msg"></param>
|
||||
protected virtual Task OnClosed(bool manual, string msg)
|
||||
{
|
||||
if (this.IsHandshaked)
|
||||
{
|
||||
this.IsHandshaked = false;
|
||||
this.WaitHandlePool.CancelAll();
|
||||
}
|
||||
|
||||
if (manual)
|
||||
{
|
||||
return EasyTask.CompletedTask;
|
||||
}
|
||||
if (this.Closed != null)
|
||||
{
|
||||
return this.Closed.Invoke(this, msg);
|
||||
}
|
||||
return EasyTask.CompletedTask;
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// 正在握手连接
|
||||
/// </summary>
|
||||
/// <param name="e"></param>
|
||||
/// <returns></returns>
|
||||
protected virtual Task OnHandshaking(DmtpVerifyEventArgs e)
|
||||
{
|
||||
if (this.Handshaking != null)
|
||||
{
|
||||
return this.Handshaking.Invoke(this, e);
|
||||
}
|
||||
return EasyTask.CompletedTask;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 握手连接完成
|
||||
/// </summary>
|
||||
/// <param name="e"></param>
|
||||
/// <returns></returns>
|
||||
protected virtual Task OnHandshaked(DmtpVerifyEventArgs e)
|
||||
{
|
||||
if (this.Handshaked != null)
|
||||
{
|
||||
return this.Handshaked.Invoke(this, e);
|
||||
}
|
||||
return EasyTask.CompletedTask;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 当Id修改时
|
||||
/// </summary>
|
||||
/// <param name="e"></param>
|
||||
/// <returns></returns>
|
||||
protected virtual Task OnIdChanged(IdChangedEventArgs e)
|
||||
{
|
||||
if (this.IdChanged != null)
|
||||
{
|
||||
return this.IdChanged.Invoke(this, e);
|
||||
}
|
||||
return EasyTask.CompletedTask;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 当完成创建通道时
|
||||
/// </summary>
|
||||
/// <param name="e"></param>
|
||||
/// <returns></returns>
|
||||
protected virtual Task OnCreatedChannel(CreateChannelEventArgs e)
|
||||
{
|
||||
if (this.CreatedChannel != null)
|
||||
{
|
||||
return this.CreatedChannel.Invoke(this, e);
|
||||
}
|
||||
return EasyTask.CompletedTask;
|
||||
}
|
||||
|
||||
private void PrivateOnHandshaked(object obj)
|
||||
{
|
||||
this.OnHandshaked((DmtpVerifyEventArgs)obj);
|
||||
}
|
||||
|
||||
private void PrivateOnCreatedChannel(object obj)
|
||||
{
|
||||
this.OnCreatedChannel((CreateChannelEventArgs)obj);
|
||||
}
|
||||
#endregion
|
||||
|
||||
#region const
|
||||
|
||||
/// <summary>
|
||||
@@ -368,7 +455,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
/// <returns></returns>
|
||||
public virtual bool InputReceivedData(DmtpMessage message)
|
||||
public virtual async Task<bool> InputReceivedData(DmtpMessage message)
|
||||
{
|
||||
this.LastActiveTime = DateTime.Now;
|
||||
var byteBlock = message.BodyByteBlock;
|
||||
@@ -376,7 +463,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
case P0_Close:
|
||||
{
|
||||
this.Close(false, message.GetBodyString());
|
||||
_ = this.OnClosed(false, message.GetBodyString());
|
||||
return true;
|
||||
}
|
||||
case P1_Handshake_Request:
|
||||
@@ -391,11 +478,11 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
Metadata = waitVerify.Metadata,
|
||||
Id = waitVerify.Id,
|
||||
};
|
||||
this.OnHandshaking?.Invoke(this, args);
|
||||
await this.OnHandshaking(args).ConfigureFalseAwait();
|
||||
|
||||
if (args.Id.HasValue())
|
||||
{
|
||||
this.OnResetId?.Invoke(this, new WaitSetId(this.Id, args.Id));
|
||||
await this.OnIdChanged(new IdChangedEventArgs(this.Id, args.Id)).ConfigureFalseAwait();
|
||||
this.Id = args.Id;
|
||||
}
|
||||
|
||||
@@ -403,24 +490,23 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
waitVerify.Id = this.Id;
|
||||
waitVerify.Status = 1;
|
||||
this.SendJsonObject(P2_Handshake_Response, waitVerify);
|
||||
await this.SendJsonObjectAsync(P2_Handshake_Response, waitVerify).ConfigureFalseAwait();
|
||||
this.IsHandshaked = true;
|
||||
args.Message = "Success";
|
||||
|
||||
Task.Factory.StartNew(this.PrivateHandshaked, args);
|
||||
_ = Task.Factory.StartNew(this.PrivateOnHandshaked, args);
|
||||
}
|
||||
else//不允许连接
|
||||
{
|
||||
waitVerify.Status = 2;
|
||||
waitVerify.Message = args.Message;
|
||||
this.SendJsonObject(P2_Handshake_Response, waitVerify);
|
||||
this.Close(false, args.Message);
|
||||
await this.SendJsonObjectAsync(P2_Handshake_Response, waitVerify).ConfigureFalseAwait();
|
||||
_ = this.OnClosed(false, args.Message);
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
this.Logger.Error(this, $"在protocol={message.ProtocolFlags}中发生错误。信息:{ex.Message}");
|
||||
this.Close(false, ex.Message);
|
||||
_ = this.OnClosed(false, ex.Message);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
@@ -449,7 +535,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
var waitSetId = this.ResolveJsonObject<WaitSetId>(message.GetBodyString());
|
||||
try
|
||||
{
|
||||
this.OnResetId?.Invoke(this, waitSetId);
|
||||
await this.OnIdChanged(new IdChangedEventArgs(waitSetId.OldId, waitSetId.NewId)).ConfigureFalseAwait();
|
||||
this.Id = waitSetId.NewId;
|
||||
waitSetId.Status = 1;
|
||||
}
|
||||
@@ -458,7 +544,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
waitSetId.Status = 2;
|
||||
waitSetId.Message = ex.Message;
|
||||
}
|
||||
this.SendJsonObject(P4_ResetId_Response, waitSetId);
|
||||
await this.SendJsonObjectAsync(P4_ResetId_Response, waitSetId).ConfigureFalseAwait();
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
@@ -486,11 +572,12 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
|
||||
if (this.AllowRoute && waitPing.Route)
|
||||
{
|
||||
if (this.TryRoute(RouteType.Ping, waitPing))
|
||||
|
||||
if (await this.TryRoute(new PackageRouterEventArgs(RouteType.Ping, waitPing)).ConfigureFalseAwait())
|
||||
{
|
||||
if (this.TryFindDmtpActor(waitPing.TargetId, out var actor))
|
||||
if (await this.TryFindDmtpActor(waitPing.TargetId).ConfigureFalseAwait() is DmtpActor actor)
|
||||
{
|
||||
actor.Send(P5_Ping_Request, byteBlock);
|
||||
await actor.SendAsync(P5_Ping_Request, byteBlock).ConfigureFalseAwait();
|
||||
return true;
|
||||
}
|
||||
else
|
||||
@@ -508,7 +595,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
waitPing.Status = TouchSocketDmtpStatus.Success.ToValue();
|
||||
}
|
||||
waitPing.SwitchId();
|
||||
this.SendJsonObject(P6_Ping_Response, waitPing);
|
||||
await this.SendJsonObjectAsync(P6_Ping_Response, waitPing).ConfigureFalseAwait();
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
@@ -524,9 +611,9 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
|
||||
if (this.AllowRoute && waitPing.Route)
|
||||
{
|
||||
if (this.TryFindDmtpActor(waitPing.TargetId, out var actor))
|
||||
if (await this.TryFindDmtpActor(waitPing.TargetId).ConfigureFalseAwait() is DmtpActor actor)
|
||||
{
|
||||
actor.Send(P6_Ping_Response, byteBlock);
|
||||
await actor.SendAsync(P6_Ping_Response, byteBlock).ConfigureFalseAwait();
|
||||
}
|
||||
}
|
||||
else
|
||||
@@ -548,11 +635,11 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
waitCreateChannel.UnpackageRouter(byteBlock);
|
||||
if (this.AllowRoute && waitCreateChannel.Route)
|
||||
{
|
||||
if (this.TryRoute(RouteType.CreateChannel, waitCreateChannel))
|
||||
if (await this.TryRoute(new PackageRouterEventArgs(RouteType.CreateChannel, waitCreateChannel)).ConfigureFalseAwait())
|
||||
{
|
||||
if (this.TryFindDmtpActor(waitCreateChannel.TargetId, out var actor))
|
||||
if (await this.TryFindDmtpActor(waitCreateChannel.TargetId).ConfigureFalseAwait() is DmtpActor actor)
|
||||
{
|
||||
actor.Send(P7_CreateChannel_Request, byteBlock);
|
||||
await actor.SendAsync(P7_CreateChannel_Request, byteBlock).ConfigureFalseAwait();
|
||||
return true;
|
||||
}
|
||||
else
|
||||
@@ -593,7 +680,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
waitCreateChannel.SwitchId();
|
||||
byteBlock.Reset();
|
||||
waitCreateChannel.Package(byteBlock);
|
||||
this.Send(P8_CreateChannel_Response, byteBlock);
|
||||
await this.SendAsync(P8_CreateChannel_Response, byteBlock).ConfigureFalseAwait();
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
@@ -609,9 +696,9 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
waitCreateChannel.UnpackageRouter(byteBlock);
|
||||
if (this.AllowRoute && waitCreateChannel.Route)
|
||||
{
|
||||
if (this.TryFindDmtpActor(waitCreateChannel.TargetId, out var actor))
|
||||
if (await this.TryFindDmtpActor(waitCreateChannel.TargetId).ConfigureFalseAwait() is DmtpActor actor)
|
||||
{
|
||||
actor.Send(P8_CreateChannel_Response, byteBlock);
|
||||
await actor.SendAsync(P8_CreateChannel_Response, byteBlock).ConfigureFalseAwait();
|
||||
return true;
|
||||
}
|
||||
}
|
||||
@@ -635,9 +722,9 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
channelPackage.UnpackageRouter(byteBlock);
|
||||
if (this.AllowRoute && channelPackage.Route)
|
||||
{
|
||||
if (this.TryFindDmtpActor(channelPackage.TargetId, out var actor))
|
||||
if (await this.TryFindDmtpActor(channelPackage.TargetId).ConfigureFalseAwait() is DmtpActor actor)
|
||||
{
|
||||
actor.Send(P9_ChannelPackage, byteBlock);
|
||||
await actor.SendAsync(P9_ChannelPackage, byteBlock).ConfigureFalseAwait();
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -648,7 +735,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
channelPackage.DataType = ChannelDataType.DisposeOrder;
|
||||
byteBlock.Reset();
|
||||
channelPackage.Package(byteBlock);
|
||||
this.Send(P9_ChannelPackage, byteBlock);
|
||||
await this.SendAsync(P9_ChannelPackage, byteBlock).ConfigureFalseAwait();
|
||||
}
|
||||
}
|
||||
else
|
||||
@@ -683,7 +770,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
/// <inheritdoc/>
|
||||
public virtual bool Ping(string targetId, int timeout = 5000)
|
||||
{
|
||||
if (this.AllowRoute && this.TryFindDmtpActor(targetId, out var actor))
|
||||
if (this.AllowRoute && this.TryFindDmtpActor(targetId).GetFalseAwaitResult() is DmtpActor actor)
|
||||
{
|
||||
return actor.Ping(timeout);
|
||||
}
|
||||
@@ -697,15 +784,15 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
public virtual Task<bool> PingAsync(string targetId, int timeout = 5000)
|
||||
public virtual async Task<bool> PingAsync(string targetId, int timeout = 5000)
|
||||
{
|
||||
if (this.AllowRoute && this.TryFindDmtpActor(targetId, out var actor))
|
||||
if (this.AllowRoute && await this.TryFindDmtpActor(targetId).ConfigureFalseAwait() is DmtpActor actor)
|
||||
{
|
||||
return actor.PingAsync(timeout);
|
||||
return await actor.PingAsync(timeout).ConfigureFalseAwait();
|
||||
}
|
||||
else
|
||||
{
|
||||
return this.PrivatePingAsync(targetId, timeout);
|
||||
return await this.PrivatePingAsync(targetId, timeout).ConfigureFalseAwait();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -724,7 +811,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
if (waitData.WaitResult.Status == 1)
|
||||
{
|
||||
this.OnResetId?.Invoke(this, new WaitSetId(this.Id, id));
|
||||
this.OnIdChanged(new IdChangedEventArgs(this.Id, id)).GetFalseAwaitResult();
|
||||
this.Id = id;
|
||||
}
|
||||
else
|
||||
@@ -754,13 +841,13 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
|
||||
this.SendJsonObject(P3_ResetId_Request, waitSetId);
|
||||
|
||||
switch (await waitData.WaitAsync(5000))
|
||||
switch (await waitData.WaitAsync(5000).ConfigureFalseAwait())
|
||||
{
|
||||
case WaitDataStatus.SetRunning:
|
||||
{
|
||||
if (waitData.WaitResult.Status == 1)
|
||||
{
|
||||
this.OnResetId?.Invoke(this, new WaitSetId(this.Id, id));
|
||||
await this.OnIdChanged(new IdChangedEventArgs(this.Id, id)).ConfigureFalseAwait();
|
||||
this.Id = id;
|
||||
}
|
||||
else
|
||||
@@ -801,6 +888,17 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
this.Send(protocol, bytes, 0, bytes.Length);
|
||||
}
|
||||
|
||||
private Task SendJsonObjectAsync<T>(ushort protocol, in T obj)
|
||||
{
|
||||
#if NET6_0_OR_GREATER
|
||||
var bytes = System.Text.Json.JsonSerializer.SerializeToUtf8Bytes(obj, typeof(T), TouchSokcetDmtpSourceGenerationContext.Default);
|
||||
#else
|
||||
var bytes = SerializeConvert.JsonSerializeToBytes(obj);
|
||||
#endif
|
||||
|
||||
return this.SendAsync(protocol, bytes, 0, bytes.Length);
|
||||
}
|
||||
|
||||
private T ResolveJsonObject<T>(string json)
|
||||
{
|
||||
#if NET6_0_OR_GREATER
|
||||
@@ -836,31 +934,34 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
public virtual bool TryFindDmtpActor(string targetId, out DmtpActor actor)
|
||||
public virtual async Task<DmtpActor> TryFindDmtpActor(string targetId)
|
||||
{
|
||||
if (targetId == this.Id)
|
||||
{
|
||||
actor = this;
|
||||
return true;
|
||||
return this;
|
||||
}
|
||||
if (this.OnFindDmtpActor?.Invoke(targetId) is DmtpActor newActor)
|
||||
if (this.FindDmtpActor != null)
|
||||
{
|
||||
actor = newActor;
|
||||
return true;
|
||||
if (await this.FindDmtpActor.Invoke(targetId).ConfigureFalseAwait() is DmtpActor newActor)
|
||||
{
|
||||
return newActor;
|
||||
}
|
||||
}
|
||||
|
||||
actor = default;
|
||||
return false;
|
||||
return default;
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
public virtual bool TryRoute(RouteType routerType, RouterPackage routerPackage)
|
||||
public virtual async Task<bool> TryRoute(PackageRouterEventArgs e)
|
||||
{
|
||||
try
|
||||
{
|
||||
var args = new PackageRouterEventArgs(routerType, routerPackage);
|
||||
this.OnRouting?.Invoke(this, args);
|
||||
return args.IsPermitOperation;
|
||||
if (this.Routing != null)
|
||||
{
|
||||
await this.Routing.Invoke(this, e).ConfigureFalseAwait();
|
||||
return e.IsPermitOperation;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
catch
|
||||
{
|
||||
@@ -868,27 +969,6 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
}
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
public virtual bool TryRoute(RouteType routerType, WaitRouterPackage routerPackage)
|
||||
{
|
||||
try
|
||||
{
|
||||
var args = new PackageRouterEventArgs(routerType, routerPackage);
|
||||
this.OnRouting?.Invoke(this, args);
|
||||
routerPackage.Message = args.Message;
|
||||
return args.IsPermitOperation;
|
||||
}
|
||||
catch
|
||||
{
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
private void PrivateHandshaked(object obj)
|
||||
{
|
||||
this.OnHandshaked?.Invoke(this, (DmtpVerifyEventArgs)obj);
|
||||
}
|
||||
|
||||
private bool PrivatePing(string targetId, int timeout)
|
||||
{
|
||||
var waitPing = new WaitPing
|
||||
@@ -942,7 +1022,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
try
|
||||
{
|
||||
this.SendJsonObject(P5_Ping_Request, waitPing);
|
||||
switch (await waitData.WaitAsync(timeout))
|
||||
switch (await waitData.WaitAsync(timeout).ConfigureFalseAwait())
|
||||
{
|
||||
case WaitDataStatus.SetRunning:
|
||||
{
|
||||
@@ -979,16 +1059,15 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
/// <param name="disposing"></param>
|
||||
protected override void Dispose(bool disposing)
|
||||
{
|
||||
this.OnClose = null;
|
||||
this.OnRouting = null;
|
||||
this.OnFindDmtpActor = null;
|
||||
this.OnHandshaked = null;
|
||||
this.OnHandshaking = null;
|
||||
this.OnResetId = null;
|
||||
|
||||
this.Closed = null;
|
||||
this.Routing = null;
|
||||
this.FindDmtpActor = null;
|
||||
this.Handshaked = null;
|
||||
this.Handshaking = null;
|
||||
this.IdChanged = null;
|
||||
this.OutputSend = null;
|
||||
this.OnClosed(true, nameof(Dispose));
|
||||
this.WaitHandlePool.SafeDispose();
|
||||
this.Close(false, nameof(Dispose));
|
||||
base.Dispose(disposing);
|
||||
}
|
||||
|
||||
@@ -1005,7 +1084,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
new ArraySegment<byte>(TouchSocketBitConverter.BigEndian.GetBytes(length)),
|
||||
new ArraySegment<byte>(buffer,offset,length)
|
||||
};
|
||||
this.OutputSend?.Invoke(this, transferBytes);
|
||||
this.OutputSend.Invoke(this, transferBytes);
|
||||
this.LastActiveTime = DateTime.Now;
|
||||
}
|
||||
|
||||
@@ -1022,10 +1101,20 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
/// <inheritdoc/>
|
||||
public virtual Task SendAsync(ushort protocol, byte[] buffer, int offset, int length)
|
||||
{
|
||||
return Task.Run(() =>
|
||||
var transferBytes = new ArraySegment<byte>[]
|
||||
{
|
||||
this.Send(protocol, buffer, offset, length);
|
||||
});
|
||||
new ArraySegment<byte>(TouchSocketBitConverter.BigEndian.GetBytes(protocol)),
|
||||
new ArraySegment<byte>(TouchSocketBitConverter.BigEndian.GetBytes(length)),
|
||||
new ArraySegment<byte>(buffer,offset,length)
|
||||
};
|
||||
this.LastActiveTime = DateTime.Now;
|
||||
return this.OutputSendAsync.Invoke(this, transferBytes);
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
public virtual Task SendAsync(ushort protocol, ByteBlock byteBlock)
|
||||
{
|
||||
return this.SendAsync(protocol, byteBlock.Buffer, 0, byteBlock.Len);
|
||||
}
|
||||
|
||||
#endregion 协议异步发送
|
||||
@@ -1059,7 +1148,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
throw new ArgumentException($"“{nameof(targetId)}”不能为 null 或空。", nameof(targetId));
|
||||
}
|
||||
if (this.AllowRoute && this.TryFindDmtpActor(targetId, out var actor))
|
||||
if (this.AllowRoute && this.TryFindDmtpActor(targetId).GetFalseAwaitResult() is DmtpActor actor)
|
||||
{
|
||||
return actor.CreateChannel(id, metadata);
|
||||
}
|
||||
@@ -1077,7 +1166,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
throw new ArgumentException($"“{nameof(targetId)}”不能为 null 或空。", nameof(targetId));
|
||||
}
|
||||
|
||||
if (this.AllowRoute && this.TryFindDmtpActor(targetId, out var actor))
|
||||
if (this.AllowRoute && this.TryFindDmtpActor(targetId).GetFalseAwaitResult() is DmtpActor actor)
|
||||
{
|
||||
return actor.CreateChannel(metadata);
|
||||
}
|
||||
@@ -1100,37 +1189,37 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
public virtual Task<IDmtpChannel> CreateChannelAsync(string targetId, int id, Metadata metadata = default)
|
||||
public virtual async Task<IDmtpChannel> CreateChannelAsync(string targetId, int id, Metadata metadata = default)
|
||||
{
|
||||
if (string.IsNullOrEmpty(targetId))
|
||||
{
|
||||
throw new ArgumentException($"“{nameof(targetId)}”不能为 null 或空。", nameof(targetId));
|
||||
}
|
||||
if (this.AllowRoute && this.TryFindDmtpActor(targetId, out var actor))
|
||||
if (this.AllowRoute && await this.TryFindDmtpActor(targetId).ConfigureFalseAwait() is DmtpActor actor)
|
||||
{
|
||||
return actor.CreateChannelAsync(id, metadata);
|
||||
return await actor.CreateChannelAsync(id, metadata).ConfigureFalseAwait();
|
||||
}
|
||||
else
|
||||
{
|
||||
return this.PrivateCreateChannelAsync(targetId, false, id, metadata);
|
||||
return await this.PrivateCreateChannelAsync(targetId, false, id, metadata).ConfigureFalseAwait();
|
||||
}
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
public virtual Task<IDmtpChannel> CreateChannelAsync(string targetId, Metadata metadata = default)
|
||||
public virtual async Task<IDmtpChannel> CreateChannelAsync(string targetId, Metadata metadata = default)
|
||||
{
|
||||
if (string.IsNullOrEmpty(targetId))
|
||||
{
|
||||
throw new ArgumentException($"“{nameof(targetId)}”不能为 null 或空。", nameof(targetId));
|
||||
}
|
||||
|
||||
if (this.AllowRoute && this.TryFindDmtpActor(targetId, out var actor))
|
||||
if (this.AllowRoute && await this.TryFindDmtpActor(targetId).ConfigureFalseAwait() is DmtpActor actor)
|
||||
{
|
||||
return actor.CreateChannelAsync(metadata);
|
||||
return await actor.CreateChannelAsync(metadata).ConfigureFalseAwait();
|
||||
}
|
||||
else
|
||||
{
|
||||
return this.PrivateCreateChannelAsync(targetId, true, 0, metadata);
|
||||
return await this.PrivateCreateChannelAsync(targetId, true, 0, metadata).ConfigureFalseAwait();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1208,9 +1297,14 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
var channel = new InternalChannel(this, targetId, result.Metadata);
|
||||
channel.SetId(result.ChannelId);
|
||||
channel.SetUsing();
|
||||
return this.m_userChannels.TryAdd(result.ChannelId, channel)
|
||||
? (IDmtpChannel)channel
|
||||
: throw new Exception(TouchSocketDmtpStatus.UnknownError.GetDescription());
|
||||
if (this.m_userChannels.TryAdd(result.ChannelId, channel))
|
||||
{
|
||||
return channel;
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new Exception(TouchSocketDmtpStatus.UnknownError.GetDescription());
|
||||
}
|
||||
}
|
||||
case TouchSocketDmtpStatus.ClientNotFind:
|
||||
{
|
||||
@@ -1269,8 +1363,8 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
try
|
||||
{
|
||||
waitCreateChannel.Package(byteBlock);
|
||||
this.Send(P7_CreateChannel_Request, byteBlock);
|
||||
switch (await waitData.WaitAsync(10 * 1000))
|
||||
await this.SendAsync(P7_CreateChannel_Request, byteBlock).ConfigureFalseAwait();
|
||||
switch (await waitData.WaitAsync(10 * 1000).ConfigureFalseAwait())
|
||||
{
|
||||
case WaitDataStatus.SetRunning:
|
||||
{
|
||||
@@ -1282,9 +1376,14 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
var channel = new InternalChannel(this, targetId, result.Metadata);
|
||||
channel.SetId(result.ChannelId);
|
||||
channel.SetUsing();
|
||||
return this.m_userChannels.TryAdd(result.ChannelId, channel)
|
||||
? (IDmtpChannel)channel
|
||||
: throw new Exception(TouchSocketDmtpStatus.UnknownError.GetDescription());
|
||||
if (this.m_userChannels.TryAdd(result.ChannelId, channel))
|
||||
{
|
||||
return channel;
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new Exception(TouchSocketDmtpStatus.UnknownError.GetDescription());
|
||||
}
|
||||
}
|
||||
case TouchSocketDmtpStatus.ClientNotFind:
|
||||
{
|
||||
@@ -1333,7 +1432,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
channel.SetId(id);
|
||||
if (this.m_userChannels.TryAdd(id, channel))
|
||||
{
|
||||
Task.Factory.StartNew(this.ThisRequestCreateChannel, new CreateChannelEventArgs(id, metadata));
|
||||
Task.Factory.StartNew(this.PrivateOnCreatedChannel, new CreateChannelEventArgs(id, metadata));
|
||||
return true;
|
||||
}
|
||||
else
|
||||
@@ -1344,16 +1443,6 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
}
|
||||
}
|
||||
|
||||
private void ThisRequestCreateChannel(object state)
|
||||
{
|
||||
try
|
||||
{
|
||||
this.OnCreateChannel?.Invoke(this, (CreateChannelEventArgs)state);
|
||||
}
|
||||
catch
|
||||
{
|
||||
}
|
||||
}
|
||||
|
||||
#endregion IDmtpChannel
|
||||
}
|
||||
|
@@ -152,9 +152,8 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
/// <summary>
|
||||
/// 关闭
|
||||
/// </summary>
|
||||
/// <param name="sendClose">是否发送close报文</param>
|
||||
/// <param name="message">传递消息</param>
|
||||
void Close(bool sendClose, string message);
|
||||
void Close(string message);
|
||||
|
||||
/// <summary>
|
||||
/// 向当前对点发送一个Ping报文,并且等待回应。
|
||||
@@ -226,6 +225,14 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
/// <param name="length"></param>
|
||||
Task SendAsync(ushort protocol, byte[] buffer, int offset, int length);
|
||||
|
||||
/// <summary>
|
||||
/// 异步发送字节块
|
||||
/// </summary>
|
||||
/// <param name="protocol"></param>
|
||||
/// <param name="byteBlock"></param>
|
||||
/// <returns></returns>
|
||||
Task SendAsync(ushort protocol, ByteBlock byteBlock);
|
||||
|
||||
/// <summary>
|
||||
/// 以Fast序列化,发送小(64K)对象。接收方需要使用ReadObject读取对象。
|
||||
/// </summary>
|
||||
@@ -260,25 +267,20 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
/// 尝试获取指定Id的DmtpActor。一般此方法仅在Service下有效。
|
||||
/// </summary>
|
||||
/// <param name="targetId"></param>
|
||||
/// <param name="actor"></param>
|
||||
/// <returns></returns>
|
||||
bool TryFindDmtpActor(string targetId, out DmtpActor actor);
|
||||
Task<DmtpActor> TryFindDmtpActor(string targetId);
|
||||
|
||||
/// <summary>
|
||||
/// 尝试请求路由,触发路由相关插件。
|
||||
/// 尝试请求路由,触发路由相关插件。并在路由失败时向<see cref="MsgPermitEventArgs.Message"/>中传递消息。
|
||||
/// </summary>
|
||||
/// <param name="routerType"></param>
|
||||
/// <param name="routerPackage"></param>
|
||||
/// <returns></returns>
|
||||
bool TryRoute(RouteType routerType, RouterPackage routerPackage);
|
||||
Task<bool> TryRoute(PackageRouterEventArgs e);
|
||||
|
||||
/// <summary>
|
||||
/// 尝试请求路由,触发路由相关插件。并在路由失败时向<see cref="MsgRouterPackage.Message"/>中传递消息。
|
||||
/// 发送Close请求
|
||||
/// </summary>
|
||||
/// <param name="routerType"></param>
|
||||
/// <param name="routerPackage"></param>
|
||||
/// <returns></returns>
|
||||
bool TryRoute(RouteType routerType, WaitRouterPackage routerPackage);
|
||||
/// <param name="msg"></param>
|
||||
bool SendClose(string msg);
|
||||
|
||||
#endregion 方法
|
||||
}
|
||||
|
@@ -10,6 +10,12 @@
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
using ThingsGateway.Foundation.Core;
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
/// <summary>
|
||||
@@ -17,17 +23,22 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
/// </summary>
|
||||
public class TcpDmtpAdapter : CustomFixedHeaderByteBlockDataHandlingAdapter<DmtpMessage>
|
||||
{
|
||||
private SpinLock m_locker = new SpinLock();
|
||||
private readonly SemaphoreSlim m_locker = new SemaphoreSlim(1, 1);
|
||||
|
||||
/// <inheritdoc/>
|
||||
public override bool CanSendRequestInfo => true;
|
||||
|
||||
/// <inheritdoc/>
|
||||
public override bool CanSplicingSend => false;
|
||||
public override bool CanSplicingSend => true;
|
||||
|
||||
/// <inheritdoc/>
|
||||
public override int HeaderLength => 6;
|
||||
|
||||
/// <summary>
|
||||
/// 最大拼接
|
||||
/// </summary>
|
||||
public const int MaxSplicing = 1024 * 64;
|
||||
|
||||
/// <inheritdoc/>
|
||||
protected override DmtpMessage GetInstance()
|
||||
{
|
||||
@@ -40,6 +51,25 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
request.SafeDispose();
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
protected override async Task PreviewSendAsync(IRequestInfo requestInfo)
|
||||
{
|
||||
if (!(requestInfo is DmtpMessage message))
|
||||
{
|
||||
throw new Exception($"无法将{nameof(requestInfo)}转换为{nameof(DmtpMessage)}");
|
||||
}
|
||||
if (message.BodyByteBlock != null && message.BodyByteBlock.Length > this.MaxPackageSize)
|
||||
{
|
||||
throw new Exception("发送的BodyLength={requestInfo.BodyLength},大于设定的MaxPackageSize={this.MaxPackageSize}");
|
||||
}
|
||||
using (var byteBlock = new ByteBlock(message.GetLength()))
|
||||
{
|
||||
message.Build(byteBlock);
|
||||
await this.GoSendAsync(byteBlock.Buffer, 0, byteBlock.Len);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/// <inheritdoc/>
|
||||
protected override void PreviewSend(IRequestInfo requestInfo)
|
||||
{
|
||||
@@ -58,6 +88,54 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
}
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
protected override async Task PreviewSendAsync(IList<ArraySegment<byte>> transferBytes)
|
||||
{
|
||||
if (transferBytes.Count == 0)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
var length = 0;
|
||||
foreach (var item in transferBytes)
|
||||
{
|
||||
length += item.Count;
|
||||
}
|
||||
|
||||
if (length > this.MaxPackageSize)
|
||||
{
|
||||
throw new Exception("发送数据大于设定值,相同解析器可能无法收到有效数据,已终止发送");
|
||||
}
|
||||
if (length > this.MaxPackageSize)
|
||||
{
|
||||
try
|
||||
{
|
||||
|
||||
await this.m_locker.WaitAsync();
|
||||
foreach (var item in transferBytes)
|
||||
{
|
||||
await this.GoSendAsync(item.Array, item.Offset, item.Count);
|
||||
}
|
||||
}
|
||||
finally
|
||||
{
|
||||
this.m_locker.Release();
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
using (var byteBlock = new ByteBlock(length))
|
||||
{
|
||||
foreach (var item in transferBytes)
|
||||
{
|
||||
byteBlock.Write(item.Array, item.Offset, item.Count);
|
||||
}
|
||||
await this.GoSendAsync(byteBlock.Buffer, 0, byteBlock.Len);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
protected override void PreviewSend(IList<ArraySegment<byte>> transferBytes)
|
||||
{
|
||||
@@ -77,20 +155,31 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
throw new Exception("发送数据大于设定值,相同解析器可能无法收到有效数据,已终止发送");
|
||||
}
|
||||
|
||||
var lockTaken = false;
|
||||
try
|
||||
if (length > this.MaxPackageSize)
|
||||
{
|
||||
this.m_locker.Enter(ref lockTaken);
|
||||
foreach (var item in transferBytes)
|
||||
try
|
||||
{
|
||||
this.GoSend(item.Array, item.Offset, item.Count);
|
||||
|
||||
this.m_locker.Wait();
|
||||
foreach (var item in transferBytes)
|
||||
{
|
||||
this.GoSend(item.Array, item.Offset, item.Count);
|
||||
}
|
||||
}
|
||||
finally
|
||||
{
|
||||
this.m_locker.Release();
|
||||
}
|
||||
}
|
||||
finally
|
||||
else
|
||||
{
|
||||
if (lockTaken)
|
||||
using (var byteBlock = new ByteBlock(length))
|
||||
{
|
||||
this.m_locker.Exit(false);
|
||||
foreach (var item in transferBytes)
|
||||
{
|
||||
byteBlock.Write(item.Array, item.Offset, item.Count);
|
||||
}
|
||||
this.GoSend(byteBlock.Buffer, 0, byteBlock.Len);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@@ -10,6 +10,7 @@
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
/// <summary>
|
||||
|
@@ -22,6 +22,7 @@
|
||||
// 感谢您的下载和使用
|
||||
//------------------------------------------------------------------------------
|
||||
//------------------------------------------------------------------------------
|
||||
using ThingsGateway.Foundation.Core;
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
|
@@ -33,8 +33,8 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
#region 字段
|
||||
|
||||
private bool m_allowRoute;
|
||||
private Func<string, IDmtpActor> m_findDmtpActor;
|
||||
private DmtpActor m_smtpActor;
|
||||
private Func<string, Task<IDmtpActor>> m_findDmtpActor;
|
||||
private DmtpActor m_dmtpActor;
|
||||
private readonly SemaphoreSlim m_semaphore = new SemaphoreSlim(1, 1);
|
||||
#endregion 字段
|
||||
|
||||
@@ -45,7 +45,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
public bool IsHandshaked => this.DmtpActor != null && this.DmtpActor.IsHandshaked;
|
||||
|
||||
/// <inheritdoc/>
|
||||
public IDmtpActor DmtpActor { get => this.m_smtpActor; }
|
||||
public IDmtpActor DmtpActor { get => this.m_dmtpActor; }
|
||||
|
||||
#region 连接
|
||||
|
||||
@@ -78,7 +78,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
if (response.StatusCode == 101)
|
||||
{
|
||||
this.SwitchProtocolToDmtp();
|
||||
this.m_smtpActor.Handshake(this.Config.GetValue(DmtpConfigExtension.VerifyTokenProperty),
|
||||
this.m_dmtpActor.Handshake(this.Config.GetValue(DmtpConfigExtension.VerifyTokenProperty),
|
||||
this.Config.GetValue(DmtpConfigExtension.DefaultIdProperty),
|
||||
timeout, this.Config.GetValue(DmtpConfigExtension.MetadataProperty), CancellationToken.None);
|
||||
return this;
|
||||
@@ -114,7 +114,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
if (response.StatusCode == 101)
|
||||
{
|
||||
this.SwitchProtocolToDmtp();
|
||||
this.m_smtpActor.Handshake(this.Config.GetValue(DmtpConfigExtension.VerifyTokenProperty),
|
||||
this.m_dmtpActor.Handshake(this.Config.GetValue(DmtpConfigExtension.VerifyTokenProperty),
|
||||
this.Config.GetValue(DmtpConfigExtension.DefaultIdProperty),
|
||||
timeout, this.Config.GetValue(DmtpConfigExtension.MetadataProperty), token);
|
||||
return this;
|
||||
@@ -156,7 +156,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
if (response.StatusCode == 101)
|
||||
{
|
||||
this.SwitchProtocolToDmtp();
|
||||
await this.m_smtpActor.HandshakeAsync(this.Config.GetValue(DmtpConfigExtension.VerifyTokenProperty),
|
||||
await this.m_dmtpActor.HandshakeAsync(this.Config.GetValue(DmtpConfigExtension.VerifyTokenProperty),
|
||||
this.Config.GetValue(DmtpConfigExtension.DefaultIdProperty),
|
||||
timeout, this.Config.GetValue(DmtpConfigExtension.MetadataProperty), CancellationToken.None);
|
||||
return this;
|
||||
@@ -184,7 +184,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
}
|
||||
if (!this.Online)
|
||||
{
|
||||
await base.ConnectAsync(timeout, token);
|
||||
await base.ConnectAsync(timeout);
|
||||
}
|
||||
|
||||
var request = new HttpRequest()
|
||||
@@ -197,7 +197,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
if (response.StatusCode == 101)
|
||||
{
|
||||
this.SwitchProtocolToDmtp();
|
||||
await this.m_smtpActor.HandshakeAsync(this.Config.GetValue(DmtpConfigExtension.VerifyTokenProperty),
|
||||
await this.m_dmtpActor.HandshakeAsync(this.Config.GetValue(DmtpConfigExtension.VerifyTokenProperty),
|
||||
this.Config.GetValue(DmtpConfigExtension.DefaultIdProperty),
|
||||
timeout, this.Config.GetValue(DmtpConfigExtension.MetadataProperty), token);
|
||||
return this;
|
||||
@@ -215,19 +215,44 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
|
||||
#endregion 连接
|
||||
|
||||
#region 断开
|
||||
/// <inheritdoc/>
|
||||
protected override void Dispose(bool disposing)
|
||||
{
|
||||
this.DmtpActor.SafeDispose();
|
||||
this.m_dmtpActor?.SafeDispose();
|
||||
base.Dispose(disposing);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 发送<see cref="IDmtpActor"/>关闭消息。
|
||||
/// </summary>
|
||||
/// <param name="msg"></param>
|
||||
/// <returns></returns>
|
||||
public override void Close(string msg = "")
|
||||
{
|
||||
if (this.m_dmtpActor != null)
|
||||
{
|
||||
this.m_dmtpActor.SendClose(msg);
|
||||
this.m_dmtpActor.Close(msg);
|
||||
}
|
||||
base.Close(msg);
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
protected override async Task OnDisconnected(DisconnectEventArgs e)
|
||||
{
|
||||
this.m_dmtpActor?.Close(e.Message);
|
||||
await base.OnDisconnected(e);
|
||||
}
|
||||
|
||||
#endregion
|
||||
|
||||
/// <inheritdoc/>
|
||||
protected override async Task ReceivedData(ReceivedDataEventArgs e)
|
||||
{
|
||||
if (this.Protocol == DmtpUtility.DmtpProtocol && e.RequestInfo is DmtpMessage message)
|
||||
{
|
||||
if (!this.m_smtpActor.InputReceivedData(message))
|
||||
if (!await this.m_dmtpActor.InputReceivedData(message))
|
||||
{
|
||||
if (this.PluginsManager.Enable)
|
||||
{
|
||||
@@ -250,25 +275,19 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
}
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
protected override async Task OnDisconnected(DisconnectEventArgs e)
|
||||
{
|
||||
await base.OnDisconnected(e);
|
||||
this.DmtpActor.Close(false, e.Message);
|
||||
}
|
||||
|
||||
#region ResetId
|
||||
|
||||
///<inheritdoc cref="IDmtpActor.ResetId(string)"/>
|
||||
public void ResetId(string id)
|
||||
{
|
||||
this.m_smtpActor.ResetId(id);
|
||||
this.m_dmtpActor.ResetId(id);
|
||||
}
|
||||
|
||||
///<inheritdoc cref="IDmtpActor.ResetIdAsync(string)"/>
|
||||
public Task ResetIdAsync(string newId)
|
||||
{
|
||||
return this.m_smtpActor.ResetIdAsync(newId);
|
||||
return this.m_dmtpActor.ResetIdAsync(newId);
|
||||
}
|
||||
|
||||
#endregion ResetId
|
||||
@@ -277,72 +296,47 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
this.Protocol = DmtpUtility.DmtpProtocol;
|
||||
this.SetDataHandlingAdapter(new TcpDmtpAdapter());
|
||||
this.m_smtpActor = new SealedDmtpActor(this.m_allowRoute)
|
||||
this.m_dmtpActor = new SealedDmtpActor(this.m_allowRoute)
|
||||
{
|
||||
OutputSend = DmtpActorSend,
|
||||
OnRouting = OnDmtpActorRouting,
|
||||
OnHandshaking = this.OnDmtpActorHandshaking,
|
||||
OnHandshaked = OnDmtpActorHandshaked,
|
||||
OnClose = OnDmtpActorClose,
|
||||
OnCreateChannel = this.OnDmtpActorCreateChannel,
|
||||
OutputSend = this.DmtpActorSend,
|
||||
OutputSendAsync = this.DmtpActorSendAsync,
|
||||
Routing = this.OnDmtpActorRouting,
|
||||
Handshaking = this.OnDmtpActorHandshaking,
|
||||
Handshaked = this.OnDmtpActorHandshaked,
|
||||
Closed = OnDmtpActorClose,
|
||||
CreatedChannel = this.OnDmtpActorCreateChannel,
|
||||
Logger = this.Logger,
|
||||
Client = this,
|
||||
OnFindDmtpActor = this.m_findDmtpActor
|
||||
FindDmtpActor = this.m_findDmtpActor
|
||||
};
|
||||
}
|
||||
|
||||
#region 内部委托绑定
|
||||
|
||||
private void OnDmtpActorClose(DmtpActor actor, string msg)
|
||||
private Task OnDmtpActorClose(DmtpActor actor, string msg)
|
||||
{
|
||||
base.Close(msg);
|
||||
base.BreakOut(false, msg);
|
||||
return EasyTask.CompletedTask;
|
||||
}
|
||||
|
||||
private void OnDmtpActorCreateChannel(DmtpActor actor, CreateChannelEventArgs e)
|
||||
private Task OnDmtpActorCreateChannel(DmtpActor actor, CreateChannelEventArgs e)
|
||||
{
|
||||
this.OnCreateChannel(e);
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
this.PluginsManager.Raise(nameof(IDmtpCreateChannelPlugin.OnCreateChannel), this, e);
|
||||
return this.OnCreateChannel(e);
|
||||
}
|
||||
|
||||
private void OnDmtpActorHandshaked(DmtpActor actor, DmtpVerifyEventArgs e)
|
||||
private Task OnDmtpActorHandshaked(DmtpActor actor, DmtpVerifyEventArgs e)
|
||||
{
|
||||
this.OnHandshaked(e);
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
if (this.PluginsManager.Enable && this.PluginsManager.Raise(nameof(IDmtpHandshakedPlugin.OnDmtpHandshaked), this, e))
|
||||
{
|
||||
return;
|
||||
}
|
||||
return this.OnHandshaked(e);
|
||||
}
|
||||
|
||||
private void OnDmtpActorHandshaking(DmtpActor actor, DmtpVerifyEventArgs e)
|
||||
private Task OnDmtpActorHandshaking(DmtpActor actor, DmtpVerifyEventArgs e)
|
||||
{
|
||||
this.OnHandshaking(e);
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
this.PluginsManager.Raise(nameof(IDmtpHandshakingPlugin.OnDmtpHandshaking), this, e);
|
||||
return this.OnHandshaking(e);
|
||||
}
|
||||
|
||||
private void OnDmtpActorRouting(DmtpActor actor, PackageRouterEventArgs e)
|
||||
private Task OnDmtpActorRouting(DmtpActor actor, PackageRouterEventArgs e)
|
||||
{
|
||||
this.OnRouting(e);
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
if (this.PluginsManager.Enable && this.PluginsManager.Raise(nameof(IDmtpRoutingPlugin.OnDmtpRouting), this, e))
|
||||
{
|
||||
return;
|
||||
}
|
||||
return this.OnRouting(e);
|
||||
}
|
||||
|
||||
private void DmtpActorSend(DmtpActor actor, ArraySegment<byte>[] transferBytes)
|
||||
@@ -350,6 +344,11 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
base.Send(transferBytes);
|
||||
}
|
||||
|
||||
private Task DmtpActorSendAsync(DmtpActor actor, ArraySegment<byte>[] transferBytes)
|
||||
{
|
||||
return base.SendAsync(transferBytes);
|
||||
}
|
||||
|
||||
#endregion 内部委托绑定
|
||||
|
||||
#region 事件触发
|
||||
@@ -358,32 +357,53 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
/// 当创建通道
|
||||
/// </summary>
|
||||
/// <param name="e"></param>
|
||||
protected virtual void OnCreateChannel(CreateChannelEventArgs e)
|
||||
protected virtual async Task OnCreateChannel(CreateChannelEventArgs e)
|
||||
{
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpCreateChannelPlugin.OnCreateChannel), this, e);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 在完成握手连接时
|
||||
/// </summary>
|
||||
/// <param name="e"></param>
|
||||
protected virtual void OnHandshaked(DmtpVerifyEventArgs e)
|
||||
protected virtual async Task OnHandshaked(DmtpVerifyEventArgs e)
|
||||
{
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpHandshakedPlugin.OnDmtpHandshaked), this, e);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 即将握手连接时
|
||||
/// </summary>
|
||||
/// <param name="e">参数</param>
|
||||
protected virtual void OnHandshaking(DmtpVerifyEventArgs e)
|
||||
protected virtual async Task OnHandshaking(DmtpVerifyEventArgs e)
|
||||
{
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpHandshakingPlugin.OnDmtpHandshaking), this, e);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 当需要转发路由包时
|
||||
/// </summary>
|
||||
/// <param name="e"></param>
|
||||
protected virtual void OnRouting(PackageRouterEventArgs e)
|
||||
protected virtual async Task OnRouting(PackageRouterEventArgs e)
|
||||
{
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpRoutingPlugin.OnDmtpRouting), this, e);
|
||||
}
|
||||
|
||||
#endregion 事件触发
|
||||
|
@@ -46,7 +46,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
#region 字段
|
||||
|
||||
private bool m_allowRoute;
|
||||
private Func<string, IDmtpActor> m_findDmtpActor;
|
||||
private Func<string, Task<IDmtpActor>> m_findDmtpActor;
|
||||
|
||||
#endregion 字段
|
||||
|
||||
@@ -68,17 +68,28 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
await base.OnConnected(socketClient, e);
|
||||
}
|
||||
|
||||
private IDmtpActor OnServiceFindDmtpActor(string id)
|
||||
{
|
||||
return this.TryGetSocketClient(id, out var client) ? client.DmtpActor : null;
|
||||
}
|
||||
|
||||
private DmtpActor PrivateOnRpcActorInit()
|
||||
{
|
||||
return new SealedDmtpActor(this.m_allowRoute)
|
||||
{
|
||||
OnFindDmtpActor = this.m_allowRoute ? (this.m_findDmtpActor ?? this.OnServiceFindDmtpActor) : null
|
||||
FindDmtpActor = this.FindDmtpActor
|
||||
};
|
||||
}
|
||||
|
||||
private async Task<IDmtpActor> FindDmtpActor(string id)
|
||||
{
|
||||
if (this.m_allowRoute)
|
||||
{
|
||||
if (this.m_findDmtpActor != null)
|
||||
{
|
||||
return await this.m_findDmtpActor.Invoke(id);
|
||||
}
|
||||
return this.TryGetSocketClient(id, out var client) ? client.DmtpActor : null;
|
||||
}
|
||||
else
|
||||
{
|
||||
return null;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@@ -31,14 +31,14 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
public class HttpDmtpSocketClient : HttpSocketClient, IHttpDmtpSocketClient
|
||||
{
|
||||
internal Func<DmtpActor> m_internalOnRpcActorInit;
|
||||
private DmtpActor m_smtpActor;
|
||||
private DmtpActor m_dmtpActor;
|
||||
|
||||
/// <inheritdoc/>
|
||||
public IDmtpActor DmtpActor { get => this.m_dmtpActor; }
|
||||
|
||||
/// <inheritdoc/>
|
||||
public bool IsHandshaked => this.DmtpActor != null && this.DmtpActor.IsHandshaked;
|
||||
|
||||
/// <inheritdoc/>
|
||||
public IDmtpActor DmtpActor { get => this.m_smtpActor; }
|
||||
|
||||
/// <summary>
|
||||
/// 验证超时时间,默认为3000ms
|
||||
/// </summary>
|
||||
@@ -49,97 +49,67 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
/// </summary>
|
||||
public string VerifyToken => this.Config.GetValue(DmtpConfigExtension.VerifyTokenProperty);
|
||||
|
||||
#region 断开
|
||||
|
||||
/// <inheritdoc/>
|
||||
public override void Close(string msg = "")
|
||||
{
|
||||
if (this.m_smtpActor == null)
|
||||
if (this.m_dmtpActor != null)
|
||||
{
|
||||
base.Close(msg);
|
||||
return;
|
||||
this.m_dmtpActor.SendClose(msg);
|
||||
this.m_dmtpActor.Close(msg);
|
||||
}
|
||||
this.m_smtpActor.Close(true, msg);
|
||||
base.Close(msg);
|
||||
}
|
||||
|
||||
#region ResetId
|
||||
|
||||
/// <inheritdoc cref="IDmtpActor.ResetId(string)"/>
|
||||
public override void ResetId(string newId)
|
||||
{
|
||||
if (this.m_smtpActor == null)
|
||||
{
|
||||
base.ResetId(newId);
|
||||
return;
|
||||
}
|
||||
this.m_smtpActor.ResetId(newId);
|
||||
}
|
||||
|
||||
///<inheritdoc cref="IDmtpActor.ResetIdAsync(string)"/>
|
||||
public async Task ResetIdAsync(string newId)
|
||||
{
|
||||
if (this.m_smtpActor == null)
|
||||
{
|
||||
base.ResetId(newId);
|
||||
return;
|
||||
}
|
||||
await this.m_smtpActor.ResetIdAsync(newId);
|
||||
}
|
||||
|
||||
#endregion ResetId
|
||||
|
||||
/// <summary>
|
||||
/// <inheritdoc/>
|
||||
/// </summary>
|
||||
/// <param name="disposing"></param>
|
||||
protected override void Dispose(bool disposing)
|
||||
{
|
||||
this.DmtpActor?.SafeDispose();
|
||||
this.m_dmtpActor?.SafeDispose();
|
||||
base.Dispose(disposing);
|
||||
}
|
||||
|
||||
///// <inheritdoc/>
|
||||
//protected override bool HandleReceivedData(ByteBlock byteBlock, IRequestInfo requestInfo)
|
||||
//{
|
||||
// if (this.Protocol == DmtpUtility.DmtpProtocol && requestInfo is DmtpMessage message)
|
||||
// {
|
||||
// if (!this.m_smtpActor.InputReceivedData(message))
|
||||
// {
|
||||
// if (this.PluginsManager.Enable)
|
||||
// {
|
||||
// this.PluginsManager.Raise(nameof(IDmtpReceivedPlugin.OnDmtpReceived), this, new DmtpMessageEventArgs(message));
|
||||
// }
|
||||
// }
|
||||
|
||||
// return false;
|
||||
// }
|
||||
// else
|
||||
// {
|
||||
// return base.HandleReceivedData(byteBlock, requestInfo);
|
||||
// }
|
||||
//}
|
||||
|
||||
/// <inheritdoc/>
|
||||
protected override async Task ReceivedData(ReceivedDataEventArgs e)
|
||||
{
|
||||
if (this.Protocol == DmtpUtility.DmtpProtocol && e.RequestInfo is DmtpMessage message)
|
||||
{
|
||||
if (!this.m_smtpActor.InputReceivedData(message))
|
||||
{
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpReceivedPlugin.OnDmtpReceived), this, new DmtpMessageEventArgs(message));
|
||||
}
|
||||
}
|
||||
await base.ReceivedData(e);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// <inheritdoc/>
|
||||
/// </summary>
|
||||
/// <param name="e"></param>
|
||||
protected override async Task OnDisconnected(DisconnectEventArgs e)
|
||||
{
|
||||
this.DmtpActor?.Close(false, e.Message);
|
||||
this.m_dmtpActor?.Close(e.Message);
|
||||
await base.OnDisconnected(e);
|
||||
}
|
||||
|
||||
#endregion 断开
|
||||
|
||||
#region ResetId
|
||||
|
||||
/// <inheritdoc cref="IDmtpActor.ResetId(string)"/>
|
||||
public override void ResetId(string newId)
|
||||
{
|
||||
if (this.m_dmtpActor == null)
|
||||
{
|
||||
base.ResetId(newId);
|
||||
return;
|
||||
}
|
||||
this.m_dmtpActor.ResetId(newId);
|
||||
}
|
||||
|
||||
///<inheritdoc cref="IDmtpActor.ResetIdAsync(string)"/>
|
||||
public async Task ResetIdAsync(string newId)
|
||||
{
|
||||
if (this.m_dmtpActor == null)
|
||||
{
|
||||
base.ResetId(newId);
|
||||
return;
|
||||
}
|
||||
await this.m_dmtpActor.ResetIdAsync(newId);
|
||||
}
|
||||
|
||||
#endregion ResetId
|
||||
|
||||
/// <summary>
|
||||
/// <inheritdoc/>
|
||||
/// </summary>
|
||||
@@ -158,66 +128,73 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
await base.OnReceivedHttpRequest(request);
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
protected override async Task ReceivedData(ReceivedDataEventArgs e)
|
||||
{
|
||||
if (this.Protocol == DmtpUtility.DmtpProtocol && e.RequestInfo is DmtpMessage message)
|
||||
{
|
||||
if (!await this.m_dmtpActor.InputReceivedData(message))
|
||||
{
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpReceivedPlugin.OnDmtpReceived), this, new DmtpMessageEventArgs(message));
|
||||
}
|
||||
}
|
||||
await base.ReceivedData(e);
|
||||
}
|
||||
|
||||
private Task OnDmtpIdChanged(DmtpActor actor, IdChangedEventArgs e)
|
||||
{
|
||||
this.DirectResetId(e.NewId);
|
||||
return EasyTask.CompletedTask;
|
||||
}
|
||||
|
||||
private void SetRpcActor(DmtpActor actor)
|
||||
{
|
||||
actor.Id = this.Id;
|
||||
actor.OnResetId = this.ThisOnResetId;
|
||||
actor.IdChanged = this.OnDmtpIdChanged;
|
||||
actor.OutputSendAsync = this.ThisDmtpActorOutputSendAsync;
|
||||
actor.OutputSend = this.ThisDmtpActorOutputSend;
|
||||
actor.Client = this;
|
||||
actor.OnClose = this.OnDmtpActorClose;
|
||||
actor.OnRouting = this.OnDmtpActorRouting;
|
||||
actor.OnHandshaked = this.OnDmtpActorHandshaked;
|
||||
actor.OnHandshaking = this.OnDmtpActorHandshaking;
|
||||
actor.OnCreateChannel = this.OnDmtpActorCreateChannel;
|
||||
actor.Closed = this.OnDmtpActorClose;
|
||||
actor.Routing = this.OnDmtpActorRouting;
|
||||
actor.Handshaked = this.OnDmtpActorHandshaked;
|
||||
actor.Handshaking = this.OnDmtpActorHandshaking;
|
||||
actor.CreatedChannel = this.OnDmtpActorCreatedChannel;
|
||||
actor.Logger = this.Logger;
|
||||
this.m_smtpActor = actor;
|
||||
this.m_dmtpActor = actor;
|
||||
|
||||
this.Protocol = DmtpUtility.DmtpProtocol;
|
||||
this.SetDataHandlingAdapter(new TcpDmtpAdapter());
|
||||
}
|
||||
|
||||
private void ThisOnResetId(DmtpActor actor, WaitSetId waitSetId)
|
||||
{
|
||||
this.DirectResetId(waitSetId.NewId);
|
||||
}
|
||||
|
||||
private void ThisDmtpActorOutputSend(DmtpActor actor, ArraySegment<byte>[] transferBytes)
|
||||
{
|
||||
base.Send(transferBytes);
|
||||
}
|
||||
|
||||
private Task ThisDmtpActorOutputSendAsync(DmtpActor actor, ArraySegment<byte>[] transferBytes)
|
||||
{
|
||||
return base.SendAsync(transferBytes);
|
||||
}
|
||||
|
||||
#region 内部委托绑定
|
||||
|
||||
private void OnDmtpActorClose(DmtpActor actor, string msg)
|
||||
private Task OnDmtpActorClose(DmtpActor actor, string msg)
|
||||
{
|
||||
base.Close(msg);
|
||||
base.BreakOut(false, msg);
|
||||
return EasyTask.CompletedTask;
|
||||
}
|
||||
|
||||
private void OnDmtpActorCreateChannel(DmtpActor actor, CreateChannelEventArgs e)
|
||||
private Task OnDmtpActorCreatedChannel(DmtpActor actor, CreateChannelEventArgs e)
|
||||
{
|
||||
this.OnCreateChannel(e);
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
this.PluginsManager.Raise(nameof(IDmtpCreateChannelPlugin.OnCreateChannel), this, e);
|
||||
return this.OnCreatedChannel(e);
|
||||
}
|
||||
|
||||
private void OnDmtpActorHandshaked(DmtpActor actor, DmtpVerifyEventArgs e)
|
||||
private Task OnDmtpActorHandshaked(DmtpActor actor, DmtpVerifyEventArgs e)
|
||||
{
|
||||
this.OnHandshaked(e);
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
if (this.PluginsManager.Enable && this.PluginsManager.Raise(nameof(IDmtpHandshakedPlugin.OnDmtpHandshaked), this, e))
|
||||
{
|
||||
return;
|
||||
}
|
||||
return this.OnHandshaked(e);
|
||||
}
|
||||
|
||||
private void OnDmtpActorHandshaking(DmtpActor actor, DmtpVerifyEventArgs e)
|
||||
private Task OnDmtpActorHandshaking(DmtpActor actor, DmtpVerifyEventArgs e)
|
||||
{
|
||||
if (e.Token == this.VerifyToken)
|
||||
{
|
||||
@@ -228,25 +205,12 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
e.Message = "Token不受理";
|
||||
}
|
||||
|
||||
this.OnHandshaking(e);
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
this.PluginsManager.Raise(nameof(IDmtpHandshakingPlugin.OnDmtpHandshaking), this, e);
|
||||
return this.OnHandshaking(e);
|
||||
}
|
||||
|
||||
private void OnDmtpActorRouting(DmtpActor actor, PackageRouterEventArgs e)
|
||||
private Task OnDmtpActorRouting(DmtpActor actor, PackageRouterEventArgs e)
|
||||
{
|
||||
this.OnRouting(e);
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
if (this.PluginsManager.Enable && this.PluginsManager.Raise(nameof(IDmtpRoutingPlugin.OnDmtpRouting), this, e))
|
||||
{
|
||||
return;
|
||||
}
|
||||
return this.OnRouting(e);
|
||||
}
|
||||
|
||||
#endregion 内部委托绑定
|
||||
@@ -257,32 +221,53 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
/// 当创建通道
|
||||
/// </summary>
|
||||
/// <param name="e"></param>
|
||||
protected virtual void OnCreateChannel(CreateChannelEventArgs e)
|
||||
protected virtual async Task OnCreatedChannel(CreateChannelEventArgs e)
|
||||
{
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpCreateChannelPlugin.OnCreateChannel), this, e);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 在完成握手连接时
|
||||
/// </summary>
|
||||
/// <param name="e"></param>
|
||||
protected virtual void OnHandshaked(DmtpVerifyEventArgs e)
|
||||
protected virtual async Task OnHandshaked(DmtpVerifyEventArgs e)
|
||||
{
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpHandshakedPlugin.OnDmtpHandshaked), this, e);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 在验证Token时
|
||||
/// </summary>
|
||||
/// <param name="e">参数</param>
|
||||
protected virtual void OnHandshaking(DmtpVerifyEventArgs e)
|
||||
protected virtual async Task OnHandshaking(DmtpVerifyEventArgs e)
|
||||
{
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpHandshakingPlugin.OnDmtpHandshaking), this, e);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 在需要转发路由包时。
|
||||
/// </summary>
|
||||
/// <param name="e"></param>
|
||||
protected virtual void OnRouting(PackageRouterEventArgs e)
|
||||
protected virtual async Task OnRouting(PackageRouterEventArgs e)
|
||||
{
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpRoutingPlugin.OnDmtpRouting), this, e);
|
||||
}
|
||||
|
||||
#endregion 事件
|
||||
|
@@ -10,6 +10,10 @@
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
using ThingsGateway.Foundation.Http;
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
/// <summary>
|
||||
|
@@ -39,7 +39,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
public IDmtpActor DmtpActor { get => this.m_smtpActor; }
|
||||
public IDmtpActor DmtpActor { get => this.m_dmtpActor; }
|
||||
|
||||
/// <inheritdoc cref="IDmtpActor.Id"/>
|
||||
public string Id => this.DmtpActor.Id;
|
||||
@@ -48,14 +48,16 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
|
||||
private readonly SemaphoreSlim m_semaphore = new SemaphoreSlim(1, 1);
|
||||
private bool m_allowRoute;
|
||||
private Func<string, IDmtpActor> m_findDmtpActor;
|
||||
private SealedDmtpActor m_smtpActor;
|
||||
private SealedDmtpActor m_dmtpActor;
|
||||
private Func<string, Task<IDmtpActor>> m_findDmtpActor;
|
||||
|
||||
#endregion 字段
|
||||
|
||||
/// <inheritdoc cref="IDmtpActor.IsHandshaked"/>
|
||||
public bool IsHandshaked => this.DmtpActor != null && this.DmtpActor.IsHandshaked;
|
||||
|
||||
#region 断开
|
||||
|
||||
/// <summary>
|
||||
/// 发送<see cref="IDmtpActor"/>关闭消息。
|
||||
/// </summary>
|
||||
@@ -63,10 +65,27 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
/// <returns></returns>
|
||||
public override void Close(string msg = "")
|
||||
{
|
||||
this.DmtpActor.Close(true, msg);
|
||||
this.m_dmtpActor?.SendClose(msg);
|
||||
this.m_dmtpActor?.Close(msg);
|
||||
base.Close(msg);
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
protected override void Dispose(bool disposing)
|
||||
{
|
||||
this.m_dmtpActor?.SafeDispose();
|
||||
base.Dispose(disposing);
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
protected override async Task OnDisconnected(DisconnectEventArgs e)
|
||||
{
|
||||
this.m_dmtpActor?.Close(e.Message);
|
||||
await base.OnDisconnected(e).ConfigureFalseAwait();
|
||||
}
|
||||
|
||||
#endregion 断开
|
||||
|
||||
#region 连接
|
||||
|
||||
/// <summary>
|
||||
@@ -87,7 +106,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
base.Connect(timeout);
|
||||
}
|
||||
|
||||
this.m_smtpActor.Handshake(this.Config.GetValue(DmtpConfigExtension.VerifyTokenProperty),
|
||||
this.m_dmtpActor.Handshake(this.Config.GetValue(DmtpConfigExtension.VerifyTokenProperty),
|
||||
this.Config.GetValue(DmtpConfigExtension.DefaultIdProperty), timeout, this.Config.GetValue(DmtpConfigExtension.MetadataProperty), CancellationToken.None);
|
||||
return this;
|
||||
}
|
||||
@@ -107,7 +126,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
base.Connect(timeout);
|
||||
}
|
||||
|
||||
this.m_smtpActor.Handshake(this.Config.GetValue(DmtpConfigExtension.VerifyTokenProperty),
|
||||
this.m_dmtpActor.Handshake(this.Config.GetValue(DmtpConfigExtension.VerifyTokenProperty),
|
||||
this.Config.GetValue(DmtpConfigExtension.DefaultIdProperty), timeout, this.Config.GetValue(DmtpConfigExtension.MetadataProperty), token);
|
||||
return this;
|
||||
}
|
||||
@@ -129,11 +148,10 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
}
|
||||
if (!this.Online)
|
||||
{
|
||||
await base.ConnectAsync(timeout);
|
||||
await base.ConnectAsync(timeout).ConfigureFalseAwait();
|
||||
}
|
||||
|
||||
await this.m_smtpActor.HandshakeAsync(this.Config.GetValue(DmtpConfigExtension.VerifyTokenProperty),
|
||||
this.Config.GetValue(DmtpConfigExtension.DefaultIdProperty), timeout, this.Config.GetValue(DmtpConfigExtension.MetadataProperty), CancellationToken.None);
|
||||
await this.m_dmtpActor.HandshakeAsync(this.Config.GetValue(DmtpConfigExtension.VerifyTokenProperty), this.Config.GetValue(DmtpConfigExtension.DefaultIdProperty), timeout, this.Config.GetValue(DmtpConfigExtension.MetadataProperty), CancellationToken.None).ConfigureFalseAwait();
|
||||
return this;
|
||||
}
|
||||
finally
|
||||
@@ -154,11 +172,10 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
}
|
||||
if (!this.Online)
|
||||
{
|
||||
await base.ConnectAsync(timeout, token);
|
||||
await base.ConnectAsync(timeout).ConfigureFalseAwait();
|
||||
}
|
||||
|
||||
await this.m_smtpActor.HandshakeAsync(this.Config.GetValue(DmtpConfigExtension.VerifyTokenProperty),
|
||||
this.Config.GetValue(DmtpConfigExtension.DefaultIdProperty), timeout, this.Config.GetValue(DmtpConfigExtension.MetadataProperty), token);
|
||||
await this.m_dmtpActor.HandshakeAsync(this.Config.GetValue(DmtpConfigExtension.VerifyTokenProperty), this.Config.GetValue(DmtpConfigExtension.DefaultIdProperty), timeout, this.Config.GetValue(DmtpConfigExtension.MetadataProperty), token).ConfigureFalseAwait();
|
||||
return this;
|
||||
}
|
||||
finally
|
||||
@@ -174,13 +191,13 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
///<inheritdoc cref="IDmtpActor.ResetId(string)"/>
|
||||
public void ResetId(string id)
|
||||
{
|
||||
this.m_smtpActor.ResetId(id);
|
||||
this.m_dmtpActor.ResetId(id);
|
||||
}
|
||||
|
||||
///<inheritdoc cref="IDmtpActor.ResetIdAsync(string)"/>
|
||||
public Task ResetIdAsync(string newId)
|
||||
{
|
||||
return this.m_smtpActor.ResetIdAsync(newId);
|
||||
return this.m_dmtpActor.ResetIdAsync(newId);
|
||||
}
|
||||
|
||||
#endregion ResetId
|
||||
@@ -229,13 +246,6 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
|
||||
#endregion 发送
|
||||
|
||||
/// <inheritdoc/>
|
||||
protected override void Dispose(bool disposing)
|
||||
{
|
||||
this.DmtpActor.SafeDispose();
|
||||
base.Dispose(disposing);
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
protected override void LoadConfig(TouchSocketConfig config)
|
||||
{
|
||||
@@ -246,37 +256,31 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
this.m_allowRoute = true;
|
||||
this.m_findDmtpActor = this.Container.Resolve<IDmtpRouteService>().FindDmtpActor;
|
||||
}
|
||||
this.m_smtpActor = new SealedDmtpActor(this.m_allowRoute)
|
||||
this.m_dmtpActor = new SealedDmtpActor(this.m_allowRoute)
|
||||
{
|
||||
OutputSend = this.DmtpActorSend,
|
||||
OnRouting = this.OnDmtpActorRouting,
|
||||
OnHandshaking = this.OnDmtpActorHandshaking,
|
||||
OnHandshaked = this.OnDmtpActorHandshaked,
|
||||
OnClose = this.OnDmtpActorClose,
|
||||
OutputSendAsync = this.DmtpActorSendAsync,
|
||||
Routing = this.OnDmtpActorRouting,
|
||||
Handshaking = this.OnDmtpActorHandshaking,
|
||||
Handshaked = this.OnDmtpActorHandshaked,
|
||||
Closed = this.OnDmtpActorClose,
|
||||
Logger = this.Logger,
|
||||
Client = this,
|
||||
OnFindDmtpActor = this.m_findDmtpActor,
|
||||
OnCreateChannel = this.OnDmtpActorCreateChannel
|
||||
FindDmtpActor = this.m_findDmtpActor,
|
||||
CreatedChannel = this.OnDmtpActorCreateChannel
|
||||
};
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
protected override async Task OnDisconnected(DisconnectEventArgs e)
|
||||
{
|
||||
await base.OnDisconnected(e);
|
||||
this.DmtpActor.Close(false, e.Message);
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
protected override async Task ReceivedData(ReceivedDataEventArgs e)
|
||||
{
|
||||
var message = (DmtpMessage)e.RequestInfo;
|
||||
if (!this.m_smtpActor.InputReceivedData(message))
|
||||
if (!await this.m_dmtpActor.InputReceivedData(message).ConfigureFalseAwait())
|
||||
{
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpReceivedPlugin.OnDmtpReceived), this, new DmtpMessageEventArgs(message));
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpReceivedPlugin.OnDmtpReceived), this, new DmtpMessageEventArgs(message)).ConfigureFalseAwait();
|
||||
}
|
||||
|
||||
await base.ReceivedData(e);
|
||||
await base.ReceivedData(e).ConfigureFalseAwait();
|
||||
}
|
||||
|
||||
#region 内部委托绑定
|
||||
@@ -286,52 +290,35 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
base.Send(transferBytes);
|
||||
}
|
||||
|
||||
private void OnDmtpActorClose(DmtpActor actor, string msg)
|
||||
private Task DmtpActorSendAsync(DmtpActor actor, ArraySegment<byte>[] transferBytes)
|
||||
{
|
||||
base.Close(msg);
|
||||
return base.SendAsync(transferBytes);
|
||||
}
|
||||
|
||||
private void OnDmtpActorCreateChannel(DmtpActor actor, CreateChannelEventArgs e)
|
||||
private Task OnDmtpActorClose(DmtpActor actor, string msg)
|
||||
{
|
||||
this.OnCreateChannel(e);
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
this.PluginsManager.Raise(nameof(IDmtpCreateChannelPlugin.OnCreateChannel), this, e);
|
||||
this.BreakOut(false, msg);
|
||||
return EasyTask.CompletedTask;
|
||||
}
|
||||
|
||||
private void OnDmtpActorHandshaked(DmtpActor actor, DmtpVerifyEventArgs e)
|
||||
private Task OnDmtpActorCreateChannel(DmtpActor actor, CreateChannelEventArgs e)
|
||||
{
|
||||
this.OnHandshaked(e);
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
if (this.PluginsManager.Enable && this.PluginsManager.Raise(nameof(IDmtpHandshakedPlugin.OnDmtpHandshaked), this, e))
|
||||
{
|
||||
return;
|
||||
}
|
||||
return this.OnCreatedChannel(e);
|
||||
}
|
||||
|
||||
private void OnDmtpActorHandshaking(DmtpActor actor, DmtpVerifyEventArgs e)
|
||||
private Task OnDmtpActorHandshaked(DmtpActor actor, DmtpVerifyEventArgs e)
|
||||
{
|
||||
this.OnHandshaking(e);
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
this.PluginsManager.Raise(nameof(IDmtpHandshakingPlugin.OnDmtpHandshaking), this, e);
|
||||
return this.OnHandshaked(e);
|
||||
}
|
||||
|
||||
private void OnDmtpActorRouting(DmtpActor actor, PackageRouterEventArgs e)
|
||||
private Task OnDmtpActorHandshaking(DmtpActor actor, DmtpVerifyEventArgs e)
|
||||
{
|
||||
if (this.PluginsManager.Enable && this.PluginsManager.Raise(nameof(IDmtpRoutingPlugin.OnDmtpRouting), this, e))
|
||||
{
|
||||
return;
|
||||
}
|
||||
this.OnRouting(e);
|
||||
return this.OnHandshaking(e);
|
||||
}
|
||||
|
||||
private Task OnDmtpActorRouting(DmtpActor actor, PackageRouterEventArgs e)
|
||||
{
|
||||
return this.OnRouting(e);
|
||||
}
|
||||
|
||||
#endregion 内部委托绑定
|
||||
@@ -342,32 +329,53 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
/// 当创建通道
|
||||
/// </summary>
|
||||
/// <param name="e"></param>
|
||||
protected virtual void OnCreateChannel(CreateChannelEventArgs e)
|
||||
protected virtual async Task OnCreatedChannel(CreateChannelEventArgs e)
|
||||
{
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpCreateChannelPlugin.OnCreateChannel), this, e).ConfigureFalseAwait();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 在完成握手连接时
|
||||
/// </summary>
|
||||
/// <param name="e"></param>
|
||||
protected virtual void OnHandshaked(DmtpVerifyEventArgs e)
|
||||
protected virtual async Task OnHandshaked(DmtpVerifyEventArgs e)
|
||||
{
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpHandshakedPlugin.OnDmtpHandshaked), this, e).ConfigureFalseAwait();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 即将握手连接时
|
||||
/// </summary>
|
||||
/// <param name="e">参数</param>
|
||||
protected virtual void OnHandshaking(DmtpVerifyEventArgs e)
|
||||
protected virtual async Task OnHandshaking(DmtpVerifyEventArgs e)
|
||||
{
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpHandshakingPlugin.OnDmtpHandshaking), this, e).ConfigureFalseAwait();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 当需要转发路由包时
|
||||
/// </summary>
|
||||
/// <param name="e"></param>
|
||||
protected virtual void OnRouting(PackageRouterEventArgs e)
|
||||
protected virtual async Task OnRouting(PackageRouterEventArgs e)
|
||||
{
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpRoutingPlugin.OnDmtpRouting), this, e).ConfigureFalseAwait();
|
||||
}
|
||||
|
||||
#endregion 事件触发
|
||||
|
@@ -41,7 +41,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
#region 字段
|
||||
|
||||
private bool m_allowRoute;
|
||||
private Func<string, IDmtpActor> m_findDmtpActor;
|
||||
private Func<string, Task<IDmtpActor>> m_findDmtpActor;
|
||||
|
||||
#endregion 字段
|
||||
|
||||
@@ -73,14 +73,25 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
socketClient.SetDmtpActor(new SealedDmtpActor(this.m_allowRoute)
|
||||
{
|
||||
Id = e.Id,
|
||||
OnFindDmtpActor = this.m_allowRoute ? (this.m_findDmtpActor ?? this.OnServiceFindDmtpActor) : null
|
||||
FindDmtpActor = this.FindDmtpActor
|
||||
});
|
||||
await base.OnConnecting(socketClient, e);
|
||||
}
|
||||
|
||||
private IDmtpActor OnServiceFindDmtpActor(string id)
|
||||
private async Task<IDmtpActor> FindDmtpActor(string id)
|
||||
{
|
||||
return this.TryGetSocketClient(id, out var client) ? client.DmtpActor : null;
|
||||
if (this.m_allowRoute)
|
||||
{
|
||||
if (this.m_findDmtpActor != null)
|
||||
{
|
||||
return await this.m_findDmtpActor.Invoke(id);
|
||||
}
|
||||
return this.TryGetSocketClient(id, out var client) ? client.DmtpActor : null;
|
||||
}
|
||||
else
|
||||
{
|
||||
return null;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@@ -30,7 +30,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
/// </summary>
|
||||
public partial class TcpDmtpSocketClient : SocketClient, ITcpDmtpSocketClient
|
||||
{
|
||||
private DmtpActor m_smtpActor;
|
||||
private DmtpActor m_dmtpActor;
|
||||
|
||||
/// <summary>
|
||||
/// TcpDmtpSocketClient
|
||||
@@ -41,7 +41,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
public IDmtpActor DmtpActor { get => this.m_smtpActor; }
|
||||
public IDmtpActor DmtpActor { get => this.m_dmtpActor; }
|
||||
|
||||
/// <inheritdoc cref="IDmtpActor.IsHandshaked"/>
|
||||
public bool IsHandshaked => this.DmtpActor != null && this.DmtpActor.IsHandshaked;
|
||||
@@ -58,36 +58,23 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
|
||||
#region 内部委托绑定
|
||||
|
||||
private void OnDmtpActorClose(DmtpActor actor, string msg)
|
||||
private Task OnDmtpActorClose(DmtpActor actor, string msg)
|
||||
{
|
||||
base.Close(msg);
|
||||
base.BreakOut(false, msg);
|
||||
return EasyTask.CompletedTask;
|
||||
}
|
||||
|
||||
private void OnDmtpActorCreateChannel(DmtpActor actor, CreateChannelEventArgs e)
|
||||
private Task OnDmtpActorCreateChannel(DmtpActor actor, CreateChannelEventArgs e)
|
||||
{
|
||||
this.OnCreateChannel(e);
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
this.PluginsManager.Raise(nameof(IDmtpCreateChannelPlugin.OnCreateChannel), this, e);
|
||||
return this.OnCreateChannel(e);
|
||||
}
|
||||
|
||||
private void OnDmtpActorHandshaked(DmtpActor actor, DmtpVerifyEventArgs e)
|
||||
private Task OnDmtpActorHandshaked(DmtpActor actor, DmtpVerifyEventArgs e)
|
||||
{
|
||||
this.OnHandshaked(e);
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
if (this.PluginsManager.Enable && this.PluginsManager.Raise(nameof(IDmtpHandshakedPlugin.OnDmtpHandshaked), this, e))
|
||||
{
|
||||
return;
|
||||
}
|
||||
return this.OnHandshaked(e);
|
||||
}
|
||||
|
||||
private void OnDmtpActorHandshaking(DmtpActor actor, DmtpVerifyEventArgs e)
|
||||
private async Task OnDmtpActorHandshaking(DmtpActor actor, DmtpVerifyEventArgs e)
|
||||
{
|
||||
if (e.Token == this.VerifyToken)
|
||||
{
|
||||
@@ -98,25 +85,12 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
e.Message = "Token不受理";
|
||||
}
|
||||
|
||||
this.OnHandshaking(e);
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
this.PluginsManager.Raise(nameof(IDmtpHandshakingPlugin.OnDmtpHandshaking), this, e);
|
||||
await this.OnHandshaking(e).ConfigureFalseAwait();
|
||||
}
|
||||
|
||||
private void OnDmtpActorRouting(DmtpActor actor, PackageRouterEventArgs e)
|
||||
private Task OnDmtpActorRouting(DmtpActor actor, PackageRouterEventArgs e)
|
||||
{
|
||||
this.OnRouting(e);
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
if (this.PluginsManager.Enable && this.PluginsManager.Raise(nameof(IDmtpRoutingPlugin.OnDmtpRouting), this, e))
|
||||
{
|
||||
return;
|
||||
}
|
||||
return this.OnRouting(e);
|
||||
}
|
||||
|
||||
#endregion 内部委托绑定
|
||||
@@ -127,99 +101,138 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
/// 当创建通道
|
||||
/// </summary>
|
||||
/// <param name="e"></param>
|
||||
protected virtual void OnCreateChannel(CreateChannelEventArgs e)
|
||||
protected virtual async Task OnCreateChannel(CreateChannelEventArgs e)
|
||||
{
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpCreateChannelPlugin.OnCreateChannel), this, e).ConfigureFalseAwait();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 在完成握手连接时
|
||||
/// </summary>
|
||||
/// <param name="e"></param>
|
||||
protected virtual void OnHandshaked(DmtpVerifyEventArgs e)
|
||||
protected virtual async Task OnHandshaked(DmtpVerifyEventArgs e)
|
||||
{
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpHandshakedPlugin.OnDmtpHandshaked), this, e).ConfigureFalseAwait();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 在验证Token时
|
||||
/// </summary>
|
||||
/// <param name="e">参数</param>
|
||||
protected virtual void OnHandshaking(DmtpVerifyEventArgs e)
|
||||
protected virtual async Task OnHandshaking(DmtpVerifyEventArgs e)
|
||||
{
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpHandshakingPlugin.OnDmtpHandshaking), this, e).ConfigureFalseAwait();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 在需要转发路由包时。
|
||||
/// </summary>
|
||||
/// <param name="e"></param>
|
||||
protected virtual void OnRouting(PackageRouterEventArgs e)
|
||||
protected virtual async Task OnRouting(PackageRouterEventArgs e)
|
||||
{
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpRoutingPlugin.OnDmtpRouting), this, e);
|
||||
}
|
||||
|
||||
#endregion 事件
|
||||
|
||||
/// <inheritdoc/>
|
||||
#region 断开
|
||||
|
||||
/// <summary>
|
||||
/// 发送<see cref="IDmtpActor"/>关闭消息。
|
||||
/// </summary>
|
||||
/// <param name="msg"></param>
|
||||
/// <returns></returns>
|
||||
public override void Close(string msg = "")
|
||||
{
|
||||
this.m_smtpActor.Close(true, msg);
|
||||
this.m_dmtpActor?.SendClose(msg);
|
||||
this.m_dmtpActor?.Close(msg);
|
||||
base.Close(msg);
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
protected override void Dispose(bool disposing)
|
||||
{
|
||||
this.m_dmtpActor?.SafeDispose();
|
||||
base.Dispose(disposing);
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
protected override async Task OnDisconnected(DisconnectEventArgs e)
|
||||
{
|
||||
this.m_dmtpActor?.Close(e.Message);
|
||||
await base.OnDisconnected(e).ConfigureFalseAwait();
|
||||
}
|
||||
|
||||
#endregion 断开
|
||||
|
||||
#region ResetId
|
||||
|
||||
///<inheritdoc cref="IDmtpActor.ResetId(string)"/>
|
||||
public override void ResetId(string id)
|
||||
{
|
||||
this.m_smtpActor.ResetId(id);
|
||||
this.m_dmtpActor.ResetId(id);
|
||||
}
|
||||
|
||||
///<inheritdoc cref="IDmtpActor.ResetIdAsync(string)"/>
|
||||
public Task ResetIdAsync(string newId)
|
||||
{
|
||||
return this.m_smtpActor.ResetIdAsync(newId);
|
||||
return this.m_dmtpActor.ResetIdAsync(newId);
|
||||
}
|
||||
|
||||
#endregion ResetId
|
||||
|
||||
internal void SetDmtpActor(DmtpActor actor)
|
||||
{
|
||||
actor.OnResetId = this.ThisOnResetId;
|
||||
actor.IdChanged = this.ThisOnResetId;
|
||||
actor.OutputSend = this.ThisDmtpActorOutputSend;
|
||||
actor.OutputSendAsync = this.ThisDmtpActorOutputSendAsync;
|
||||
actor.Client = this;
|
||||
actor.OnClose = this.OnDmtpActorClose;
|
||||
actor.OnRouting = this.OnDmtpActorRouting;
|
||||
actor.OnHandshaked = this.OnDmtpActorHandshaked;
|
||||
actor.OnHandshaking = this.OnDmtpActorHandshaking;
|
||||
actor.OnCreateChannel = this.OnDmtpActorCreateChannel;
|
||||
actor.Closed = this.OnDmtpActorClose;
|
||||
actor.Routing = this.OnDmtpActorRouting;
|
||||
actor.Handshaked = this.OnDmtpActorHandshaked;
|
||||
actor.Handshaking = this.OnDmtpActorHandshaking;
|
||||
actor.CreatedChannel = this.OnDmtpActorCreateChannel;
|
||||
actor.Logger = this.Logger;
|
||||
this.m_smtpActor = actor;
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
protected override void Dispose(bool disposing)
|
||||
{
|
||||
this.DmtpActor.SafeDispose();
|
||||
base.Dispose(disposing);
|
||||
this.m_dmtpActor = actor;
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
protected override async Task ReceivedData(ReceivedDataEventArgs e)
|
||||
{
|
||||
var message = (DmtpMessage)e.RequestInfo;
|
||||
if (!this.m_smtpActor.InputReceivedData(message))
|
||||
if (!await this.m_dmtpActor.InputReceivedData(message).ConfigureFalseAwait())
|
||||
{
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpReceivedPlugin.OnDmtpReceived), this, new DmtpMessageEventArgs(message));
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpReceivedPlugin.OnDmtpReceived), this, new DmtpMessageEventArgs(message)).ConfigureFalseAwait();
|
||||
}
|
||||
await base.ReceivedData(e);
|
||||
await base.ReceivedData(e).ConfigureFalseAwait();
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
protected override async Task OnConnected(ConnectedEventArgs e)
|
||||
{
|
||||
this.m_smtpActor.Id = this.Id;
|
||||
await base.OnConnected(e);
|
||||
this.m_dmtpActor.Id = this.Id;
|
||||
await base.OnConnected(e).ConfigureFalseAwait();
|
||||
|
||||
_ = Task.Run(async () =>
|
||||
{
|
||||
await Task.Delay(this.VerifyTimeout);
|
||||
await Task.Delay(this.VerifyTimeout).ConfigureFalseAwait();
|
||||
if (!this.IsHandshaked)
|
||||
{
|
||||
this.TryShutdown();
|
||||
@@ -228,21 +241,20 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
});
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
protected override async Task OnDisconnected(DisconnectEventArgs e)
|
||||
{
|
||||
this.DmtpActor.Close(false, e.Message);
|
||||
await base.OnDisconnected(e);
|
||||
}
|
||||
|
||||
private void ThisDmtpActorOutputSend(DmtpActor actor, ArraySegment<byte>[] transferBytes)
|
||||
{
|
||||
base.Send(transferBytes);
|
||||
}
|
||||
|
||||
private void ThisOnResetId(DmtpActor rpcActor, WaitSetId waitSetId)
|
||||
private Task ThisDmtpActorOutputSendAsync(DmtpActor actor, ArraySegment<byte>[] transferBytes)
|
||||
{
|
||||
this.DirectResetId(waitSetId.NewId);
|
||||
return base.SendAsync(transferBytes);
|
||||
}
|
||||
|
||||
private Task ThisOnResetId(DmtpActor rpcActor, IdChangedEventArgs e)
|
||||
{
|
||||
this.DirectResetId(e.NewId);
|
||||
return EasyTask.CompletedTask;
|
||||
}
|
||||
|
||||
#region 发送
|
||||
|
@@ -84,7 +84,7 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
}
|
||||
|
||||
var message = DmtpMessage.CreateFrom(e.ByteBlock);
|
||||
if (!client.InputReceivedData(message))
|
||||
if (!await client.InputReceivedData(message))
|
||||
{
|
||||
if (this.PluginsManager.Enable)
|
||||
{
|
||||
|
@@ -22,7 +22,11 @@
|
||||
// 感谢您的下载和使用
|
||||
//------------------------------------------------------------------------------
|
||||
//------------------------------------------------------------------------------
|
||||
using System;
|
||||
using System.Net;
|
||||
using System.Threading.Tasks;
|
||||
using ThingsGateway.Foundation.Core;
|
||||
using ThingsGateway.Foundation.Sockets;
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
{
|
||||
@@ -45,16 +49,17 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
{
|
||||
this.Id = endPoint.ToString();
|
||||
this.OutputSend = this.RpcActorSend;
|
||||
this.OnCreateChannel = this.OnDmtpActorCreateChannel;
|
||||
this.OutputSendAsync = this.RpcActorSendAsync;
|
||||
this.CreatedChannel = this.OnDmtpActorCreatedChannel;
|
||||
this.m_udpSession = udpSession;
|
||||
this.m_endPoint = endPoint;
|
||||
this.Logger = logger;
|
||||
this.Client = this;
|
||||
}
|
||||
|
||||
private void OnDmtpActorCreateChannel(DmtpActor actor, CreateChannelEventArgs e)
|
||||
private Task OnDmtpActorCreatedChannel(DmtpActor actor, CreateChannelEventArgs e)
|
||||
{
|
||||
this.pluginsManager.Raise(nameof(IDmtpCreateChannelPlugin.OnCreateChannel), this, e);
|
||||
return this.pluginsManager.RaiseAsync(nameof(IDmtpCreateChannelPlugin.OnCreateChannel), this, e);
|
||||
}
|
||||
|
||||
public bool Created(IPluginsManager pluginsManager)
|
||||
@@ -117,5 +122,10 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
{
|
||||
this.m_udpSession.Send(this.m_endPoint, transferBytes);
|
||||
}
|
||||
|
||||
private Task RpcActorSendAsync(DmtpActor actor, ArraySegment<byte>[] transferBytes)
|
||||
{
|
||||
return this.m_udpSession.SendAsync(this.m_endPoint, transferBytes);
|
||||
}
|
||||
}
|
||||
}
|
@@ -22,7 +22,12 @@
|
||||
// 感谢您的下载和使用
|
||||
//------------------------------------------------------------------------------
|
||||
//------------------------------------------------------------------------------
|
||||
using System;
|
||||
using System.Net.WebSockets;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
using ThingsGateway.Foundation.Core;
|
||||
using ThingsGateway.Foundation.Sockets;
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
@@ -50,15 +55,16 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
|
||||
#region 字段
|
||||
|
||||
private readonly SemaphoreSlim m_semaphore = new SemaphoreSlim(1, 1);
|
||||
private readonly SemaphoreSlim m_semaphoreForConnect = new SemaphoreSlim(1, 1);
|
||||
private readonly SemaphoreSlim m_semaphoreForSend = new SemaphoreSlim(1, 1);
|
||||
private ClientWebSocket m_client;
|
||||
private SealedDmtpActor m_dmtpActor;
|
||||
private Func<string, IDmtpActor> m_findDmtpActor;
|
||||
private Func<string, Task<IDmtpActor>> m_findDmtpActor;
|
||||
private int m_receiveBufferSize = 1024 * 10;
|
||||
private ValueCounter m_receiveCounter;
|
||||
private int m_sendBufferSize = 1024 * 10;
|
||||
private ValueCounter m_sendCounter;
|
||||
private TcpDmtpAdapter m_smtpAdapter;
|
||||
private TcpDmtpAdapter m_dmtpAdapter;
|
||||
|
||||
#endregion 字段
|
||||
|
||||
@@ -115,56 +121,15 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
/// <returns></returns>
|
||||
public void Close(string msg = "")
|
||||
{
|
||||
this.DmtpActor.Close(true, msg);
|
||||
this.m_dmtpActor.SendClose(msg);
|
||||
this.m_dmtpActor.Close(msg);
|
||||
this.PrivateClose(msg);
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
public async Task ConnectAsync(int timeout = 5000)
|
||||
public Task ConnectAsync(int timeout = 5000)
|
||||
{
|
||||
try
|
||||
{
|
||||
await this.m_semaphore.WaitAsync();
|
||||
if (this.IsHandshaked)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
if (this.m_client == null || this.m_client.State != WebSocketState.Open)
|
||||
{
|
||||
this.m_client.SafeDispose();
|
||||
this.m_client = new ClientWebSocket();
|
||||
await this.m_client.ConnectAsync(this.RemoteIPHost, default);
|
||||
|
||||
this.m_dmtpActor = new SealedDmtpActor(false)
|
||||
{
|
||||
OutputSend = this.OnDmtpActorSend,
|
||||
OnRouting = this.OnDmtpActorRouting,
|
||||
OnHandshaking = this.OnDmtpActorHandshaking,
|
||||
OnHandshaked = this.OnDmtpActorHandshaked,
|
||||
OnClose = this.OnDmtpActorClose,
|
||||
Logger = this.Logger,
|
||||
Client = this,
|
||||
OnFindDmtpActor = this.m_findDmtpActor,
|
||||
OnCreateChannel = this.OnDmtpActorCreateChannel
|
||||
};
|
||||
|
||||
this.m_smtpAdapter = new TcpDmtpAdapter()
|
||||
{
|
||||
ReceivedCallBack = this.PrivateHandleReceivedData
|
||||
};
|
||||
_ = this.BeginReceive();
|
||||
}
|
||||
|
||||
this.m_dmtpActor.Handshake(this.Config.GetValue(DmtpConfigExtension.VerifyTokenProperty),
|
||||
this.Config.GetValue(DmtpConfigExtension.DefaultIdProperty),
|
||||
timeout, this.Config.GetValue(DmtpConfigExtension.MetadataProperty), CancellationToken.None);
|
||||
this.IsHandshaked = true;
|
||||
}
|
||||
finally
|
||||
{
|
||||
this.m_semaphore.Release();
|
||||
}
|
||||
return this.ConnectAsync(CancellationToken.None, timeout);
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
@@ -172,7 +137,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
try
|
||||
{
|
||||
await this.m_semaphore.WaitAsync();
|
||||
await this.m_semaphoreForConnect.WaitAsync();
|
||||
if (this.IsHandshaked)
|
||||
{
|
||||
return;
|
||||
@@ -187,17 +152,18 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
this.m_dmtpActor = new SealedDmtpActor(false)
|
||||
{
|
||||
OutputSend = this.OnDmtpActorSend,
|
||||
OnRouting = this.OnDmtpActorRouting,
|
||||
OnHandshaking = this.OnDmtpActorHandshaking,
|
||||
OnHandshaked = this.OnDmtpActorHandshaked,
|
||||
OnClose = this.OnDmtpActorClose,
|
||||
OutputSendAsync = this.OnDmtpActorSendAsync,
|
||||
Routing = this.OnDmtpActorRouting,
|
||||
Handshaking = this.OnDmtpActorHandshaking,
|
||||
Handshaked = this.OnDmtpActorHandshaked,
|
||||
Closed = this.OnDmtpActorClose,
|
||||
Logger = this.Logger,
|
||||
Client = this,
|
||||
OnFindDmtpActor = this.m_findDmtpActor,
|
||||
OnCreateChannel = this.OnDmtpActorCreateChannel
|
||||
};
|
||||
FindDmtpActor = this.m_findDmtpActor,
|
||||
CreatedChannel = this.OnDmtpActorCreateChannel
|
||||
}; ;
|
||||
|
||||
this.m_smtpAdapter = new TcpDmtpAdapter()
|
||||
this.m_dmtpAdapter = new TcpDmtpAdapter()
|
||||
{
|
||||
ReceivedCallBack = this.PrivateHandleReceivedData
|
||||
};
|
||||
@@ -211,7 +177,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
}
|
||||
finally
|
||||
{
|
||||
this.m_semaphore.Release();
|
||||
this.m_semaphoreForConnect.Release();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -315,7 +281,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
byteBlock.SetLength(result.Count);
|
||||
this.m_receiveCounter.Increment(result.Count);
|
||||
|
||||
this.m_smtpAdapter.ReceivedInput(byteBlock);
|
||||
this.m_dmtpAdapter.ReceivedInput(byteBlock);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -337,7 +303,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
this.m_client.CloseAsync(WebSocketCloseStatus.NormalClosure, msg, CancellationToken.None);
|
||||
this.m_client.SafeDispose();
|
||||
this.DmtpActor.SafeDispose();
|
||||
this.m_smtpAdapter.SafeDispose();
|
||||
this.m_dmtpAdapter.SafeDispose();
|
||||
this.OnDisconnected(new DisconnectEventArgs(manual, msg));
|
||||
}
|
||||
}
|
||||
@@ -403,7 +369,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
private void PrivateHandleReceivedData(ByteBlock byteBlock, IRequestInfo requestInfo)
|
||||
{
|
||||
var message = (DmtpMessage)requestInfo;
|
||||
if (!this.m_dmtpActor.InputReceivedData(message))
|
||||
if (!this.m_dmtpActor.InputReceivedData(message).GetFalseAwaitResult())
|
||||
{
|
||||
this.PluginsManager.Raise(nameof(IDmtpReceivedPlugin.OnDmtpReceived), this, new DmtpMessageEventArgs(message));
|
||||
}
|
||||
@@ -411,70 +377,81 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
|
||||
#region 内部委托绑定
|
||||
|
||||
private void OnDmtpActorClose(DmtpActor actor, string arg2)
|
||||
private Task OnDmtpActorClose(DmtpActor actor, string arg2)
|
||||
{
|
||||
this.PrivateClose(arg2);
|
||||
return EasyTask.CompletedTask;
|
||||
}
|
||||
|
||||
private void OnDmtpActorCreateChannel(DmtpActor actor, CreateChannelEventArgs e)
|
||||
private Task OnDmtpActorCreateChannel(DmtpActor actor, CreateChannelEventArgs e)
|
||||
{
|
||||
this.OnCreateChannel(e);
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
this.PluginsManager.Raise(nameof(IDmtpCreateChannelPlugin.OnCreateChannel), this, e);
|
||||
return this.OnCreateChannel(e);
|
||||
}
|
||||
|
||||
private void OnDmtpActorHandshaked(DmtpActor actor, DmtpVerifyEventArgs e)
|
||||
private Task OnDmtpActorHandshaked(DmtpActor actor, DmtpVerifyEventArgs e)
|
||||
{
|
||||
this.OnHandshaked(e);
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
if (this.PluginsManager.Raise(nameof(IDmtpHandshakedPlugin.OnDmtpHandshaked), this, e))
|
||||
{
|
||||
return;
|
||||
}
|
||||
return this.OnHandshaked(e);
|
||||
}
|
||||
|
||||
private void OnDmtpActorHandshaking(DmtpActor actor, DmtpVerifyEventArgs e)
|
||||
private Task OnDmtpActorHandshaking(DmtpActor actor, DmtpVerifyEventArgs e)
|
||||
{
|
||||
this.OnHandshaking(e);
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
this.PluginsManager.Raise(nameof(IDmtpHandshakingPlugin.OnDmtpHandshaking), this, e);
|
||||
return this.OnHandshaking(e);
|
||||
}
|
||||
|
||||
private void OnDmtpActorRouting(DmtpActor actor, PackageRouterEventArgs e)
|
||||
private Task OnDmtpActorRouting(DmtpActor actor, PackageRouterEventArgs e)
|
||||
{
|
||||
if (this.PluginsManager.Raise(nameof(IDmtpRoutingPlugin.OnDmtpRouting), this, e))
|
||||
{
|
||||
return;
|
||||
}
|
||||
this.OnRouting(e);
|
||||
return this.OnRouting(e);
|
||||
}
|
||||
|
||||
private void OnDmtpActorSend(DmtpActor actor, ArraySegment<byte>[] transferBytes)
|
||||
{
|
||||
for (var i = 0; i < transferBytes.Length; i++)
|
||||
try
|
||||
{
|
||||
Task task;
|
||||
if (i == transferBytes.Length - 1)
|
||||
this.m_semaphoreForSend.Wait();
|
||||
for (var i = 0; i < transferBytes.Length; i++)
|
||||
{
|
||||
task = this.m_client.SendAsync(transferBytes[i], WebSocketMessageType.Binary, true, CancellationToken.None);
|
||||
Task task;
|
||||
if (i == transferBytes.Length - 1)
|
||||
{
|
||||
task = this.m_client.SendAsync(transferBytes[i], WebSocketMessageType.Binary, true, CancellationToken.None);
|
||||
}
|
||||
else
|
||||
{
|
||||
task = this.m_client.SendAsync(transferBytes[i], WebSocketMessageType.Binary, false, CancellationToken.None);
|
||||
}
|
||||
task.GetFalseAwaitResult();
|
||||
this.m_sendCounter.Increment(transferBytes[i].Count);
|
||||
}
|
||||
else
|
||||
{
|
||||
task = this.m_client.SendAsync(transferBytes[i], WebSocketMessageType.Binary, false, CancellationToken.None);
|
||||
}
|
||||
task.GetFalseAwaitResult();
|
||||
this.m_sendCounter.Increment(transferBytes[i].Count);
|
||||
}
|
||||
finally
|
||||
{
|
||||
this.m_semaphoreForSend.Release();
|
||||
}
|
||||
}
|
||||
|
||||
private async Task OnDmtpActorSendAsync(DmtpActor actor, ArraySegment<byte>[] transferBytes)
|
||||
{
|
||||
try
|
||||
{
|
||||
await this.m_semaphoreForSend.WaitAsync();
|
||||
for (var i = 0; i < transferBytes.Length; i++)
|
||||
{
|
||||
if (i == transferBytes.Length - 1)
|
||||
{
|
||||
await this.m_client.SendAsync(transferBytes[i], WebSocketMessageType.Binary, true, CancellationToken.None);
|
||||
}
|
||||
else
|
||||
{
|
||||
await this.m_client.SendAsync(transferBytes[i], WebSocketMessageType.Binary, false, CancellationToken.None);
|
||||
}
|
||||
this.m_sendCounter.Increment(transferBytes[i].Count);
|
||||
}
|
||||
}
|
||||
finally
|
||||
{
|
||||
this.m_semaphoreForSend.Release();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
#endregion 内部委托绑定
|
||||
@@ -485,32 +462,53 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
/// 当创建通道
|
||||
/// </summary>
|
||||
/// <param name="e"></param>
|
||||
protected virtual void OnCreateChannel(CreateChannelEventArgs e)
|
||||
protected virtual async Task OnCreateChannel(CreateChannelEventArgs e)
|
||||
{
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpCreateChannelPlugin.OnCreateChannel), this, e);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 在完成握手连接时
|
||||
/// </summary>
|
||||
/// <param name="e"></param>
|
||||
protected virtual void OnHandshaked(DmtpVerifyEventArgs e)
|
||||
protected virtual async Task OnHandshaked(DmtpVerifyEventArgs e)
|
||||
{
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpHandshakedPlugin.OnDmtpHandshaked), this, e);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 即将握手连接时
|
||||
/// </summary>
|
||||
/// <param name="e">参数</param>
|
||||
protected virtual void OnHandshaking(DmtpVerifyEventArgs e)
|
||||
protected virtual async Task OnHandshaking(DmtpVerifyEventArgs e)
|
||||
{
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpHandshakingPlugin.OnDmtpHandshaking), this, e);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 当需要转发路由包时
|
||||
/// </summary>
|
||||
/// <param name="e"></param>
|
||||
protected virtual void OnRouting(PackageRouterEventArgs e)
|
||||
protected virtual async Task OnRouting(PackageRouterEventArgs e)
|
||||
{
|
||||
if (e.Handled)
|
||||
{
|
||||
return;
|
||||
}
|
||||
await this.PluginsManager.RaiseAsync(nameof(IDmtpRoutingPlugin.OnDmtpRouting), this, e);
|
||||
}
|
||||
|
||||
#endregion 事件触发
|
||||
|
@@ -10,6 +10,7 @@
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
/// <summary>
|
||||
|
@@ -10,6 +10,9 @@
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
using System.Threading.Tasks;
|
||||
using ThingsGateway.Foundation.Core;
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
/// <summary>
|
||||
|
@@ -10,6 +10,9 @@
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
using ThingsGateway.Foundation.Core;
|
||||
using ThingsGateway.Foundation.Sockets;
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
/// <summary>
|
||||
|
@@ -22,6 +22,7 @@
|
||||
// 感谢您的下载和使用
|
||||
//------------------------------------------------------------------------------
|
||||
//------------------------------------------------------------------------------
|
||||
using ThingsGateway.Foundation.Core;
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
|
@@ -10,6 +10,11 @@
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
using System;
|
||||
using System.IO;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
using ThingsGateway.Foundation.Core;
|
||||
using ThingsGateway.Foundation.Resources;
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
@@ -22,10 +27,10 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
/// <summary>
|
||||
/// 创建一个<see cref="DmtpFileTransferActor"/>
|
||||
/// </summary>
|
||||
/// <param name="smtpActor"></param>
|
||||
public DmtpFileTransferActor(IDmtpActor smtpActor)
|
||||
/// <param name="dmtpActor"></param>
|
||||
public DmtpFileTransferActor(IDmtpActor dmtpActor)
|
||||
{
|
||||
this.DmtpActor = smtpActor;
|
||||
this.DmtpActor = dmtpActor;
|
||||
}
|
||||
|
||||
#region 委托
|
||||
@@ -61,12 +66,8 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
|
||||
#endregion 字段
|
||||
|
||||
/// <summary>
|
||||
/// 处理收到的消息
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
/// <returns></returns>
|
||||
public bool InputReceivedData(DmtpMessage message)
|
||||
/// <inheritdoc/>
|
||||
public async Task<bool> InputReceivedData(DmtpMessage message)
|
||||
{
|
||||
var byteBlock = message.BodyByteBlock;
|
||||
if (message.ProtocolFlags == this.m_pullFileResourceInfo_Request)
|
||||
@@ -77,11 +78,11 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
waitFileResource.UnpackageRouter(byteBlock);
|
||||
if (waitFileResource.Route && this.DmtpActor.AllowRoute)
|
||||
{
|
||||
if (this.DmtpActor.TryRoute(RouteType.PullFile, waitFileResource))
|
||||
if (await this.DmtpActor.TryRoute(new PackageRouterEventArgs(RouteType.PullFile, waitFileResource)))
|
||||
{
|
||||
if (this.DmtpActor.TryFindDmtpActor(waitFileResource.TargetId, out var actor))
|
||||
if (await this.DmtpActor.TryFindDmtpActor(waitFileResource.TargetId) is DmtpActor actor)
|
||||
{
|
||||
actor.Send(this.m_pullFileResourceInfo_Request, byteBlock);
|
||||
await actor.SendAsync(this.m_pullFileResourceInfo_Request, byteBlock);
|
||||
return true;
|
||||
}
|
||||
else
|
||||
@@ -96,12 +97,12 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
waitFileResource.SwitchId();
|
||||
byteBlock.Reset();
|
||||
waitFileResource.Package(byteBlock);
|
||||
this.DmtpActor.Send(this.m_pullFileResourceInfo_Response, byteBlock);
|
||||
await this.DmtpActor.SendAsync(this.m_pullFileResourceInfo_Response, byteBlock);
|
||||
}
|
||||
else
|
||||
{
|
||||
waitFileResource.UnpackageBody(byteBlock);
|
||||
Task.Factory.StartNew(this.RequestPullFileResourceInfo, waitFileResource);
|
||||
_ = this.RequestPullFileResourceInfo(waitFileResource);
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
@@ -118,9 +119,9 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
waitFileResource.UnpackageRouter(byteBlock);
|
||||
if (this.DmtpActor.AllowRoute && waitFileResource.Route)
|
||||
{
|
||||
if (this.DmtpActor.TryFindDmtpActor(waitFileResource.TargetId, out var actor))
|
||||
if (await this.DmtpActor.TryFindDmtpActor(waitFileResource.TargetId) is DmtpActor actor)
|
||||
{
|
||||
actor.Send(this.m_pullFileResourceInfo_Response, byteBlock);
|
||||
await actor.SendAsync(this.m_pullFileResourceInfo_Response, byteBlock);
|
||||
}
|
||||
}
|
||||
else
|
||||
@@ -143,9 +144,9 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
waitFileSection.UnpackageRouter(byteBlock);
|
||||
if (this.DmtpActor.AllowRoute && waitFileSection.Route)
|
||||
{
|
||||
if (this.DmtpActor.TryFindDmtpActor(waitFileSection.TargetId, out var actor))
|
||||
if (await this.DmtpActor.TryFindDmtpActor(waitFileSection.TargetId) is DmtpActor actor)
|
||||
{
|
||||
actor.Send(this.m_pullFileSection_Request, byteBlock);
|
||||
await actor.SendAsync(this.m_pullFileSection_Request, byteBlock);
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -153,7 +154,7 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
waitFileSection.SwitchId();
|
||||
byteBlock.Reset();
|
||||
waitFileSection.Package(byteBlock);
|
||||
this.DmtpActor.Send(this.m_pullFileSection_Response, byteBlock);
|
||||
await this.DmtpActor.SendAsync(this.m_pullFileSection_Response, byteBlock);
|
||||
}
|
||||
}
|
||||
else
|
||||
@@ -177,9 +178,9 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
waitFileSection.UnpackageRouter(byteBlock);
|
||||
if (this.DmtpActor.AllowRoute && waitFileSection.Route)
|
||||
{
|
||||
if (this.DmtpActor.TryFindDmtpActor(waitFileSection.TargetId, out var actor))
|
||||
if (await this.DmtpActor.TryFindDmtpActor(waitFileSection.TargetId) is DmtpActor actor)
|
||||
{
|
||||
actor.Send(this.m_pullFileSection_Response, byteBlock);
|
||||
await actor.SendAsync(this.m_pullFileSection_Response, byteBlock);
|
||||
}
|
||||
}
|
||||
else
|
||||
@@ -202,11 +203,11 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
waitFileResource.UnpackageRouter(byteBlock);
|
||||
if (waitFileResource.Route && this.DmtpActor.AllowRoute)
|
||||
{
|
||||
if (this.DmtpActor.TryRoute(RouteType.PullFile, waitFileResource))
|
||||
if (await this.DmtpActor.TryRoute(new PackageRouterEventArgs(RouteType.PullFile, waitFileResource)))
|
||||
{
|
||||
if (this.DmtpActor.TryFindDmtpActor(waitFileResource.TargetId, out var actor))
|
||||
if (await this.DmtpActor.TryFindDmtpActor(waitFileResource.TargetId) is DmtpActor actor)
|
||||
{
|
||||
actor.Send(this.m_pushFileResourceInfo_Request, byteBlock);
|
||||
await actor.SendAsync(this.m_pushFileResourceInfo_Request, byteBlock);
|
||||
return true;
|
||||
}
|
||||
else
|
||||
@@ -221,12 +222,12 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
byteBlock.Reset();
|
||||
waitFileResource.SwitchId();
|
||||
waitFileResource.Package(byteBlock);
|
||||
this.DmtpActor.Send(this.m_pushFileResourceInfo_Response, byteBlock);
|
||||
await this.DmtpActor.SendAsync(this.m_pushFileResourceInfo_Response, byteBlock);
|
||||
}
|
||||
else
|
||||
{
|
||||
waitFileResource.UnpackageBody(byteBlock);
|
||||
Task.Factory.StartNew(this.RequestPushFileResourceInfo, waitFileResource);
|
||||
_ = this.RequestPushFileResourceInfo(waitFileResource);
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
@@ -243,9 +244,9 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
waitFileResource.UnpackageRouter(byteBlock);
|
||||
if (this.DmtpActor.AllowRoute && waitFileResource.Route)
|
||||
{
|
||||
if (this.DmtpActor.TryFindDmtpActor(waitFileResource.TargetId, out var actor))
|
||||
if (await this.DmtpActor.TryFindDmtpActor(waitFileResource.TargetId) is DmtpActor actor)
|
||||
{
|
||||
actor.Send(this.m_pushFileResourceInfo_Response, byteBlock);
|
||||
await actor.SendAsync(this.m_pushFileResourceInfo_Response, byteBlock);
|
||||
}
|
||||
}
|
||||
else
|
||||
@@ -268,9 +269,9 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
waitFileSection.UnpackageRouter(byteBlock);
|
||||
if (this.DmtpActor.AllowRoute && waitFileSection.Route)
|
||||
{
|
||||
if (this.DmtpActor.TryFindDmtpActor(waitFileSection.TargetId, out var actor))
|
||||
if (await this.DmtpActor.TryFindDmtpActor(waitFileSection.TargetId) is DmtpActor actor)
|
||||
{
|
||||
actor.Send(this.m_pushFileSection_Request, byteBlock);
|
||||
await actor.SendAsync(this.m_pushFileSection_Request, byteBlock);
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -278,7 +279,7 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
waitFileSection.SwitchId();
|
||||
byteBlock.Reset();
|
||||
waitFileSection.Package(byteBlock);
|
||||
this.DmtpActor.Send(this.m_pushFileSection_Response, byteBlock);
|
||||
await this.DmtpActor.SendAsync(this.m_pushFileSection_Response, byteBlock);
|
||||
}
|
||||
}
|
||||
else
|
||||
@@ -303,9 +304,9 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
waitFileSection.UnpackageRouter(byteBlock);
|
||||
if (this.DmtpActor.AllowRoute && waitFileSection.Route)
|
||||
{
|
||||
if (this.DmtpActor.TryFindDmtpActor(waitFileSection.TargetId, out var actor))
|
||||
if (await this.DmtpActor.TryFindDmtpActor(waitFileSection.TargetId) is DmtpActor actor)
|
||||
{
|
||||
actor.Send(this.m_pushFileSection_Response, byteBlock);
|
||||
await actor.SendAsync(this.m_pushFileSection_Response, byteBlock);
|
||||
}
|
||||
}
|
||||
else
|
||||
@@ -328,9 +329,9 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
waitFinishedPackage.UnpackageRouter(byteBlock);
|
||||
if (this.DmtpActor.AllowRoute && waitFinishedPackage.Route)
|
||||
{
|
||||
if (this.DmtpActor.TryFindDmtpActor(waitFinishedPackage.TargetId, out var actor))
|
||||
if (await this.DmtpActor.TryFindDmtpActor(waitFinishedPackage.TargetId) is DmtpActor actor)
|
||||
{
|
||||
actor.Send(this.m_finishedFileResourceInfo_Request, byteBlock);
|
||||
await actor.SendAsync(this.m_finishedFileResourceInfo_Request, byteBlock);
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -338,13 +339,13 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
waitFinishedPackage.SwitchId();
|
||||
byteBlock.Reset();
|
||||
waitFinishedPackage.Package(byteBlock);
|
||||
this.DmtpActor.Send(this.m_finishedFileResourceInfo_Response, byteBlock);
|
||||
await this.DmtpActor.SendAsync(this.m_finishedFileResourceInfo_Response, byteBlock);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
waitFinishedPackage.UnpackageBody(byteBlock);
|
||||
Task.Factory.StartNew(this.RequestFinishedFileResourceInfo, waitFinishedPackage);
|
||||
_ = this.RequestFinishedFileResourceInfo(waitFinishedPackage);
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
@@ -361,9 +362,9 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
waitFinishedPackage.UnpackageRouter(byteBlock);
|
||||
if (this.DmtpActor.AllowRoute && waitFinishedPackage.Route)
|
||||
{
|
||||
if (this.DmtpActor.TryFindDmtpActor(waitFinishedPackage.TargetId, out var actor))
|
||||
if (await this.DmtpActor.TryFindDmtpActor(waitFinishedPackage.TargetId) is DmtpActor actor)
|
||||
{
|
||||
actor.Send(this.m_finishedFileResourceInfo_Response, byteBlock);
|
||||
await actor.SendAsync(this.m_finishedFileResourceInfo_Response, byteBlock);
|
||||
}
|
||||
}
|
||||
else
|
||||
@@ -386,11 +387,11 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
waitSmallFilePackage.UnpackageRouter(byteBlock);
|
||||
if (waitSmallFilePackage.Route && this.DmtpActor.AllowRoute)
|
||||
{
|
||||
if (this.DmtpActor.TryRoute(RouteType.PullFile, waitSmallFilePackage))
|
||||
if (await this.DmtpActor.TryRoute(new PackageRouterEventArgs(RouteType.PullFile, waitSmallFilePackage)))
|
||||
{
|
||||
if (this.DmtpActor.TryFindDmtpActor(waitSmallFilePackage.TargetId, out var actor))
|
||||
if (await this.DmtpActor.TryFindDmtpActor(waitSmallFilePackage.TargetId) is DmtpActor actor)
|
||||
{
|
||||
actor.Send(this.m_pullSmallFile_Request, byteBlock);
|
||||
await actor.SendAsync(this.m_pullSmallFile_Request, byteBlock);
|
||||
return true;
|
||||
}
|
||||
else
|
||||
@@ -405,12 +406,12 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
byteBlock.Reset();
|
||||
waitSmallFilePackage.SwitchId();
|
||||
waitSmallFilePackage.Package(byteBlock);
|
||||
this.DmtpActor.Send(this.m_pullSmallFile_Response, byteBlock);
|
||||
await this.DmtpActor.SendAsync(this.m_pullSmallFile_Response, byteBlock);
|
||||
}
|
||||
else
|
||||
{
|
||||
waitSmallFilePackage.UnpackageBody(byteBlock);
|
||||
Task.Factory.StartNew(this.RequestPullSmallFile, waitSmallFilePackage);
|
||||
_ = this.RequestPullSmallFile(waitSmallFilePackage);
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
@@ -427,9 +428,9 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
waitSmallFilePackage.UnpackageRouter(byteBlock);
|
||||
if (this.DmtpActor.AllowRoute && waitSmallFilePackage.Route)
|
||||
{
|
||||
if (this.DmtpActor.TryFindDmtpActor(waitSmallFilePackage.TargetId, out var actor))
|
||||
if (await this.DmtpActor.TryFindDmtpActor(waitSmallFilePackage.TargetId) is DmtpActor actor)
|
||||
{
|
||||
actor.Send(this.m_pullSmallFile_Response, byteBlock);
|
||||
await actor.SendAsync(this.m_pullSmallFile_Response, byteBlock);
|
||||
}
|
||||
}
|
||||
else
|
||||
@@ -452,11 +453,11 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
waitSmallFilePackage.UnpackageRouter(byteBlock);
|
||||
if (waitSmallFilePackage.Route && this.DmtpActor.AllowRoute)
|
||||
{
|
||||
if (this.DmtpActor.TryRoute(RouteType.PullFile, waitSmallFilePackage))
|
||||
if (await this.DmtpActor.TryRoute(new PackageRouterEventArgs(RouteType.PullFile, waitSmallFilePackage)))
|
||||
{
|
||||
if (this.DmtpActor.TryFindDmtpActor(waitSmallFilePackage.TargetId, out var actor))
|
||||
if (await this.DmtpActor.TryFindDmtpActor(waitSmallFilePackage.TargetId) is DmtpActor actor)
|
||||
{
|
||||
actor.Send(this.m_pushSmallFile_Request, byteBlock);
|
||||
await actor.SendAsync(this.m_pushSmallFile_Request, byteBlock);
|
||||
return true;
|
||||
}
|
||||
else
|
||||
@@ -472,12 +473,12 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
byteBlock.Reset();
|
||||
waitSmallFilePackage.SwitchId();
|
||||
waitSmallFilePackage.Package(byteBlock);
|
||||
this.DmtpActor.Send(this.m_pushSmallFile_Response, byteBlock);
|
||||
await this.DmtpActor.SendAsync(this.m_pushSmallFile_Response, byteBlock);
|
||||
}
|
||||
else
|
||||
{
|
||||
waitSmallFilePackage.UnpackageBody(byteBlock);
|
||||
Task.Factory.StartNew(this.RequestPushSmallFile, waitSmallFilePackage);
|
||||
_ = this.RequestPushSmallFile(waitSmallFilePackage);
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
@@ -495,9 +496,9 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
|
||||
if (this.DmtpActor.AllowRoute && waitSmallFilePackage.Route)
|
||||
{
|
||||
if (this.DmtpActor.TryFindDmtpActor(waitSmallFilePackage.TargetId, out var actor))
|
||||
if (await this.DmtpActor.TryFindDmtpActor(waitSmallFilePackage.TargetId) is DmtpActor actor)
|
||||
{
|
||||
actor.Send(this.m_pushSmallFile_Response, byteBlock);
|
||||
await actor.SendAsync(this.m_pushSmallFile_Response, byteBlock);
|
||||
}
|
||||
}
|
||||
else
|
||||
@@ -568,24 +569,20 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
return this.FileController.GetFullPath(this.m_rootPath, path);
|
||||
}
|
||||
|
||||
private bool TryFindDmtpFileTransferActor(string targetId, out DmtpFileTransferActor rpcActor)
|
||||
private async Task<DmtpFileTransferActor> TryFindDmtpFileTransferActor(string targetId)
|
||||
{
|
||||
if (targetId == this.DmtpActor.Id)
|
||||
{
|
||||
rpcActor = this;
|
||||
return true;
|
||||
return this;
|
||||
}
|
||||
if (this.DmtpActor.TryFindDmtpActor(targetId, out var smtpActor))
|
||||
if (await this.DmtpActor.TryFindDmtpActor(targetId).ConfigureFalseAwait() is DmtpActor dmtpActor)
|
||||
{
|
||||
if (smtpActor.GetDmtpFileTransferActor() is DmtpFileTransferActor newActor)
|
||||
if (dmtpActor.GetDmtpFileTransferActor() is DmtpFileTransferActor newActor)
|
||||
{
|
||||
rpcActor = newActor;
|
||||
return true;
|
||||
return newActor;
|
||||
}
|
||||
}
|
||||
|
||||
rpcActor = default;
|
||||
return false;
|
||||
return default;
|
||||
}
|
||||
|
||||
#region Id传输
|
||||
@@ -598,9 +595,9 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
return this.PrivateFinishedFileResourceInfo(targetId, fileResourceInfo, code, metadata, timeout, token);
|
||||
}
|
||||
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpFileTransferActor(targetId, out var rpcActor))
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpFileTransferActor(targetId).GetFalseAwaitResult() is DmtpFileTransferActor actor)
|
||||
{
|
||||
return rpcActor.FinishedFileResourceInfo(fileResourceInfo, code, metadata, timeout, token);
|
||||
return actor.FinishedFileResourceInfo(fileResourceInfo, code, metadata, timeout, token);
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -625,9 +622,9 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
return this.PrivatePullFileResourceInfo(targetId, path, metadata, fileSectionSize, timeout, token);
|
||||
}
|
||||
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpFileTransferActor(targetId, out var rpcActor))
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpFileTransferActor(targetId).GetFalseAwaitResult() is DmtpFileTransferActor actor)
|
||||
{
|
||||
return rpcActor.PullFileResourceInfo(path, metadata, fileSectionSize, timeout, token);
|
||||
return actor.PullFileResourceInfo(path, metadata, fileSectionSize, timeout, token);
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -652,9 +649,9 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
return this.PrivatePullFileSection(targetId, fileSection, timeout, token);
|
||||
}
|
||||
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpFileTransferActor(targetId, out var rpcActor))
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpFileTransferActor(targetId).GetFalseAwaitResult() is DmtpFileTransferActor actor)
|
||||
{
|
||||
return rpcActor.PullFileSection(fileSection, timeout, token);
|
||||
return actor.PullFileSection(fileSection, timeout, token);
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -679,9 +676,9 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
return this.PrivatePushFileResourceInfo(targetId, savePath, fileResourceLocator, metadata, timeout, token);
|
||||
}
|
||||
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpFileTransferActor(targetId, out var rpcActor))
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpFileTransferActor(targetId).GetFalseAwaitResult() is DmtpFileTransferActor actor)
|
||||
{
|
||||
return rpcActor.PushFileResourceInfo(savePath, fileResourceLocator, metadata, timeout, token);
|
||||
return actor.PushFileResourceInfo(savePath, fileResourceLocator, metadata, timeout, token);
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -715,9 +712,9 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
return this.PrivatePushFileSection(targetId, fileResourceLocator, fileSection, timeout, token);
|
||||
}
|
||||
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpFileTransferActor(targetId, out var rpcActor))
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpFileTransferActor(targetId).GetFalseAwaitResult() is DmtpFileTransferActor actor)
|
||||
{
|
||||
return rpcActor.PushFileSection(fileResourceLocator, fileSection, timeout, token);
|
||||
return actor.PushFileSection(fileResourceLocator, fileSection, timeout, token);
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -1261,7 +1258,7 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
{
|
||||
waitFinishedPackage.SwitchId();
|
||||
waitFinishedPackage.Package(byteBlock);
|
||||
this.DmtpActor.Send(this.m_finishedFileResourceInfo_Response, byteBlock);
|
||||
await this.DmtpActor.SendAsync(this.m_finishedFileResourceInfo_Response, byteBlock);
|
||||
}
|
||||
|
||||
var args = new FileTransferedEventArgs(transferType, waitFinishedPackage?.Metadata, resourceInfo?.FileInfo, waitFinishedPackage.Code == ResultCode.Canceled ? Result.Canceled : resultThis)
|
||||
@@ -1332,7 +1329,7 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
{
|
||||
waitFileResource.SwitchId();
|
||||
waitFileResource.Package(byteBlock);
|
||||
this.DmtpActor.Send(this.m_pullFileResourceInfo_Response, byteBlock);
|
||||
await this.DmtpActor.SendAsync(this.m_pullFileResourceInfo_Response, byteBlock);
|
||||
}
|
||||
}
|
||||
catch
|
||||
@@ -1454,7 +1451,7 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
{
|
||||
waitFileResource.SwitchId();
|
||||
waitFileResource.Package(byteBlock);
|
||||
this.DmtpActor.Send(this.m_pushFileResourceInfo_Response, byteBlock);
|
||||
await this.DmtpActor.SendAsync(this.m_pushFileResourceInfo_Response, byteBlock);
|
||||
}
|
||||
}
|
||||
catch
|
||||
@@ -1528,7 +1525,7 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
/// <inheritdoc/>
|
||||
public PullSmallFileResult PullSmallFile(string targetId, string path, Metadata metadata = null, int timeout = 5000, CancellationToken token = default)
|
||||
{
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpFileTransferActor(targetId, out var actor))
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpFileTransferActor(targetId).GetFalseAwaitResult() is DmtpFileTransferActor actor)
|
||||
{
|
||||
return actor.PullSmallFile(path, metadata, timeout, token);
|
||||
}
|
||||
@@ -1565,9 +1562,9 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
/// <inheritdoc/>
|
||||
public Result PushSmallFile(string targetId, string savePath, FileInfo fileInfo, Metadata metadata = null, int timeout = 5000, CancellationToken token = default)
|
||||
{
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpFileTransferActor(targetId, out var rpcActor))
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpFileTransferActor(targetId).GetFalseAwaitResult() is DmtpFileTransferActor actor)
|
||||
{
|
||||
return rpcActor.PushSmallFile(savePath, fileInfo, metadata, timeout, token);
|
||||
return actor.PushSmallFile(savePath, fileInfo, metadata, timeout, token);
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -1827,7 +1824,7 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
{
|
||||
waitSmallFilePackage.SwitchId();
|
||||
waitSmallFilePackage.Package(byteBlock);
|
||||
this.DmtpActor.Send(this.m_pullSmallFile_Response, byteBlock);
|
||||
await this.DmtpActor.SendAsync(this.m_pullSmallFile_Response, byteBlock);
|
||||
}
|
||||
|
||||
var resultArgs = new FileTransferedEventArgs(
|
||||
@@ -1891,7 +1888,7 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
using (var byteBlock = new ByteBlock())
|
||||
{
|
||||
waitSmallFilePackage.Package(byteBlock);
|
||||
this.DmtpActor.Send(this.m_pushSmallFile_Response, byteBlock);
|
||||
await this.DmtpActor.SendAsync(this.m_pushSmallFile_Response, byteBlock);
|
||||
}
|
||||
|
||||
var resultArgs = new FileTransferedEventArgs(
|
||||
|
@@ -22,6 +22,10 @@
|
||||
// 感谢您的下载和使用
|
||||
//------------------------------------------------------------------------------
|
||||
//------------------------------------------------------------------------------
|
||||
using System.IO;
|
||||
using System.Threading;
|
||||
using System.Threading.Tasks;
|
||||
using ThingsGateway.Foundation.Core;
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
{
|
||||
|
@@ -22,6 +22,11 @@
|
||||
// 感谢您的下载和使用
|
||||
//------------------------------------------------------------------------------
|
||||
//------------------------------------------------------------------------------
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
using System.Linq;
|
||||
using ThingsGateway.Foundation.Core;
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
{
|
||||
|
@@ -22,6 +22,7 @@
|
||||
// 感谢您的下载和使用
|
||||
//------------------------------------------------------------------------------
|
||||
//------------------------------------------------------------------------------
|
||||
using ThingsGateway.Foundation.Core;
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
{
|
||||
|
@@ -22,6 +22,7 @@
|
||||
// 感谢您的下载和使用
|
||||
//------------------------------------------------------------------------------
|
||||
//------------------------------------------------------------------------------
|
||||
using ThingsGateway.Foundation.Core;
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
{
|
||||
|
@@ -10,6 +10,7 @@
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
{
|
||||
/// <summary>
|
||||
@@ -48,7 +49,7 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
/// <inheritdoc/>
|
||||
public Task OnDmtpHandshaking(IDmtpActorObject client, DmtpVerifyEventArgs e)
|
||||
{
|
||||
var smtpFileTransferActor = new DmtpFileTransferActor(client.DmtpActor)
|
||||
var dmtpFileTransferActor = new DmtpFileTransferActor(client.DmtpActor)
|
||||
{
|
||||
FileController = this.m_fileResourceController,
|
||||
OnFileTransfering = this.OnFileTransfering,
|
||||
@@ -56,25 +57,25 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
RootPath = this.RootPath,
|
||||
MaxSmallFileLength = this.MaxSmallFileLength
|
||||
};
|
||||
smtpFileTransferActor.SetProtocolFlags(this.StartProtocol);
|
||||
client.DmtpActor.SetDmtpFileTransferActor(smtpFileTransferActor);
|
||||
dmtpFileTransferActor.SetProtocolFlags(this.StartProtocol);
|
||||
client.DmtpActor.SetDmtpFileTransferActor(dmtpFileTransferActor);
|
||||
|
||||
return e.InvokeNext();
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
public Task OnDmtpReceived(IDmtpActorObject client, DmtpMessageEventArgs e)
|
||||
public async Task OnDmtpReceived(IDmtpActorObject client, DmtpMessageEventArgs e)
|
||||
{
|
||||
if (client.DmtpActor.GetDmtpFileTransferActor() is DmtpFileTransferActor smtpFileTransferActor)
|
||||
if (client.DmtpActor.GetDmtpFileTransferActor() is DmtpFileTransferActor dmtpFileTransferActor)
|
||||
{
|
||||
if (smtpFileTransferActor.InputReceivedData(e.DmtpMessage))
|
||||
if (await dmtpFileTransferActor.InputReceivedData(e.DmtpMessage))
|
||||
{
|
||||
e.Handled = true;
|
||||
return EasyTask.CompletedTask;
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
return e.InvokeNext();
|
||||
await e.InvokeNext();
|
||||
}
|
||||
|
||||
/// <inheritdoc cref="IDmtpFileTransferActor.MaxSmallFileLength"/>
|
||||
|
@@ -48,21 +48,21 @@ namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
/// <summary>
|
||||
/// 从<see cref="DmtpActor"/>中获取<see cref="IDmtpFileTransferActor"/>
|
||||
/// </summary>
|
||||
/// <param name="smtpActor"></param>
|
||||
/// <param name="dmtpActor"></param>
|
||||
/// <returns></returns>
|
||||
public static IDmtpFileTransferActor GetDmtpFileTransferActor(this IDmtpActor smtpActor)
|
||||
public static IDmtpFileTransferActor GetDmtpFileTransferActor(this IDmtpActor dmtpActor)
|
||||
{
|
||||
return smtpActor.GetValue(DmtpFileTransferActorProperty);
|
||||
return dmtpActor.GetValue(DmtpFileTransferActorProperty);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 向<see cref="DmtpActor"/>中设置<see cref="DmtpFileTransferActor"/>
|
||||
/// </summary>
|
||||
/// <param name="smtpActor"></param>
|
||||
/// <param name="smtpRpcActor"></param>
|
||||
internal static void SetDmtpFileTransferActor(this IDmtpActor smtpActor, DmtpFileTransferActor smtpRpcActor)
|
||||
/// <param name="dmtpActor"></param>
|
||||
/// <param name="dmtpRpcActor"></param>
|
||||
internal static void SetDmtpFileTransferActor(this IDmtpActor dmtpActor, DmtpFileTransferActor dmtpRpcActor)
|
||||
{
|
||||
smtpActor.SetValue(DmtpFileTransferActorProperty, smtpRpcActor);
|
||||
dmtpActor.SetValue(DmtpFileTransferActorProperty, dmtpRpcActor);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@@ -10,6 +10,7 @@
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
{
|
||||
/// <summary>
|
||||
|
@@ -10,6 +10,7 @@
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
{
|
||||
/// <summary>
|
||||
|
@@ -22,6 +22,8 @@
|
||||
// 感谢您的下载和使用
|
||||
//------------------------------------------------------------------------------
|
||||
//------------------------------------------------------------------------------
|
||||
using System;
|
||||
using System.IO;
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp.FileTransfer
|
||||
{
|
||||
|
@@ -22,10 +22,10 @@ namespace ThingsGateway.Foundation.Dmtp.Redis
|
||||
/// <summary>
|
||||
/// DmtpRedisActor
|
||||
/// </summary>
|
||||
/// <param name="smtpActor"></param>
|
||||
public DmtpRedisActor(IDmtpActor smtpActor)
|
||||
/// <param name="dmtpActor"></param>
|
||||
public DmtpRedisActor(IDmtpActor dmtpActor)
|
||||
{
|
||||
this.DmtpActor = smtpActor;
|
||||
this.DmtpActor = dmtpActor;
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
@@ -241,7 +241,7 @@ namespace ThingsGateway.Foundation.Dmtp.Redis
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
/// <returns></returns>
|
||||
public bool InputReceivedData(DmtpMessage message)
|
||||
public async Task<bool> InputReceivedData(DmtpMessage message)
|
||||
{
|
||||
if (message.ProtocolFlags == this.m_redis_Request)
|
||||
{
|
||||
@@ -311,7 +311,7 @@ namespace ThingsGateway.Foundation.Dmtp.Redis
|
||||
using (var byteBlock = new ByteBlock())
|
||||
{
|
||||
waitResult.Package(byteBlock);
|
||||
this.DmtpActor.Send(this.m_redis_Response, byteBlock);
|
||||
await this.DmtpActor.SendAsync(this.m_redis_Response, byteBlock);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
@@ -22,6 +22,8 @@
|
||||
// 感谢您的下载和使用
|
||||
//------------------------------------------------------------------------------
|
||||
//------------------------------------------------------------------------------
|
||||
using System;
|
||||
using ThingsGateway.Foundation.Core;
|
||||
using ThingsGateway.Foundation.Resources;
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp.Redis
|
||||
@@ -52,16 +54,16 @@ namespace ThingsGateway.Foundation.Dmtp.Redis
|
||||
/// <summary>
|
||||
/// 从<see cref="DmtpActor"/>中获得<see cref="IDmtpRedisActor"/>
|
||||
/// </summary>
|
||||
/// <param name="smtpActor"></param>
|
||||
/// <param name="dmtpActor"></param>
|
||||
/// <returns></returns>
|
||||
public static IDmtpRedisActor GetDmtpRedisActor(this IDmtpActor smtpActor)
|
||||
public static IDmtpRedisActor GetDmtpRedisActor(this IDmtpActor dmtpActor)
|
||||
{
|
||||
return smtpActor.GetValue(DmtpRedisActorProperty);
|
||||
return dmtpActor.GetValue(DmtpRedisActorProperty);
|
||||
}
|
||||
|
||||
internal static void SetStmpRedisActor(this IDmtpActor smtpActor, DmtpRedisActor redisClient)
|
||||
internal static void SetStmpRedisActor(this IDmtpActor dmtpActor, DmtpRedisActor redisClient)
|
||||
{
|
||||
smtpActor.SetValue(DmtpRedisActorProperty, redisClient);
|
||||
dmtpActor.SetValue(DmtpRedisActorProperty, redisClient);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@@ -22,6 +22,8 @@
|
||||
// 感谢您的下载和使用
|
||||
//------------------------------------------------------------------------------
|
||||
//------------------------------------------------------------------------------
|
||||
using System.Threading.Tasks;
|
||||
using ThingsGateway.Foundation.Core;
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp.Redis
|
||||
{
|
||||
@@ -58,30 +60,30 @@ namespace ThingsGateway.Foundation.Dmtp.Redis
|
||||
/// <inheritdoc/>
|
||||
public Task OnDmtpHandshaking(IDmtpActorObject client, DmtpVerifyEventArgs e)
|
||||
{
|
||||
var smtpRedisActor = new DmtpRedisActor(client.DmtpActor)
|
||||
var dmtpRedisActor = new DmtpRedisActor(client.DmtpActor)
|
||||
{
|
||||
ICache = this.ICache,
|
||||
Converter = this.Converter
|
||||
};
|
||||
|
||||
smtpRedisActor.SetProtocolFlags(this.StartProtocol);
|
||||
client.DmtpActor.SetStmpRedisActor(smtpRedisActor);
|
||||
dmtpRedisActor.SetProtocolFlags(this.StartProtocol);
|
||||
client.DmtpActor.SetStmpRedisActor(dmtpRedisActor);
|
||||
|
||||
return e.InvokeNext();
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
public Task OnDmtpReceived(IDmtpActorObject client, DmtpMessageEventArgs e)
|
||||
public async Task OnDmtpReceived(IDmtpActorObject client, DmtpMessageEventArgs e)
|
||||
{
|
||||
if (client.DmtpActor.GetDmtpRedisActor() is DmtpRedisActor redisClient)
|
||||
{
|
||||
if (redisClient.InputReceivedData(e.DmtpMessage))
|
||||
if (await redisClient.InputReceivedData(e.DmtpMessage))
|
||||
{
|
||||
e.Handled = true;
|
||||
return EasyTask.CompletedTask;
|
||||
return;
|
||||
}
|
||||
}
|
||||
return e.InvokeNext();
|
||||
await e.InvokeNext();
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
|
@@ -22,6 +22,8 @@
|
||||
// 感谢您的下载和使用
|
||||
//------------------------------------------------------------------------------
|
||||
//------------------------------------------------------------------------------
|
||||
using System;
|
||||
using ThingsGateway.Foundation.Core;
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp.Redis
|
||||
{
|
||||
|
@@ -22,6 +22,7 @@
|
||||
// 感谢您的下载和使用
|
||||
//------------------------------------------------------------------------------
|
||||
//------------------------------------------------------------------------------
|
||||
using ThingsGateway.Foundation.Core;
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp.Redis
|
||||
{
|
||||
|
@@ -36,10 +36,10 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
/// <summary>
|
||||
/// 创建一个DmtpRpcActor
|
||||
/// </summary>
|
||||
/// <param name="smtpActor"></param>
|
||||
public DmtpRpcActor(IDmtpActor smtpActor)
|
||||
/// <param name="dmtpActor"></param>
|
||||
public DmtpRpcActor(IDmtpActor dmtpActor)
|
||||
{
|
||||
this.DmtpActor = smtpActor;
|
||||
this.DmtpActor = dmtpActor;
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
@@ -69,7 +69,7 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
/// <returns></returns>
|
||||
public bool InputReceivedData(DmtpMessage message)
|
||||
public async Task<bool> InputReceivedData(DmtpMessage message)
|
||||
{
|
||||
var byteBlock = message.BodyByteBlock;
|
||||
|
||||
@@ -77,14 +77,13 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
{
|
||||
try
|
||||
{
|
||||
//Console.WriteLine(byteBlock.Len);
|
||||
var rpcPackage = new DmtpRpcPackage();
|
||||
rpcPackage.UnpackageRouter(byteBlock);
|
||||
if (rpcPackage.Route && this.DmtpActor.AllowRoute)
|
||||
{
|
||||
if (this.DmtpActor.TryRoute(RouteType.Rpc, rpcPackage))
|
||||
if (await this.DmtpActor.TryRoute(new PackageRouterEventArgs(RouteType.Rpc, rpcPackage)).ConfigureFalseAwait())
|
||||
{
|
||||
if (this.DmtpActor.TryFindDmtpActor(rpcPackage.TargetId, out var actor))
|
||||
if (await this.DmtpActor.TryFindDmtpActor(rpcPackage.TargetId).ConfigureFalseAwait() is DmtpActor actor)
|
||||
{
|
||||
actor.Send(this.m_invoke_Request, byteBlock);
|
||||
return true;
|
||||
@@ -108,8 +107,7 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
else
|
||||
{
|
||||
rpcPackage.UnpackageBody(byteBlock);
|
||||
Task.Factory.StartNew(this.InvokeThis, rpcPackage);
|
||||
//this.InvokeThis(rpcPackage);
|
||||
_ = Task.Factory.StartNew(this.InvokeThis, rpcPackage);
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
@@ -126,7 +124,7 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
rpcPackage.UnpackageRouter(byteBlock);
|
||||
if (this.DmtpActor.AllowRoute && rpcPackage.Route)
|
||||
{
|
||||
if (this.DmtpActor.TryFindDmtpActor(rpcPackage.TargetId, out var actor))
|
||||
if (await this.DmtpActor.TryFindDmtpActor(rpcPackage.TargetId).ConfigureFalseAwait() is DmtpActor actor)
|
||||
{
|
||||
actor.Send(this.m_invoke_Response, byteBlock);
|
||||
}
|
||||
@@ -151,7 +149,7 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
canceledPackage.UnpackageRouter(byteBlock);
|
||||
if (this.DmtpActor.AllowRoute && canceledPackage.Route)
|
||||
{
|
||||
if (this.DmtpActor.TryFindDmtpActor(canceledPackage.TargetId, out var actor))
|
||||
if (await this.DmtpActor.TryFindDmtpActor(canceledPackage.TargetId).ConfigureFalseAwait() is DmtpActor actor)
|
||||
{
|
||||
actor.Send(this.m_cancelInvoke, byteBlock);
|
||||
}
|
||||
@@ -203,7 +201,7 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
try
|
||||
{
|
||||
var rpcPackage = (DmtpRpcPackage)o;
|
||||
//Console.WriteLine(rpcPackage.MethodName);
|
||||
|
||||
var psData = rpcPackage.ParametersBytes;
|
||||
if (rpcPackage.Feedback == FeedbackType.WaitSend)
|
||||
{
|
||||
@@ -227,7 +225,7 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
|
||||
var invokeResult = new InvokeResult();
|
||||
object[] ps = null;
|
||||
var methodInstance = this.GetInvokeMethod?.Invoke(rpcPackage.MethodName);
|
||||
var methodInstance = this.GetInvokeMethod.Invoke(rpcPackage.MethodName);
|
||||
DmtpRpcCallContext callContext = null;
|
||||
if (methodInstance != null)
|
||||
{
|
||||
@@ -283,7 +281,7 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
{
|
||||
transientRpcServer.CallContext = callContext;
|
||||
}
|
||||
invokeResult = await RpcStore.ExecuteAsync(rpcServer, ps, callContext);
|
||||
invokeResult = await RpcStore.ExecuteAsync(rpcServer, ps, callContext).ConfigureFalseAwait();
|
||||
}
|
||||
|
||||
if (rpcPackage.Feedback == FeedbackType.OnlySend)
|
||||
@@ -369,24 +367,20 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
}
|
||||
}
|
||||
|
||||
private bool TryFindDmtpRpcActor(string targetId, out DmtpRpcActor rpcActor)
|
||||
private async Task<DmtpRpcActor> TryFindDmtpRpcActor(string targetId)
|
||||
{
|
||||
if (targetId == this.DmtpActor.Id)
|
||||
{
|
||||
rpcActor = this;
|
||||
return true;
|
||||
return this;
|
||||
}
|
||||
if (this.DmtpActor.TryFindDmtpActor(targetId, out var smtpActor))
|
||||
if (await this.DmtpActor.TryFindDmtpActor(targetId).ConfigureFalseAwait() is DmtpActor dmtpActor)
|
||||
{
|
||||
if (smtpActor.GetDmtpRpcActor() is DmtpRpcActor newActor)
|
||||
if (dmtpActor.GetDmtpRpcActor() is DmtpRpcActor newActor)
|
||||
{
|
||||
rpcActor = newActor;
|
||||
return true;
|
||||
return newActor;
|
||||
}
|
||||
}
|
||||
|
||||
rpcActor = default;
|
||||
return false;
|
||||
return default;
|
||||
}
|
||||
|
||||
#region Rpc
|
||||
@@ -504,8 +498,6 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
|
||||
var waitData = this.DmtpActor.WaitHandlePool.GetWaitData(rpcPackage);
|
||||
|
||||
|
||||
|
||||
try
|
||||
{
|
||||
using (var byteBlock = new ByteBlock())
|
||||
@@ -532,7 +524,6 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
this.DmtpActor.Send(this.m_invoke_Request, byteBlock.Buffer, 0, byteBlock.Len);
|
||||
}
|
||||
|
||||
|
||||
switch (invokeOption.FeedbackType)
|
||||
{
|
||||
case FeedbackType.OnlySend:
|
||||
@@ -689,8 +680,6 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
|
||||
var waitData = this.DmtpActor.WaitHandlePool.GetWaitData(rpcPackage);
|
||||
|
||||
|
||||
|
||||
try
|
||||
{
|
||||
using (var byteBlock = new ByteBlock())
|
||||
@@ -722,7 +711,6 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
this.DmtpActor.Send(this.m_invoke_Request, byteBlock.Buffer, 0, byteBlock.Len);
|
||||
}
|
||||
|
||||
|
||||
switch (invokeOption.FeedbackType)
|
||||
{
|
||||
case FeedbackType.OnlySend:
|
||||
@@ -779,8 +767,6 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
|
||||
var waitData = this.DmtpActor.WaitHandlePool.GetWaitDataAsync(rpcPackage);
|
||||
|
||||
|
||||
|
||||
try
|
||||
{
|
||||
using (var byteBlock = new ByteBlock())
|
||||
@@ -818,7 +804,7 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
|
||||
case FeedbackType.WaitSend:
|
||||
{
|
||||
switch (await waitData.WaitAsync(invokeOption.Timeout))
|
||||
switch (await waitData.WaitAsync(invokeOption.Timeout).ConfigureFalseAwait())
|
||||
{
|
||||
case WaitDataStatus.SetRunning:
|
||||
break;
|
||||
@@ -832,7 +818,7 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
}
|
||||
case FeedbackType.WaitInvoke:
|
||||
{
|
||||
switch (await waitData.WaitAsync(invokeOption.Timeout))
|
||||
switch (await waitData.WaitAsync(invokeOption.Timeout).ConfigureFalseAwait())
|
||||
{
|
||||
case WaitDataStatus.SetRunning:
|
||||
{
|
||||
@@ -898,7 +884,6 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
this.DmtpActor.Send(this.m_invoke_Request, byteBlock.Buffer, 0, byteBlock.Len);
|
||||
}
|
||||
|
||||
|
||||
switch (invokeOption.FeedbackType)
|
||||
{
|
||||
case FeedbackType.OnlySend:
|
||||
@@ -907,7 +892,7 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
}
|
||||
case FeedbackType.WaitSend:
|
||||
{
|
||||
switch (await waitData.WaitAsync(invokeOption.Timeout))
|
||||
switch (await waitData.WaitAsync(invokeOption.Timeout).ConfigureFalseAwait())
|
||||
{
|
||||
case WaitDataStatus.Overtime:
|
||||
{
|
||||
@@ -918,7 +903,7 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
}
|
||||
case FeedbackType.WaitInvoke:
|
||||
{
|
||||
switch (await waitData.WaitAsync(invokeOption.Timeout))
|
||||
switch (await waitData.WaitAsync(invokeOption.Timeout).ConfigureFalseAwait())
|
||||
{
|
||||
case WaitDataStatus.SetRunning:
|
||||
{
|
||||
@@ -961,7 +946,7 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
throw new ArgumentException($"“{nameof(invokeKey)}”不能为 null 或空。", nameof(invokeKey));
|
||||
}
|
||||
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpRpcActor(targetId, out var actor))
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpRpcActor(targetId).GetFalseAwaitResult() is DmtpRpcActor actor)
|
||||
{
|
||||
actor.Invoke(invokeKey, invokeOption, parameters);
|
||||
return;
|
||||
@@ -977,7 +962,6 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
|
||||
var waitData = this.DmtpActor.WaitHandlePool.GetReverseWaitData(rpcPackage);
|
||||
|
||||
|
||||
try
|
||||
{
|
||||
using (var byteBlock = new ByteBlock())
|
||||
@@ -1009,7 +993,6 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
this.DmtpActor.Send(this.m_invoke_Request, byteBlock.Buffer, 0, byteBlock.Len);
|
||||
}
|
||||
|
||||
|
||||
switch (invokeOption.FeedbackType)
|
||||
{
|
||||
case FeedbackType.OnlySend:
|
||||
@@ -1069,9 +1052,9 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
throw new ArgumentException($"“{nameof(invokeKey)}”不能为 null 或空。", nameof(invokeKey));
|
||||
}
|
||||
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpRpcActor(targetId, out var rpcActor))
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpRpcActor(targetId).GetFalseAwaitResult() is DmtpRpcActor actor)
|
||||
{
|
||||
return rpcActor.Invoke(returnType, invokeKey, invokeOption, parameters);
|
||||
return actor.Invoke(returnType, invokeKey, invokeOption, parameters);
|
||||
}
|
||||
|
||||
var rpcPackage = new DmtpRpcPackage
|
||||
@@ -1084,10 +1067,8 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
|
||||
var waitData = this.DmtpActor.WaitHandlePool.GetReverseWaitData(rpcPackage);
|
||||
|
||||
|
||||
try
|
||||
{
|
||||
|
||||
using (var byteBlock = new ByteBlock())
|
||||
{
|
||||
if (invokeOption == default)
|
||||
@@ -1116,7 +1097,6 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
this.DmtpActor.Send(this.m_invoke_Request, byteBlock.Buffer, 0, byteBlock.Len);
|
||||
}
|
||||
|
||||
|
||||
switch (invokeOption.FeedbackType)
|
||||
{
|
||||
case FeedbackType.OnlySend:
|
||||
@@ -1175,9 +1155,9 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
throw new ArgumentException($"“{nameof(invokeKey)}”不能为 null 或空。", nameof(invokeKey));
|
||||
}
|
||||
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpRpcActor(targetId, out var rpcActor))
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpRpcActor(targetId).GetFalseAwaitResult() is DmtpRpcActor actor)
|
||||
{
|
||||
rpcActor.Invoke(invokeKey, invokeOption, ref parameters, types);
|
||||
actor.Invoke(invokeKey, invokeOption, ref parameters, types);
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -1191,7 +1171,6 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
|
||||
var waitData = this.DmtpActor.WaitHandlePool.GetReverseWaitData(rpcPackage);
|
||||
|
||||
|
||||
try
|
||||
{
|
||||
using (var byteBlock = new ByteBlock())
|
||||
@@ -1219,7 +1198,6 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
this.DmtpActor.Send(this.m_invoke_Request, byteBlock.Buffer, 0, byteBlock.Len);
|
||||
}
|
||||
|
||||
|
||||
switch (invokeOption.FeedbackType)
|
||||
{
|
||||
case FeedbackType.OnlySend:
|
||||
@@ -1289,9 +1267,9 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
throw new ArgumentException($"“{nameof(invokeKey)}”不能为 null 或空。", nameof(invokeKey));
|
||||
}
|
||||
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpRpcActor(targetId, out var rpcActor))
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpRpcActor(targetId).GetFalseAwaitResult() is DmtpRpcActor actor)
|
||||
{
|
||||
return rpcActor.Invoke(returnType, invokeKey, invokeOption, ref parameters, types);
|
||||
return actor.Invoke(returnType, invokeKey, invokeOption, ref parameters, types);
|
||||
}
|
||||
|
||||
var rpcPackage = new DmtpRpcPackage
|
||||
@@ -1304,7 +1282,6 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
|
||||
var waitData = this.DmtpActor.WaitHandlePool.GetReverseWaitData(rpcPackage);
|
||||
|
||||
|
||||
try
|
||||
{
|
||||
using (var byteBlock = new ByteBlock())
|
||||
@@ -1330,7 +1307,6 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
this.DmtpActor.Send(this.m_invoke_Request, byteBlock.Buffer, 0, byteBlock.Len);
|
||||
}
|
||||
|
||||
|
||||
switch (invokeOption.FeedbackType)
|
||||
{
|
||||
case FeedbackType.OnlySend:
|
||||
@@ -1400,9 +1376,9 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
throw new ArgumentException($"“{nameof(invokeKey)}”不能为 null 或空。", nameof(invokeKey));
|
||||
}
|
||||
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpRpcActor(targetId, out var actor))
|
||||
if (this.DmtpActor.AllowRoute && await this.TryFindDmtpRpcActor(targetId).ConfigureFalseAwait() is DmtpRpcActor actor)
|
||||
{
|
||||
await actor.InvokeAsync(invokeKey, invokeOption, parameters);
|
||||
await actor.InvokeAsync(invokeKey, invokeOption, parameters).ConfigureFalseAwait();
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -1416,7 +1392,6 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
|
||||
var waitData = this.DmtpActor.WaitHandlePool.GetReverseWaitDataAsync(rpcPackage);
|
||||
|
||||
|
||||
try
|
||||
{
|
||||
using (var byteBlock = new ByteBlock())
|
||||
@@ -1448,7 +1423,6 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
this.DmtpActor.Send(this.m_invoke_Request, byteBlock.Buffer, 0, byteBlock.Len);
|
||||
}
|
||||
|
||||
|
||||
switch (invokeOption.FeedbackType)
|
||||
{
|
||||
case FeedbackType.OnlySend:
|
||||
@@ -1456,7 +1430,7 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
|
||||
case FeedbackType.WaitSend:
|
||||
{
|
||||
switch (await waitData.WaitAsync(invokeOption.Timeout))
|
||||
switch (await waitData.WaitAsync(invokeOption.Timeout).ConfigureFalseAwait())
|
||||
{
|
||||
case WaitDataStatus.SetRunning:
|
||||
break;
|
||||
@@ -1470,7 +1444,7 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
}
|
||||
case FeedbackType.WaitInvoke:
|
||||
{
|
||||
switch (await waitData.WaitAsync(invokeOption.Timeout))
|
||||
switch (await waitData.WaitAsync(invokeOption.Timeout).ConfigureFalseAwait())
|
||||
{
|
||||
case WaitDataStatus.SetRunning:
|
||||
{
|
||||
@@ -1508,9 +1482,9 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
throw new ArgumentException($"“{nameof(invokeKey)}”不能为 null 或空。", nameof(invokeKey));
|
||||
}
|
||||
|
||||
if (this.DmtpActor.AllowRoute && this.TryFindDmtpRpcActor(targetId, out var rpcActor))
|
||||
if (this.DmtpActor.AllowRoute && await this.TryFindDmtpRpcActor(targetId).ConfigureFalseAwait() is DmtpRpcActor actor)
|
||||
{
|
||||
return await rpcActor.InvokeAsync(returnType, invokeKey, invokeOption, parameters);
|
||||
return await actor.InvokeAsync(returnType, invokeKey, invokeOption, parameters).ConfigureFalseAwait();
|
||||
}
|
||||
|
||||
var rpcPackage = new DmtpRpcPackage
|
||||
@@ -1553,8 +1527,6 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
this.DmtpActor.Send(this.m_invoke_Request, byteBlock.Buffer, 0, byteBlock.Len);
|
||||
}
|
||||
|
||||
|
||||
|
||||
switch (invokeOption.FeedbackType)
|
||||
{
|
||||
case FeedbackType.OnlySend:
|
||||
@@ -1563,7 +1535,7 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
}
|
||||
case FeedbackType.WaitSend:
|
||||
{
|
||||
switch (await waitData.WaitAsync(invokeOption.Timeout))
|
||||
switch (await waitData.WaitAsync(invokeOption.Timeout).ConfigureFalseAwait())
|
||||
{
|
||||
case WaitDataStatus.Overtime:
|
||||
{
|
||||
@@ -1574,7 +1546,7 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
}
|
||||
case FeedbackType.WaitInvoke:
|
||||
{
|
||||
switch (await waitData.WaitAsync(invokeOption.Timeout))
|
||||
switch (await waitData.WaitAsync(invokeOption.Timeout).ConfigureFalseAwait())
|
||||
{
|
||||
case WaitDataStatus.SetRunning:
|
||||
{
|
||||
|
@@ -10,6 +10,7 @@
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
{
|
||||
/// <summary>
|
||||
|
@@ -42,11 +42,11 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
/// <summary>
|
||||
/// 从<see cref="DmtpActor"/>中获取<see cref="IDmtpRpcActor"/>
|
||||
/// </summary>
|
||||
/// <param name="smtpActor"></param>
|
||||
/// <param name="dmtpActor"></param>
|
||||
/// <returns></returns>
|
||||
public static IDmtpRpcActor GetDmtpRpcActor(this IDmtpActor smtpActor)
|
||||
public static IDmtpRpcActor GetDmtpRpcActor(this IDmtpActor dmtpActor)
|
||||
{
|
||||
return smtpActor.GetValue(DmtpRpcActorProperty);
|
||||
return dmtpActor.GetValue(DmtpRpcActorProperty);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -57,12 +57,12 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
/// <exception cref="ArgumentNullException"></exception>
|
||||
public static IDmtpRpcActor GetDmtpRpcActor(this IDmtpActorObject client)
|
||||
{
|
||||
var smtpRpcActor = client.DmtpActor.GetDmtpRpcActor();
|
||||
if (smtpRpcActor is null)
|
||||
var dmtpRpcActor = client.DmtpActor.GetDmtpRpcActor();
|
||||
if (dmtpRpcActor is null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(smtpRpcActor), TouchSocketDmtpResource.DmtpRpcActorArgumentNull.GetDescription());
|
||||
throw new ArgumentNullException(nameof(dmtpRpcActor), TouchSocketDmtpResource.DmtpRpcActorArgumentNull.GetDescription());
|
||||
}
|
||||
return smtpRpcActor;
|
||||
return dmtpRpcActor;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -73,22 +73,22 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
/// <exception cref="ArgumentNullException"></exception>
|
||||
public static TDmtpRpcActor GetDmtpRpcActor<TDmtpRpcActor>(this IDmtpActorObject client) where TDmtpRpcActor : IDmtpRpcActor
|
||||
{
|
||||
var smtpRpcActor = client.DmtpActor.GetDmtpRpcActor();
|
||||
if (smtpRpcActor is null)
|
||||
var dmtpRpcActor = client.DmtpActor.GetDmtpRpcActor();
|
||||
if (dmtpRpcActor is null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(smtpRpcActor), TouchSocketDmtpResource.DmtpRpcActorArgumentNull.GetDescription());
|
||||
throw new ArgumentNullException(nameof(dmtpRpcActor), TouchSocketDmtpResource.DmtpRpcActorArgumentNull.GetDescription());
|
||||
}
|
||||
return (TDmtpRpcActor)smtpRpcActor;
|
||||
return (TDmtpRpcActor)dmtpRpcActor;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 向<see cref="DmtpActor"/>中设置<see cref="IDmtpRpcActor"/>
|
||||
/// </summary>
|
||||
/// <param name="smtpActor"></param>
|
||||
/// <param name="smtpRpcActor"></param>
|
||||
internal static void SetDmtpRpcActor(this IDmtpActor smtpActor, IDmtpRpcActor smtpRpcActor)
|
||||
/// <param name="dmtpActor"></param>
|
||||
/// <param name="dmtpRpcActor"></param>
|
||||
internal static void SetDmtpRpcActor(this IDmtpActor dmtpActor, IDmtpRpcActor dmtpRpcActor)
|
||||
{
|
||||
smtpActor.SetValue(DmtpRpcActorProperty, smtpRpcActor);
|
||||
dmtpActor.SetValue(DmtpRpcActorProperty, dmtpRpcActor);
|
||||
}
|
||||
|
||||
#region 插件扩展
|
||||
|
@@ -10,6 +10,7 @@
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
{
|
||||
/// <summary>
|
||||
@@ -94,9 +95,9 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
return this.ActionMap.GetMethodInstance(name);
|
||||
}
|
||||
|
||||
private DmtpRpcActor PrivateCreateDmtpRpcActor(IDmtpActor smtpActor)
|
||||
private DmtpRpcActor PrivateCreateDmtpRpcActor(IDmtpActor dmtpActor)
|
||||
{
|
||||
return new DmtpRpcActor(smtpActor);
|
||||
return new DmtpRpcActor(dmtpActor);
|
||||
}
|
||||
|
||||
#region Rpc配置
|
||||
@@ -135,31 +136,30 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
pluginsManager.Add<IDmtpActorObject, DmtpMessageEventArgs>(nameof(IDmtpReceivedPlugin.OnDmtpReceived), this.OnDmtpReceived);
|
||||
}
|
||||
|
||||
private Task OnDmtpHandshaking(IDmtpActorObject client, DmtpVerifyEventArgs e)
|
||||
private async Task OnDmtpHandshaking(IDmtpActorObject client, DmtpVerifyEventArgs e)
|
||||
{
|
||||
var smtpRpcActor = CreateDmtpRpcActor(client.DmtpActor);
|
||||
smtpRpcActor.RpcStore = this.RpcStore;
|
||||
smtpRpcActor.SerializationSelector = this.SerializationSelector;
|
||||
smtpRpcActor.GetInvokeMethod = this.GetInvokeMethod;
|
||||
var dmtpRpcActor = this.CreateDmtpRpcActor(client.DmtpActor);
|
||||
dmtpRpcActor.RpcStore = this.RpcStore;
|
||||
dmtpRpcActor.SerializationSelector = this.SerializationSelector;
|
||||
dmtpRpcActor.GetInvokeMethod = this.GetInvokeMethod;
|
||||
|
||||
smtpRpcActor.SetProtocolFlags(this.StartProtocol);
|
||||
client.DmtpActor.SetDmtpRpcActor(smtpRpcActor);
|
||||
dmtpRpcActor.SetProtocolFlags(this.StartProtocol);
|
||||
client.DmtpActor.SetDmtpRpcActor(dmtpRpcActor);
|
||||
|
||||
return e.InvokeNext();
|
||||
await e.InvokeNext();
|
||||
}
|
||||
|
||||
private Task OnDmtpReceived(IDmtpActorObject client, DmtpMessageEventArgs e)
|
||||
private async Task OnDmtpReceived(IDmtpActorObject client, DmtpMessageEventArgs e)
|
||||
{
|
||||
if (client.DmtpActor.GetDmtpRpcActor() is DmtpRpcActor smtpRpcActor)
|
||||
if (client.DmtpActor.GetDmtpRpcActor() is DmtpRpcActor dmtpRpcActor)
|
||||
{
|
||||
if (smtpRpcActor.InputReceivedData(e.DmtpMessage))
|
||||
if (await dmtpRpcActor.InputReceivedData(e.DmtpMessage).ConfigureFalseAwait())
|
||||
{
|
||||
e.Handled = true;
|
||||
return EasyTask.CompletedTask;
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
return e.InvokeNext();
|
||||
await e.InvokeNext();
|
||||
}
|
||||
|
||||
#endregion Config
|
||||
|
@@ -108,10 +108,10 @@ namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
|
||||
internal void LoadInvokeOption(IInvokeOption option)
|
||||
{
|
||||
if (option is DmtpInvokeOption smtpInvokeOption)
|
||||
if (option is DmtpInvokeOption dmtpInvokeOption)
|
||||
{
|
||||
this.Feedback = smtpInvokeOption.FeedbackType;
|
||||
this.SerializationType = smtpInvokeOption.SerializationType;
|
||||
this.Feedback = dmtpInvokeOption.FeedbackType;
|
||||
this.SerializationType = dmtpInvokeOption.SerializationType;
|
||||
}
|
||||
else if (option is InvokeOption invokeOption)
|
||||
{
|
||||
|
@@ -22,6 +22,9 @@
|
||||
// 感谢您的下载和使用
|
||||
//------------------------------------------------------------------------------
|
||||
//------------------------------------------------------------------------------
|
||||
using System.Threading;
|
||||
using ThingsGateway.Foundation.Core;
|
||||
using ThingsGateway.Foundation.Rpc;
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp.Rpc
|
||||
{
|
||||
|
@@ -10,6 +10,7 @@
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
/// <summary>
|
||||
@@ -27,6 +28,6 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
/// </summary>
|
||||
/// <param name="message"></param>
|
||||
/// <returns>当满足本协议时,应当返回<see langword="true"/>,其他时候应该返回<see langword="false"/>.</returns>
|
||||
public bool InputReceivedData(DmtpMessage message);
|
||||
public Task<bool> InputReceivedData(DmtpMessage message);
|
||||
}
|
||||
}
|
@@ -12,7 +12,6 @@
|
||||
|
||||
#if NET6_0_OR_GREATER
|
||||
using System.Text.Json.Serialization;
|
||||
|
||||
using ThingsGateway.Foundation.Core;
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp
|
||||
|
@@ -58,7 +58,7 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
failedCount++;
|
||||
if (failedCount > this.MaxFailCount)
|
||||
{
|
||||
client.DmtpActor.Close(true, "自动心跳失败次数达到最大,已断开连接。");
|
||||
client.DmtpActor.Close("自动心跳失败次数达到最大,已断开连接。");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@@ -10,6 +10,7 @@
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
/// <summary>
|
||||
|
@@ -10,6 +10,7 @@
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
/// <summary>
|
||||
|
@@ -10,6 +10,7 @@
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
/// <summary>
|
||||
|
@@ -10,6 +10,7 @@
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
/// <summary>
|
||||
|
@@ -10,6 +10,9 @@
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
using System;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
/// <summary>
|
||||
@@ -18,8 +21,8 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
public class DmtpRouteService : IDmtpRouteService
|
||||
{
|
||||
/// <summary>
|
||||
/// 查找路由的委托
|
||||
/// <inheritdoc/>
|
||||
/// </summary>
|
||||
public Func<string, IDmtpActor> FindDmtpActor { get; set; }
|
||||
public Func<string, Task<IDmtpActor>> FindDmtpActor { get ; set ; }
|
||||
}
|
||||
}
|
@@ -10,6 +10,7 @@
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
/// <summary>
|
||||
@@ -31,12 +32,26 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
/// </summary>
|
||||
/// <param name="container"></param>
|
||||
/// <param name="func"></param>
|
||||
public static void AddDmtpRouteService(this IContainer container, Func<string, IDmtpActor> func)
|
||||
public static void AddDmtpRouteService(this IContainer container, Func<string, Task<IDmtpActor>> func)
|
||||
{
|
||||
container.RegisterSingleton<IDmtpRouteService>(new DmtpRouteService()
|
||||
{
|
||||
FindDmtpActor = func
|
||||
});
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 添加基于设定委托的Dmtp路由服务。
|
||||
/// </summary>
|
||||
/// <param name="container"></param>
|
||||
/// <param name="action"></param>
|
||||
public static void AddDmtpRouteService(this IContainer container, Func<string, IDmtpActor> action)
|
||||
{
|
||||
AddDmtpRouteService(container, async (id) =>
|
||||
{
|
||||
await EasyTask.CompletedTask;
|
||||
return action.Invoke(id);
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
@@ -10,6 +10,7 @@
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
|
||||
namespace ThingsGateway.Foundation.Dmtp
|
||||
{
|
||||
/// <summary>
|
||||
@@ -20,6 +21,6 @@ namespace ThingsGateway.Foundation.Dmtp
|
||||
/// <summary>
|
||||
/// 查找其他IDmtpActor
|
||||
/// </summary>
|
||||
Func<string, IDmtpActor> FindDmtpActor { get; set; }
|
||||
Func<string, Task<IDmtpActor>> FindDmtpActor { get; set; }
|
||||
}
|
||||
}
|
@@ -72,7 +72,7 @@ namespace ThingsGateway.Foundation.Http.WebSockets
|
||||
{
|
||||
return new WebSocketReceiveResult(this.ComplateRead, null);
|
||||
}
|
||||
await this.m_resetEventForRead.WaitOneAsync(token);
|
||||
await this.m_resetEventForRead.WaitOneAsync(token).ConfigureFalseAwait();
|
||||
return new WebSocketReceiveResult(this.ComplateRead, this.m_dataFrame);
|
||||
}
|
||||
#if NET6_0_OR_GREATER
|
||||
@@ -82,7 +82,7 @@ namespace ThingsGateway.Foundation.Http.WebSockets
|
||||
{
|
||||
return new WebSocketReceiveResult(this.ComplateRead, null);
|
||||
}
|
||||
await this.m_resetEventForRead.WaitOneAsync(token);
|
||||
await this.m_resetEventForRead.WaitOneAsync(token).ConfigureFalseAwait();
|
||||
return new WebSocketReceiveResult(this.ComplateRead, this.m_dataFrame);
|
||||
}
|
||||
#endif
|
||||
@@ -146,7 +146,7 @@ namespace ThingsGateway.Foundation.Http.WebSockets
|
||||
{
|
||||
return true;
|
||||
}
|
||||
if (await this.m_resetEventForComplateRead.WaitOneAsync(TimeSpan.FromSeconds(10)))
|
||||
if (await this.m_resetEventForComplateRead.WaitOneAsync(TimeSpan.FromSeconds(10)).ConfigureFalseAwait())
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
@@ -10,7 +10,6 @@
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
using System.Diagnostics;
|
||||
using System.IO.Ports;
|
||||
|
||||
namespace ThingsGateway.Foundation.Serial;
|
||||
@@ -40,13 +39,12 @@ public class SerialCore : IDisposable, ISender
|
||||
public readonly object SyncRoot = new object();
|
||||
|
||||
private long m_bufferRate;
|
||||
private SpinLock m_lock;
|
||||
private bool m_online => m_serialPort?.IsOpen == true;
|
||||
private int m_receiveBufferSize = 1024 * 10;
|
||||
private ValueCounter m_receiveCounter;
|
||||
private int m_sendBufferSize = 1024 * 10;
|
||||
private ValueCounter m_sendCounter;
|
||||
private readonly EasyLock m_semaphore = new EasyLock();
|
||||
private readonly EasyLock m_semaphoreForSend = new EasyLock();
|
||||
private SerialPort m_serialPort;
|
||||
|
||||
#endregion 字段
|
||||
@@ -56,7 +54,6 @@ public class SerialCore : IDisposable, ISender
|
||||
/// </summary>
|
||||
public SerialCore()
|
||||
{
|
||||
this.m_lock = new SpinLock(Debugger.IsAttached);
|
||||
this.m_receiveCounter = new ValueCounter
|
||||
{
|
||||
Period = TimeSpan.FromSeconds(1),
|
||||
@@ -215,7 +212,6 @@ public class SerialCore : IDisposable, ISender
|
||||
this.OnBreakOut = null;
|
||||
this.UserToken = null;
|
||||
this.m_bufferRate = 1;
|
||||
this.m_lock = new SpinLock();
|
||||
this.m_receiveBufferSize = this.MinBufferSize;
|
||||
this.m_sendBufferSize = this.MinBufferSize;
|
||||
}
|
||||
@@ -231,15 +227,14 @@ public class SerialCore : IDisposable, ISender
|
||||
/// <param name="length"></param>
|
||||
public virtual void Send(byte[] buffer, int offset, int length)
|
||||
{
|
||||
var lockTaken = false;
|
||||
try
|
||||
{
|
||||
this.m_lock.Enter(ref lockTaken);
|
||||
this.m_semaphoreForSend.Wait();
|
||||
this.m_serialPort.Write(buffer, offset, length);
|
||||
}
|
||||
finally
|
||||
{
|
||||
if (lockTaken) this.m_lock.Exit(false);
|
||||
this.m_semaphoreForSend.Release();
|
||||
}
|
||||
this.m_sendCounter.Increment(length);
|
||||
}
|
||||
@@ -256,13 +251,13 @@ public class SerialCore : IDisposable, ISender
|
||||
{
|
||||
try
|
||||
{
|
||||
await this.m_semaphore.WaitAsync();
|
||||
await this.m_semaphoreForSend.WaitAsync();
|
||||
|
||||
this.m_serialPort.Write(buffer, offset, length);
|
||||
}
|
||||
finally
|
||||
{
|
||||
this.m_semaphore.Release();
|
||||
this.m_semaphoreForSend.Release();
|
||||
}
|
||||
|
||||
this.m_sendCounter.Increment(length);
|
||||
|
@@ -255,7 +255,7 @@ public class SerialSessionBase : BaseSerial, ISerialSession
|
||||
{
|
||||
Task.Factory.StartNew(this.PrivateOnDisconnecting, new DisconnectEventArgs(true, msg));
|
||||
this.MainSerialPort.TryClose();
|
||||
this.BreakOut(default, true, msg);
|
||||
this.BreakOut(true, msg);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -272,7 +272,7 @@ public class SerialSessionBase : BaseSerial, ISerialSession
|
||||
if (this.m_online)
|
||||
{
|
||||
Task.Factory.StartNew(this.PrivateOnDisconnecting, new DisconnectEventArgs(true, $"{nameof(Dispose)}主动断开"));
|
||||
this.BreakOut(default, true, $"{nameof(Dispose)}主动断开");
|
||||
this.BreakOut(true, $"{nameof(Dispose)}主动断开");
|
||||
}
|
||||
}
|
||||
base.Dispose(disposing);
|
||||
@@ -361,7 +361,16 @@ public class SerialSessionBase : BaseSerial, ISerialSession
|
||||
|
||||
#endregion
|
||||
|
||||
private void BreakOut(SerialCore core, bool manual, string msg)
|
||||
private void SerialCoreBreakOut(SerialCore core, bool manual, string msg)
|
||||
{
|
||||
this.BreakOut(manual, msg);
|
||||
}
|
||||
/// <summary>
|
||||
/// BreakOut。
|
||||
/// </summary>
|
||||
/// <param name="manual"></param>
|
||||
/// <param name="msg"></param>
|
||||
protected void BreakOut(bool manual, string msg)
|
||||
{
|
||||
lock (this.SyncRoot)
|
||||
{
|
||||
@@ -759,7 +768,7 @@ public class SerialSessionBase : BaseSerial, ISerialSession
|
||||
}
|
||||
this.m_serialCore.Reset(serialPort);
|
||||
this.m_serialCore.OnReceived = this.HandleReceived;
|
||||
this.m_serialCore.OnBreakOut = this.BreakOut;
|
||||
this.m_serialCore.OnBreakOut = this.SerialCoreBreakOut;
|
||||
if (this.Config.GetValue(TouchSocketConfigExtension.MinBufferSizeProperty) is int minValue)
|
||||
{
|
||||
this.m_serialCore.MinBufferSize = minValue;
|
||||
|
@@ -10,7 +10,6 @@
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
using System.Diagnostics;
|
||||
using System.Net.Security;
|
||||
using System.Net.Sockets;
|
||||
|
||||
@@ -41,14 +40,13 @@ public class TcpCore : SocketAsyncEventArgs, IDisposable, ISender
|
||||
public readonly object SyncRoot = new object();
|
||||
|
||||
private long m_bufferRate;
|
||||
private SpinLock m_lock;
|
||||
private volatile bool m_online;
|
||||
private int m_receiveBufferSize = 1024 * 10;
|
||||
private ValueCounter m_receiveCounter;
|
||||
private int m_sendBufferSize = 1024 * 10;
|
||||
private ValueCounter m_sendCounter;
|
||||
private Socket m_socket;
|
||||
private readonly EasyLock m_semaphore = new();
|
||||
private readonly EasyLock m_semaphoreForSend = new();
|
||||
#endregion 字段
|
||||
|
||||
/// <summary>
|
||||
@@ -56,7 +54,6 @@ public class TcpCore : SocketAsyncEventArgs, IDisposable, ISender
|
||||
/// </summary>
|
||||
public TcpCore()
|
||||
{
|
||||
this.m_lock = new SpinLock(Debugger.IsAttached);
|
||||
this.m_receiveCounter = new ValueCounter
|
||||
{
|
||||
Period = TimeSpan.FromSeconds(1),
|
||||
@@ -295,7 +292,6 @@ public class TcpCore : SocketAsyncEventArgs, IDisposable, ISender
|
||||
this.OnBreakOut = null;
|
||||
this.UserToken = null;
|
||||
this.m_bufferRate = 1;
|
||||
this.m_lock = new SpinLock();
|
||||
this.m_receiveBufferSize = this.MinBufferSize;
|
||||
this.m_sendBufferSize = this.MinBufferSize;
|
||||
this.m_online = false;
|
||||
@@ -318,10 +314,9 @@ public class TcpCore : SocketAsyncEventArgs, IDisposable, ISender
|
||||
}
|
||||
else
|
||||
{
|
||||
var lockTaken = false;
|
||||
try
|
||||
{
|
||||
this.m_lock.Enter(ref lockTaken);
|
||||
this.m_semaphoreForSend.Wait();
|
||||
while (length > 0)
|
||||
{
|
||||
var r = this.m_socket.Send(buffer, offset, length, SocketFlags.None);
|
||||
@@ -335,7 +330,7 @@ public class TcpCore : SocketAsyncEventArgs, IDisposable, ISender
|
||||
}
|
||||
finally
|
||||
{
|
||||
if (lockTaken) this.m_lock.Exit(false);
|
||||
this.m_semaphoreForSend.Release();
|
||||
}
|
||||
}
|
||||
this.m_sendCounter.Increment(length);
|
||||
@@ -363,7 +358,7 @@ public class TcpCore : SocketAsyncEventArgs, IDisposable, ISender
|
||||
{
|
||||
try
|
||||
{
|
||||
await this.m_semaphore.WaitAsync();
|
||||
await this.m_semaphoreForSend.WaitAsync();
|
||||
|
||||
while (length > 0)
|
||||
{
|
||||
@@ -378,7 +373,7 @@ public class TcpCore : SocketAsyncEventArgs, IDisposable, ISender
|
||||
}
|
||||
finally
|
||||
{
|
||||
this.m_semaphore.Release();
|
||||
this.m_semaphoreForSend.Release();
|
||||
}
|
||||
}
|
||||
#else
|
||||
@@ -390,7 +385,7 @@ public class TcpCore : SocketAsyncEventArgs, IDisposable, ISender
|
||||
{
|
||||
try
|
||||
{
|
||||
await this.m_semaphore.WaitAsync();
|
||||
await this.m_semaphoreForSend.WaitAsync();
|
||||
|
||||
while (length > 0)
|
||||
{
|
||||
@@ -405,7 +400,7 @@ public class TcpCore : SocketAsyncEventArgs, IDisposable, ISender
|
||||
}
|
||||
finally
|
||||
{
|
||||
this.m_semaphore.Release();
|
||||
this.m_semaphoreForSend.Release();
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
@@ -149,7 +149,7 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
this.BreakOut(default, false, ex.ToString());
|
||||
this.BreakOut(false, ex.ToString());
|
||||
}
|
||||
}
|
||||
|
||||
@@ -226,7 +226,7 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
var tcpCore = this.Service.RentTcpCore();
|
||||
tcpCore.Reset(socket);
|
||||
tcpCore.OnReceived = this.HandleReceived;
|
||||
tcpCore.OnBreakOut = this.BreakOut;
|
||||
tcpCore.OnBreakOut = this.TcpCoreBreakOut;
|
||||
if (this.Config.GetValue(TouchSocketConfigExtension.MinBufferSizeProperty) is int minValue)
|
||||
{
|
||||
tcpCore.MinBufferSize = minValue;
|
||||
@@ -239,7 +239,17 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
this.m_tcpCore = tcpCore;
|
||||
}
|
||||
|
||||
private void BreakOut(TcpCore core, bool manual, string msg)
|
||||
private void TcpCoreBreakOut(TcpCore core, bool manual, string msg)
|
||||
{
|
||||
this.BreakOut(manual, msg);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 中断连接
|
||||
/// </summary>
|
||||
/// <param name="manual"></param>
|
||||
/// <param name="msg"></param>
|
||||
protected void BreakOut(bool manual, string msg)
|
||||
{
|
||||
if (this.GetSocketCliectCollection().TryRemove(this.Id, out _))
|
||||
{
|
||||
@@ -397,7 +407,7 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
{
|
||||
var tcp = this.m_tcpCore;
|
||||
this.m_tcpCore = null;
|
||||
this.Service?.ReturnTcpCore(tcp);
|
||||
this.Service.ReturnTcpCore(tcp);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -424,7 +434,7 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
{
|
||||
Task.Factory.StartNew(this.PrivateOnDisconnecting, new DisconnectEventArgs(true, msg));
|
||||
this.MainSocket.TryClose();
|
||||
this.BreakOut(default, true, msg);
|
||||
this.BreakOut(true, msg);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -505,7 +515,7 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
if (this.Online)
|
||||
{
|
||||
Task.Factory.StartNew(this.PrivateOnDisconnecting, new DisconnectEventArgs(true, $"{nameof(Dispose)}主动断开"));
|
||||
this.BreakOut(default, true, $"{nameof(Dispose)}主动断开");
|
||||
this.BreakOut(true, $"{nameof(Dispose)}主动断开");
|
||||
}
|
||||
|
||||
base.Dispose(disposing);
|
||||
|
@@ -280,7 +280,7 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
{
|
||||
Task.Factory.StartNew(this.PrivateOnDisconnecting, new DisconnectEventArgs(true, msg));
|
||||
this.MainSocket.TryClose();
|
||||
this.BreakOut(default, true, msg);
|
||||
this.BreakOut(true, msg);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -297,7 +297,7 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
if (this.m_online)
|
||||
{
|
||||
Task.Factory.StartNew(this.PrivateOnDisconnecting, new DisconnectEventArgs(true, $"{nameof(Dispose)}主动断开"));
|
||||
this.BreakOut(default, true, $"{nameof(Dispose)}主动断开");
|
||||
this.BreakOut(true, $"{nameof(Dispose)}主动断开");
|
||||
}
|
||||
}
|
||||
base.Dispose(disposing);
|
||||
@@ -502,7 +502,17 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
{
|
||||
return this.GetIPPort();
|
||||
}
|
||||
private void BreakOut(TcpCore core, bool manual, string msg)
|
||||
|
||||
private void TcpCoreBreakOut(TcpCore core, bool manual, string msg)
|
||||
{
|
||||
this.BreakOut(manual, msg);
|
||||
}
|
||||
/// <summary>
|
||||
/// BreakOut。
|
||||
/// </summary>
|
||||
/// <param name="manual"></param>
|
||||
/// <param name="msg"></param>
|
||||
protected void BreakOut(bool manual, string msg)
|
||||
{
|
||||
lock (this.SyncRoot)
|
||||
{
|
||||
@@ -935,7 +945,7 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
}
|
||||
this.m_tcpCore.Reset(socket);
|
||||
this.m_tcpCore.OnReceived = this.HandleReceived;
|
||||
this.m_tcpCore.OnBreakOut = this.BreakOut;
|
||||
this.m_tcpCore.OnBreakOut = this.TcpCoreBreakOut;
|
||||
if (this.Config.GetValue(TouchSocketConfigExtension.MinBufferSizeProperty) is int minValue)
|
||||
{
|
||||
this.m_tcpCore.MinBufferSize = minValue;
|
||||
|
@@ -204,7 +204,7 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
public class UdpPackageAdapter : UdpDataHandlingAdapter
|
||||
{
|
||||
private readonly SnowflakeIdGenerator m_iDGenerator;
|
||||
private readonly ConcurrentDictionary<long, UdpPackage> revStore;
|
||||
private readonly ConcurrentDictionary<long, UdpPackage> m_revStore;
|
||||
private int m_mtu = 1472;
|
||||
|
||||
/// <summary>
|
||||
@@ -212,7 +212,7 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
/// </summary>
|
||||
public UdpPackageAdapter()
|
||||
{
|
||||
this.revStore = new ConcurrentDictionary<long, UdpPackage>();
|
||||
this.m_revStore = new ConcurrentDictionary<long, UdpPackage>();
|
||||
this.m_iDGenerator = new SnowflakeIdGenerator(4);
|
||||
}
|
||||
|
||||
@@ -250,17 +250,17 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
var udpFrame = new UdpFrame();
|
||||
if (udpFrame.Parse(byteBlock.Buffer, 0, byteBlock.Len))
|
||||
{
|
||||
var udpPackage = this.revStore.GetOrAdd(udpFrame.Id, (i) => new UdpPackage(i, this.Timeout, this.revStore));
|
||||
var udpPackage = this.m_revStore.GetOrAdd(udpFrame.Id, (i) => new UdpPackage(i, this.Timeout, this.m_revStore));
|
||||
udpPackage.Add(udpFrame);
|
||||
if (udpPackage.Length > this.MaxPackageSize)
|
||||
{
|
||||
this.revStore.TryRemove(udpPackage.Id, out _);
|
||||
this.m_revStore.TryRemove(udpPackage.Id, out _);
|
||||
this.Logger?.Error("数据长度大于设定的最大值。");
|
||||
return;
|
||||
}
|
||||
if (udpPackage.IsComplated)
|
||||
{
|
||||
if (this.revStore.TryRemove(udpPackage.Id, out _))
|
||||
if (this.m_revStore.TryRemove(udpPackage.Id, out _))
|
||||
{
|
||||
using (var block = new ByteBlock(udpPackage.Length))
|
||||
{
|
||||
|
@@ -42,7 +42,7 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
public async Task<ReceiverResult> ReadAsync(CancellationToken token)
|
||||
{
|
||||
this.ThrowIfDisposed();
|
||||
await this.m_resetEventForRead.WaitOneAsync(token);
|
||||
await this.m_resetEventForRead.WaitOneAsync(token).ConfigureFalseAwait();
|
||||
return new ReceiverResult(this.ComplateRead, this.m_byteBlock, this.m_requestInfo);
|
||||
}
|
||||
|
||||
@@ -51,7 +51,7 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
public async ValueTask<ReceiverResult> ValueReadAsync(CancellationToken token)
|
||||
{
|
||||
this.ThrowIfDisposed();
|
||||
await this.m_resetEventForRead.WaitOneAsync(token);
|
||||
await this.m_resetEventForRead.WaitOneAsync(token).ConfigureFalseAwait();
|
||||
return new ReceiverResult(this.ComplateRead, this.m_byteBlock, this.m_requestInfo);
|
||||
}
|
||||
#endif
|
||||
|
@@ -28,7 +28,6 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
internal class WaitingClient<TClient> : DisposableObject, IWaitingClient<TClient> where TClient : IClient, ISender
|
||||
{
|
||||
private readonly EasyLock m_semaphoreSlim = new();
|
||||
private volatile bool m_breaked;
|
||||
private CancellationTokenSource m_cancellationTokenSource;
|
||||
|
||||
|
||||
@@ -75,8 +74,7 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
{
|
||||
try
|
||||
{
|
||||
this.m_semaphoreSlim.Wait();
|
||||
this.m_breaked = false;
|
||||
this.m_semaphoreSlim.Wait(token);
|
||||
if (token.CanBeCanceled)
|
||||
{
|
||||
this.m_cancellationTokenSource = CancellationTokenSource.CreateLinkedTokenSource(token);
|
||||
@@ -85,7 +83,7 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
{
|
||||
this.m_cancellationTokenSource = new CancellationTokenSource(5000);
|
||||
}
|
||||
using (m_cancellationTokenSource)
|
||||
using (this.m_cancellationTokenSource)
|
||||
{
|
||||
if (this.WaitingOptions.RemoteIPHost != null && this.Client is IUdpSession session)
|
||||
{
|
||||
@@ -113,7 +111,6 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
{
|
||||
if (receiverResult.IsClosed)
|
||||
{
|
||||
this.m_breaked = true;
|
||||
this.Cancel();
|
||||
}
|
||||
var response = new ResponsedData(receiverResult.ByteBlock?.ToArray(), receiverResult.RequestInfo);
|
||||
@@ -135,10 +132,6 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
}
|
||||
}
|
||||
}
|
||||
catch (OperationCanceledException)
|
||||
{
|
||||
return this.WaitingOptions.ThrowBreakException && this.m_breaked ? throw new Exception("等待已终止。可能是客户端已掉线,或者被注销。") : throw new TimeoutException();
|
||||
}
|
||||
finally
|
||||
{
|
||||
this.m_cancellationTokenSource = null;
|
||||
@@ -156,8 +149,7 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
{
|
||||
try
|
||||
{
|
||||
await this.m_semaphoreSlim.WaitAsync();
|
||||
this.m_breaked = false;
|
||||
await this.m_semaphoreSlim.WaitAsync(token);
|
||||
if (token.CanBeCanceled)
|
||||
{
|
||||
this.m_cancellationTokenSource = CancellationTokenSource.CreateLinkedTokenSource(token);
|
||||
@@ -166,7 +158,7 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
{
|
||||
this.m_cancellationTokenSource = new CancellationTokenSource(5000);
|
||||
}
|
||||
using (m_cancellationTokenSource)
|
||||
using (this.m_cancellationTokenSource)
|
||||
{
|
||||
if (this.WaitingOptions.RemoteIPHost != null && this.Client is IUdpSession session)
|
||||
{
|
||||
@@ -194,7 +186,6 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
{
|
||||
if (receiverResult.IsClosed)
|
||||
{
|
||||
this.m_breaked = true;
|
||||
this.Cancel();
|
||||
}
|
||||
var response = new ResponsedData(receiverResult.ByteBlock?.ToArray(), receiverResult.RequestInfo);
|
||||
@@ -216,10 +207,6 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
}
|
||||
}
|
||||
}
|
||||
catch (OperationCanceledException)
|
||||
{
|
||||
return this.WaitingOptions.ThrowBreakException && this.m_breaked ? throw new Exception("等待已终止。可能是客户端已掉线,或者被注销。") : throw new TimeoutException();
|
||||
}
|
||||
finally
|
||||
{
|
||||
this.m_cancellationTokenSource = null;
|
||||
|
@@ -30,22 +30,11 @@ namespace ThingsGateway.Foundation.Sockets
|
||||
/// </summary>
|
||||
public class WaitingOptions
|
||||
{
|
||||
|
||||
/// <summary>
|
||||
/// 当Client为Tcp系时。是否在断开连接时立即触发结果。默认会返回null。当<see cref="ThrowBreakException"/>为<see langword="true"/>时,会触发异常。
|
||||
/// </summary>
|
||||
public bool BreakTrigger { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// 远程地址(仅在Udp模式下生效)
|
||||
/// </summary>
|
||||
public IPHost RemoteIPHost { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// 当Client为Tcp系时。是否在断开连接时以异常返回结果。
|
||||
/// </summary>
|
||||
public bool ThrowBreakException { get; set; } = true;
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// 筛选函数
|
||||
|
@@ -1,6 +1,6 @@
|
||||
<Project>
|
||||
<PropertyGroup>
|
||||
<Version>3.0.0.20</Version>
|
||||
<Version>3.0.0.23</Version>
|
||||
<LangVersion>latest</LangVersion>
|
||||
<ImplicitUsings>enable</ImplicitUsings>
|
||||
<TargetFrameworks>net6.0;net7.0</TargetFrameworks>
|
||||
|
@@ -0,0 +1,39 @@
|
||||
#region copyright
|
||||
//------------------------------------------------------------------------------
|
||||
// 此代码版权声明为全文件覆盖,如有原作者特别声明,会在下方手动补充
|
||||
// 此代码版权(除特别声明外的代码)归作者本人Diego所有
|
||||
// 源代码使用协议遵循本仓库的开源协议及附加协议
|
||||
// Gitee源代码仓库:https://gitee.com/diego2098/ThingsGateway
|
||||
// Github源代码仓库:https://github.com/kimdiego2098/ThingsGateway
|
||||
// 使用文档:https://diego2098.gitee.io/thingsgateway-docs/
|
||||
// QQ群:605534569
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
using Opc.Ua.Configuration;
|
||||
|
||||
namespace ThingsGateway.Plugin.OPCUA;
|
||||
|
||||
|
||||
public partial class OPCUAServer
|
||||
{
|
||||
public class ApplicationMessageDlg : IApplicationMessageDlg
|
||||
{
|
||||
private string message = string.Empty;
|
||||
private ILog _log;
|
||||
public ApplicationMessageDlg(ILog log)
|
||||
{
|
||||
_log = log;
|
||||
}
|
||||
public override void Message(string text, bool ask)
|
||||
{
|
||||
message = text;
|
||||
}
|
||||
|
||||
public override async Task<bool> ShowAsync()
|
||||
{
|
||||
_log.Warning(message);
|
||||
return await Task.FromResult(true);
|
||||
}
|
||||
}
|
||||
}
|
@@ -0,0 +1,59 @@
|
||||
#region copyright
|
||||
//------------------------------------------------------------------------------
|
||||
// 此代码版权声明为全文件覆盖,如有原作者特别声明,会在下方手动补充
|
||||
// 此代码版权(除特别声明外的代码)归作者本人Diego所有
|
||||
// 源代码使用协议遵循本仓库的开源协议及附加协议
|
||||
// Gitee源代码仓库:https://gitee.com/diego2098/ThingsGateway
|
||||
// Github源代码仓库:https://github.com/kimdiego2098/ThingsGateway
|
||||
// 使用文档:https://diego2098.gitee.io/thingsgateway-docs/
|
||||
// QQ群:605534569
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
using Microsoft.Extensions.Logging;
|
||||
|
||||
namespace ThingsGateway.Plugin.OPCUA;
|
||||
|
||||
|
||||
public partial class OPCUAServer
|
||||
{
|
||||
private class OPCUALogger : ILogger
|
||||
{
|
||||
private ILog _log;
|
||||
public OPCUALogger(ILog log)
|
||||
{
|
||||
_log = log;
|
||||
|
||||
}
|
||||
/// <summary>
|
||||
/// Set the log level
|
||||
/// </summary>
|
||||
public Microsoft.Extensions.Logging.LogLevel LogLevel { get; set; } = Microsoft.Extensions.Logging.LogLevel.Trace;
|
||||
/// <inheritdoc/>
|
||||
public IDisposable BeginScope<TState>(TState state) => default;
|
||||
/// <inheritdoc/>
|
||||
public bool IsEnabled(Microsoft.Extensions.Logging.LogLevel logLevel) => logLevel >= LogLevel;
|
||||
/// <inheritdoc/>
|
||||
public void Log<TState>(
|
||||
Microsoft.Extensions.Logging.LogLevel logLevel,
|
||||
EventId eventId,
|
||||
TState state,
|
||||
Exception exception,
|
||||
Func<TState, Exception, string> formatter)
|
||||
{
|
||||
if (!IsEnabled(logLevel))
|
||||
{
|
||||
return;
|
||||
}
|
||||
else
|
||||
{
|
||||
var message = formatter(state, exception);
|
||||
_log.Log((Foundation.Core.LogLevel)(byte)logLevel, state, message, exception);
|
||||
if (logLevel > Microsoft.Extensions.Logging.LogLevel.Information)
|
||||
{
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@@ -63,7 +63,7 @@ public partial class OPCUAServer : UpLoadBase
|
||||
public override async Task BeforStartAsync(CancellationToken cancellationToken)
|
||||
{
|
||||
// 启动服务器。
|
||||
await m_application.CheckApplicationInstanceCertificate(true, 0, 1200);
|
||||
await m_application.CheckApplicationInstanceCertificate(false, 0, 1200);
|
||||
await m_application.Start(m_server);
|
||||
}
|
||||
/// <inheritdoc/>
|
||||
@@ -90,7 +90,7 @@ public partial class OPCUAServer : UpLoadBase
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
LogMessage.LogWarning(ex);
|
||||
LogMessage.LogWarning(ex);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -98,7 +98,7 @@ public partial class OPCUAServer : UpLoadBase
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
LogMessage.LogWarning(ex);
|
||||
LogMessage.LogWarning(ex);
|
||||
}
|
||||
if (driverPropertys.CycleInterval > UploadDeviceThread.CycleInterval + 50)
|
||||
{
|
||||
@@ -138,9 +138,13 @@ public partial class OPCUAServer : UpLoadBase
|
||||
_uploadVariables = null;
|
||||
CollectVariableRunTimes.Clear();
|
||||
}
|
||||
|
||||
/// <inheritdoc/>
|
||||
protected override void Init(UploadDeviceRunTime device)
|
||||
{
|
||||
ApplicationInstance.MessageDlg = new ApplicationMessageDlg(LogMessage);//默认返回true
|
||||
|
||||
//Utils.SetLogger(new OPCUALogger(LogMessage)); //调试用途
|
||||
m_application = new ApplicationInstance();
|
||||
m_configuration = GetDefaultConfiguration();
|
||||
m_configuration.Validate(ApplicationType.Server).GetAwaiter().GetResult();
|
||||
@@ -169,7 +173,7 @@ public partial class OPCUAServer : UpLoadBase
|
||||
private ApplicationConfiguration GetDefaultConfiguration()
|
||||
{
|
||||
ApplicationConfiguration config = new();
|
||||
string url = driverPropertys.OpcUaStringUrl;
|
||||
var urls = driverPropertys.OpcUaStringUrl.Split(new string[] { ";" }, StringSplitOptions.RemoveEmptyEntries);
|
||||
// 签名及加密验证
|
||||
ServerSecurityPolicyCollection policies = new();
|
||||
var userTokens = new UserTokenPolicyCollection();
|
||||
@@ -242,13 +246,14 @@ public partial class OPCUAServer : UpLoadBase
|
||||
|
||||
config.ApplicationName = "ThingsGateway OPCUAServer";
|
||||
config.ApplicationType = ApplicationType.Server;
|
||||
config.ApplicationUri = Utils.Format(@"urn:{0}:thingsgatewayopcuaserver", System.Net.Dns.GetHostName());
|
||||
config.ApplicationUri = driverPropertys.ApplicationUri;
|
||||
|
||||
|
||||
config.ServerConfiguration = new ServerConfiguration()
|
||||
{
|
||||
// 配置登录的地址
|
||||
BaseAddresses = new string[] { url },
|
||||
BaseAddresses = urls,
|
||||
|
||||
SecurityPolicies = policies,
|
||||
UserTokenPolicies = userTokens,
|
||||
ShutdownDelay = 1,
|
||||
@@ -269,7 +274,7 @@ public partial class OPCUAServer : UpLoadBase
|
||||
MaxNotificationQueueSize = 100, // 为每个被监视项目保存在队列中的最大证书数
|
||||
MaxNotificationsPerPublish = 1000, // 每次发布的最大通知数
|
||||
MinMetadataSamplingInterval = 1000, // 元数据的最小采样间隔
|
||||
MaxRegistrationInterval = 30000, // 两次注册尝试之间的最大时间(以毫秒为单位)
|
||||
MaxRegistrationInterval = -1, // 两次注册尝试之间的最大时间(以毫秒为单位)//不提供注册
|
||||
|
||||
};
|
||||
config.SecurityConfiguration = new SecurityConfiguration()
|
||||
@@ -283,7 +288,8 @@ public partial class OPCUAServer : UpLoadBase
|
||||
{
|
||||
StoreType = CertificateStoreType.X509Store,
|
||||
StorePath = "CurrentUser\\UAServer_ThingsGateway",
|
||||
SubjectName = "CN=ThingsGateway OPCUAServer, C=CN, S=GUANGZHOU, O=ThingsGateway, DC=" + System.Net.Dns.GetHostName(),
|
||||
SubjectName = driverPropertys.SubjectName,
|
||||
//ValidationOptions = CertificateValidationOptions.SuppressHostNameInvalid,
|
||||
},
|
||||
|
||||
TrustedPeerCertificates = new CertificateTrustList()
|
||||
@@ -323,7 +329,7 @@ public partial class OPCUAServer : UpLoadBase
|
||||
|
||||
|
||||
config.CertificateValidator = new CertificateValidator();
|
||||
config.CertificateValidator.Update(config);
|
||||
config.CertificateValidator.Update(config).GetAwaiter().GetResult();
|
||||
config.Extensions = new XmlElementCollection();
|
||||
|
||||
return config;
|
||||
|
@@ -10,6 +10,8 @@
|
||||
//------------------------------------------------------------------------------
|
||||
#endregion
|
||||
|
||||
using Opc.Ua;
|
||||
|
||||
namespace ThingsGateway.Plugin.OPCUA;
|
||||
|
||||
/// <inheritdoc/>
|
||||
@@ -18,8 +20,21 @@ public class OPCUAServerProperty : UpDriverPropertyBase
|
||||
/// <summary>
|
||||
/// 服务地址
|
||||
/// </summary>
|
||||
[DeviceProperty("服务地址", "")]
|
||||
[DeviceProperty("服务地址", "分号分割数组,可设置多个url")]
|
||||
public string OpcUaStringUrl { get; set; } = "opc.tcp://127.0.0.1:49321";
|
||||
/// <summary>
|
||||
/// SubjectName
|
||||
/// </summary>
|
||||
[DeviceProperty("SubjectName", "")]
|
||||
public string SubjectName { get; set; } = "CN=ThingsGateway OPCUAServer, C=CN, S=GUANGZHOU, O=ThingsGateway, DC=" + System.Net.Dns.GetHostName();
|
||||
|
||||
/// <summary>
|
||||
/// ApplicationUri
|
||||
/// </summary>
|
||||
[DeviceProperty("ApplicationUri", "")]
|
||||
public string ApplicationUri { get; set; } = Utils.Format(@"urn:{0}:thingsgatewayopcuaserver", System.Net.Dns.GetHostName());
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// 安全策略
|
||||
/// </summary>
|
||||
|
@@ -67,6 +67,8 @@ public class SQLDB : UpLoadBase
|
||||
await Task.CompletedTask;
|
||||
}
|
||||
|
||||
private bool readDBInitSuccess;
|
||||
|
||||
public override async Task ExecuteAsync(CancellationToken cancellationToken)
|
||||
{
|
||||
var db = GetHisDbAsync();
|
||||
@@ -75,14 +77,33 @@ public class SQLDB : UpLoadBase
|
||||
{
|
||||
if (exRealTimerTick.IsTickHappen())
|
||||
{
|
||||
|
||||
try
|
||||
{
|
||||
var varList = _uploadVariables.ToList().Adapt<List<SQLRealValue>>();
|
||||
|
||||
if (!readDBInitSuccess)
|
||||
{
|
||||
//事务
|
||||
var result = db.UseTran(() =>
|
||||
{
|
||||
db.Storageable(varList).As(driverPropertys.ReadDBTableName).PageSize(10000).ExecuteSqlBulkCopy();
|
||||
//db.Fastest<SQLRealValue>().AS(driverPropertys.ReadDBTableName).PageSize(100000).BulkMerge(varList);
|
||||
});
|
||||
if (result.IsSuccess)//如果成功了
|
||||
{
|
||||
readDBInitSuccess = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
throw new(result.ErrorMessage);
|
||||
}
|
||||
}
|
||||
|
||||
if (varList?.Count != 0)
|
||||
{
|
||||
//var result = await db.Storageable(varList).As(driverPropertys.ReadDBTableName).ExecuteCommandAsync(cancellationToken);
|
||||
await db.Fastest<SQLRealValue>().AS(driverPropertys.ReadDBTableName).PageSize(100000).BulkUpdateAsync(varList);
|
||||
|
||||
db.Fastest<SQLRealValue>().AS(driverPropertys.ReadDBTableName).PageSize(100000).BulkUpdate(varList);
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
@@ -180,6 +201,7 @@ public class SQLDB : UpLoadBase
|
||||
{
|
||||
try
|
||||
{
|
||||
readDBInitSuccess = false;
|
||||
_globalDeviceData?.AllVariables?.ForEach(a => a.VariableValueChange -= VariableValueChange);
|
||||
_uploadVariables = null;
|
||||
}
|
||||
@@ -307,7 +329,7 @@ public class SQLDB : UpLoadBase
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
LogMessage.LogWarning(ex);
|
||||
LogMessage.LogWarning(ex);
|
||||
}
|
||||
|
||||
|
||||
@@ -316,7 +338,7 @@ public class SQLDB : UpLoadBase
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
LogMessage.LogWarning(ex);
|
||||
LogMessage.LogWarning(ex);
|
||||
await CacheDb.AddCacheData("", dbInserts.ToJsonString(), driverPropertys.CacheMaxCount);
|
||||
}
|
||||
|
||||
|
@@ -1,6 +1,6 @@
|
||||
<Project>
|
||||
<PropertyGroup>
|
||||
<Version>3.0.0.20</Version>
|
||||
<Version>3.0.0.23</Version>
|
||||
<LangVersion>latest</LangVersion>
|
||||
<TargetFrameworks>net6.0;net7.0</TargetFrameworks>
|
||||
<Authors>Diego</Authors>
|
||||
|
@@ -1,6 +1,6 @@
|
||||
<Project>
|
||||
<PropertyGroup>
|
||||
<Version>3.0.0.20</Version>
|
||||
<Version>3.0.0.23</Version>
|
||||
<LangVersion>latest</LangVersion>
|
||||
<ImplicitUsings>enable</ImplicitUsings>
|
||||
<TargetFrameworks>net6.0;net7.0</TargetFrameworks>
|
||||
@@ -11,7 +11,6 @@
|
||||
<SignAssembly>True</SignAssembly>
|
||||
<DelaySign>False</DelaySign>
|
||||
<SatelliteResourceLanguages>zh-Hans</SatelliteResourceLanguages>
|
||||
<GenerateDocumentationFile>True</GenerateDocumentationFile>
|
||||
</PropertyGroup>
|
||||
|
||||
|
||||
|
@@ -2,6 +2,7 @@
|
||||
|
||||
<PropertyGroup>
|
||||
<DocumentationFile>$(MSBuildProjectName).xml</DocumentationFile>
|
||||
<GenerateDocumentationFile>True</GenerateDocumentationFile>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
|
@@ -2,6 +2,7 @@
|
||||
|
||||
<PropertyGroup>
|
||||
<DocumentationFile>$(MSBuildProjectName).xml</DocumentationFile>
|
||||
<GenerateDocumentationFile>True</GenerateDocumentationFile>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
|
@@ -9,6 +9,7 @@
|
||||
//"DbType": "MySql", //数据库类型
|
||||
"ConnectionString": "Data Source=Admin.db;", //连接字符串
|
||||
"DbType": "Sqlite", //数据库类型
|
||||
"LanguageType": "Chinese",//中文提示
|
||||
"IsAutoCloseConnection": true, //是否自动释放
|
||||
"IsInitDb": true, //是否初始化数据库,适用于codefirst
|
||||
"IsUnderLine": false, //是否驼峰转下划线
|
||||
@@ -21,6 +22,7 @@
|
||||
//"DbType": "MySql", //数据库类型
|
||||
"ConnectionString": "Data Source=Log.db", //连接字符串
|
||||
"DbType": "Sqlite", //数据库类型
|
||||
"LanguageType": "Chinese", //中文提示
|
||||
"IsAutoCloseConnection": true, //是否自动释放
|
||||
"IsInitDb": true, //是否初始化数据库,适用于codefirst
|
||||
"IsUnderLine": false, //是否驼峰转下划线
|
||||
@@ -33,6 +35,7 @@
|
||||
//"DbType": "MySql", //数据库类型
|
||||
"ConnectionString": "Data Source=ThingsGateway.db", //连接字符串
|
||||
"DbType": "Sqlite", //数据库类型
|
||||
"LanguageType": "Chinese", //中文提示
|
||||
"IsAutoCloseConnection": true, //是否自动释放
|
||||
"IsInitDb": true, //是否初始化数据库,适用于codefirst
|
||||
"IsUnderLine": false, //是否驼峰转下划线
|
||||
|
@@ -6,7 +6,7 @@ export const language = ["en","zh"];
|
||||
export const removeDefaultStopWordFilter = false;
|
||||
export const removeDefaultStemmer = false;
|
||||
export { default as Mark } from "E:\\Tg\\ThingsGateway\\ThingsGateway-DEV\\handbook\\node_modules\\mark.js\\dist\\mark.js"
|
||||
export const searchIndexUrl = "search-index{dir}.json?_=5f24d3ee";
|
||||
export const searchIndexUrl = "search-index{dir}.json?_=264c6792";
|
||||
export const searchResultLimits = 8;
|
||||
export const searchResultContextMaxLength = 50;
|
||||
export const explicitSearchResultPath = true;
|
||||
|
@@ -227,9 +227,9 @@
|
||||
"179": {
|
||||
"js": [
|
||||
{
|
||||
"file": "assets/js/main.cf42840d.js",
|
||||
"hash": "41e8aa8c7cbe401b",
|
||||
"publicPath": "/thingsgateway-docs/assets/js/main.cf42840d.js"
|
||||
"file": "assets/js/main.90bffab9.js",
|
||||
"hash": "6774eb8ed9189628",
|
||||
"publicPath": "/thingsgateway-docs/assets/js/main.90bffab9.js"
|
||||
}
|
||||
]
|
||||
},
|
||||
@@ -299,9 +299,9 @@
|
||||
"1303": {
|
||||
"js": [
|
||||
{
|
||||
"file": "assets/js/runtime~main.2b19bbf8.js",
|
||||
"hash": "e48e0c0408aa1c4e",
|
||||
"publicPath": "/thingsgateway-docs/assets/js/runtime~main.2b19bbf8.js"
|
||||
"file": "assets/js/runtime~main.2d62406a.js",
|
||||
"hash": "fc67bb23388f4a51",
|
||||
"publicPath": "/thingsgateway-docs/assets/js/runtime~main.2d62406a.js"
|
||||
}
|
||||
]
|
||||
},
|
||||
@@ -398,9 +398,9 @@
|
||||
"3371": {
|
||||
"js": [
|
||||
{
|
||||
"file": "assets/js/d22033f9.6a725d32.js",
|
||||
"hash": "edd7fef77b05ef57",
|
||||
"publicPath": "/thingsgateway-docs/assets/js/d22033f9.6a725d32.js"
|
||||
"file": "assets/js/d22033f9.838d285d.js",
|
||||
"hash": "b8c8ee41012bac15",
|
||||
"publicPath": "/thingsgateway-docs/assets/js/d22033f9.838d285d.js"
|
||||
}
|
||||
]
|
||||
},
|
||||
@@ -619,9 +619,9 @@
|
||||
"8707": {
|
||||
"js": [
|
||||
{
|
||||
"file": "assets/js/4c79e569.5c5c0d05.js",
|
||||
"hash": "e9c712a478ed50e6",
|
||||
"publicPath": "/thingsgateway-docs/assets/js/4c79e569.5c5c0d05.js"
|
||||
"file": "assets/js/4c79e569.b07342bd.js",
|
||||
"hash": "c0362a85c0105049",
|
||||
"publicPath": "/thingsgateway-docs/assets/js/4c79e569.b07342bd.js"
|
||||
}
|
||||
]
|
||||
},
|
||||
|
@@ -12,8 +12,8 @@
|
||||
"tags": [],
|
||||
"version": "current",
|
||||
"lastUpdatedBy": "Kimdiego2098",
|
||||
"lastUpdatedAt": 1697632930,
|
||||
"formattedLastUpdatedAt": "Oct 18, 2023",
|
||||
"lastUpdatedAt": 1697718988,
|
||||
"formattedLastUpdatedAt": "Oct 19, 2023",
|
||||
"frontMatter": {
|
||||
"id": "upgrade",
|
||||
"title": "历史更新"
|
||||
|
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
1
handbook/build/assets/js/d22033f9.838d285d.js
Normal file
1
handbook/build/assets/js/d22033f9.838d285d.js
Normal file
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user