namespace ZB.MOM.WW.OtOpcUa.Commons.OpcUa; /// /// Abstraction over the OPC UA SDK's address space. OpcUaPublishActor consumes this /// so the Runtime project doesn't reference Opc.Ua.Server directly — production /// binds a real SDK-backed sink in the fused Host's wiring, dev/Mac binds the /// no-op. /// public interface IOpcUaAddressSpaceSink { /// Write a Variable node's current value + quality + source timestamp. void WriteValue(string nodeId, object? value, OpcUaQuality quality, DateTime sourceTimestampUtc); /// Write an alarm-condition Variable's active/acknowledged state. void WriteAlarmState(string alarmNodeId, bool active, bool acknowledged, DateTime sourceTimestampUtc); /// /// Ensure a folder node exists under the given parent. Used by Phase7Applier to /// materialise the UNS Area/Line/Equipment hierarchy in the address space. When /// is null the folder is parented under the namespace /// root. Idempotent: calling twice with the same id is safe. /// void EnsureFolder(string folderNodeId, string? parentNodeId, string displayName); /// /// Ensure a Variable node exists at , parented under /// (or the namespace root when null). Created with /// Bad quality + null value; subsequent calls update both. /// Used by Phase7Applier to materialise Galaxy / SystemPlatform tags ahead of any /// driver-side subscribe so OPC UA clients can browse them. Idempotent. /// /// OPC UA built-in type name ("Boolean" / "Int32" / "Float" / etc.). void EnsureVariable(string variableNodeId, string? parentFolderNodeId, string displayName, string dataType); /// /// Tear down + repopulate the address space. Called by OpcUaPublishActor after a /// successful deployment apply so the node manager reflects the new config. Idempotent. /// void RebuildAddressSpace(); } /// OPC UA status code projection — Good / Uncertain / Bad. Real SDK has finer-grained /// codes; the engine actors only need this 3-state classification. public enum OpcUaQuality { Good, Uncertain, Bad } /// No-op sink. Bound by default so the actors are safe to run in dev / Mac / /// integration tests without a real SDK behind them. public sealed class NullOpcUaAddressSpaceSink : IOpcUaAddressSpaceSink { public static readonly NullOpcUaAddressSpaceSink Instance = new(); private NullOpcUaAddressSpaceSink() { } public void WriteValue(string nodeId, object? value, OpcUaQuality quality, DateTime sourceTimestampUtc) { } public void WriteAlarmState(string alarmNodeId, bool active, bool acknowledged, DateTime sourceTimestampUtc) { } public void EnsureFolder(string folderNodeId, string? parentNodeId, string displayName) { } public void EnsureVariable(string variableNodeId, string? parentFolderNodeId, string displayName, string dataType) { } public void RebuildAddressSpace() { } }