OPC Studio User's Guide and Reference
WhereClause Property (UAEventFilter)
Example 



OpcLabs.EasyOpcUA Assembly > OpcLabs.EasyOpc.UA Namespace > UAEventFilter Class : WhereClause Property
The criteria limiting the Notifications.
Syntax
'Declaration
 
<DataMemberAttribute()>
Public Property WhereClause As UAContentFilterElement
'Usage
 
Dim instance As UAEventFilter
Dim value As UAContentFilterElement
 
instance.WhereClause = value
 
value = instance.WhereClause
[DataMember()]
public UAContentFilterElement WhereClause {get; set;}
[DataMember()]
public:
property UAContentFilterElement^ WhereClause {
   UAContentFilterElement^ get();
   void set (    UAContentFilterElement^ value);
}

Property Value

This value of this property can be null (Nothing in Visual Basic).

The default value of this property is null.

Remarks

In order to obtain or modify this parameter, access the UAMonitoringParameters.EventFilter property of OpcLabs.EasyOpc.UA.OperationModel.UAMonitoredItemArguments.MonitoringParameters.

This method or property does not throw any exceptions, aside from execution exceptions such as System.Threading.ThreadAbortException or System.OutOfMemoryException.

Because the OpcLabs.EasyOpc.UA.Filtering.UAContentFilterElementBuilder has an implicit conversion to OpcLabs.EasyOpc.UA.Filtering.UAContentFilterElement, in languages that support implicit conversion operators (such as C# or VB.NET), you can simply use a OpcLabs.EasyOpc.UA.Filtering.UAContentFilterElementBuilder in place of OpcLabs.EasyOpc.UA.Filtering.UAContentFilterElement value when setting this property, and the corresponding OPC UA content filter element will be constructed automatically. When the implicit conversion operators are not supported (such as with Python.NET), you can convert a OpcLabs.EasyOpc.UA.Filtering.UAContentFilterElementBuilder to OpcLabs.EasyOpc.UA.Filtering.UAContentFilterElement using the OpcLabs.EasyOpc.UA.Filtering.UAContentFilterElementBuilder.ToUAContentFilterElement static method instead.

Example
// This example shows how to specify criteria for event notifications.
//
// Find all latest examples here: https://opclabs.doc-that.com/files/onlinedocs/OPCLabs-OpcStudio/Latest/examples.html .
// OPC client and subscriber examples in C# on GitHub: https://github.com/OPCLabs/Examples-QuickOPC-CSharp .
// Missing some example? Ask us for it on our Online Forums, https://www.opclabs.com/forum/index ! You do not have to own
// a commercial license in order to use Online Forums, and we reply to every post.

using System;
using OpcLabs.EasyOpc.UA;
using OpcLabs.EasyOpc.UA.AddressSpace;
using OpcLabs.EasyOpc.UA.AddressSpace.Standard;
using OpcLabs.EasyOpc.UA.AlarmsAndConditions;
using OpcLabs.EasyOpc.UA.Filtering;
using OpcLabs.EasyOpc.UA.OperationModel;

namespace UADocExamples.AlarmsAndConditions
{
    class WhereClause
    {
        public static void Main1()
        {
            UAEndpointDescriptor endpointDescriptor =
                "opc.tcp://opcua.demo-this.com:62544/Quickstarts/AlarmConditionServer";

            // Instantiate the client object and hook events.
            var client = new EasyUAClient();
            client.EventNotification += client_EventNotification;

            Console.WriteLine("Subscribing...");
            client.SubscribeEvent(
                endpointDescriptor,
                UAObjectIds.Server,
                1000,
                new UAEventFilterBuilder(
                    // Either the severity is >= 500, or the event comes from a specified source node
                    UAFilterElements.Or(
                        UAFilterElements.GreaterThanOrEqual(UABaseEventObject.Operands.Severity, 500),
                        UAFilterElements.Equals(
                            UABaseEventObject.Operands.SourceNode, 
                            new UANodeId("nsu=http://opcfoundation.org/Quickstarts/AlarmCondition ;ns=2;s=1:Metals/SouthMotor"))),
                    UABaseEventObject.AllFields));

            Console.WriteLine("Processing event notifications for 30 seconds...");
            System.Threading.Thread.Sleep(30 * 1000);

            Console.WriteLine("Unsubscribing...");
            client.UnsubscribeAllMonitoredItems();

            Console.WriteLine("Waiting for 5 seconds...");
            System.Threading.Thread.Sleep(5 * 1000);

            Console.WriteLine("Finished.");
        }

        static void client_EventNotification(object sender, EasyUAEventNotificationEventArgs e)
        {
            // Display the event.
            Console.WriteLine(e);
        }


        // Example output:
        //
        //Subscribing...
        //13000008
        //Processing event notifications for 30 seconds...
        //[] Success
        //[] Success; Refresh; RefreshInitiated
        //[] Success; Refresh; [SouthMotor] 100! {DialogConditionType} "The dialog was activated" @9/9/2021 2:22:18 PM (10 fields)
        //[] Success; Refresh; [SouthMotor] 700! {ExclusiveDeviationAlarmType} "The alarm severity has increased." @9/22/2021 7:17:59 AM (10 fields)
        //[] Success; Refresh; [SouthMotor] 900! {NonExclusiveLevelAlarmType} "The alarm severity has increased." @9/22/2021 7:17:57 AM (10 fields)
        //[] Success; Refresh; [SouthMotor] 100! {TripAlarmType} "The alarm is active." @9/22/2021 7:17:59 AM (10 fields)
        //[] Success; Refresh; [SouthMotor] 100! {TripAlarmType} "The alarm severity has increased." @9/9/2021 3:39:51 PM (10 fields)
        //[] Success; Refresh; [SouthMotor] 100! {TripAlarmType} "The alarm severity has increased." @9/9/2021 3:38:57 PM (10 fields)
        //[] Success; Refresh; RefreshComplete
        //[] Success; [SouthMotor] 100! {NonExclusiveLevelAlarmType} "The alarm was deactivated by the system." @9/22/2021 7:18:05 AM (10 fields)
        //[] Success; [SouthMotor] 300! {TripAlarmType} "The alarm severity has increased." @9/22/2021 7:18:08 AM (10 fields)
        //[] Success; [SouthMotor] 900! {ExclusiveDeviationAlarmType} "The alarm severity has increased." @9/22/2021 7:18:10 AM (10 fields)
        //[] Success; [SouthMotor] 100! {NonExclusiveLevelAlarmType} "The alarm is active." @9/22/2021 7:18:13 AM (10 fields)
        //[] Success; [SouthMotor] 500! {TripAlarmType} "The alarm severity has increased." @9/22/2021 7:18:17 AM (10 fields)
        //[] Success; [SouthMotor] 100! {ExclusiveDeviationAlarmType} "The alarm was deactivated by the system." @9/22/2021 7:18:21 AM (10 fields)
        //[] Success; [SouthMotor] 300! {NonExclusiveLevelAlarmType} "The alarm severity has increased." @9/22/2021 7:18:21 AM (10 fields)
        //[] Success; [SouthMotor] 700! {TripAlarmType} "The alarm severity has increased." @9/22/2021 7:18:26 AM (10 fields)
        //[] Success; [SouthMotor] 500! {NonExclusiveLevelAlarmType} "The alarm severity has increased." @9/22/2021 7:18:29 AM (10 fields)
        //[] Success; [SouthMotor] 100! {ExclusiveDeviationAlarmType} "The alarm is active." @9/22/2021 7:18:32 AM (10 fields)
        //Unsubscribing...
        //Waiting for 5 seconds...
        //Finished.
    }
}
# This example shows how to specify criteria for event notifications.
#
# Find all latest examples here: https://opclabs.doc-that.com/files/onlinedocs/OPCLabs-OpcStudio/Latest/examples.html .
# OPC client and subscriber examples in PowerShell on GitHub: https://github.com/OPCLabs/Examples-QuickOPC-PowerShell .
# Missing some example? Ask us for it on our Online Forums, https://www.opclabs.com/forum/index ! You do not have to own
# a commercial license in order to use Online Forums, and we reply to every post.

#requires -Version 5.1
using namespace OpcLabs.EasyOpc.UA
using namespace OpcLabs.EasyOpc.UA.AddressSpace
using namespace OpcLabs.EasyOpc.UA.AddressSpace.Standard

# The path below assumes that the current directory is [ProductDir]/Examples-NET/PowerShell/Windows .
Add-Type -Path "../../../Components/Opclabs.QuickOpc/net472/OpcLabs.EasyOpcUA.dll"
Add-Type -Path "../../../Components/Opclabs.QuickOpc/net472/OpcLabs.EasyOpcUAComponents.dll"

# Define which server we will work with.
[UAEndpointDescriptor]$endpointDescriptor = "opc.tcp://opcua.demo-this.com:62544/Quickstarts/AlarmConditionServer"

# Instantiate the client object.
$client = New-Object EasyUAClient

# Event notification handler
Register-ObjectEvent -InputObject $client -EventName EventNotification -Action { 
    # Display the event.
    Write-Host $EventArgs
}

Write-Host "Subscribing..."
[IEasyUAClientExtension]::SubscribeEvent($client, 
    $endpointDescriptor, 
    [UAObjectIds]::Server, 
    1000,
    [UAEventFilter](New-Object UAEventFilterBuilder(
        [UAFilterElements]::Equals(
            [UABaseEventObject+Operands]::SourceNode, 
            (New-Object UANodeId("nsu=http://opcfoundation.org/Quickstarts/AlarmCondition ;ns=2;s=1:Metals/SouthMotor"))),
        [UABaseEventObject]::AllFields))
    )

Write-Host "Processing event notifications for 30 seconds..."
$stopwatch =  [System.Diagnostics.Stopwatch]::StartNew() 
while ($stopwatch.Elapsed.TotalSeconds -lt 30) {    
    Start-Sleep -Seconds 1
}

Write-Host "Unsubscribing..."
$client.UnsubscribeAllMonitoredItems()

Write-Host "Waiting for 5 seconds..."
Start-Sleep -Seconds 5

Write-Host "Finished."


# Example output:
#
#Subscribing...
#13000008
#Processing event notifications for 30 seconds...
#[] Success
#[] Success; Refresh; RefreshInitiated
#[] Success; Refresh; [SouthMotor] 100! {DialogConditionType} "The dialog was activated" @9/9/2021 2:22:18 PM (10 fields)
#[] Success; Refresh; [SouthMotor] 700! {ExclusiveDeviationAlarmType} "The alarm severity has increased." @9/22/2021 7:17:59 AM (10 fields)
#[] Success; Refresh; [SouthMotor] 900! {NonExclusiveLevelAlarmType} "The alarm severity has increased." @9/22/2021 7:17:57 AM (10 fields)
#[] Success; Refresh; [SouthMotor] 100! {TripAlarmType} "The alarm is active." @9/22/2021 7:17:59 AM (10 fields)
#[] Success; Refresh; [SouthMotor] 100! {TripAlarmType} "The alarm severity has increased." @9/9/2021 3:39:51 PM (10 fields)
#[] Success; Refresh; [SouthMotor] 100! {TripAlarmType} "The alarm severity has increased." @9/9/2021 3:38:57 PM (10 fields)
#[] Success; Refresh; RefreshComplete
#[] Success; [SouthMotor] 100! {NonExclusiveLevelAlarmType} "The alarm was deactivated by the system." @9/22/2021 7:18:05 AM (10 fields)
#[] Success; [SouthMotor] 300! {TripAlarmType} "The alarm severity has increased." @9/22/2021 7:18:08 AM (10 fields)
#[] Success; [SouthMotor] 900! {ExclusiveDeviationAlarmType} "The alarm severity has increased." @9/22/2021 7:18:10 AM (10 fields)
#[] Success; [SouthMotor] 100! {NonExclusiveLevelAlarmType} "The alarm is active." @9/22/2021 7:18:13 AM (10 fields)
#[] Success; [SouthMotor] 500! {TripAlarmType} "The alarm severity has increased." @9/22/2021 7:18:17 AM (10 fields)
#[] Success; [SouthMotor] 100! {ExclusiveDeviationAlarmType} "The alarm was deactivated by the system." @9/22/2021 7:18:21 AM (10 fields)
#[] Success; [SouthMotor] 300! {NonExclusiveLevelAlarmType} "The alarm severity has increased." @9/22/2021 7:18:21 AM (10 fields)
#[] Success; [SouthMotor] 700! {TripAlarmType} "The alarm severity has increased." @9/22/2021 7:18:26 AM (10 fields)
#[] Success; [SouthMotor] 500! {NonExclusiveLevelAlarmType} "The alarm severity has increased." @9/22/2021 7:18:29 AM (10 fields)
#[] Success; [SouthMotor] 100! {ExclusiveDeviationAlarmType} "The alarm is active." @9/22/2021 7:18:32 AM (10 fields)
#Unsubscribing...
#Waiting for 5 seconds...
#Finished.
// This example shows how to specify criteria for event notifications.
//
// Find all latest examples here: https://opclabs.doc-that.com/files/onlinedocs/OPCLabs-OpcStudio/Latest/examples.html .
// Missing some example? Ask us for it on our Online Forums, https://www.opclabs.com/forum/index ! You do not have to own
// a commercial license in order to use Online Forums, and we reply to every post.

type
  TClientEventHandlers3 = class
    procedure OnEventNotification(
      Sender: TObject;
      sender0: OleVariant;
      eventArgs: _EasyUAEventNotificationEventArgs);
  end;

procedure TClientEventHandlers3.OnEventNotification(
  Sender: TObject;
  sender0: OleVariant;
  eventArgs: _EasyUAEventNotificationEventArgs);
begin
  // Display the event
  WriteLn(eventArgs.ToString);
end;

class procedure WhereClause.Main;

  function ToUAAttributeField(Operand: UASimpleAttributeOperand): UAAttributeField;
  var
    AttributeField: UAAttributeField;
  begin
    AttributeField := CoUAAttributeField.Create;
    AttributeField.Operand := Operand;
    ToUAAttributeField := AttributeField;
  end;

  function ObjectTypeIds_BaseEventType: UANodeId;
  var
    NodeId: UANodeId;
  begin
    NodeId := CoUANodeId.Create;
    NodeId.StandardName := 'BaseEventType';
    ObjectTypeIds_BaseEventType := NodeId;
  end;

  function UAFilterElements_SimpleAttribute(TypeId: UANodeId; SimpleRelativeBrowsePathString: string): UASimpleAttributeOperand;
  var
    Operand: UASimpleAttributeOperand;
    BrowsePathParser: UABrowsePathParser;
  begin
    BrowsePathParser := CoUABrowsePathParser.Create;
    Operand := CoUASimpleAttributeOperand.Create;
    Operand.TypeId.NodeId := TypeId;
    Operand.QualifiedNames := BrowsePathParser.ParseRelative(SimpleRelativeBrowsePathString).ToUAQualifiedNameCollection;
    UAFilterElements_SimpleAttribute := Operand;
  end;

  function UABaseEventObject_Operands_NodeId: UASimpleAttributeOperand;
  var
    Operand: UASimpleAttributeOperand;
  begin
    Operand := CoUASimpleAttributeOperand.Create;
    Operand.TypeId.NodeId.StandardName := 'BaseEventType';
    Operand.AttributeId := UAAttributeId_NodeId;
    UABaseEventObject_Operands_NodeId := Operand;
  end;

  function UABaseEventObject_Operands_EventId: UASimpleAttributeOperand;
  begin
    UABaseEventObject_Operands_EventId := UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType, '/EventId');
  end;

  function UABaseEventObject_Operands_EventType: UASimpleAttributeOperand;
  begin
    UABaseEventObject_Operands_EventType := UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType, '/EventType');
  end;

  function UABaseEventObject_Operands_SourceNode: UASimpleAttributeOperand;
  begin
    UABaseEventObject_Operands_SourceNode := UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType, '/SourceNode');
  end;

  function UABaseEventObject_Operands_SourceName: UASimpleAttributeOperand;
  begin
    UABaseEventObject_Operands_SourceName := UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType, '/SourceName');
  end;

  function UABaseEventObject_Operands_Time: UASimpleAttributeOperand;
  begin
    UABaseEventObject_Operands_Time := UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType, '/Time');
  end;

  function UABaseEventObject_Operands_ReceiveTime: UASimpleAttributeOperand;
  begin
    UABaseEventObject_Operands_ReceiveTime := UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType, '/ReceiveTime');
  end;

  function UABaseEventObject_Operands_LocalTime: UASimpleAttributeOperand;
  begin
    UABaseEventObject_Operands_LocalTime := UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType, '/LocalTime');
  end;

  function UABaseEventObject_Operands_Message: UASimpleAttributeOperand;
  begin
    UABaseEventObject_Operands_Message := UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType, '/Message');
  end;

  function UABaseEventObject_Operands_Severity: UASimpleAttributeOperand;
  begin
    UABaseEventObject_Operands_Severity := UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType, '/Severity');
  end;

  function UABaseEventObject_AllFields: UAAttributeFieldCollection;
  var
    Fields: UAAttributeFieldCollection;
  begin
    Fields := CoUAAttributeFieldCollection.Create;

    Fields.Add(ToUAAttributeField(UABaseEventObject_Operands_NodeId));

    Fields.Add(ToUAAttributeField(UABaseEventObject_Operands_EventId));
    Fields.Add(ToUAAttributeField(UABaseEventObject_Operands_EventType));
    Fields.Add(ToUAAttributeField(UABaseEventObject_Operands_SourceNode));
    Fields.Add(ToUAAttributeField(UABaseEventObject_Operands_SourceName));
    Fields.Add(ToUAAttributeField(UABaseEventObject_Operands_Time));
    Fields.Add(ToUAAttributeField(UABaseEventObject_Operands_ReceiveTime));
    Fields.Add(ToUAAttributeField(UABaseEventObject_Operands_LocalTime));
    Fields.Add(ToUAAttributeField(UABaseEventObject_Operands_Message));
    Fields.Add(ToUAAttributeField(UABaseEventObject_Operands_Severity));

    UABaseEventObject_AllFields := Fields;
  end;

var
  Arguments: OleVariant;
  EvsClient: TEvsEasyUAClient;
  Client: EasyUAClient;
  ClientEventHandlers: TClientEventHandlers3;
  Handle: Cardinal;
  HandleArray: OleVariant;
  MonitoredItemArguments: EasyUAMonitoredItemArguments;
  MonitoringParameters: UAMonitoringParameters;
  EventFilter: UAEventFilter;
  WhereClause: UAContentFilterElement;
  Operand1: UASimpleAttributeOperand;
  Operand2: UALiteralOperand;
  Operand3: UASimpleAttributeOperand;
  Operand4: UALiteralOperand;
  SourceNodeId: UANodeId;
  Element1, Element2: UAContentFilterElement;
  BaseEventType: UANodeId;
begin
  // Instantiate the client object and hook events
  EvsClient := TEvsEasyUAClient.Create(nil);
  Client := EvsClient.ComServer;
  ClientEventHandlers := TClientEventHandlers3.Create;
  EvsClient.OnEventNotification := @ClientEventHandlers.OnEventNotification;

  WriteLn('Subscribing...');

  WhereClause := CoUAContentFilterElement.Create;
  BaseEventType := CoUaNodeId.Create;
  BaseEventType.StandardName := 'BaseEventType';

  // Either the severity is >= 500, or the event comes from a specified source node
  Operand1 := UABaseEventObject_Operands_Severity;
  Operand2 := CoUALiteralOperand.Create;
  Operand2.Value := 500;
  Element1 := CoUAContentFilterElement.Create;
  Element1.FilterOperator := UAFilterOperator_GreaterThanOrEqual;
  Element1.FilterOperands.Add(Operand1);
  Element1.FilterOperands.Add(Operand2);
  Operand3 := UABaseEventObject_Operands_SourceNode;
  SourceNodeId := CoUANodeId.Create;
  SourceNodeId.ExpandedText := 'nsu=http://opcfoundation.org/Quickstarts/AlarmCondition;ns=2;s=1:Metals/SouthMotor';
  Operand4 := CoUALiteralOperand.Create;
  Operand4.Value := SourceNodeId;
  Element2 := CoUAContentFilterElement.Create;
  Element2.FilterOperator := UAFilterOperator_Equals;
  Element2.FilterOperands.Add(Operand3);
  Element2.FilterOperands.Add(Operand4);
  WhereClause.FilterOperator := UAFilterOperator_Or;
  WhereClause.FilterOperands.Add(Element1);
  WhereClause.FilterOperands.Add(Element2);

  EventFilter := CoUAEventFilter.Create;
  EventFilter.SelectClauses := UABaseEventObject_AllFields;
  EventFilter.WhereClause := WhereClause;

  MonitoringParameters := CoUAMonitoringParameters.Create;
  MonitoringParameters.SamplingInterval := 1000;
  MonitoringParameters.EventFilter := EventFilter;
  MonitoringParameters.QueueSize := 1000;

  MonitoredItemArguments := CoEasyUAMonitoredItemArguments.Create;
  MonitoredItemArguments.EndpointDescriptor.UrlString := 'opc.tcp://opcua.demo-this.com:62544/Quickstarts/AlarmConditionServer';
  MonitoredItemArguments.NodeDescriptor.NodeId.StandardName := 'Server';
  MonitoredItemArguments.MonitoringParameters := MonitoringParameters;
  //MonitoredItemArguments.SubscriptionParameters.PublishingInterval := 0;
  MonitoredItemArguments.AttributeId := UAAttributeId_EventNotifier;

  Arguments := VarArrayCreate([0, 0], varVariant);
  Arguments[0] := MonitoredItemArguments;

  TVarData(HandleArray).VType := varArray or varVariant;
  TVarData(HandleArray).VArray := PVarArray(
    Client.SubscribeMultipleMonitoredItems(PSafeArray(TVarData(Arguments).VArray)));

  WriteLn('Processing event notifications for 30 seconds...');
  PumpSleep(30*1000);

  WriteLn('Unsubscribing...');
  Client.UnsubscribeAllMonitoredItems;

  WriteLn('Waiting for 5 seconds...');
  PumpSleep(5*1000);

  WriteLn('Finished...');
end;
// This example shows how to specify criteria for event notifications.
//
// Find all latest examples here: https://opclabs.doc-that.com/files/onlinedocs/OPCLabs-OpcStudio/Latest/examples.html .
// OPC client and subscriber examples in Object Pascal (Delphi) on GitHub: https://github.com/OPCLabs/Examples-QuickOPC-OP .
// Missing some example? Ask us for it on our Online Forums, https://www.opclabs.com/forum/index ! You do not have to own
// a commercial license in order to use Online Forums, and we reply to every post.

type
  THelperMethods10 = class
    class function ObjectTypeIds_BaseEventType: _UANodeId; static;
    class function UABaseEventObject_Operands_EventId: _UASimpleAttributeOperand; static;
    class function UABaseEventObject_Operands_EventType: _UASimpleAttributeOperand; static;
    class function UABaseEventObject_Operands_NodeId: _UASimpleAttributeOperand; static;
    class function UAFilterElements_SimpleAttribute(TypeId: _UANodeId; simpleRelativeBrowsePathString: string): _UASimpleAttributeOperand; static;
    class function UABaseEventObject_Operands_SourceName: _UASimpleAttributeOperand; static;
    class function UABaseEventObject_Operands_Time: _UASimpleAttributeOperand; static;
    class function UABaseEventObject_Operands_ReceiveTime: _UASimpleAttributeOperand; static;
    class function UABaseEventObject_Operands_LocalTime: _UASimpleAttributeOperand;
    class function UABaseEventObject_Operands_SourceNode: _UASimpleAttributeOperand; static;
    class function UABaseEventObject_Operands_Message: _UASimpleAttributeOperand; static;
    class function UABaseEventObject_Operands_Severity: _UASimpleAttributeOperand; static;
    class function UABaseEventObject_AllFields: _UAAttributeFieldCollection; static;
  end;

type
  TClientEventHandlers10 = class
    procedure Client_EventNotification(
      ASender: TObject;
      sender: OleVariant;
      const eventArgs: _EasyUAEventNotificationEventArgs);
  end;

procedure TClientEventHandlers10.Client_EventNotification(
  ASender: TObject;
  sender: OleVariant;
  const eventArgs: _EasyUAEventNotificationEventArgs);
begin
  // Display the event
  WriteLn(eventArgs.ToString);
end;

class procedure WhereClause.Main;
const
  UAObjectIds_Server = 'nsu=http://opcfoundation.org/UA/;i=2253';
var
  Arguments: OleVariant;
  Client: TEasyUAClient;
  ClientEventHandlers: TClientEventHandlers10;
  Element1, Element2: _UAContentFilterElement;
  EndpointDescriptor: string;
  EventFilter: _UAEventFilter;
  MonitoredItemArguments: _EasyUAMonitoredItemArguments;
  MonitoringParameters: _UAMonitoringParameters;
  Operand1, Operand3: _UASimpleAttributeOperand;
  Operand2, Operand4: _UALiteralOperand;
  SourceNodeId: _UANodeId;
  WhereClause: _UAContentFilterElement;
begin
  EndpointDescriptor := 'opc.tcp://opcua.demo-this.com:62544/Quickstarts/AlarmConditionServer';

  // Instantiate the client object and hook events
  Client := TEasyUAClient.Create(nil);
  ClientEventHandlers := TClientEventHandlers10.Create;
  Client.OnEventNotification := ClientEventHandlers.Client_EventNotification;

  WriteLn('Subscribing...');

  WhereClause := CoUAContentFilterElement.Create;

  // Either the severity is >= 500, or the event comes from a specified source node
  Operand1 := THelperMethods10.UABaseEventObject_Operands_Severity;
  Operand2 := CoUALiteralOperand.Create;
  Operand2.Value := 500;
  Element1 := CoUAContentFilterElement.Create;
  Element1.FilterOperator := UAFilterOperator_GreaterThanOrEqual;
  Element1.FilterOperands.Add(Operand1);
  Element1.FilterOperands.Add(Operand2);
  Operand3 := THelperMethods10.UABaseEventObject_Operands_SourceNode;
  SourceNodeId := CoUANodeId.Create;
  SourceNodeId.ExpandedText := 'nsu=http://opcfoundation.org/Quickstarts/AlarmCondition;ns=2;s=1:Metals/SouthMotor';
  Operand4 := CoUALiteralOperand.Create;
  Operand4.Value := SourceNodeId;
  Element2 := CoUAContentFilterElement.Create;
  Element2.FilterOperator := UAFilterOperator_Equals;
  Element2.FilterOperands.Add(Operand3);
  Element2.FilterOperands.Add(Operand4);
  WhereClause.FilterOperator := UAFilterOperator_Or;
  WhereClause.FilterOperands.Add(Element1);
  WhereClause.FilterOperands.Add(Element2);

  EventFilter := CoUAEventFilter.Create;
  EventFilter.SelectClauses := THelperMethods10.UABaseEventObject_AllFields;
  EventFilter.WhereClause := WhereClause;

  MonitoringParameters := CoUAMonitoringParameters.Create;
  MonitoringParameters.SamplingInterval := 1000;
  MonitoringParameters.EventFilter := EventFilter;
  MonitoringParameters.QueueSize := 1000;

  MonitoredItemArguments := CoEasyUAMonitoredItemArguments.Create;
  MonitoredItemArguments.EndpointDescriptor.UrlString := 'opc.tcp://opcua.demo-this.com:62544/Quickstarts/AlarmConditionServer';
  MonitoredItemArguments.NodeDescriptor.NodeId.StandardName := 'Server';
  MonitoredItemArguments.MonitoringParameters := MonitoringParameters;
  //MonitoredItemArguments.SubscriptionParameters.PublishingInterval := 0;
  MonitoredItemArguments.AttributeId := UAAttributeId_EventNotifier;

  Arguments := VarArrayCreate([0, 0], varVariant);
  Arguments[0] := MonitoredItemArguments;

  Client.SubscribeMultipleMonitoredItems(Arguments);

  WriteLn('Processing event notifications for 30 seconds...');
  PumpSleep(30*1000);

  WriteLn('Unsubscribing...');
  Client.UnsubscribeAllMonitoredItems;

  WriteLn('Waiting for 5 seconds...');
  Sleep(5*1000);

  WriteLn('Finished.');
  VarClear(Arguments);
  FreeAndNil(Client);
  FreeAndNil(ClientEventHandlers);
end;


class function THelperMethods10.ObjectTypeIds_BaseEventType: _UANodeId;
  var NodeId: _UANodeId;
  begin
    NodeId := CoUANodeId.Create;
    NodeId.StandardName := 'BaseEventType';
    Result := NodeId;
  end;

class function THelperMethods10.UAFilterElements_SimpleAttribute(TypeId: _UANodeId; simpleRelativeBrowsePathString: string): _UASimpleAttributeOperand;
var
  BrowsePathParser: _UABrowsePathParser;
  Operand: _UASimpleAttributeOperand;
begin
  BrowsePathParser := CoUABrowsePathParser.Create;
  Operand := CoUASimpleAttributeOperand.Create;
  Operand.TypeId.NodeId := TypeId;
  Operand.QualifiedNames := BrowsePathParser.ParseRelative(simpleRelativeBrowsePathString).ToUAQualifiedNameCollection;
  Result := Operand;
end;

class function THelperMethods10.UABaseEventObject_Operands_EventId: _UASimpleAttributeOperand;
begin
  Result := UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType, '/EventId');
end;

class function THelperMethods10.UABaseEventObject_Operands_EventType: _UASimpleAttributeOperand;
begin
  Result := UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType, '/EventType');
end;

class function THelperMethods10.UABaseEventObject_Operands_NodeId: _UASimpleAttributeOperand;
var
  Operand: _UASimpleAttributeOperand;
begin
  Operand := CoUASimpleAttributeOperand.Create;
  Operand.TypeId.NodeId.StandardName := 'BaseEventType';
  Operand.AttributeId := UAAttributeId_NodeId;
  Result := Operand;
end;

class function THelperMethods10.UABaseEventObject_Operands_SourceNode: _UASimpleAttributeOperand;
begin
  Result := UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType, '/SourceNode');
end;

class function THelperMethods10.UABaseEventObject_Operands_SourceName: _UASimpleAttributeOperand;
begin
  Result := UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType, '/SourceName');
end;

class function THelperMethods10.UABaseEventObject_Operands_Time: _UASimpleAttributeOperand;
begin
  Result := UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType, '/Time');
end;

class function THelperMethods10.UABaseEventObject_Operands_ReceiveTime: _UASimpleAttributeOperand;
begin
  Result := UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType, '/ReceiveTime');
end;

class function THelperMethods10.UABaseEventObject_Operands_LocalTime: _UASimpleAttributeOperand;
begin
  Result := UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType, '/LocalTime');
end;

class function THelperMethods10.UABaseEventObject_Operands_Message: _UASimpleAttributeOperand;
begin
  Result := UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType, '/Message');
end;

class function THelperMethods10.UABaseEventObject_Operands_Severity: _UASimpleAttributeOperand;
begin
  Result := UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType, '/Severity');
end;

class function THelperMethods10.UABaseEventObject_AllFields: _UAAttributeFieldCollection;
var
  Fields: _UAAttributeFieldCollection;
begin
  Fields := CoUAAttributeFieldCollection.Create;
  Fields.Add(UABaseEventObject_Operands_NodeId.ToUAAttributeField);
  Fields.Add(UABaseEventObject_Operands_EventId.ToUAAttributeField);
  Fields.Add(UABaseEventObject_Operands_EventType.ToUAAttributeField);
  Fields.Add(UABaseEventObject_Operands_SourceNode.ToUAAttributeField);
  Fields.Add(UABaseEventObject_Operands_SourceName.ToUAAttributeField);
  Fields.Add(UABaseEventObject_Operands_Time.ToUAAttributeField);
  Fields.Add(UABaseEventObject_Operands_ReceiveTime.ToUAAttributeField);
  Fields.Add(UABaseEventObject_Operands_LocalTime.ToUAAttributeField);
  Fields.Add(UABaseEventObject_Operands_Message.ToUAAttributeField);
  Fields.Add(UABaseEventObject_Operands_Severity.ToUAAttributeField);

  Result := Fields;
end;
// This example shows how to specify criteria for event notifications.
//
// Find all latest examples here: https://opclabs.doc-that.com/files/onlinedocs/OPCLabs-OpcStudio/Latest/examples.html .
// OPC client and subscriber examples in PHP on GitHub: https://github.com/OPCLabs/Examples-QuickOPC-PHP .
// Missing some example? Ask us for it on our Online Forums, https://www.opclabs.com/forum/index ! You do not have to own
// a commercial license in order to use Online Forums, and we reply to every post.

const UAAttributeId_NodeId = 1;
const UAAttributeId_EventNotifier = 12;

const UAFilterOperator_Equals = 1;
const UAFilterOperator_GreaterThanOrEqual = 5;
const UAFilterOperator_Or = 12;

const UAObjectIds_Server = 'nsu=http://opcfoundation.org/UA/;i=2253';

class ClientEvents {
    function EventNotification($Sender, $E)
    {
        // Display the event
        printf("%s\n", $E);
    }
}

$EndpointDescriptor = "opc.tcp://opcua.demo-this.com:62544/Quickstarts/AlarmConditionServer";

// Instantiate the client object and hook events
$Client = new COM("OpcLabs.EasyOpc.UA.EasyUAClient");
$ClientEvents = new ClientEvents();
com_event_sink($Client, $ClientEvents, "DEasyUAClientEvents");

$WhereClause = new COM("OpcLabs.EasyOpc.UA.Filtering.UAContentFilterElement");

// Either the severity is >= 500, or the event comes from a specified source node
$Operand1 = UABaseEventObject_Operands_Severity();
$Operand2 = new COM("OpcLabs.EasyOpc.UA.Filtering.UALiteralOperand");
$Operand2->Value = 500;
$Element1 = new COM("OpcLabs.EasyOpc.UA.Filtering.UAContentFilterElement");
$Element1->FilterOperator = UAFilterOperator_GreaterThanOrEqual;
$Element1->FilterOperands->Add($Operand1);
$Element1->FilterOperands->Add($Operand2);
$Operand3 = UABaseEventObject_Operands_SourceNode();
$SourceNodeId = new COM("OpcLabs.EasyOpc.UA.AddressSpace.UANodeId");
$SourceNodeId->ExpandedText = "nsu=http://opcfoundation.org/Quickstarts/AlarmCondition;ns=2;s=1:Metals/SouthMotor";
$Operand4 = new COM("OpcLabs.EasyOpc.UA.Filtering.UALiteralOperand");
$Operand4->Value = $SourceNodeId;
$Element2 = new COM("OpcLabs.EasyOpc.UA.Filtering.UAContentFilterElement");
$Element2->FilterOperator = UAFilterOperator_Equals;
$Element2->FilterOperands->Add($Operand3);
$Element2->FilterOperands->Add($Operand4);
$WhereClause->FilterOperator = UAFilterOperator_Or;
$WhereClause->FilterOperands->Add($Element1);
$WhereClause->FilterOperands->Add($Element2);

$EventFilter = new COM("OpcLabs.EasyOpc.UA.UAEventFilter");
$EventFilter->SelectClauses = UABaseEventObject_AllFields();
$EventFilter->WhereClause = $WhereClause;

$MonitoringParameters = new COM("OpcLabs.EasyOpc.UA.UAMonitoringParameters");
$MonitoringParameters->SamplingInterval = 1000;
$MonitoringParameters->EventFilter = $EventFilter;
$MonitoringParameters->QueueSize = 1000;

$MonitoredItemArguments = new COM("OpcLabs.EasyOpc.UA.OperationModel.EasyUAMonitoredItemArguments");
$MonitoredItemArguments->EndpointDescriptor->UrlString = $EndpointDescriptor;
$MonitoredItemArguments->NodeDescriptor->NodeId->StandardName = "Server";
$MonitoredItemArguments->MonitoringParameters = $MonitoringParameters;
$MonitoredItemArguments->SubscriptionParameters->PublishingInterval = 0;
$MonitoredItemArguments->AttributeId = UAAttributeId_EventNotifier;

$arguments[0] = $MonitoredItemArguments;

printf("Subscribing...\n");
$Client->SubscribeMultipleMonitoredItems($arguments);

printf("Processing monitored item changed events for 30 seconds...\n");
$startTime = time(); do { com_message_pump(1000); } while (time() < $startTime + 30);

printf("Unsubscribing...\n");
$Client->UnsubscribeAllMonitoredItems;

printf("Waiting for 5 seconds...\n");
$startTime = time(); do { com_message_pump(1000); } while (time() < $startTime + 5);


function ObjectTypeIds_BaseEventType() {
    $NodeId = new COM("OpcLabs.EasyOpc.UA.AddressSpace.UANodeId");
    $NodeId->StandardName = "BaseEventType";
    return $NodeId;
}

function UAFilterElements_SimpleAttribute($TypeId, $simpleRelativeBrowsePathString) {
  $BrowsePathParser = new COM("OpcLabs.EasyOpc.UA.Navigation.Parsing.UABrowsePathParser");
  $Operand = new COM("OpcLabs.EasyOpc.UA.Filtering.UASimpleAttributeOperand");
  $Operand->TypeId->NodeId = $TypeId;
  $Operand->QualifiedNames = $BrowsePathParser->ParseRelative($simpleRelativeBrowsePathString)->ToUAQualifiedNameCollection;
  return $Operand;
}

function UABaseEventObject_Operands_NodeId() {
    $Operand = new COM("OpcLabs.EasyOpc.UA.Filtering.UASimpleAttributeOperand");
    $Operand->TypeId->NodeId->StandardName = "BaseEventType";
    $Operand->AttributeId = UAAttributeId_NodeId;
    return $Operand;
}

function UABaseEventObject_Operands_EventId() {
  return UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType(), "/EventId");
}

function UABaseEventObject_Operands_EventType() {
  return UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType(), "/EventType");
}

function UABaseEventObject_Operands_SourceNode() {
  return UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType(), "/SourceNode");
}

function UABaseEventObject_Operands_SourceName() {
  return UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType(), "/SourceName");
}

function UABaseEventObject_Operands_Time() {
  return UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType(), "/Time");
}

function UABaseEventObject_Operands_ReceiveTime() {
  return UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType(), "/ReceiveTime");
}

function UABaseEventObject_Operands_LocalTime() {
  return UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType(), "/LocalTime");
}

function UABaseEventObject_Operands_Message() {
  return UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType(), "/Message");
}

function UABaseEventObject_Operands_Severity() {
  return UAFilterElements_SimpleAttribute(ObjectTypeIds_BaseEventType(), "/Severity");
}

function UABaseEventObject_AllFields() {
    $Fields = new COM("OpcLabs.EasyOpc.UA.UAAttributeFieldCollection");
    $Fields->Add(UABaseEventObject_Operands_NodeId()->ToUAAttributeField);
    $Fields->Add(UABaseEventObject_Operands_EventId()->ToUAAttributeField);
    $Fields->Add(UABaseEventObject_Operands_EventType()->ToUAAttributeField);
    $Fields->Add(UABaseEventObject_Operands_SourceNode()->ToUAAttributeField);
    $Fields->Add(UABaseEventObject_Operands_SourceName()->ToUAAttributeField);
    $Fields->Add(UABaseEventObject_Operands_Time()->ToUAAttributeField);
    $Fields->Add(UABaseEventObject_Operands_ReceiveTime()->ToUAAttributeField);
    $Fields->Add(UABaseEventObject_Operands_LocalTime()->ToUAAttributeField);
    $Fields->Add(UABaseEventObject_Operands_Message()->ToUAAttributeField);
    $Fields->Add(UABaseEventObject_Operands_Severity()->ToUAAttributeField);

    return $Fields;
}
# This example shows how to specify criteria for event notifications.
#
# Find all latest examples here: https://opclabs.doc-that.com/files/onlinedocs/OPCLabs-OpcStudio/Latest/examples.html .
# OPC client and subscriber examples in Python on GitHub: https://github.com/OPCLabs/Examples-QuickOPC-Python .
# Missing some example? Ask us for it on our Online Forums, https://www.opclabs.com/forum/index ! You do not have to own
# a commercial license in order to use Online Forums, and we reply to every post.
# The QuickOPC package is needed. Install it using "pip install opclabs_quickopc".
import opclabs_quickopc
import time

# Import .NET namespaces.
from OpcLabs.EasyOpc.UA import *
from OpcLabs.EasyOpc.UA.AddressSpace import *
from OpcLabs.EasyOpc.UA.AddressSpace.Standard import *
from OpcLabs.EasyOpc.UA.AlarmsAndConditions import *
from OpcLabs.EasyOpc.UA.Filtering import *
from OpcLabs.EasyOpc.UA.OperationModel import *


def eventNotification(sender, eventArgs):
    # Display the event.
    print(eventArgs)


# Define which server we will work with.
endpointDescriptor = UAEndpointDescriptor('opc.tcp://opcua.demo-this.com:62544/Quickstarts/AlarmConditionServer')

# Instantiate the client object and hook events.
client = EasyUAClient()
client.EventNotification += eventNotification

print('Subscribing...')

eventFilterBuilder = UAEventFilterBuilder(
    # Either the severity is >= 500, or the event comes from a specified source node.
    UAFilterElements.Or(
        UAFilterElements.GreaterThanOrEqual(UABaseEventObject.Operands.Severity, 500),
        UAFilterElements.Equals(
            UABaseEventObject.Operands.SourceNode,
            UANodeId('nsu=http://opcfoundation.org/Quickstarts/AlarmCondition ;ns=2;s=1:Metals/SouthMotor'))),
    UABaseEventObject.AllFields)

IEasyUAClientExtension.SubscribeEvent(
    client,
    endpointDescriptor,
    UANodeDescriptor(UAObjectIds.Server),
    1000,
    UAEventFilterBuilder.ToUAEventFilter(eventFilterBuilder))

print('Processing event notifications for 30 seconds...')
time.sleep(30)

print('Unsubscribing...')
client.UnsubscribeAllMonitoredItems()

print('Waiting for 5 seconds...')
time.sleep(5)

print('Finished.')
Requirements

Target Platforms: .NET Framework: Windows 10 (selected versions), Windows 11 (selected versions), Windows Server 2016, Windows Server 2022; .NET: Linux, macOS, Microsoft Windows

See Also