# Event Stream

Opens an event stream to your filter specifications.


## Open an event stream {#openeventstream}

Opens a new event stream according to your request filters. Unlike our other APIs, a request to /api/events/ returns a stream of data, where each line is a JSON object. The response body contains all the events in that stream. Since streams by definition go on forever, Real-Time Data Streaming will never end the response without some external reason.


[Jump to examples ↓](#openeventstream-examples)

### `POST /api/events`

{{< note >}}
In the request specification, JSON collection types have semantic meaning.

**array**: Arrays indicate a boolean `"OR"`. Wherever an array appears in the specification, the resulting stream will contain the events passing any of the conditions defined by the array. An empty array results in a `400` response.

**object**: Object attributes indicate a boolean `"AND"`. All conditions in the object must be satisfied in order for an event to be written to the response. If you would like all events to pass the condition the attribute defines, omit the attribute. If an unexpected attribute appears on an event, a status code `400` response will be returned.

{{< /note >}}

{{< important >}}
Airship will occasionally add:

* New properties to existing objects.

* New event types, which will be JSON objects with new values for the type field.

Your integration must be tolerant of these kinds of changes.

{{< /important >}}

**Security:**

- [bearerAuth]({{< ref "/developer/rest-api/connect/introduction/" >}}#security-bearerAuth)

**Request headers:**

| Name | Type | Required | Description |
|------|------|----------|-------------|
| `X-UA-Appkey` | `string` | Required | The App Key for the project you want to return events for. |

**Request body**

**Content-Type:** `application/json`

[Events request]({{< ref "/developer/rest-api/connect/schemas/others/" >}}#eventsrequest)

**Responses**

**`200`** The response to a successful request is an unending stream of [newline-delimited JSON](https://github.com/ndjson/ndjson-spec). Each non-empty line in the response represents a single event.

This response body is of arbitrarily large size. As long as the connection is open, Airship will continue to write to the data stream. If no events have been dispatched down a connection for some time, the API will write to the connection to prevent it from being closed for inactivity. By default, only a blank line (a single newline character) will be written. If the `enable_offset_updates` field in the request is `true`, then instead of a blank line, an event will be written with type `OFFSET_UPDATE`. These events have no `body` or `device` field, and always have `occurred` and `processed` times indicating when they were sent. The `offset` field will contain the offset of the last event considered for inclusion in the stream whether or not it was actually sent. This may be useful to track position in the stream when using a filter which removes much of it.


These events should not be stored, and will be different for every connection even if requests are identical. `OFFSET_UPDATE` events are not subject to filters, and if requested will be delivered regardless of those specified. You should always check the type field before handling any delivered event.


If you receive no data or new line characters for ninety seconds, close the connection and reconnect.


Response body:

**Content-Type:** `application/vnd.urbanairship+x-ndjson; version=3;`

**One of:**

- [Attribute operation event]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#attribute_operation)

  Attribute operation events indicate a change in the device's attributes. Because attribute operations are related to a device, they will have a `device` field.

If you set an attribute on a Named User, Airship records events for each device associated with the Named User.


- [Close]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#close)

  Occurs when a user closes the app. Close events are often latent, as they aren't sent back to Airship until the user activates the app again.


- `allOf`

  Events relating to regulatory compliance for email and SMS channels.

- [Contact change]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#contact_change)

  Occurs when a contact is uninstalled, associated with a channel or Named User, or dissociated from a 
channel or Named User.


- [Control]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#control)

  Occurs when a device is excluded from a push because it was arbitrarily selected as a member of a control group for a [Message A/B test](/docs/guides/experimentation/a-b-tests/messages/), [Sequence A/B test](/docs/guides/experimentation/a-b-tests/sequences/), or [Holdout Experiment](/docs/guides/experimentation/holdout-experiments/).


- [Custom]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#custom)

  Represents Custom Events that are either emitted from the Airship SDK or submitted through the Custom Events API. You can configure Custom Events yourself. There are also several CUSTOM-type events for email and SMS that are defined by Airship.

In general, you can expect device information if the event source is `SDK` or if the event is one of the defined email or SMS events (as defined by `event_type`).


- [Feature Flag interaction event]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#feature_flag_interaction)

  Occurs when a user interacts with a tracked flagged feature. See [Feature Flags](/docs/guides/experimentation/feature-flags/#interaction-events). The events have a flag ID and flag name, which identify which flagged feature a user interacted with. They also have a boolean `eligible` field, which indicates whether or not the user was in the Feature Flag audience and had access to the feature.


- [First open]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#first_open)

  This event occurs when a user first registers a channel in your app. This event fires only once per user, when a channel is first registered. Channel registration most commonly occurs immediately after the first app open but can happen at other times as well, for example, if channel registration was delayed. The [open](#open) event fires on every app open, including the first.

- [First opt-in]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#first_opt_in)

  This event appears in the stream when a channel is first opted in. This event is specific to email (commercial), SMS, and open channels.

- [In-app button tap]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#in_app_button_tap)

  Occurs when a button is tapped within a Scene.


- [In-app experiences]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#in_app_experiences)

  Events that occur related to the display and completion behavior of a Scene. These events are derived from source events generated by the SDK, so a single user action may generate two events: one for the SDK event, one representing the user action as it relates to their actual activity within the app or website.


- [In-app form display]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#in_app_form_display)

  Occurs when a survey form in a Scene is displayed.


- [In-app form result]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#in_app_form_result)

  Occurs when a survey form in a Scene is submitted.


- [In-app message control]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#in_app_message_control)

  Occurs when an In-App Automation or Scene is not delivered because the targeted user's contact or Channel ID was part of a control group for a [Holdout Experiment](/docs/guides/experimentation/holdout-experiments/).


- [In-app message display]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#in_app_message_display)

  Occurs when an In-App Automation or Scene is displayed to a user. Because the event pertains to a specific device, the device information object will be populated.


- [In-app message exclusion]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#in_app_message_exclusion)

  Occurs when an In-App Automation or Scene is not displayed on a device because the user was banned. See [Ban Lists](/docs/guides/audience/segmentation/ban-lists/).


- [In-app message expiration]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#in_app_message_expiration)

  Occurs when a new In-App Automation or Scene message has taken the place of another message, a message has passed its expiration, or because displaying the message in-app would be redundant. This event type may be latent. It is not emitted until the app becomes active.


- [In-app message resolution]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#in_app_message_resolution)

  Occurs when an In-App Automation or Scene is cleared from the display, either by user action or timeout. Because this event pertains to an individual device, the device information object will be present.


- [In-app page swipe]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#in_app_page_swipe)

  Occurs when a user swipes to the next or previous page (screen) in a pager (specific to Scenes).


- [In-app page view]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#in_app_page_view)

  Occurs when a page (screen) is displayed within a pager (specific to Scenes).


- [In-app pager completed]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#in_app_pager_completed)

  Occurs when the last page (screen) of a pager is viewed for the first time (specific to Scenes).


- [In-app pager summary]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#in_app_pager_summary)

  Describes the full path a user took within a pager (specific to Scenes), including the order of pages (screens) visited and time spent per page.


- [Label event]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#label_event)

  Occurs when you update a Scene screen name.


- [Location]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#location)

  An event declaring the device to be at a particular latitude and longitude.

- [Mobile originated event]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#mobile_originated)

  Represents a message action that originated from a user — like an inbound SMS or email.

- [Open]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#open)

  Occurs when a user opens your app. This event fires every time a user opens your app, including the first time. See also the [first open](#first-open) event.

- [Push body]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#push_body)

  Occurs when you initiate a push, automation, or sequence.

Airship fulfills delivery over a time interval with a number of child pushes, each with a unique Push ID and a common Group ID. There is no guarantee that push body events (defined in Push Body Event) for the child pushes fulfilling a group will appear in the stream.

**Note:** When you start, pause, or publish a sequence, Airship emits a `push_body` event for the sequence itself, and each message contained within the sequence (i.e., messages +1). After you start a sequence, Airship does not issue subsequent `push_body` events for the sequence unless you pause or publish changes to the sequence.


- [Region event]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#region)

  Region events are emitted when a device enters or exits a geofence or the range of any of a set of bluetooth beacons. Region events require a Gimbal integration. Events for Gimbal customers include the Gimbal application instance identifier as `com.urbanairship.gimbal.aii` within the `identifiers` object.


- [Rich control]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#rich_control)

  Occurs when a Message Center message is not delivered to a user because they are in a control group for a [Sequence A/B test](/docs/guides/experimentation/a-b-tests/sequences/) or [Holdout Experiment](/docs/guides/experimentation/holdout-experiments/).

- [Rich delete]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#rich_delete)

  Occurs when a user deletes a Message Center message from their inbox.

- [Rich delivery]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#rich_delivery)

  Occurs when a Message Center message is delivered to a user's inbox.

Even though rich push deliveries may or may not cause an alert on the user's lock screen, they are always associated with a push identifier in the Airship system.


- [Rich read]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#rich_read)

  Occurs when a user reads a Message Center message in their inbox.

- [Screen viewed]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#screen_viewed)

  Occurs when a user has finished viewing a screen. It is up to you to instrument your application with names for each screen. Doing so will allow you to determine the user's path by filtering on the fields in the table below.


- [Send]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#send)

  Occurs whenever a push notification is sent to a device identified in the audience selector of a message.


- [Send aborted]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#send_aborted)

  Occurs when a push is dropped from our system before delivery is attempted. This can happen:

  * When using [External Data Feeds](/docs/guides/personalization/sources/external-data-feeds/) to personalize a message and an error was encountered or the feed returned a non-successful response
  * When a [Message Limit](/docs/guides/messaging/project/config/message-limits/) is met
  * When a [Ban List](/docs/guides/audience/segmentation/ban-lists/) webhook issues a `drop` response for a user

Device information for the device that did not receive the push is included with `SEND_ABORTED` events.


- [Send rejected]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#send_rejected)

  Occurs when a push fails during communication with a third party, like APNs or GCM. This typically indicates that the user has uninstalled the app or otherwise invalidated the last-registered credentials stored in Airship. The event contains the rejected push and the group, variant, or campaigns the push belonged to.


Device information for the device that did not receive the push is included with `SEND_REJECTED` events.


- [Short link click event]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#short_link_click)

  Occurs when a user taps or "clicks" an Airship-shortened link in an SMS or MMS message.

- [Subscription event]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#subscription)

  `SUBSCRIPTION` events reflect changes to users' subscription preferences — reflected in opt_in and opt_out values. These events help you track a user's subscription status in the system and the total number of subscribers.


- [Subscription list event]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#subscription_list)

  Occurs when subscription list enrollment changes for a device or user.


- [Tag change]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#tag_change)

  Occurs when tags change for a device.


- [Uninstall]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#uninstall)

  Occurs when a user uninstalls an Airship-integrated app in response to a push.

- [Web click event]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#web_click)

  Occurs when a user interacts with a web notification, e.g., clicked or tapped it. Web Click events have a device attribute on the event indicating the channel that was the target of the notification. The body of a Web Click Event is an associated push object.


- [Web session event]({{< ref "/developer/rest-api/connect/schemas/events/" >}}#web_session)

  Occurs when an opted in user begins interacting with a website. Web Session events have a device attribute, indicating the channel associated with the user.



**`402`** Like other Airship applications, Real-Time Data Streaming supports a limited number of simultaneous connections. If you exceed this number, you may receive this response.

**`404`** We do not have data for the specified App key. This is likely because we have yet to ingress or generate any data for your app.

**Examples**

*Example event stream request*

```http
POST /api/events HTTP/1.1
Authorization: Bearer <authorization token>
X-UA-Appkey: <appkey>
Accept: application/vnd.urbanairship+x-ndjson; version=3;
Content-Type: application/json

{
    "filters": [
        {
            "device_types": [
                "android",
                "amazon"
            ],
            "devices": [
                {
                    "channel": "5b389366-7caf-43e2-a19c-6159c7ea9936"
                },
                {
                    "channel": "c8044c8a-d5fa-4e58-91d4-54d0f70b7409"
                },
                {
                    "named_user_id": "George"
                }
            ],
            "latency": 20000000
        },
        {
            "notifications": [
                {
                    "group_id": "a30abf06-7878-4096-9535-b50ac0ad6e8e"
                }
            ],
            "types": [
                "OPEN"
            ]
        }
    ],
    "resume_offset": "MTAwMDAwMDAyMjg1NA",
    "subset": {
        "proportion": 0.3,
        "type": "SAMPLE"
    }
}

```

*Response*

```http
HTTP/1.1 200 OK
Content-encoding: gzip
Content-Type: application/vnd.urbanairship+json; version=3;

{"id" : "ff76bb85-74bc-4511-a3bf-11b6117784db", "type": "UNINSTALL", "offset": "MTIzNQ", "occurred": "2015-05-03T02:32:12.088Z", "processed": "2015-05-03T12:12:43.180Z", "device": {"channel":"a61448e1-be63-43ee-84eb-19446ba743f0", "device_type":"ANDROID", "android_channel": "a61448e1-be63-43ee-84eb-19446ba743f0"}}
{"id" : "8e50350e-dd9f-41af-b98e-b0e5d4b27dea","type": "SEND","offset": "NTIxMDM1","occurred": "2015-05-02T02:31:22.088Z","processed": "2015-05-02T02:32:43.181Z","device": {"channel":"5117f2a7-ba58-4981-9456-169959511d1a", "device_type":"IOS", "ios_channel": "5117f2a7-ba58-4981-9456-169959511d1a" },"body": {"push_id": "0c173744-dd35-4b5e-9f7f-2b7e0ce0e36e", "alerting": true}}
{"id" : "ff76bb85-74bc-4511-a3bf-11b6117784db", "type": "UNINSTALL", "offset": "MTIzNQ", "occurred": "2015-05-03T02:32:12.088Z", "processed": "2015-05-03T12:12:43.180Z", "device": {"channel":"a61448e1-be63-43ee-84eb-19446ba743f0", "device_type":"ANDROID", "android_channel": "a61448e1-be63-43ee-84eb-19446ba743f0"}}
{"device":{"channel":"820e4493-e4c9-4577-99bc-a98180599f73","delivery_address":"new.user@urbanairship.com","device_type":"EMAIL"},"id":"00000169-4a14-67b2-1ddd-d9e733622c3a","occurred":"2019-03-04T19:00:45.106Z","offset":"1000001260057","processed":"2019-03-04T19:00:47.094Z","type":"FIRST_OPT_IN"}

```

*Response object*

```json
{
   "id": "8e50350e-dd9f-41af-b98e-b0e5d4b27dea",
   "type": "SEND",
   "offset": "NTIxMDM1",
   "occurred": "2015-05-02T02:31:22.088Z",
   "processed": "2015-05-02T02:32:43.181Z",
   "device": {
      "channel": "5117f2a7-ba58-4981-9456-169959511d1a",
      "device_type": "IOS"
   },
   "body": {
      "push_id": "0c173744-dd35-4b5e-9f7f-2b7e0ce0e36e",
      "alerting": true
   }
}
{
  "device": {
    "channel": "820e4493-e4c9-4577-99bc-a98180599f73",
    "delivery_address": "new.user@urbanairship.com",
    "device_type": "EMAIL"
  },
  "id": "00000169-4a14-67b2-1ddd-d9e733622c3a",
  "occurred": "2019-03-04T19:00:45.106Z",
  "offset": "1000001260057",
  "processed": "2019-03-04T19:00:47.094Z",
  "type": "FIRST_OPT_IN"
}

```

---

