Opc.Ua.ServerTest.SessionTest.DoKeepAliveTest C# (CSharp) Method

DoKeepAliveTest() private method

Tests the session keep alive when there are no errors.
private DoKeepAliveTest ( ) : bool
return bool
        private bool DoKeepAliveTest()
        {
            bool success = true;
            
            double increment = MaxProgress/3;
            double position  = 0;

            m_keepAliveCount = 0;

            int currentKeepAlive = Session.KeepAliveInterval;
            List<Subscription> subscriptions = new List<Subscription>();
            KeepAliveEventHandler handler = new KeepAliveEventHandler(Session_KeepAlive); 

            try
            {
                Session.KeepAlive += handler;

                // add several subscriptions with long publish intervals.
                for (int publishingInterval = 10000; publishingInterval <= 20000; publishingInterval += 1000)
                {
                    Subscription subscription = new Subscription();

                    subscription.MaxMessageCount = 100;
                    subscription.LifetimeCount = 100;
                    subscription.KeepAliveCount = 10;
                    subscription.PublishingEnabled = true;
                    subscription.PublishingInterval = publishingInterval;

                    MonitoredItem monitoredItem = new MonitoredItem();

                    monitoredItem.StartNodeId = VariableIds.Server_ServerStatus_CurrentTime;
                    monitoredItem.AttributeId = Attributes.Value;
                    monitoredItem.SamplingInterval = -1;
                    monitoredItem.QueueSize = 0;
                    monitoredItem.DiscardOldest = true;

                    subscription.AddItem(monitoredItem);
                    Session.AddSubscription(subscription);
                    subscription.Create();
                    subscriptions.Add(subscription);
                }
                
                // get a value to read.
                ReadValueId nodeToRead = new ReadValueId();
                nodeToRead.NodeId = VariableIds.Server_ServerStatus;
                nodeToRead.AttributeId = Attributes.Value;
                ReadValueIdCollection nodesToRead = new ReadValueIdCollection();
                nodesToRead.Add(nodeToRead);

                int testDuration = 5000;

                // make sure the keep alives come at the expected rate.
                for (int keepAliveInterval = 500; keepAliveInterval < 2000; keepAliveInterval += 500)
                {
                    m_keepAliveCount = 0;

                    DateTime start = DateTime.UtcNow;
                    
                    DataValueCollection results = null;
                    DiagnosticInfoCollection diagnosticsInfos = null;

                    Session.Read(
                        null,
                        0,
                        TimestampsToReturn.Neither,
                        nodesToRead,
                        out results,
                        out diagnosticsInfos);

                    ClientBase.ValidateResponse(results, nodesToRead);
                    ClientBase.ValidateDiagnosticInfos(diagnosticsInfos, nodesToRead);

                    ServerStatusDataType status = ExtensionObject.ToEncodeable(results[0].Value as ExtensionObject) as ServerStatusDataType;

                    if (status == null)
                    {
                        Log("Server did not return a valid ServerStatusDataType structure. Value={0}, Status={1}", results[0].WrappedValue, results[0].StatusCode);
                        return false;
                    }

                    if ((DateTime.UtcNow - start).TotalSeconds > 1)
                    {
                        Log("Unexpected delay reading the ServerStatus structure. Delay={0}s", (DateTime.UtcNow - start).TotalSeconds);
                        return false;
                    }

                    Log("Setting keep alive interval to {0}ms.", keepAliveInterval);

                    Session.KeepAliveInterval = keepAliveInterval;

                    if (m_errorEvent.WaitOne(testDuration, false))
                    {
                        Log("Unexpected error waiting for session keep alives. {0}", m_error.ToLongString());
                        return false;
                    }

                    if (m_keepAliveCount < testDuration / keepAliveInterval)
                    {
                        Log("Missing session keep alives. Expected={0}, Actual={1}", testDuration / keepAliveInterval, m_keepAliveCount);
                        return false;
                    }

                    Log("{0} keep alives received in {1}ms.", m_keepAliveCount, testDuration);

                    position += increment;
                    ReportProgress(position);
                }

                ReportProgress(MaxProgress);
            }
            finally
            {
                Session.RemoveSubscriptions(subscriptions);
                Session.KeepAliveInterval = currentKeepAlive;
                Session.KeepAlive -= handler;
            }

            return success;
        }