A clause that identifies a field to return with the event.
Inheritance: IFormattable
示例#1
0
        /// <summary>
        /// Adds the specified property to the event filter.
        /// </summary>
        public void AddSelectClause(NodeId eventTypeId, QualifiedName propertyName)
        {
            SimpleAttributeOperand clause = new SimpleAttributeOperand();

            clause.TypeDefinitionId = eventTypeId;
            clause.AttributeId      = Attributes.Value;

            clause.BrowsePath.Add(propertyName);

            SelectClauses.Add(clause);
        }
示例#2
0
        /// <summary>
        /// Adds the specified browse path to the event filter.
        /// </summary>
        public void AddSelectClause(NodeId eventTypeId, string browsePath, uint attributeId)
        {
            SimpleAttributeOperand clause = new SimpleAttributeOperand();

            clause.TypeDefinitionId = eventTypeId;
            clause.AttributeId      = attributeId;

            if (!String.IsNullOrEmpty(browsePath))
            {
                clause.BrowsePath = SimpleAttributeOperand.Parse(browsePath);
            }

            SelectClauses.Add(clause);
        }
示例#3
0
        /// <summary>
        /// Initializes a new instance of the <see cref="EventFieldDefinition"/> class.
        /// </summary>
        /// <param name="parentField">The parent field.</param>
        /// <param name="reference">The reference to the instance declaration node.</param>
        public EventFieldDefinition(EventFieldDefinition parentField, ReferenceDescription reference)
        {
            DeclarationNode = reference;

            Operand = new SimpleAttributeOperand();

            // setting the typedefinition id to null ignores the event type when evaluating the operand.
            Operand.TypeDefinitionId = null;

            // event filters only support the NodeId attribute for objects and the Value attribute for Variables.
            Operand.AttributeId = (reference.NodeClass == NodeClass.Variable) ? Attributes.Value : Attributes.NodeId;

            // prefix the browse path with the parent browse path.
            if (parentField != null)
            {
                Operand.BrowsePath = new QualifiedNameCollection(parentField.Operand.BrowsePath);
            }

            // add the child browse name.
            Operand.BrowsePath.Add(reference.BrowseName);

            // may select sub-sets of array values. Not used in this sample.
            Operand.IndexRange = null;

            // construct the display name.
            StringBuilder buffer = new StringBuilder();

            for (int ii = 0; ii < Operand.BrowsePath.Count; ii++)
            {
                if (buffer.Length > 0)
                {
                    buffer.Append('/');
                }

                buffer.Append(Operand.BrowsePath[ii].Name);
            }

            DisplayName = buffer.ToString();
        }
        /// <summary>
        /// Initializes the instance from an event notification.
        /// </summary>
        /// <param name="context">The context.</param>
        /// <param name="fields">The fields selected for the event notification.</param>
        /// <param name="e">The event notification.</param>
        /// <remarks>
        /// This method creates components based on the browse paths in the event field and sets
        /// the NodeId or Value based on values in the event notification.
        /// </remarks>
        public void Update(
            ISystemContext context,
            SimpleAttributeOperandCollection fields,
            EventFieldList e)
        {
            for (int ii = 0; ii < fields.Count; ii++)
            {
                SimpleAttributeOperand field = fields[ii];
                object value = e.EventFields[ii].Value;

                // check if value provided.
                if (value == null)
                {
                    continue;
                }

                // extract the NodeId for the event.
                if (field.BrowsePath.Count == 0)
                {
                    if (field.AttributeId == Attributes.NodeId)
                    {
                        this.NodeId = value as NodeId;
                        continue;
                    }
                }

                // extract the type definition for the event.
                if (field.BrowsePath.Count == 1)
                {
                    if (field.AttributeId == Attributes.Value)
                    {
                        if (field.BrowsePath[0] == BrowseNames.EventType)
                        {
                            m_typeDefinitionId = value as NodeId;
                            continue;
                        }
                    }
                }

                // save value for child node.
                NodeState parent = this;

                for (int jj = 0; jj < field.BrowsePath.Count; jj++)
                {
                    // find a predefined child identified by the browse name.
                    BaseInstanceState child = parent.CreateChild(context, field.BrowsePath[jj]);

                    // create a placeholder for unknown children.
                    if (child == null)
                    {
                        if (field.AttributeId == Attributes.Value)
                        {
                            child = new BaseDataVariableState(parent);
                        }
                        else
                        {
                            child = new BaseObjectState(parent);
                        }

                        parent.AddChild(child);
                    }

                    // ensure the browse name is set.
                    if (QualifiedName.IsNull(child.BrowseName))
                    {
                        child.BrowseName = field.BrowsePath[jj];
                    }

                    // ensure the display name is set.
                    if (LocalizedText.IsNullOrEmpty(child.DisplayName))
                    {
                        child.DisplayName = child.BrowseName.Name;
                    }

                    // process next element in path.
                    if (jj < field.BrowsePath.Count - 1)
                    {
                        parent = child;
                        continue;
                    }

                    // save the variable value.
                    if (field.AttributeId == Attributes.Value)
                    {
                        BaseVariableState variable = child as BaseVariableState;

                        if (variable != null && field.AttributeId == Attributes.Value)
                        {
                            try
                            {
                                variable.WrappedValue = e.EventFields[ii];
                            }
                            catch (Exception)
                            {
                                variable.Value = null;
                            }
                        }

                        break;
                    }

                    // save the node id.
                    child.NodeId = value as NodeId;
                }
            }
        }
示例#5
0
        /// <summary>
        /// Adds the specified browse path to the event filter.
        /// </summary>
        public void AddSelectClause(NodeId eventTypeId, string browsePath, uint attributeId)
        {
            SimpleAttributeOperand clause = new SimpleAttributeOperand();

            clause.TypeDefinitionId = eventTypeId;
            clause.AttributeId      = attributeId;

            if (!String.IsNullOrEmpty(browsePath))
            {
                clause.BrowsePath = SimpleAttributeOperand.Parse(browsePath);
            }            

            SelectClauses.Add(clause);
        }
示例#6
0
        /// <summary>
        /// Adds the specified property to the event filter.
        /// </summary>
        public void AddSelectClause(NodeId eventTypeId, QualifiedName propertyName)
        {
            SimpleAttributeOperand clause = new SimpleAttributeOperand();

            clause.TypeDefinitionId = eventTypeId;
            clause.AttributeId      = Attributes.Value;

            clause.BrowsePath.Add(propertyName);

            SelectClauses.Add(clause);
        }
        /// <summary>
        /// Collects the fields for the instance node.
        /// </summary>
        /// <param name="session">The session.</param>
        /// <param name="nodeId">The node id.</param>
        /// <param name="parentPath">The parent path.</param>
        /// <param name="fields">The event fields.</param>
        /// <param name="fieldNodeIds">The node id for the declaration of the field.</param>
        /// <param name="foundNodes">The table of found nodes.</param>
        private static void CollectFields(
            Session session,
            NodeId nodeId,
            QualifiedNameCollection parentPath,
            SimpleAttributeOperandCollection fields,
            List<NodeId> fieldNodeIds,
            Dictionary<NodeId, QualifiedNameCollection> foundNodes)
        {
            // find all of the children of the field.
            BrowseDescription nodeToBrowse = new BrowseDescription();

            nodeToBrowse.NodeId = nodeId;
            nodeToBrowse.BrowseDirection = BrowseDirection.Forward;
            nodeToBrowse.ReferenceTypeId = ReferenceTypeIds.Aggregates;
            nodeToBrowse.IncludeSubtypes = true;
            nodeToBrowse.NodeClassMask = (uint)(NodeClass.Object | NodeClass.Variable);
            nodeToBrowse.ResultMask = (uint)BrowseResultMask.All;

            ReferenceDescriptionCollection children = ClientUtils.Browse(session, nodeToBrowse, false);

            if (children == null)
            {
                return;
            }

            // process the children.
            for (int ii = 0; ii < children.Count; ii++)
            {
                ReferenceDescription child = children[ii];

                if (child.NodeId.IsAbsolute)
                {
                    continue;
                }

                // construct browse path.
                QualifiedNameCollection browsePath = new QualifiedNameCollection(parentPath);
                browsePath.Add(child.BrowseName);

                // check if the browse path is already in the list.
                int index = ContainsPath(fields, browsePath);

                if (index < 0)
                {
                    SimpleAttributeOperand field = new SimpleAttributeOperand();

                    field.TypeDefinitionId = ObjectTypeIds.BaseEventType;
                    field.BrowsePath = browsePath;
                    field.AttributeId = (child.NodeClass == NodeClass.Variable) ? Attributes.Value : Attributes.NodeId;

                    fields.Add(field);
                    fieldNodeIds.Add((NodeId)child.NodeId);
                }

                // recusively find all of the children.
                NodeId targetId = (NodeId)child.NodeId;

                // need to guard against loops.
                if (!foundNodes.ContainsKey(targetId))
                {
                    foundNodes.Add(targetId, browsePath);
                    CollectFields(session, (NodeId)child.NodeId, browsePath, fields, fieldNodeIds, foundNodes);
                }
            }
        }
示例#8
0
        /// <summary>
        /// Constructs the event filter for the subscription.
        /// </summary>
        /// <returns>The event filter.</returns>
        public EventFilter ConstructFilter(Session session)
        {
            EventFilter filter = new EventFilter();

            // the select clauses specify the values returned with each event notification.
            filter.SelectClauses = SelectClauses;

            // the where clause restricts the events returned by the server.
            // it works a lot like the WHERE clause in a SQL statement and supports
            // arbitrary expession trees where the operands are literals or event fields.
            ContentFilter whereClause = new ContentFilter();

            // the code below constructs a filter that looks like this:
            // (Severity >= X OR LastSeverity >= X) AND (SuppressedOrShelved == False) AND (OfType(A) OR OfType(B))

            // add the severity.
            ContentFilterElement element1 = null;
            ContentFilterElement element2 = null;

            if (Severity > EventSeverity.Min)
            {
                // select the Severity property of the event.
                SimpleAttributeOperand operand1 = new SimpleAttributeOperand();
                operand1.TypeDefinitionId = ObjectTypeIds.BaseEventType;
                operand1.BrowsePath.Add(BrowseNames.Severity);
                operand1.AttributeId = Attributes.Value;

                // specify the value to compare the Severity property with.
                LiteralOperand operand2 = new LiteralOperand();
                operand2.Value = new Variant((ushort)Severity);

                // specify that the Severity property must be GreaterThanOrEqual the value specified.
                element1 = whereClause.Push(FilterOperator.GreaterThanOrEqual, operand1, operand2);
            }

            // add the suppressed or shelved.
            if (!IgnoreSuppressedOrShelved)
            {
                // select the SuppressedOrShelved property of the event.
                SimpleAttributeOperand operand1 = new SimpleAttributeOperand();
                operand1.TypeDefinitionId = ObjectTypeIds.BaseEventType;
                operand1.BrowsePath.Add(BrowseNames.SuppressedOrShelved);
                operand1.AttributeId = Attributes.Value;

                // specify the value to compare the Severity property with.
                LiteralOperand operand2 = new LiteralOperand();
                operand2.Value = new Variant(false);

                // specify that the Severity property must Equal the value specified.
                element2 = whereClause.Push(FilterOperator.Equals, operand1, operand2);
                
                // chain multiple elements together with an AND clause.
                if (element1 != null)
                {
                    element1 = whereClause.Push(FilterOperator.And, element1, element2);
                }
                else
                {
                    element1 = element2;
                }
            }

            // add the event types.
            if (EventTypes != null && EventTypes.Count > 0)
            {
                element2 = null;

                // save the last element.
                for (int ii = 0; ii < EventTypes.Count; ii++)
                {
                    // for this example uses the 'OfType' operator to limit events to thoses with specified event type. 
                    LiteralOperand operand1 = new LiteralOperand();
                    operand1.Value = new Variant(EventTypes[ii]);
                    ContentFilterElement element3 = whereClause.Push(FilterOperator.OfType, operand1);

                    // need to chain multiple types together with an OR clause.
                    if (element2 != null)
                    {
                        element2 = whereClause.Push(FilterOperator.Or, element2, element3);
                    }
                    else
                    {
                        element2 = element3;
                    }
                }

                // need to link the set of event types with the previous filters.
                if (element1 != null)
                {
                    whereClause.Push(FilterOperator.And, element1, element2);
                }
            }

            filter.WhereClause = whereClause;

            // return filter.
            return filter;
        }
示例#9
0
        /// <summary>
        /// Constructs the select clauses for a set of event types.
        /// </summary>
        /// <param name="session">The session.</param>
        /// <param name="eventTypeIds">The event type ids.</param>
        /// <returns>The select clauses for all fields discovered.</returns>
        /// <remarks>
        /// Each event type is an ObjectType in the address space. The fields supported by the
        /// server are defined as children of the ObjectType. Many of the fields are manadatory
        /// and are defined by the UA information model, however, indiviudual servers many not 
        /// support all of the optional fields.
        /// 
        /// This method browses the type model and 
        /// </remarks>
        public SimpleAttributeOperandCollection ConstructSelectClauses(
            Session session,
            params NodeId[] eventTypeIds)
        {
            // browse the type model in the server address space to find the fields available for the event type.
            SimpleAttributeOperandCollection selectClauses = new SimpleAttributeOperandCollection();

            // must always request the NodeId for the condition instances.
            // this can be done by specifying an operand with an empty browse path.
            SimpleAttributeOperand operand = new SimpleAttributeOperand();

            operand.TypeDefinitionId = ObjectTypeIds.BaseEventType;
            operand.AttributeId = Attributes.NodeId;
            operand.BrowsePath = new QualifiedNameCollection();

            selectClauses.Add(operand);

            // add the fields for the selected EventTypes.
            if (eventTypeIds != null)
            {
                for (int ii = 0; ii < eventTypeIds.Length; ii++)
                {
                    CollectFields(session, eventTypeIds[ii], selectClauses);
                }
            }

            // use BaseEventType as the default if no EventTypes specified.
            else
            {
                CollectFields(session, ObjectTypeIds.BaseEventType, selectClauses);
            }

            return selectClauses;
        }