Revert OPC
This commit is contained in:
@@ -218,7 +218,7 @@ namespace Modbus.Net.Modbus.NA200H
|
||||
var head = splitString[0];
|
||||
var tail = splitString[1];
|
||||
string sub;
|
||||
if (tail.Contains('.'))
|
||||
if (tail.Contains("."))
|
||||
{
|
||||
var splitString2 = tail.Split('.');
|
||||
sub = splitString2[1];
|
||||
|
||||
@@ -1,7 +1,8 @@
|
||||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFrameworks>net6.0</TargetFrameworks>
|
||||
<TargetFrameworks>net6.0;net462</TargetFrameworks>
|
||||
<LangVersion>11.0</LangVersion>
|
||||
<AssemblyName>Modbus.Net.Modbus.NA200H</AssemblyName>
|
||||
<RootNamespace>Modbus.Net.Modbus.NA200H</RootNamespace>
|
||||
<PackageId>Modbus.Net.Modbus.NA200H</PackageId>
|
||||
|
||||
@@ -1,7 +1,8 @@
|
||||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFrameworks>net6.0</TargetFrameworks>
|
||||
<TargetFrameworks>net6.0;net462</TargetFrameworks>
|
||||
<LangVersion>11.0</LangVersion>
|
||||
<AssemblyName>Modbus.Net.Modbus.SelfDefinedSample</AssemblyName>
|
||||
<RootNamespace>Modbus.Net.Modbus.SelfDefinedSample</RootNamespace>
|
||||
<PackageId>Modbus.Net.Modbus.SelfDefinedSample</PackageId>
|
||||
|
||||
@@ -126,7 +126,7 @@ namespace Modbus.Net.Modbus
|
||||
var head = splitString[0];
|
||||
var tail = splitString[1];
|
||||
string sub;
|
||||
if (tail.Contains('.'))
|
||||
if (tail.Contains("."))
|
||||
{
|
||||
var splitString2 = tail.Split('.');
|
||||
sub = splitString2[1];
|
||||
|
||||
@@ -203,7 +203,7 @@ namespace Modbus.Net.Modbus
|
||||
/// <returns></returns>
|
||||
Task<ReturnStruct<ushort[]>> GetMultipleRegister(ushort readStartingAddress, ushort quantityToRead, ushort writeStartingAddress, ushort[] writeValues);
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// FIFO队列读取方法
|
||||
/// </summary>
|
||||
|
||||
@@ -1,7 +1,8 @@
|
||||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFrameworks>net6.0</TargetFrameworks>
|
||||
<TargetFrameworks>net6.0;net462</TargetFrameworks>
|
||||
<LangVersion>11.0</LangVersion>
|
||||
<AssemblyName>Modbus.Net.Modbus</AssemblyName>
|
||||
<RootNamespace>Modbus.Net.Modbus</RootNamespace>
|
||||
<PackageId>Modbus.Net.Modbus</PackageId>
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
using System.Text;
|
||||
|
||||
namespace Modbus.Net.Modbus
|
||||
{
|
||||
|
||||
@@ -389,7 +389,7 @@ namespace Modbus.Net.Modbus
|
||||
formattingBytes = Format(r_message.SlaveAddress, r_message.FunctionCode,
|
||||
r_message.StartAddress, r_message.WriteCount, r_message.WriteByteCount, dataValue);
|
||||
}
|
||||
|
||||
|
||||
return formattingBytes;
|
||||
}
|
||||
|
||||
@@ -493,7 +493,7 @@ namespace Modbus.Net.Modbus
|
||||
{
|
||||
var r_message = (ReadExceptionStatusModbusInputStruct)message;
|
||||
byte[] formattingBytes;
|
||||
|
||||
|
||||
formattingBytes = Format(r_message.SlaveAddress, r_message.FunctionCode);
|
||||
|
||||
return formattingBytes;
|
||||
@@ -613,10 +613,10 @@ namespace Modbus.Net.Modbus
|
||||
public override byte[] Format(IInputStruct message)
|
||||
{
|
||||
var r_message = (DiagnoticsModbusInputStruct)message;
|
||||
|
||||
|
||||
var formattingBytes = Format(r_message.SlaveAddress, r_message.FunctionCode,
|
||||
r_message.SubFunction, r_message.Data);
|
||||
|
||||
|
||||
return formattingBytes;
|
||||
}
|
||||
|
||||
@@ -1260,7 +1260,7 @@ namespace Modbus.Net.Modbus
|
||||
SlaveAddress = slaveAddress;
|
||||
FunctionCode = (byte)ModbusProtocolFunctionCode.WriteFileRecord;
|
||||
byte count = 0;
|
||||
foreach(var writeRecord in writeRecords)
|
||||
foreach (var writeRecord in writeRecords)
|
||||
{
|
||||
count += (byte)(writeRecord.RecordData.Length * 2 + 7);
|
||||
}
|
||||
@@ -1574,7 +1574,7 @@ namespace Modbus.Net.Modbus
|
||||
/// 读起始地址
|
||||
/// </summary>
|
||||
public ushort ReadStartingAddress { get; }
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// 读个数
|
||||
/// </summary>
|
||||
@@ -1656,8 +1656,8 @@ namespace Modbus.Net.Modbus
|
||||
{
|
||||
var r_message = (ReadWriteMultipleRegistersModbusInputStruct)message;
|
||||
|
||||
var formattingBytes = Format(r_message.SlaveAddress, r_message.FunctionCode, r_message.ReadStartingAddress,
|
||||
r_message.QuantityToRead, r_message.WriteStartingAddress, r_message.QuantityToWrite,
|
||||
var formattingBytes = Format(r_message.SlaveAddress, r_message.FunctionCode, r_message.ReadStartingAddress,
|
||||
r_message.QuantityToRead, r_message.WriteStartingAddress, r_message.QuantityToWrite,
|
||||
r_message.WriteByteCount, r_message.WriteValues);
|
||||
|
||||
return formattingBytes;
|
||||
@@ -1674,8 +1674,8 @@ namespace Modbus.Net.Modbus
|
||||
var slaveAddress = ValueHelper.GetInstance(Endian).GetByte(messageBytes, ref flag);
|
||||
var functionCode = ValueHelper.GetInstance(Endian).GetByte(messageBytes, ref flag);
|
||||
var byteCount = ValueHelper.GetInstance(Endian).GetByte(messageBytes, ref flag);
|
||||
ushort[] readValues= new ushort[byteCount / 2];
|
||||
for (int i = 0; i< byteCount / 2; i++)
|
||||
ushort[] readValues = new ushort[byteCount / 2];
|
||||
for (int i = 0; i < byteCount / 2; i++)
|
||||
{
|
||||
readValues[i] = ValueHelper.GetInstance(Endian).GetUShort(messageBytes, ref flag);
|
||||
}
|
||||
|
||||
@@ -53,15 +53,15 @@ namespace Modbus.Net.Modbus
|
||||
/// <summary>
|
||||
/// Modbus基础Api入口
|
||||
/// </summary>
|
||||
public class ModbusUtility : BaseUtility<byte[], byte[], ProtocolUnit<byte[], byte[]>, PipeUnit>,
|
||||
IUtilityMethodExceptionStatus,
|
||||
IUtilityMethodDiagnotics,
|
||||
IUtilityMethodCommEventCounter,
|
||||
IUtilityMethodCommEventLog,
|
||||
IUtilityMethodSlaveId,
|
||||
IUtilityMethodFileRecord,
|
||||
IUtilityMethodMaskRegister,
|
||||
IUtilityMethodMultipleRegister,
|
||||
public class ModbusUtility : BaseUtility<byte[], byte[], ProtocolUnit<byte[], byte[]>, PipeUnit>,
|
||||
IUtilityMethodExceptionStatus,
|
||||
IUtilityMethodDiagnotics,
|
||||
IUtilityMethodCommEventCounter,
|
||||
IUtilityMethodCommEventLog,
|
||||
IUtilityMethodSlaveId,
|
||||
IUtilityMethodFileRecord,
|
||||
IUtilityMethodMaskRegister,
|
||||
IUtilityMethodMultipleRegister,
|
||||
IUtilityMethodFIFOQueue
|
||||
{
|
||||
private static readonly ILogger<ModbusUtility> logger = LogProvider.CreateLogger<ModbusUtility>();
|
||||
@@ -414,7 +414,7 @@ namespace Modbus.Net.Modbus
|
||||
inputStruct);
|
||||
return new ReturnStruct<CommEventLogData>()
|
||||
{
|
||||
Datas = new CommEventLogData() { Status = outputStruct.Status, Events = outputStruct.Events},
|
||||
Datas = new CommEventLogData() { Status = outputStruct.Status, Events = outputStruct.Events },
|
||||
IsSuccess = true,
|
||||
ErrorCode = 0,
|
||||
ErrorMsg = null
|
||||
@@ -444,7 +444,7 @@ namespace Modbus.Net.Modbus
|
||||
inputStruct);
|
||||
return new ReturnStruct<SlaveIdData>()
|
||||
{
|
||||
Datas = new SlaveIdData() { SlaveId = outputStruct.SlaveId, IndicatorStatus = outputStruct.RunIndicatorStatus, AdditionalData = outputStruct.AdditionalData},
|
||||
Datas = new SlaveIdData() { SlaveId = outputStruct.SlaveId, IndicatorStatus = outputStruct.RunIndicatorStatus, AdditionalData = outputStruct.AdditionalData },
|
||||
IsSuccess = true,
|
||||
ErrorCode = 0,
|
||||
ErrorMsg = null
|
||||
@@ -534,7 +534,7 @@ namespace Modbus.Net.Modbus
|
||||
inputStruct);
|
||||
return new ReturnStruct<MaskRegisterData>()
|
||||
{
|
||||
Datas = new MaskRegisterData() { ReferenceAddress = outputStruct.ReferenceAddress, AndMask = outputStruct.AndMask, OrMask = outputStruct.OrMask},
|
||||
Datas = new MaskRegisterData() { ReferenceAddress = outputStruct.ReferenceAddress, AndMask = outputStruct.AndMask, OrMask = outputStruct.OrMask },
|
||||
IsSuccess = true,
|
||||
ErrorCode = 0,
|
||||
ErrorMsg = null
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
using Hylasoft.Opc.Common;
|
||||
using Hylasoft.Opc.Da;
|
||||
using Hylasoft.Opc.Ua;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
@@ -19,7 +20,7 @@ namespace Modbus.Net.OPC
|
||||
/// <summary>
|
||||
/// Connect the client to the OPC Server
|
||||
/// </summary>
|
||||
Task Connect();
|
||||
void Connect();
|
||||
|
||||
/// <summary>
|
||||
/// Read a tag
|
||||
@@ -64,6 +65,25 @@ namespace Modbus.Net.OPC
|
||||
Task<IEnumerable<Node>> ExploreFolderAsync(string tag);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// UaClient Extend
|
||||
/// </summary>
|
||||
public class MyDaClient : DaClient, IClientExtend
|
||||
{
|
||||
/// <summary>
|
||||
/// UaClient Extend
|
||||
/// </summary>
|
||||
/// <param name="serverUrl">Url address of Opc UA server</param>
|
||||
public MyDaClient(Uri serverUrl) : base(serverUrl)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Unified root node
|
||||
/// </summary>
|
||||
public Node RootNodeBase => RootNode;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// DaClient Extend
|
||||
/// </summary>
|
||||
|
||||
61
Modbus.Net/Modbus.Net.OPC/FBox/FBoxOpcDaManchine.cs
Normal file
61
Modbus.Net/Modbus.Net.OPC/FBox/FBoxOpcDaManchine.cs
Normal file
@@ -0,0 +1,61 @@
|
||||
using System.Collections.Generic;
|
||||
using System.Configuration;
|
||||
|
||||
namespace Modbus.Net.OPC.FBox
|
||||
{
|
||||
/// <summary>
|
||||
/// FBox的Opc服务设备
|
||||
/// </summary>
|
||||
public class FBoxOpcDaMachine : OpcDaMachine
|
||||
{
|
||||
/// <summary>
|
||||
/// 构造函数
|
||||
/// </summary>
|
||||
/// <param name="id">设备id</param>
|
||||
/// <param name="localSequence">页名称</param>
|
||||
/// <param name="linkerName">设备名称</param>
|
||||
/// <param name="getAddresses">获取地址</param>
|
||||
/// <param name="keepConnect">是否保持连接</param>
|
||||
public FBoxOpcDaMachine(string id, string localSequence, string linkerName,
|
||||
IEnumerable<AddressUnit> getAddresses, bool keepConnect)
|
||||
: base(
|
||||
id,
|
||||
ConfigurationManager.AppSettings["FBoxOpcDaHost"] ?? "opcda://localhost/FBoxOpcServer", getAddresses,
|
||||
keepConnect, true)
|
||||
{
|
||||
LocalSequence = localSequence;
|
||||
LinkerName = linkerName;
|
||||
AddressFormater =
|
||||
new AddressFormaterOpc<string, string>(
|
||||
(machine, unit) =>
|
||||
new[]
|
||||
{
|
||||
"(.*)", ((FBoxOpcDaMachine) machine).LinkerName, ((FBoxOpcDaMachine) machine).LocalSequence,
|
||||
unit.Name
|
||||
}, this, '.');
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 构造函数
|
||||
/// </summary>
|
||||
/// <param name="id">设备id</param>
|
||||
/// <param name="localSequence">页名称</param>
|
||||
/// <param name="linkerName">设备名称</param>
|
||||
/// <param name="getAddresses">获取地址</param>
|
||||
public FBoxOpcDaMachine(string id, string localSequence, string linkerName,
|
||||
IEnumerable<AddressUnit> getAddresses)
|
||||
: this(id, localSequence, linkerName, getAddresses, false)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 页名称
|
||||
/// </summary>
|
||||
public string LocalSequence { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// 设备名称
|
||||
/// </summary>
|
||||
public string LinkerName { get; set; }
|
||||
}
|
||||
}
|
||||
@@ -1,7 +1,8 @@
|
||||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFrameworks>net6.0</TargetFrameworks>
|
||||
<TargetFramework>net462</TargetFramework>
|
||||
<LangVersion>11.0</LangVersion>
|
||||
<AssemblyName>Modbus.Net.OPC</AssemblyName>
|
||||
<RootNamespace>Modbus.Net.OPC</RootNamespace>
|
||||
<PackageId>Modbus.Net.OPC</PackageId>
|
||||
@@ -29,15 +30,18 @@
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Opc.UaFx.Client" Version="2.30.0" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\Libraries\h-opc\h-opc.csproj" />
|
||||
<ProjectReference Include="..\Modbus.Net\Modbus.Net.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<None Include="README.md" Pack="true" PackagePath=""/>
|
||||
<Reference Include="System.Configuration" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<None Include="README.md" Pack="true" PackagePath="" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="H.Opc" Version="0.9.3" />
|
||||
</ItemGroup>
|
||||
</Project>
|
||||
@@ -191,15 +191,11 @@ namespace Modbus.Net.OPC
|
||||
return null;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 连接PLC
|
||||
/// </summary>
|
||||
/// <returns>是否连接成功</returns>
|
||||
public override async Task<bool> ConnectAsync()
|
||||
private bool Connect()
|
||||
{
|
||||
try
|
||||
{
|
||||
await Client.Connect();
|
||||
Client.Connect();
|
||||
_connect = true;
|
||||
logger.LogInformation("opc client {ConnectionToken} connect success", ConnectionToken);
|
||||
return true;
|
||||
@@ -211,5 +207,14 @@ namespace Modbus.Net.OPC
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 连接PLC,异步
|
||||
/// </summary>
|
||||
/// <returns>是否连接成功</returns>
|
||||
public override Task<bool> ConnectAsync()
|
||||
{
|
||||
return Task.FromResult(Connect());
|
||||
}
|
||||
}
|
||||
}
|
||||
42
Modbus.Net/Modbus.Net.OPC/OpcDaConnector.cs
Normal file
42
Modbus.Net/Modbus.Net.OPC/OpcDaConnector.cs
Normal file
@@ -0,0 +1,42 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace Modbus.Net.OPC
|
||||
{
|
||||
/// <summary>
|
||||
/// Opc DA连接实现
|
||||
/// </summary>
|
||||
public class OpcDaConnector : OpcConnector
|
||||
{
|
||||
/// <summary>
|
||||
/// DA单例管理
|
||||
/// </summary>
|
||||
protected static Dictionary<string, OpcDaConnector> _instances = new Dictionary<string, OpcDaConnector>();
|
||||
|
||||
/// <summary>
|
||||
/// 构造函数
|
||||
/// </summary>
|
||||
/// <param name="host">Opc DA 服务地址</param>
|
||||
/// <param name="isRegexOn">是否开启正则匹配</param>
|
||||
protected OpcDaConnector(string host, bool isRegexOn) : base(host, isRegexOn)
|
||||
{
|
||||
Client = new MyDaClient(new Uri(ConnectionToken));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 根据服务地址生成DA单例
|
||||
/// </summary>
|
||||
/// <param name="host">Opc DA 服务地址</param>
|
||||
/// <param name="isRegexOn">是否开启正则匹配</param>
|
||||
/// <returns>Opc DA 连接器实例</returns>
|
||||
public static OpcDaConnector Instance(string host, bool isRegexOn)
|
||||
{
|
||||
if (!_instances.ContainsKey(host))
|
||||
{
|
||||
var connector = new OpcDaConnector(host, isRegexOn);
|
||||
_instances.Add(host, connector);
|
||||
}
|
||||
return _instances[host];
|
||||
}
|
||||
}
|
||||
}
|
||||
74
Modbus.Net/Modbus.Net.OPC/OpcDaMachine.cs
Normal file
74
Modbus.Net/Modbus.Net.OPC/OpcDaMachine.cs
Normal file
@@ -0,0 +1,74 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace Modbus.Net.OPC
|
||||
{
|
||||
/// <summary>
|
||||
/// Opc DA设备
|
||||
/// </summary>
|
||||
/// <typeparam name="TKey">设备Id类型</typeparam>
|
||||
/// <typeparam name="TUnitKey">设备包含的地址的Id类型</typeparam>
|
||||
public class OpcDaMachine<TKey, TUnitKey> : OpcMachine<TKey, TUnitKey> where TKey : IEquatable<TKey>
|
||||
where TUnitKey : IEquatable<TUnitKey>
|
||||
{
|
||||
/// <summary>
|
||||
/// 构造函数
|
||||
/// </summary>
|
||||
/// <param name="id">设备的ID号</param>
|
||||
/// <param name="connectionString">连接地址</param>
|
||||
/// <param name="getAddresses">需要读写的数据</param>
|
||||
/// <param name="keepConnect">是否保持连接</param>
|
||||
/// <param name="isRegexOn">是否开启正则匹配</param>
|
||||
public OpcDaMachine(TKey id, string connectionString, IEnumerable<AddressUnit<TUnitKey>> getAddresses, bool keepConnect, bool isRegexOn = false)
|
||||
: base(id, getAddresses, keepConnect)
|
||||
{
|
||||
BaseUtility = new OpcDaUtility(connectionString, isRegexOn);
|
||||
((OpcUtility)BaseUtility).GetSeperator +=
|
||||
() => ((AddressFormaterOpc<TKey, TUnitKey>)AddressFormater).Seperator;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 构造函数
|
||||
/// </summary>
|
||||
/// <param name="id">设备的ID号</param>
|
||||
/// <param name="connectionString">连接地址</param>
|
||||
/// <param name="getAddresses">需要读写的数据</param>
|
||||
public OpcDaMachine(TKey id, string connectionString, IEnumerable<AddressUnit<TUnitKey>> getAddresses)
|
||||
: this(id, connectionString, getAddresses, false)
|
||||
{
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Opc DA设备
|
||||
/// </summary>
|
||||
public class OpcDaMachine : OpcMachine
|
||||
{
|
||||
/// <summary>
|
||||
/// 构造函数
|
||||
/// </summary>
|
||||
/// <param name="id">设备的ID号</param>
|
||||
/// <param name="connectionString">连接地址</param>
|
||||
/// <param name="getAddresses">需要读写的数据</param>
|
||||
/// <param name="keepConnect">是否保持连接</param>
|
||||
/// <param name="isRegexOn">是否开启正则匹配</param>
|
||||
public OpcDaMachine(string id, string connectionString, IEnumerable<AddressUnit> getAddresses, bool keepConnect, bool isRegexOn = false)
|
||||
: base(id, getAddresses, keepConnect)
|
||||
{
|
||||
BaseUtility = new OpcDaUtility(connectionString, isRegexOn);
|
||||
((OpcUtility)BaseUtility).GetSeperator +=
|
||||
() => ((AddressFormaterOpc<string, string>)AddressFormater).Seperator;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 构造函数
|
||||
/// </summary>
|
||||
/// <param name="id">设备的ID号</param>
|
||||
/// <param name="connectionString">连接地址</param>
|
||||
/// <param name="getAddresses">需要读写的数据</param>
|
||||
public OpcDaMachine(string id, string connectionString, IEnumerable<AddressUnit> getAddresses)
|
||||
: this(id, connectionString, getAddresses, false)
|
||||
{
|
||||
}
|
||||
}
|
||||
}
|
||||
38
Modbus.Net/Modbus.Net.OPC/OpcDaProtocal.cs
Normal file
38
Modbus.Net/Modbus.Net.OPC/OpcDaProtocal.cs
Normal file
@@ -0,0 +1,38 @@
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace Modbus.Net.OPC
|
||||
{
|
||||
/// <summary>
|
||||
/// Opc Da协议
|
||||
/// </summary>
|
||||
public class OpcDaProtocol : OpcProtocol
|
||||
{
|
||||
private readonly string _host;
|
||||
|
||||
private readonly bool _isRegexOn;
|
||||
|
||||
/// <summary>
|
||||
/// 构造函数
|
||||
/// </summary>
|
||||
/// <param name="host">Opc DA服务地址</param>
|
||||
/// <param name="isRegexOn">是否开启正则匹配</param>
|
||||
public OpcDaProtocol(string host, bool isRegexOn)
|
||||
{
|
||||
_host = host;
|
||||
_isRegexOn = isRegexOn;
|
||||
}
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// 连接设备
|
||||
/// </summary>
|
||||
/// <returns>是否连接成功</returns>
|
||||
public override async Task<bool> ConnectAsync()
|
||||
{
|
||||
ProtocolLinker = new OpcDaProtocolLinker(_host, _isRegexOn);
|
||||
if (!await ProtocolLinker.ConnectAsync())
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
28
Modbus.Net/Modbus.Net.OPC/OpcDaProtocalLinker.cs
Normal file
28
Modbus.Net/Modbus.Net.OPC/OpcDaProtocalLinker.cs
Normal file
@@ -0,0 +1,28 @@
|
||||
using System.Configuration;
|
||||
|
||||
namespace Modbus.Net.OPC
|
||||
{
|
||||
/// <summary>
|
||||
/// Opc Da协议连接器
|
||||
/// </summary>
|
||||
public class OpcDaProtocolLinker : OpcProtocolLinker
|
||||
{
|
||||
/// <summary>
|
||||
/// 构造函数
|
||||
/// </summary>
|
||||
/// <param name="isRegexOn">是否开启正则匹配</param>
|
||||
public OpcDaProtocolLinker(bool isRegexOn) : this(ConfigurationManager.AppSettings["OpcDaHost"], isRegexOn)
|
||||
{
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 构造函数
|
||||
/// </summary>
|
||||
/// <param name="host">Opc DA服务地址</param>
|
||||
/// <param name="isRegexOn">是否开启正则匹配</param>
|
||||
public OpcDaProtocolLinker(string host, bool isRegexOn)
|
||||
{
|
||||
BaseConnector = OpcDaConnector.Instance(host, isRegexOn);
|
||||
}
|
||||
}
|
||||
}
|
||||
18
Modbus.Net/Modbus.Net.OPC/OpcDaUtility.cs
Normal file
18
Modbus.Net/Modbus.Net.OPC/OpcDaUtility.cs
Normal file
@@ -0,0 +1,18 @@
|
||||
namespace Modbus.Net.OPC
|
||||
{
|
||||
/// <summary>
|
||||
/// Opc Da协议Api入口
|
||||
/// </summary>
|
||||
public class OpcDaUtility : OpcUtility
|
||||
{
|
||||
/// <summary>
|
||||
/// 构造函数
|
||||
/// </summary>
|
||||
/// <param name="connectionString">连接地址</param>
|
||||
/// <param name="isRegexOn">是否开启正则匹配</param>
|
||||
public OpcDaUtility(string connectionString, bool isRegexOn = false) : base(connectionString)
|
||||
{
|
||||
Wrapper = new OpcDaProtocol(ConnectionString, isRegexOn);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -48,7 +48,7 @@ namespace Modbus.Net.Siemens
|
||||
var head = splitString[0];
|
||||
var tail = splitString[1];
|
||||
string sub;
|
||||
if (tail.Contains('.'))
|
||||
if (tail.Contains("."))
|
||||
{
|
||||
var splitString2 = tail.Split('.');
|
||||
sub = splitString2[1];
|
||||
|
||||
@@ -1,7 +1,8 @@
|
||||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFrameworks>net6.0</TargetFrameworks>
|
||||
<TargetFrameworks>net6.0;net462</TargetFrameworks>
|
||||
<LangVersion>11.0</LangVersion>
|
||||
<AssemblyName>Modbus.Net.Siemens</AssemblyName>
|
||||
<RootNamespace>Modbus.Net.Siemens</RootNamespace>
|
||||
<PackageId>Modbus.Net.Siemens</PackageId>
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
using System;
|
||||
using FastEnumUtility;
|
||||
using System.Collections.Generic;
|
||||
using System.IO.Ports;
|
||||
using System.Threading;
|
||||
@@ -17,9 +17,9 @@ namespace Modbus.Net.Siemens
|
||||
/// <param name="com">串口地址</param>
|
||||
/// <param name="slaveAddress">从站号</param>
|
||||
public SiemensPpiProtocolLinker(string com, int slaveAddress)
|
||||
: base(com, slaveAddress, parity:
|
||||
ConfigurationReader.GetValue("COM:Siemens", "Parity") != null
|
||||
? Enum.Parse<Parity>(ConfigurationReader.GetValue("COM:Siemens", "Parity"))
|
||||
: base(com, slaveAddress, parity:
|
||||
ConfigurationReader.GetValue("COM:Siemens", "Parity") != null
|
||||
? FastEnum.Parse<Parity>(ConfigurationReader.GetValue("COM:Siemens", "Parity"))
|
||||
: null
|
||||
)
|
||||
{
|
||||
|
||||
@@ -28,8 +28,6 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "AnyType", "..\Samples\AnyTy
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Modbus.Net.OPC", "Modbus.Net.OPC\Modbus.Net.OPC.csproj", "{C854A379-C5EA-4CAC-9C5F-7291372D1D3F}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "h-opc", "..\Libraries\h-opc\h-opc.csproj", "{347D0027-45F6-48C9-A917-1B1DF6C66DC5}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "CrossLamp", "..\Samples\CrossLamp\CrossLamp.csproj", "{AA3A42D2-0502-41D3-929A-BAB729DF07D6}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "TripleAdd", "..\Samples\TripleAdd\TripleAdd.csproj", "{414956B8-DBD4-414C-ABD3-565580739646}"
|
||||
@@ -74,10 +72,6 @@ Global
|
||||
{C854A379-C5EA-4CAC-9C5F-7291372D1D3F}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{C854A379-C5EA-4CAC-9C5F-7291372D1D3F}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{C854A379-C5EA-4CAC-9C5F-7291372D1D3F}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{347D0027-45F6-48C9-A917-1B1DF6C66DC5}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{347D0027-45F6-48C9-A917-1B1DF6C66DC5}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{347D0027-45F6-48C9-A917-1B1DF6C66DC5}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{347D0027-45F6-48C9-A917-1B1DF6C66DC5}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{AA3A42D2-0502-41D3-929A-BAB729DF07D6}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{AA3A42D2-0502-41D3-929A-BAB729DF07D6}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{AA3A42D2-0502-41D3-929A-BAB729DF07D6}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
|
||||
@@ -13,7 +13,7 @@ namespace Modbus.Net
|
||||
private static readonly IConfigurationRoot configuration = new ConfigurationBuilder()
|
||||
.SetBasePath(Directory.GetCurrentDirectory())
|
||||
.AddJsonFile("appsettings.default.json", optional: false, reloadOnChange: true)
|
||||
.AddJsonFile("appsettings.json", optional:false, reloadOnChange: true)
|
||||
.AddJsonFile("appsettings.json", optional: false, reloadOnChange: true)
|
||||
.AddJsonFile($"appsettings.{Environment.GetEnvironmentVariable("DOTNET_ENVIRONMENT") ?? Environment.GetEnvironmentVariable("ASPNETCORE_ENVIRONMENT") ?? "Production"}.json", optional: true, reloadOnChange: true)
|
||||
.Build();
|
||||
|
||||
@@ -26,7 +26,7 @@ namespace Modbus.Net
|
||||
/// <returns>元素的值</returns>
|
||||
public static string? GetValue(string path, string key)
|
||||
{
|
||||
var split = path.Split(":");
|
||||
var split = path.Split(':');
|
||||
string? ans = null;
|
||||
while (split.Length > 0)
|
||||
{
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
using Microsoft.Extensions.Configuration;
|
||||
using FastEnumUtility;
|
||||
using Microsoft.Extensions.Configuration;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.IO;
|
||||
@@ -66,7 +67,7 @@ namespace Modbus.Net
|
||||
}
|
||||
case "endian":
|
||||
{
|
||||
paramsSet.Add(Enum.Parse<Endian>(dic["endian"]));
|
||||
paramsSet.Add(FastEnum.Parse<Endian>(dic["endian"]));
|
||||
break;
|
||||
}
|
||||
default:
|
||||
|
||||
65
Modbus.Net/Modbus.Net/Helper/EnumHelper.cs
Normal file
65
Modbus.Net/Modbus.Net/Helper/EnumHelper.cs
Normal file
@@ -0,0 +1,65 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
|
||||
namespace Modbus.Net
|
||||
{
|
||||
#if NET462
|
||||
#pragma warning disable 1591
|
||||
public static partial class EnumearbleExtensions
|
||||
{
|
||||
public static IEnumerable<T> TakeLast<T>(this IEnumerable<T> source, int count)
|
||||
{
|
||||
if (null == source)
|
||||
throw new ArgumentNullException(nameof(source));
|
||||
if (count < 0)
|
||||
throw new ArgumentOutOfRangeException(nameof(count));
|
||||
|
||||
if (0 == count)
|
||||
yield break;
|
||||
|
||||
// Optimization (see JonasH's comment)
|
||||
if (source is ICollection<T>)
|
||||
{
|
||||
foreach (T item in source.Skip(((ICollection<T>)source).Count - count))
|
||||
yield return item;
|
||||
|
||||
yield break;
|
||||
}
|
||||
|
||||
if (source is IReadOnlyCollection<T>)
|
||||
{
|
||||
foreach (T item in source.Skip(((IReadOnlyCollection<T>)source).Count - count))
|
||||
yield return item;
|
||||
|
||||
yield break;
|
||||
}
|
||||
|
||||
// General case, we have to enumerate source
|
||||
Queue<T> result = new Queue<T>();
|
||||
|
||||
foreach (T item in source)
|
||||
{
|
||||
if (result.Count == count)
|
||||
result.Dequeue();
|
||||
|
||||
result.Enqueue(item);
|
||||
}
|
||||
|
||||
foreach (T item in result)
|
||||
yield return result.Dequeue();
|
||||
}
|
||||
|
||||
public static IEnumerable<T> Append<T>(this IEnumerable<T> collection, T item)
|
||||
{
|
||||
if (collection == null)
|
||||
{
|
||||
throw new ArgumentNullException("Collection should not be null");
|
||||
}
|
||||
|
||||
return collection.Concat(Enumerable.Repeat(item, 1));
|
||||
}
|
||||
}
|
||||
#pragma warning restore 1591
|
||||
#endif
|
||||
}
|
||||
@@ -1,4 +1,4 @@
|
||||
using System;
|
||||
using FastEnumUtility;
|
||||
using System.IO.Ports;
|
||||
|
||||
namespace Modbus.Net
|
||||
@@ -63,11 +63,11 @@ namespace Modbus.Net
|
||||
protected ComProtocolLinker(string com, int slaveAddress, BaudRate? baudRate = null, Parity? parity = null, StopBits? stopBits = null, DataBits? dataBits = null, Handshake? handshake = null,
|
||||
int? connectionTimeout = null, bool? isFullDuplex = null)
|
||||
{
|
||||
baudRate = Enum.Parse<BaudRate>(baudRate != null ? baudRate.ToString() : null ?? ConfigurationReader.GetValue("COM:" + com, "BaudRate"));
|
||||
parity = Enum.Parse<Parity>(parity != null ? parity.ToString() : null ?? ConfigurationReader.GetValue("COM:" + com, "Parity"));
|
||||
stopBits = Enum.Parse<StopBits>(stopBits != null ? stopBits.ToString() : null ?? ConfigurationReader.GetValue("COM:" + com, "StopBits"));
|
||||
dataBits = Enum.Parse<DataBits>(dataBits != null ? dataBits.ToString() : null ?? ConfigurationReader.GetValue("COM:" + com, "DataBits"));
|
||||
handshake = Enum.Parse<Handshake>(handshake != null ? handshake.ToString() : null ?? ConfigurationReader.GetValue("COM:" + com, "Handshake"));
|
||||
baudRate = FastEnum.Parse<BaudRate>(baudRate != null ? baudRate.ToString() : null ?? ConfigurationReader.GetValue("COM:" + com, "BaudRate"));
|
||||
parity = FastEnum.Parse<Parity>(parity != null ? parity.ToString() : null ?? ConfigurationReader.GetValue("COM:" + com, "Parity"));
|
||||
stopBits = FastEnum.Parse<StopBits>(stopBits != null ? stopBits.ToString() : null ?? ConfigurationReader.GetValue("COM:" + com, "StopBits"));
|
||||
dataBits = FastEnum.Parse<DataBits>(dataBits != null ? dataBits.ToString() : null ?? ConfigurationReader.GetValue("COM:" + com, "DataBits"));
|
||||
handshake = FastEnum.Parse<Handshake>(handshake != null ? handshake.ToString() : null ?? ConfigurationReader.GetValue("COM:" + com, "Handshake"));
|
||||
connectionTimeout = int.Parse(connectionTimeout != null ? connectionTimeout.ToString() : null ?? ConfigurationReader.GetValue("COM:" + com, "ConnectionTimeout"));
|
||||
isFullDuplex = bool.Parse(isFullDuplex != null ? isFullDuplex.ToString() : null ?? ConfigurationReader.GetValue("COM:" + com, "FullDuplex"));
|
||||
BaseConnector = new ComConnector(com + ":" + slaveAddress, baudRate.Value, parity.Value, stopBits.Value, dataBits.Value, handshake.Value, connectionTimeout.Value, isFullDuplex.Value);
|
||||
|
||||
@@ -19,11 +19,11 @@ namespace Modbus.Net
|
||||
/// <returns>返回的数据</returns>
|
||||
public static Task<ReturnStruct<T>> InvokeGet<TMachineMethod, T>(this IMachineMethod machineMethod, object[] parameters) where TMachineMethod : IMachineMethod
|
||||
{
|
||||
if (typeof(TMachineMethod).Name[..14] != "IMachineMethod")
|
||||
if (typeof(TMachineMethod).Name.Substring(0, 14) != "IMachineMethod")
|
||||
{
|
||||
throw new NotSupportedException("IMachineMethod type name not begin with IMachineMethod");
|
||||
}
|
||||
var functionName = "Get" + typeof(TMachineMethod).Name[14..] + "Async";
|
||||
var functionName = "Get" + typeof(TMachineMethod).Name.Substring(14) + "Async";
|
||||
return InvokeGet<T>(machineMethod, functionName, parameters);
|
||||
}
|
||||
|
||||
@@ -54,11 +54,11 @@ namespace Modbus.Net
|
||||
/// <returns>设置是否成功</returns>
|
||||
public static Task<ReturnStruct<bool>> InvokeSet<TMachineMethod, T>(this IMachineMethod machineMethod, object[] parameters, T datas) where TMachineMethod : IMachineMethod
|
||||
{
|
||||
if (typeof(TMachineMethod).Name[..14] != "IMachineMethod")
|
||||
if (typeof(TMachineMethod).Name.Substring(0, 14) != "IMachineMethod")
|
||||
{
|
||||
throw new NotSupportedException("IMachineMethod type name not begin with IMachineMethod");
|
||||
}
|
||||
var functionName = "Set" + typeof(TMachineMethod).Name[14..] + "Async";
|
||||
var functionName = "Set" + typeof(TMachineMethod).Name.Substring(14) + "Async";
|
||||
return InvokeSet(machineMethod, functionName, parameters, datas);
|
||||
}
|
||||
|
||||
|
||||
@@ -1,7 +1,8 @@
|
||||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFrameworks>net6.0</TargetFrameworks>
|
||||
<TargetFrameworks>net6.0;net462</TargetFrameworks>
|
||||
<LangVersion>11.0</LangVersion>
|
||||
<AssemblyName>Modbus.Net</AssemblyName>
|
||||
<RootNamespace>Modbus.Net</RootNamespace>
|
||||
<PackageId>Modbus.Net</PackageId>
|
||||
@@ -30,6 +31,7 @@
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="DotNetty.Handlers" Version="0.7.5" />
|
||||
<PackageReference Include="FastEnum" Version="1.8.0" />
|
||||
<PackageReference Include="Microsoft.Extensions.Configuration.Binder" Version="7.0.4" />
|
||||
<PackageReference Include="Microsoft.Extensions.Configuration.Json" Version="7.0.0" />
|
||||
<PackageReference Include="Nito.AsyncEx" Version="5.1.2" />
|
||||
|
||||
@@ -18,11 +18,11 @@ namespace Modbus.Net
|
||||
/// <returns>返回的数据</returns>
|
||||
public static Task<ReturnStruct<T>> InvokeGet<TUtilityMethod, T>(this IUtilityMethod utilityMethod, object[] parameters) where TUtilityMethod : IUtilityMethod
|
||||
{
|
||||
if (typeof(TUtilityMethod).Name[..14] != "IUtilityMethod")
|
||||
if (typeof(TUtilityMethod).Name.Substring(0, 14) != "IUtilityMethod")
|
||||
{
|
||||
throw new NotSupportedException("IUtilityMethod type name not begin with IUtilityMethod");
|
||||
}
|
||||
var functionName = "Get" + typeof(TUtilityMethod).Name[14..] + "Async";
|
||||
var functionName = "Get" + typeof(TUtilityMethod).Name.Substring(14) + "Async";
|
||||
return InvokeGet<T>(utilityMethod, functionName, parameters);
|
||||
}
|
||||
|
||||
@@ -53,11 +53,11 @@ namespace Modbus.Net
|
||||
/// <returns>设置是否成功</returns>
|
||||
public static Task<ReturnStruct<bool>> InvokeSet<TUtilityMethod, T>(this IUtilityMethod utilityMethod, object[] parameters, T datas) where TUtilityMethod : IUtilityMethod
|
||||
{
|
||||
if (typeof(TUtilityMethod).Name[..14] != "IUtilityMethod")
|
||||
if (typeof(TUtilityMethod).Name.Substring(0, 14) != "IUtilityMethod")
|
||||
{
|
||||
throw new NotSupportedException("IUtilityMethod type name not begin with IUtilityMethod");
|
||||
}
|
||||
var functionName = "Set" + typeof(TUtilityMethod).Name[14..] + "Async";
|
||||
var functionName = "Set" + typeof(TUtilityMethod).Name.Substring(14) + "Async";
|
||||
return InvokeSet(utilityMethod, functionName, parameters, datas);
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user