Subscribe to Platform Events

Learning Objectives

After completing this unit, you’ll be able to:
  • Describe how to subscribe to platform event messages.
  • Use an Apex trigger to subscribe to an event.
  • Test platform events in an Apex test method.
  • Subscribe to platform events via CometD.

Subscribe to Platform Events

Now that you’ve seen how to publish platform events, how do you subscribe to them to be notified of the latest news or of the shipment of a package? On the Salesforce Platform, Apex triggers, processes, and flows receive event notifications. Visualforce and Lightning component apps receive events through CometD. In an external app, you subscribe to events using CometD as well.

Subscribe to Platform Event Notifications with Apex Triggers

You’ve probably used Apex triggers before, to perform actions based on database events. With platform events, the process is similar. You simply write an after insert Apex trigger on the event object to subscribe to incoming events. Triggers provide an autosubscription mechanism in Apex. No need to explicitly create and listen to a channel. Triggers receive event notifications from various sources—whether they’re published through Apex or APIs.

Platform events support only after insert triggers. The after insert trigger event corresponds to the time after a platform event is published. After an event message is published, the after insert trigger is fired.

To create a platform event trigger, use the Developer Console.

  1. Click the Setup icon, select Developer Console, and click File | New | Apex Trigger.
  2. Provide a name and choose your event for the sObject, and click Submit.

The Developer Console automatically adds the after insert event in the trigger template. Also, you can conveniently create a trigger from the event’s definition page in Setup, in the Triggers related list, but you have to specify the after insert keyword.

The following example shows a trigger for the Cloud News event. It iterates through each event and checks whether the news is urgent through the Urgent__c field. If the news is urgent, the trigger creates a case to dispatch a news reporter and adds the event location to the case subject.

// Trigger for listening to Cloud_News events.
trigger CloudNewsTrigger on Cloud_News__e (after insert) {    
    // List to hold all cases to be created.
    List<Case> cases = new List<Case>();
    
    // Get queue Id for case owner
    Group queue = [SELECT Id FROM Group WHERE Name='Regional Dispatch' LIMIT 1];
       
    // Iterate through each notification.
    for (Cloud_News__e event : Trigger.New) {
        if (event.Urgent__c == true) {
            // Create Case to dispatch new team.
            Case cs = new Case();
            cs.Priority = 'High';
            cs.Subject = 'News team dispatch to ' + 
                event.Location__c;
            cs.OwnerId = queue.Id;
            cases.add(cs);
        }
   }
    
    // Insert all cases corresponding to events received.
    insert cases;
}

Set Up Debug Logging

Unlike triggers on standard or custom objects, triggers on platform events don’t execute in the same Apex transaction as the one that published the event. The trigger runs in its own process under the Automated Process entity, which is a system user. As a result, debug logs corresponding to the trigger execution are created by the Automated Process entity and aren’t available in the Developer Console. To collect platform event trigger logs, add a trace flag entry for the Automated Process entity in Setup.

  1. From Setup, enter Debug Logs in the Quick Find box, then click Debug Logs.
  2. Click New.
  3. For Traced Entity Type, select Automated Process.
  4. Select the start date and expiration date for the logs you want to collect.
  5. For Debug Level, enter * and click Search.
  6. Select a predefined debug level, such as SFDC_DevConsole or click New to create your own debug level.
  7. Click Save.
Note

Note

Debug logs for Apex tests are an exception. They include logging for event triggers in the same test execution log.

Things to Note About Platform Event Triggers

Order of Event Processing
A trigger processes platform event notifications sequentially in the order they’re received. The order of events is based on the event replay ID. An Apex trigger can receive a batch of events at once. The order of events is preserved within each batch. The events in a batch can originate from one or more publishers.
Asynchronous Trigger Execution
A platform event trigger runs in its own process asynchronously and isn’t part of the transaction that published the event. As a result, there might be a delay between when an event is published and when the trigger processes the event. Don't expect the result of the trigger’s execution to be available immediately after event publishing.
Automated Process System User
Because platform event triggers don’t run under the user who executes them (the running user) but under the Automated Process system user, we set the owner ID field explicitly in our CloudNewsTrigger example. We used the ID of a sample user queue called Regional Dispatch for the trigger example. If you create a Salesforce record with an OwnerId field in the trigger, such as a case or opportunity, explicitly set the owner ID. For cases and leads, you can, alternatively, use assignment rules to set the owner.
Also, system fields, such as CreatedById and LastModifiedById, reference the Automated Process entity and not the running user.
Apex Governor Limits
Like standard or custom object triggers, platform event triggers are subject to Apex governor limits.
Apex Trigger Limitations
Platform event triggers share many of the same limitations of custom and standard object triggers. For example, you can’t make Apex callouts synchronously from triggers.

Subscriptions Related List on the Event Definition Page

You can view the state of all event triggers on the Platform Event Definition Detail page in Setup. CometD subscribers aren’t included in this list. Under Subscriptions, each active trigger is listed along with execution information and the state. Information includes the replay ID of the last published and last processed events. The state indicates whether the trigger is running or is disconnected from the subscription because of unrecoverable errors or insufficient permissions. The Error state is reached only when a trigger has been retried the maximum number of times. The following screenshot shows the Subscriptions related list on the Cloud News event detail page.

Subscriptions related list shows the state of subscribed triggers

Test Platform Event Triggers

Ensure that your platform event trigger is working properly by adding an Apex test. Before you can package or deploy any Apex code (including triggers) to production, your Apex code must have tests. To publish platform events in an Apex test, enclose the publish statements within Test.startTest and Test.stopTest statements.

// Create test events
Test.startTest();
// Publish events
Test.stopTest();
// Perform validation here

In a test context, the publish method call queues up the publish operation. The Test.stopTest() statement causes the event publishing to be carried out. After Test.stopTest(), perform your validations.

Here is an example of a test class for our Cloud_News event and its associated trigger. Publishing the event causes the associated trigger to fire. After Test.stopTest(), the test verifies that the publishing was successful by inspecting the value returned by isSuccess() in Database.SaveResult. Also, the test queries the case that the trigger created. If the case record is found, the trigger executed successfully, and the test passes.

@isTest
public class PlatformEventTest {
    @isTest static void test1() {
        // Create test event instance
        Cloud_News__e newsEvent = new Cloud_News__e(
            Location__c='Mountain City', 
            Urgent__c=true, 
            News_Content__c='Test message.');
        
        Test.startTest();

        // Call method to publish events
        Database.SaveResult sr = EventBus.publish(newsEvent);
        
        Test.stopTest();
        
        // Perform validation here

        // Verify that the publish was successful
        System.assertEquals(true, sr.isSuccess());

        // Check that the case that the trigger created is present.
        List<Case> cases = [SELECT Id FROM Case];
        // Validate that this case was found.
        // There is only one test case in test context.
        System.assertEquals(1, cases.size());
    }
}

Subscribe to Platform Event Notifications Using Clicks

To subscribe to event messages without code, create a process that starts when a platform event occurs.

This screenshot shows that a process starts when a Cloud News event occurs. When it starts, the process looks for a contact record whose mailing city matches the event notification’s location.

Process Builder matching criteria screen

Similarly, you can subscribe to a platform event message with a flow by using a Wait element. Instead of starting a flow when a platform event occurs, a flow that was started previously waits for a platform event and then resumes. For example, here’s a Wait element that waits for a Cloud News event message to occur. It only resumes if the event’s location matches {!MailingCity_Location.MailingCity}. {!MailingCity_Location} is an sObject variable in the flow.

Cloud Flow Designer Wait element

Subscribe to Platform Event Notifications with CometD

External apps subscribe to platform events with CometD and perform long polling. Platform apps, such as Visualforce pages and Lightning components, can use CometD as well. CometD is a scalable HTTP-based event routing bus that uses an AJAX push technology pattern known as Comet. It implements the Bayeux protocol. Long polling, also called Comet programming, allows emulation of an information push from a server to a client. Similar to a normal poll, the client connects and requests information from the server. However, instead of sending an empty response if information isn't available, the server holds the request and waits until information is available (an event occurs).

Salesforce provides a Java library, EMP Connector, which implements all the details of connecting to CometD and listening on a channel. You can use EMP Connector to subscribe easily to platform events. EMP Connector hides the complexity of subscribing to events. For more information about EMP Connector, check out the Java client example in the Streaming API Developer Guide.

The process of subscribing to platform event notifications through CometD is similar to subscribing to PushTopic events or generic events. The only difference is the channel name. Here is the format of the platform event topic (channel) name:

/event/<EventName>__e

For example, if you have a platform event named Cloud News, provide this channel name when subscribing.

/event/Cloud_News__e

Specify the API version at the end of the CometD URL, as follows.

// Connect to the CometD endpoint
    cometd.configure({
               url: 'https://<Salesforce_URL>/cometd/43.0/',
               requestHeaders: { Authorization: 'OAuth <Session_ID>'}
    });

Platform Event Message in JSON Format

The message of a delivered platform event looks similar to the following example for a Cloud News event.

{
  "data": {
    "schema": "_2DBiqh-utQNAjUH78FdbQ", 
    "payload": {
      "CreatedDate": "2017-04-27T16:50:40Z", 
      "CreatedById": "005D0000001cSZs", 
      "Location__c": "San Francisco", 
      "Urgent__c": true, 
      "News_Content__c": "Large highway is closed due to asteroid collision."
    }, 
    "event": {
      "replayId": 2
    }
  }, 
  "channel": "/event/Cloud_News__e"
}

The schema field in the event message contains the ID of the platform event schema (in this example, it is "schema": "_2DBiqh-utQNAjUH78FdbQ"). The schema is versioned—when the schema changes, the schema ID changes as well.

To determine if the schema of an event has changed, retrieve the schema through REST API. Use the schema ID by performing a GET request to this REST API resource: /vXX.X/event/eventSchema/Schema_ID. Alternatively, you can retrieve the event schema by supplying the event name to this endpoint: /vXX.X/sobjects/Platform_Event_Name__e/eventSchema. For more information, see the REST API Developer Guide.

Note

Note

Unlike PushTopic and generic events, platform events don’t support using filtered subscriptions. For example, subscribing to /event/Cloud_News__e?Location__c='San Francisco' to filter by location isn’t supported.

Now that you’ve seen how to use Platform Events on the Salesforce platform and in external apps, the possibilities are endless! Use Platform Events for any number of applications and integrations, such as processing business transactions or engaging in proactive customer service. With Platform Events, you adopt an event-based programming model and enjoy the benefits of event-based software architecture.

retargeting