/// <summary>
 /// Check whether valid node and return service result if not.
 /// </summary>
 /// <param name="endpoint"></param>
 /// <param name="request"></param>
 /// <returns></returns>
 private Task <ServiceResultModel> TestPublishNodeAsync(EndpointModel endpoint,
                                                        PublishStartRequestModel request)
 {
     // Test whether value exists and fail if not
     return(_opc.ExecuteServiceAsync(endpoint, null,
                                     TimeSpan.FromSeconds(10), async session => {
         var readNode = request.Item.NodeId.ToNodeId(session.MessageContext);
         if (NodeId.IsNull(readNode))
         {
             throw new ArgumentException(nameof(request.Item.NodeId));
         }
         var diagnostics = new List <OperationResultModel>();
         var response = await session.ReadAsync(
             (request.Header?.Diagnostics).ToStackModel(),
             0, TimestampsToReturn.Both, new ReadValueIdCollection {
             new ReadValueId {
                 NodeId = readNode,
                 AttributeId = Attributes.Value
             }
         });
         OperationResultEx.Validate("Publish_" + readNode, diagnostics,
                                    response.Results.Select(r => r.StatusCode),
                                    response.DiagnosticInfos, false);
         SessionClientEx.Validate(response.Results, response.DiagnosticInfos);
         if (response.Results == null || response.Results.Count == 0)
         {
             return diagnostics.ToServiceModel(request.Header?.Diagnostics,
                                               session.MessageContext);
         }
         return null;
     }));
 }
        /// <summary>
        /// Load references
        /// </summary>
        /// <param name="nodeModel"></param>
        /// <param name="ct"></param>
        /// <returns></returns>
        public async Task FetchReferencesAsync(BaseNodeModel nodeModel, CancellationToken ct)
        {
            try {
                // Read node with value
                var response = await _client.ExecuteServiceAsync(_endpoint, _elevation,
                                                                 _priority, ct, session => {
                    _encoder.Context.UpdateFromSession(session);
                    return(session.BrowseAsync(_diagnostics.ToStackModel(), null,
                                               nodeModel.NodeId, 0u, Opc.Ua.BrowseDirection.Both,
                                               ReferenceTypeIds.References, true, 0u));
                });

                SessionClientEx.Validate(response.Results, response.DiagnosticInfos);
                OperationResultEx.Validate("Browse_" + nodeModel.NodeId, Diagnostics,
                                           response.Results.Select(r => r.StatusCode), null, false);
                while (true)
                {
                    foreach (var reference in response.Results[0].References)
                    {
                        nodeModel.AddReference(reference.ReferenceTypeId,
                                               !reference.IsForward, reference.NodeId);
                        _references++;
                    }
                    if (response.Results[0].ContinuationPoint == null)
                    {
                        break;
                    }
                    response = await _client.ExecuteServiceAsync(_endpoint, _elevation,
                                                                 _priority, ct, session => {
                        _encoder.Context.UpdateFromSession(session);
                        return(session.BrowseNextAsync(_diagnostics.ToStackModel(), false,
                                                       new ByteStringCollection {
                            response.Results[0].ContinuationPoint
                        }));
                    });

                    SessionClientEx.Validate(response.Results, response.DiagnosticInfos);
                    OperationResultEx.Validate("BrowseNext_" + nodeModel.NodeId, Diagnostics,
                                               response.Results.Select(r => r.StatusCode), null, false);
                }
            }
            catch (Exception ex) {
                _logger.Error(ex, "Failed browsing node object for node {nodeId}.",
                              nodeModel.NodeId);
            }
        }
예제 #3
0
 /// <inheritdoc/>
 public async Task <(ServiceResultModel, string)> CallMethodAsync(
     string method, string request, DiagnosticsModel diagnostics)
 {
     if (string.IsNullOrEmpty(request))
     {
         throw new ArgumentNullException(nameof(request));
     }
     if (string.IsNullOrEmpty(method))
     {
         throw new ArgumentNullException(nameof(method));
     }
     return(await _client.ExecuteServiceAsync(_endpoint,
                                              null, async session => {
         var results = new List <OperationResultModel>();
         var methodCalls = new CallMethodRequestCollection {
             new CallMethodRequest {
                 ObjectId = new NodeId(kMethodCallObject, 2),
                 MethodId = new NodeId(kMethodCallMethod, 2),
                 InputArguments = new VariantCollection {
                     new Variant(method),
                     new Variant(request)
                 }
             }
         };
         var result = await session.CallAsync(diagnostics.ToStackModel(),
                                              methodCalls);
         OperationResultEx.Validate("CallMethod", results,
                                    result.Results.Select(r => r.StatusCode), result.DiagnosticInfos,
                                    methodCalls, false);
         var diagResult = results.ToServiceModel(diagnostics,
                                                 session.MessageContext);
         if (!StatusCode.IsGood(result.Results[0].StatusCode))
         {
             _logger.Error("Call returned with error {status}",
                           result.Results[0].StatusCode);
             return (diagResult, null);
         }
         if (result.Results[0].OutputArguments?.Count == 1)
         {
             var response = result.Results[0].OutputArguments[0].ToString();
             return (diagResult, response);
         }
         return (diagResult, null);
     }));
 }