You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何使用UA-.NETStandard读取自定义UDT复杂类型

UA-.NETStandard自定义UDT处理优化咨询

我基于.NET使用UA-.NETStandard开发OPC UA客户端,目前代码能成功读取PLC上的指定节点,但该节点使用自定义UDT(用户自定义数据类型)。虽然可以手动解析响应来匹配数据结构,但希望找到更优的自定义UDT处理方法。已经查看了UA-.NETStandard的GitHub示例,未找到解决方案,恳请指导。

PLC上的UDT为名为H35dispenser的自定义数据类型,包含ID等属性字段。

以下是我的代码:

var session = Session.Create(
    config,
    new ConfiguredEndpoint(null, selectedEndpoint, EndpointConfiguration.Create(config)),
    false, "", 60000, null, null
).GetAwaiter().GetResult();

InitializeComplexTypeSystem(session);

var result = session.ReadValue("ns=3;s=\"H35dispenser\".\"ID\"");
public static ComplexTypeSystem InitializeComplexTypeSystem(Session session)
{
    Console.WriteLine("Initializing ComplexTypeSystem");
    ComplexTypeSystem complexTypeSystem = new ComplexTypeSystem(session);
    complexTypeSystem.Load().Wait();
    Console.WriteLine("Initialized ComplexTypeSystem");
    return complexTypeSystem;
}

优化处理方案

  • 直接读取整个UDT节点并自动解析
    你已经初始化了ComplexTypeSystem,但当前只读取了单个字段。可以直接读取整个UDT节点,ComplexTypeSystem会自动将返回值映射为复杂类型对象:
// 读取整个H35dispenser节点
var udtNodeId = "ns=3;s=\"H35dispenser\"";
var udtValue = session.ReadValue(udtNodeId);
// 解码为复杂类型对象
var complexObject = complexTypeSystem.Decode(udtValue.Value);
// 直接访问属性,例如 complexObject.ID
  • 生成强类型类简化操作
    UA-.NETStandard支持基于服务器元数据生成C#强类型类,彻底避免手动解析:
// 生成指定命名空间的强类型代码到指定目录
complexTypeSystem.GenerateCode(@"C:\YourProject\GeneratedTypes", "YourApp.OPC.Types");

将生成的类文件添加到项目后,可直接转换读取结果:

var dispenser = complexObject as H35dispenser;
if (dispenser != null)
{
    Console.WriteLine($"ID: {dispenser.ID}");
    // 直接访问UDT的其他属性
}
  • 替换同步调用为异步模式
    当前代码使用.Wait()和.GetAwaiter().GetResult()易引发死锁,建议改用异步写法:
var session = await Session.Create(
    config,
    new ConfiguredEndpoint(null, selectedEndpoint, EndpointConfiguration.Create(config)),
    false, "", 60000, null, null
);

var complexTypeSystem = new ComplexTypeSystem(session);
await complexTypeSystem.Load();

var result = await session.ReadValueAsync("ns=3;s=\"H35dispenser\".\"ID\"");
  • 验证UDT元数据加载状态
    确保ComplexTypeSystem.Load()成功加载目标UDT,可添加检查逻辑:
var allTypes = complexTypeSystem.GetTypes();
var targetUdt = allTypes.FirstOrDefault(t => t.BrowseName.Name == "H35dispenser");
if (targetUdt == null)
{
    Console.WriteLine("目标UDT未加载,请检查节点命名空间和名称是否正确");
}

内容的提问来源于stack exchange,提问作者Dutch

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.16 17:31:00