mirror of
https://github.com/OPCFoundation/UA-.NETStandard.git
synced 2026-10-22 17:50:03 +08:00
196 lines
8.3 KiB
C#
196 lines
8.3 KiB
C#
using System;
|
|
using System.Collections.Generic;
|
|
using System.Threading.Tasks;
|
|
using Opc.Ua;
|
|
using Opc.Ua.Client;
|
|
using System.Net;
|
|
|
|
namespace NetCoreConsoleClient
|
|
{
|
|
public class Program
|
|
{
|
|
public static void Main(string[] args)
|
|
{
|
|
Console.WriteLine(".NetCore Opc.Ua Console Client sample ");
|
|
Task t = ConsoleSampleClient();
|
|
t.Wait();
|
|
}
|
|
|
|
public static async Task ConsoleSampleClient()
|
|
{
|
|
Console.WriteLine("1 - Create an Application Configuration.");
|
|
var config = new ApplicationConfiguration()
|
|
{
|
|
ApplicationName = "UA Sample Client",
|
|
ApplicationType = ApplicationType.Client,
|
|
ApplicationUri = "urn:localhost:OPCFoundation:SampleClient",
|
|
SecurityConfiguration = new SecurityConfiguration
|
|
{
|
|
ApplicationCertificate = new CertificateIdentifier
|
|
{
|
|
StoreType = @"Directory",
|
|
StorePath = @".",
|
|
SubjectName = Utils.Format(@"CN={0}, DC={1}", "UA Sample Client", Dns.GetHostName())
|
|
},
|
|
TrustedPeerCertificates = new CertificateTrustList
|
|
{
|
|
StoreType = @"Directory",
|
|
StorePath = @".",
|
|
},
|
|
TrustedIssuerCertificates = new CertificateTrustList
|
|
{
|
|
StoreType = @"Directory",
|
|
StorePath = @".",
|
|
},
|
|
NonceLength = 32,
|
|
AutoAcceptUntrustedCertificates = true
|
|
},
|
|
TransportConfigurations = new TransportConfigurationCollection(),
|
|
TransportQuotas = new TransportQuotas { OperationTimeout = 15000 },
|
|
ClientConfiguration = new ClientConfiguration { DefaultSessionTimeout = 60000 }
|
|
};
|
|
await config.Validate(ApplicationType.Client);
|
|
|
|
if (!config.SecurityConfiguration.AutoAcceptUntrustedCertificates)
|
|
{
|
|
config.CertificateValidator.CertificateValidation += new CertificateValidationEventHandler(CertificateValidator_CertificateValidation);
|
|
}
|
|
|
|
Console.WriteLine("2 - Discover endpoints of .Net UA Sample server.");
|
|
string endpointURL = "opc.tcp://" + Dns.GetHostName() + ":51210/UA/SampleServer";
|
|
var endpointCollection = DiscoverEndpoints(config, new Uri(endpointURL), 10);
|
|
|
|
Console.WriteLine("3 - Create a secure session with .Net UA Sample server.");
|
|
var secureEndpoint = SelectSecureEndpoint(endpointCollection);
|
|
var endpointConfiguration = EndpointConfiguration.Create(config);
|
|
var endpoint = new ConfiguredEndpoint(secureEndpoint.Server, endpointConfiguration);
|
|
var session = await Session.Create(config, endpoint, true, ".NetCore Console Client", 60000, null, null);
|
|
|
|
Console.WriteLine("4 - Browse the server namespace.");
|
|
ReferenceDescriptionCollection references;
|
|
Byte[] continuationPoint;
|
|
|
|
references = session.FetchReferences(ObjectIds.ObjectsFolder);
|
|
|
|
session.Browse(
|
|
null,
|
|
null,
|
|
ObjectIds.ObjectsFolder,
|
|
0u,
|
|
BrowseDirection.Forward,
|
|
ReferenceTypeIds.HierarchicalReferences,
|
|
true,
|
|
(uint)NodeClass.Variable | (uint)NodeClass.Object | (uint)NodeClass.Method,
|
|
out continuationPoint,
|
|
out references);
|
|
|
|
Console.WriteLine(" DisplayName, BrowseName, NodeClass");
|
|
foreach (var rd in references)
|
|
{
|
|
Console.WriteLine(" {0}, {1}, {2}", rd.DisplayName, rd.BrowseName, rd.NodeClass);
|
|
ReferenceDescriptionCollection nextRefs;
|
|
byte[] nextCp;
|
|
session.Browse(
|
|
null,
|
|
null,
|
|
ExpandedNodeId.ToNodeId(rd.NodeId, session.NamespaceUris),
|
|
0u,
|
|
BrowseDirection.Forward,
|
|
ReferenceTypeIds.HierarchicalReferences,
|
|
true,
|
|
(uint)NodeClass.Variable | (uint)NodeClass.Object | (uint)NodeClass.Method,
|
|
out nextCp,
|
|
out nextRefs);
|
|
|
|
foreach (var nextRd in nextRefs)
|
|
{
|
|
Console.WriteLine(" + {0}, {1}, {2}", nextRd.DisplayName, nextRd.BrowseName, nextRd.NodeClass);
|
|
}
|
|
}
|
|
|
|
Console.WriteLine("5 - Create a subscription with publishing interval of 1 second.");
|
|
var subscription = new Subscription(session.DefaultSubscription) { PublishingInterval = 1000 };
|
|
|
|
Console.WriteLine("6 - Add a list of items (server current time and status) to the subscription.");
|
|
var list = new List<MonitoredItem> { new MonitoredItem(subscription.DefaultItem) { DisplayName = "ServerStatusCurrentTime", StartNodeId = "i=2258" } };
|
|
list.ForEach(i => i.Notification += OnNotification);
|
|
subscription.AddItems(list);
|
|
|
|
Console.WriteLine("7 - Add the subscription to the session.");
|
|
session.AddSubscription(subscription);
|
|
subscription.Create();
|
|
|
|
Console.WriteLine("8 - Running...Press any key to exit...");
|
|
Console.ReadKey(true);
|
|
|
|
}
|
|
|
|
private static void OnNotification(MonitoredItem item, MonitoredItemNotificationEventArgs e)
|
|
{
|
|
foreach (var value in item.DequeueValues())
|
|
{
|
|
Console.WriteLine("{0}: {1}, {2}, {3}", item.DisplayName, value.Value, value.SourceTimestamp, value.StatusCode);
|
|
}
|
|
}
|
|
|
|
private static void CertificateValidator_CertificateValidation(CertificateValidator validator, CertificateValidationEventArgs e)
|
|
{
|
|
e.Accept = (e.Error.StatusCode == StatusCodes.BadCertificateUntrusted);
|
|
}
|
|
|
|
private static EndpointDescriptionCollection DiscoverEndpoints(ApplicationConfiguration config, Uri discoveryUrl, int timeout)
|
|
{
|
|
// use a short timeout.
|
|
EndpointConfiguration configuration = EndpointConfiguration.Create(config);
|
|
configuration.OperationTimeout = timeout;
|
|
|
|
using (DiscoveryClient client = DiscoveryClient.Create(
|
|
discoveryUrl,
|
|
EndpointConfiguration.Create(config)))
|
|
{
|
|
try
|
|
{
|
|
EndpointDescriptionCollection endpoints = client.GetEndpoints(null);
|
|
ReplaceLocalHostWithRemoteHost(endpoints, discoveryUrl);
|
|
return endpoints;
|
|
}
|
|
catch (Exception e)
|
|
{
|
|
Utils.Trace("Could not fetch endpoints from url: {0}. Reason={1}", discoveryUrl, e.Message);
|
|
throw e;
|
|
}
|
|
}
|
|
}
|
|
|
|
private static EndpointDescription SelectSecureEndpoint(EndpointDescriptionCollection endpointCollection)
|
|
{
|
|
EndpointDescription bestEndpoint = null;
|
|
foreach (EndpointDescription endpoint in endpointCollection)
|
|
{
|
|
if (endpoint.TransportProfileUri == Profiles.UaTcpTransport)
|
|
{
|
|
if (bestEndpoint == null || endpoint.SecurityLevel > bestEndpoint.SecurityLevel)
|
|
{
|
|
bestEndpoint = endpoint;
|
|
}
|
|
}
|
|
}
|
|
return bestEndpoint;
|
|
}
|
|
|
|
private static void ReplaceLocalHostWithRemoteHost(EndpointDescriptionCollection endpoints, Uri discoveryUrl)
|
|
{
|
|
foreach (EndpointDescription endpoint in endpoints)
|
|
{
|
|
endpoint.EndpointUrl = Utils.ReplaceLocalhost(endpoint.EndpointUrl, discoveryUrl.DnsSafeHost);
|
|
StringCollection updatedDiscoveryUrls = new StringCollection();
|
|
foreach (string url in endpoint.Server.DiscoveryUrls)
|
|
{
|
|
updatedDiscoveryUrls.Add(Utils.ReplaceLocalhost(url, discoveryUrl.DnsSafeHost));
|
|
}
|
|
endpoint.Server.DiscoveryUrls = updatedDiscoveryUrls;
|
|
}
|
|
}
|
|
}
|
|
}
|