using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Collections;
using Opc.Ua;
using Opc.Ua.Client;
using NLog;
namespace IOB_WIN_NEXT
{
///
/// Evento per incapsulare dati x refresh pagina
///
public class opcUaMonitItemChange : EventArgs
{
#region Private Fields
///
/// Monitored Item da notificare
///
private readonly MonitoredItem _monitoredItem;
///
/// Valore notifica
///
private readonly MonitoredItemNotification _notification;
#endregion Private Fields
#region Public Constructors
///
/// salvataggio obj
///
///
public opcUaMonitItemChange(MonitoredItem monitoredItem, MonitoredItemNotification notification)
{
_monitoredItem = monitoredItem;
_notification = notification;
}
#endregion Public Constructors
#region Public Properties
///
/// Proprietà lettura del MonitoredItem
///
public MonitoredItem CurrMonitoredItem
{
get { return _monitoredItem; }
}
///
/// Proprietà lettura della notifica
///
public MonitoredItemNotification CurrNotify
{
get { return _notification; }
}
#endregion Public Properties
}
///
/// OPC UA Client with examples of basic functionality.
///
public class UAClient
{
#region Private Fields
private readonly string currIob;
private readonly Action m_validateResponse;
private ApplicationConfiguration m_configuration;
private Session m_session;
#endregion Private Fields
#region Protected Fields
protected static Logger lg;
protected static bool isLogVerbose = false;
///
/// The user identity to use when creating the session.
///
public IUserIdentity CurrUserIdentity { get; set; } = new UserIdentity();
#endregion Protected Fields
#region Public Constructors
///
/// Initializes a new instance of the UAClient class.
///
public UAClient(ApplicationConfiguration configuration, string codIOB, string user, string pwd, bool verboseLog, Action validateResponse)
{
m_validateResponse = validateResponse;
currIob = codIOB;
lg = LogManager.GetCurrentClassLogger();
if (!string.IsNullOrEmpty(user) && !string.IsNullOrEmpty(pwd))
{
CurrUserIdentity = new UserIdentity(user, pwd);
}
else
{
CurrUserIdentity = new UserIdentity();
}
isLogVerbose = verboseLog;
m_configuration = configuration;
m_configuration.CertificateValidator.CertificateValidation += CertificateValidation;
}
#endregion Public Constructors
#region Public Events
///
/// Evento notifica variazione MonitoredItem
///
public event EventHandler eh_MonItChange;
#endregion Public Events
#region Public Properties
///
/// Gets or sets the server URL.
///
public string ServerUrl { get; set; } = "opc.tcp://localhost:4840";
///
/// Gets the client session.
///
public Session Session => m_session;
#endregion Public Properties
#region Private Methods
///
/// Handles the certificate validation event.
/// This event is triggered every time an untrusted certificate is received from the server.
///
private void CertificateValidation(CertificateValidator sender, CertificateValidationEventArgs e)
{
bool certificateAccepted = true;
// ****
// Implement a custom logic to decide if the certificate should be
// accepted or not and set certificateAccepted flag accordingly.
// The certificate can be retrieved from the e.Certificate field
// ***
ServiceResult error = e.Error;
while (error != null)
{
lgError($"{error.StatusCode} | {error.Code} | {error.LocalizedText}");
error = error.InnerResult;
}
if (certificateAccepted)
{
lgInfo($"Untrusted Certificate accepted. SubjectName = {e.Certificate.SubjectName}");
}
e.AcceptAll = certificateAccepted;
}
///
/// Handle DataChange notifications from Server
///
private void OnMonitoredItemNotification(MonitoredItem monitoredItem, MonitoredItemNotificationEventArgs e)
{
try
{
// Log MonitoredItem Notification event
MonitoredItemNotification notification = e.NotificationValue as MonitoredItemNotification;
// sollevo evento notifica vaziazione MonitoredItem
if (eh_MonItChange != null)
{
eh_MonItChange(this, new opcUaMonitItemChange(monitoredItem, notification));
}
lgTrace($"Notification Received | Variable: {monitoredItem.DisplayName} | Value: {notification.Value}");
}
catch (Exception ex)
{
lgError($"OnMonitoredItemNotification error: {ex.Message}");
}
}
#endregion Private Methods
#region Protected Methods
///
/// Effettua logging ERROR corretto impostanto anche la variabile IOB prima di scrivere...
///
///
protected void lgError(string message)
{
lg.Factory.Configuration.Variables["codIOB"] = currIob;
lg.Error(message);
}
///
/// Effettua logging INFO corretto impostanto anche la variabile IOB prima di scrivere...
///
///
protected void lgInfo(string message)
{
lg.Factory.Configuration.Variables["codIOB"] = currIob;
lg.Info(message);
}
///
/// Effettua logging DEBUG corretto impostanto anche la variabile IOB prima di scrivere...
///
///
protected void lgDebug(string message)
{
lg.Factory.Configuration.Variables["codIOB"] = currIob;
lg.Info(message);
}
///
/// Effettua logging TRACE corretto impostanto anche la variabile IOB prima di scrivere...
///
///
protected void lgTrace(string message)
{
lg.Factory.Configuration.Variables["codIOB"] = currIob;
lg.Trace(message);
}
#endregion Protected Methods
#region Public Methods
///
/// Browse Server nodes
///
public bool Browse(ushort startNodeNS, uint startNodeVal, List vetoBrowse, ref Dictionary nodeIdNameList)
{
bool fatto = false;
if (m_session == null || m_session.Connected == false)
{
lgError("Session not connected!");
return false;
}
try
{
// Create a Browser object
Browser browser = new Browser(m_session);
// Set browse parameters
browser.BrowseDirection = BrowseDirection.Forward;
browser.NodeClassMask = (int)NodeClass.Object | (int)NodeClass.Variable;
browser.ReferenceTypeId = ReferenceTypeIds.HierarchicalReferences;
//NodeId nodeToBrowse = ObjectIds.Server;
//NodeId nodeToBrowse = new NodeId("ns=4,i=5001");
NodeId nodeToBrowse = new NodeId(startNodeVal, startNodeNS);
// Call Browse service
lgTrace($"Browsing {nodeToBrowse} node...");
ReferenceDescriptionCollection browseResults = browser.Browse(nodeToBrowse);
// Display the results
lgTrace($"Browse returned {browseResults.Count} results:");
foreach (ReferenceDescription result in browseResults)
{
lgTrace($" NodeId = {result.NodeId}, TypeId = {result.TypeId}, DisplayName = {result.DisplayName.Text}, NodeClass = {result.NodeClass}, Others: {result.BinaryEncodingId} | {result.BrowseName}");
// se NON fa parte dell'elenco dei VETO di filterItems...
if (!vetoBrowse.Contains($"{result.NodeId}"))
{
// se mancasse aggiungo...
if (!nodeIdNameList.ContainsKey($"{result.NodeId}"))
{
nodeIdNameList.Add(result.NodeId.ToString(), result.DisplayName.Text);
}
}
}
fatto = true;
}
catch (Exception ex)
{
// Log Error
lgError($"Browse Error : {ex.Message}");
}
return fatto;
}
///
/// Browse Server nodes
///
public bool Browse(string browsePath, List vetoBrowse, ref Dictionary nodeIdNameList)
{
bool fatto = false;
if (m_session == null || m_session.Connected == false)
{
lgError("Session not connected!");
return false;
}
try
{
// Create a Browser object
Browser browser = new Browser(m_session);
// Set browse parameters
browser.BrowseDirection = BrowseDirection.Forward;
browser.NodeClassMask = (int)NodeClass.Object | (int)NodeClass.Variable;
browser.ReferenceTypeId = ReferenceTypeIds.HierarchicalReferences;
//NodeId nodeToBrowse = ObjectIds.Server;
//NodeId nodeToBrowse = new NodeId("ns=4;i=5001");
NodeId nodeToBrowse = new NodeId(browsePath);
//nodeToBrowse = ObjectIds.Server;
//nodeToBrowse = new NodeId("Calibratrice_L1", 4);
//nodeToBrowse = new NodeId("Dati_Mes", 4);
//nodeToBrowse = new NodeId(5001, 2);
//nodeToBrowse = new NodeId("ns=4;s=NxController");
//nodeToBrowse = new NodeId("ns=4;s=Dati_Mes");
//nodeToBrowse = new NodeId("NxController.GlobalVars", 4);
//nodeToBrowse = new NodeId("Dati_Mes", 4);
// Call Browse service
lgTrace($"Browsing {nodeToBrowse} node...");
ReferenceDescriptionCollection browseResults = browser.Browse(nodeToBrowse);
// Display the results
lgTrace($"Browse returned {browseResults.Count} results:");
foreach (ReferenceDescription result in browseResults)
{
// se veto --> loggo veto
if (vetoBrowse.Contains($"{result.NodeId}"))
{
lgTrace($"| FILTERED --> NodeId = {result.NodeId}, DisplayName = {result.DisplayName.Text}, NodeClass = {result.NodeClass}, Others: {result.BinaryEncodingId} | {result.BrowseName}");
}
// se NON fa parte dell'elenco dei VETO di filterItems...
else
{
lgTrace($" NodeId = {result.NodeId}, DisplayName = {result.DisplayName.Text}, NodeClass = {result.NodeClass}, Others: {result.BinaryEncodingId} | {result.BrowseName}");
// se mancasse aggiungo...
if (!nodeIdNameList.ContainsKey($"{result.NodeId}"))
{
nodeIdNameList.Add($"{result.NodeId}", result.DisplayName.Text);
// se è un nodo object --> faccio sub browse!
if (result.NodeClass != NodeClass.Variable)
{
this.Browse($"{result.NodeId}", vetoBrowse, ref nodeIdNameList);
}
}
}
}
fatto = true;
}
catch (Exception ex)
{
// Log Error
lgError($"Browse Error : {ex.Message}");
}
return fatto;
}
///
/// Call UA method
///
public void CallMethod()
{
if (m_session == null || m_session.Connected == false)
{
lgError("Session not connected!");
return;
}
try
{
// Define the UA Method to call
// Parent node - Objects\CTT\Methods
// Method node - Objects\CTT\Methods\Add
NodeId objectId = new NodeId("ns=2;s=Methods");
NodeId methodId = new NodeId("ns=2;s=Methods_Add");
// Define the method parameters
// Input argument requires a Float and an UInt32 value
object[] inputArguments = new object[] { (float)10.5, (uint)10 };
IList