---
updatedAt: 2026-04-29T09:49:08.000Z
---

# Reporting Engagement Using React Native SDK

User engagement types include:

* **Impression (IMP):** Reports variation impressions.
* **Click (CLICK ):** Reports when users click a displayed variation of a custom API campaign or the widget of a Recommendation campaign.
* **Slot click (SLOT\_CLICK):** In Recommendations and Sorting Optimizer campaigns, reports exactly which product was clicked.
* **Slot impression (SLOT\_IMP):** For Restaurant Recommendation campaigns only. Reports an impression for one or more slots.
* **Push notification click (PN\_CLICK):** For Reconnect push notification campaigns only. Reports clicks on the notification.

The Mobile SDK offers two ways to report them:

* Using the Choice return object from the Choose Variations call
* Using the DYSdk object

## Using the Choice return object methods

Using the Choice object is typically the easiest way to report a user engagement.

### Reporting impressions

You can report an impression for a variation using the `Choice.Variation` object.

#### reportImpression

Returns [DYResult](https://dy.dev/dy-dev/docs/swift-sdk-references#dyresult)

| Parameter | description                                                                        | Data Structure |
| :-------- | :--------------------------------------------------------------------------------- | :------------- |
| branchId  | The branch ID (if relevant)                                                        | String? = nil  |
| dayPart   | Define the period of the day the request relates to. Relevant only to Restaurants. | dayPart? = nil |

**Example**

```javascript React Native
import { choose, DayPart, engagements, isRecsPayload, isStoreRecsPayload, isStoreRecsVariation, Page } from '@DynamicYield/react-native-sdk'

async function reportImpression() {
    await engagements.reportImpression({
        decisionId: 'decisionId',
        variations: [123, 456, 789], // optional
        dayPart: DayPart.DINNER,// optional
        branchId: 'example-branch-id' // optional
    }).then((result) => {
        switch (result.status) {
            case 'SUCCESS':
                //A impression has been reported successfully
                break;
            case 'WARNING':
                result.warnings?.forEach(warning => {
                    // Log the warnings
                });
                break;
            case 'ERROR':
                const error = result.error
                //do something with the error
                break;
        }
    }).catch((error) => {
        //handle error
    });
}
```

> **Note:** If you previously sent a Choose Variations request with `isImplicitImpressionMode` set to `true`, do not report impressions for the returned variations. Reporting them will result in counting duplicate impressions.

### Reporting clicks

You can report click for a variation using the `Choice.Variation` object.

#### reportClick

Returns [DYResult](https://dy.dev/dy-dev/docs/swift-sdk-references#dyresult)

| Parameter | description                                                                        | Data Structure |
| :-------- | :--------------------------------------------------------------------------------- | :------------- |
| branchId  | The branch ID (if relevant)                                                        | String? = nil  |
| dayPart   | Define the period of the day the request relates to. Relevant only to Restaurants. | dayPart? = nil |

**Example**

```javascript React Native
import { choose, DayPart, engagements, isRecsPayload, isStoreRecsPayload, isStoreRecsVariation, Page } from '@DynamicYield/react-native-sdk'

async function reportClickViaVariation() {
    try {
        const result = await choose.chooseVariations({
            selectorNames: ['campaign-name'],
            page: Page.homePage({ location: 'screenName' })
        });

        if (result.status !== 'SUCCESS') return;

        const variation = result.choices?.find(choice => choice.name === 'campaign-name')?.variations?.[0];
        if (!variation) return;

        try {
            const clickResult = await variation.reportClick({
                branchId: 'example-branch-id', // Optional
                dayPart: DayPart.DINNER
            });
            if (clickResult.status === 'SUCCESS') {
                // A click has been reported successfully
            } else if (clickResult.status === 'WARNING') {
                clickResult.warnings?.forEach(warning => {
                    // Log the warnings
                });
            } else if (clickResult.status === 'ERROR') {
                const error = clickResult.error;
                // Do something with the error
            }
        } catch (error) {
            // Handle error
        }
    } catch (error) {
        // Handle error
    }
}
```

### Reporting slot clicks

> Relevant only for recommendations campaigns.

You can report a click or an impression for a slot using the `Choice.RecsVariation.PayLoad.Data.Slot` object.

#### reportClick

Returns [DYResult](https://dy.dev/dy-dev/docs/swift-sdk-references#dyresult)

| Parameter | description                                                                        | Data Structure |
| :-------- | :--------------------------------------------------------------------------------- | :------------- |
| branchId  | The branch ID (if relevant)                                                        | String? = nil  |
| dayPart   | Define the period of the day the request relates to. Relevant only to Restaurants. | dayPart? = nil |

**Example**

```javascript React Native
import { choose, DayPart, engagements, isRecsPayload, isStoreRecsPayload, isStoreRecsVariation, Page } from '@DynamicYield/react-native-sdk'

async function reportClickBySlot() {
    try {
        const result = await choose.chooseVariations({
            selectorNames: ['recs-campaign-name'],
            page: Page.homePage({ location: 'screenName' })
        });

        if (result.status !== 'SUCCESS') return;

        const variation = result.choices?.find(choice => choice.name === 'recs-campaign-name')?.variations?.[0];
        if (!variation) return;
        if (!isRecsPayload(variation.payload)) return
        if (!variation.payload.data.slots[0]) return

        try {
            const clickResult = await variation.payload.data.slots[0].reportClick({
                branchId: 'example-branch-id', // Optional
                dayPart: DayPart.DINNER
            });
            if (clickResult?.status === 'SUCCESS') {
                // A click has been reported successfully
            } else if (clickResult.status === 'WARNING') {
                clickResult.warnings?.forEach(warning => {
                    // Log the warnings
                });
            } else if (clickResult.status === 'ERROR') {
                const error = clickResult.error;
                // Do something with the error
            }
        } catch (error) {
            // Handle error
        }
    } catch (error) {
        // Handle error
    }
}
```

### Reporting slot impressions

You can report an impression for one or more slots using the `StoreRecsVariation` object.

> Relevant only for Restaurant recommendations campaigns.

| Parameter | Description                                                                        | Data Structure   |
| :-------- | :--------------------------------------------------------------------------------- | :--------------- |
| SlotIds   | The IDs of the slots to report an impression for                                   | \[String]? = nil |
| branchId  | The ID of the branch the recommendation is for                                     | String? = nil    |
| dayPart   | Define the period of the day the request relates to. Relevant only to Restaurants. | dayPart? = nil   |

**Example**

```javascript React Native
import { choose, DayPart, engagements, isRecsPayload, isStoreRecsPayload, isStoreRecsVariation, Page } from '@DynamicYield/react-native-sdk'

async function reportClickStoreRecsVariation() {
    try {
        const result = await choose.chooseVariations({
            selectorNames: ['store-recs-campaign-name'],
            page: Page.homePage({ location: 'screenName' })
        });

        if (result.status !== 'SUCCESS') return;

        const variation = result.choices?.find(choice => choice.name === 'store-recs-campaign-name')?.variations?.[0];
        if (!variation || !isStoreRecsVariation(variation)) return;
        if (!isStoreRecsPayload(variation.payload)) return
        const slotsIds = variation.payload.data.slots.map(slot => slot.slotId);
        if (!slotsIds) return

        try {
            const clickResult = await variation.reportSlotsImpression({
                slotsIds: slotsIds,
                branchId: 'example-branch-id', // Optional
                dayPart: DayPart.DINNER
            });
            if (clickResult?.status === 'SUCCESS') {
                // A click has been reported successfully
            } else if (clickResult.status === 'WARNING') {
                clickResult.warnings?.forEach(warning => {
                    // Log the warnings
                });
            } else if (clickResult.status === 'ERROR') {
                const error = clickResult.error;
                // Do something with the error
            }
        } catch (error) {
            // Handle error
        }
    } catch (error) {
        // Handle error
    }
}


```

## Using the DYSdk Object

You can also report engagement using the DYSdk object.

### reportImpression

Returns [DYResult](https://dy.dev/dy-dev/docs/swift-sdk-references#dyresult)

| Parameter  | Description                                                                        | Data Structure |
| :--------- | :--------------------------------------------------------------------------------- | :------------- |
| decisionId | A unique decision ID received in the Choose Variations call                        | String         |
| variations | The variation ID                                                                   | \[Int]? = nil  |
| branchId   | The ID of the branch the recommendation is for                                     | String? = nil  |
| dayPart    | Define the period of the day the request relates to. Relevant only to Restaurants. | dayPart? = nil |

**Example**

```javascript React Native
async function reportImpressionViaVariation() {
    try {
        const result = await choose.chooseVariations({
            selectorNames: ['campaign-name'],
            page: Page.homePage({ location: 'screenName' })
        });

        if (result.status !== 'SUCCESS') return;

        const variation = result.choices?.find(choice => choice.name === 'campaign-name')?.variations?.[0];
        if (!variation) return;

        try {
            const impressionResult = await variation.reportImpression({
                branchId: 'example-branch-id', // Optional
                dayPart: DayPart.DINNER
            });
            if (impressionResult.status === 'SUCCESS') {
                // A click has been reported successfully
            } else if (impressionResult.status === 'WARNING') {
                clickResult.warnings?.forEach(warning => {
                    // Log the warnings
                });
            } else if (impressionResult.status === 'ERROR') {
                const error = clickResult.error;
                // Do something with the error
            }
        } catch (error) {
            // Handle error
        }
    } catch (error) {
        // Handle error
    }
}


```

> **Note**: If you previously sent a Choose Variations request with `isImplicitImpressionMode` set to `true`, do not report impressions for the returned variations. Reporting them will result in duplicate impressions being counted.

### reportClick

Returns [DYResult](https://dy.dev/dy-dev/docs/swift-sdk-references#dyresult)

| Parameter  | Description                                                                        | Data Structure |
| :--------- | :--------------------------------------------------------------------------------- | :------------- |
| decisionId | A unique decision ID received in the Choose Variations call                        | String         |
| variation  | The variation ID                                                                   | Int? = nil     |
| branchId   | The ID of the branch the recommendation is for                                     | String? = nil  |
| dayPart    | Define the period of the day the request relates to. Relevant only to Restaurants. | dayPart? = nil |

**Example**

```javascript React Native
async function reportClick() {
    await engagements.reportClick({
        decisionId: 'decisionId',
        variation: 1234, // optional
        dayPart: DayPart.DINNER,// optional
        branchId: 'example-branch-id' // optional
    }).then((result) => {
        switch (result.status) {
            case 'SUCCESS':
                //A impression has been reported successfully
                break;
            case 'WARNING':
                result.warnings?.forEach(warning => {
                    // Log the warnings
                });
                break;
            case 'ERROR':
                const error = result.error
                //do something with the error
                break;
        }
    }).catch((error) => {
        //handle error
    });
}

```

### reportSlotClick

Returns [DYResult](https://dy.dev/dy-dev/docs/swift-sdk-references#dyresult)

[block:parameters]
{
  "data": {
    "h-0": "Parameter",
    "h-1": "Description",
    "h-2": "Data Structure",
    "0-0": "slotId <br><span style=\"color:gray; font-size:0.8em;\"><strong>Required</strong></span>",
    "0-1": "The slotId as returned from the Choose Variations call. Do not use for API custom code campaigns.",
    "0-2": "String",
    "1-0": "variationId",
    "1-1": "The variation ID",
    "1-2": "Int",
    "2-0": "branchId",
    "2-1": "The ID of the branch the recommendation is for",
    "2-2": "String? = nil",
    "3-0": "dayPart",
    "3-1": "Define the period of the day the request relates to. Relevant only to Restaurants.",
    "3-2": "dayPart? = nil"
  },
  "cols": 3,
  "rows": 4,
  "align": [
    "left",
    "left",
    "left"
  ]
}
[/block]

**Example**

```javascript React Native
async function reportSlotClick() {
    await engagements.reportSlotClick({
        variation: 1234, // optional
        slotId: 'slot-id',
        dayPart: DayPart.DINNER,// optional
        branchId: 'example-branch-id' // optional
    }).then((result) => {
        switch (result.status) {
            case 'SUCCESS':
                //A impression has been reported successfully
                break;
            case 'WARNING':
                result.warnings?.forEach(warning => {
                    // Log the warnings
                });
                break;
            case 'ERROR':
                const error = result.error
                //do something with the error
                break;
        }
    }).catch((error) => {
        //handle error
    });
}
```

### reportSlotImpression

> For Restaurant Recommendations campaigns.

Returns [DYResult](https://dy.dev/dy-dev/docs/swift-sdk-references#dyresult)

[block:parameters]
{
  "data": {
    "h-0": "Parameter",
    "h-1": "Description",
    "h-2": "Data Structure",
    "0-0": "slotIds<br><span style=\"color:gray; font-size:0.8em;\"><strong>Required</strong></span>",
    "0-1": "The slotId as returned from the Choose Variations call. Do not use for API Custom Code campaigns.",
    "0-2": "[String]",
    "1-0": "variationId",
    "1-1": "The variation ID",
    "1-2": "[Int]? = nil",
    "2-0": "branchId",
    "2-1": "The ID of the branch the recommendation is for",
    "2-2": "String? = nil",
    "3-0": "dayPart",
    "3-1": "Define the period of the day the request relates to. Relevant only to Restaurants.",
    "3-2": "dayPart? = nil"
  },
  "cols": 3,
  "rows": 4,
  "align": [
    "left",
    "left",
    "left"
  ]
}
[/block]

**Example**

```javascript React Native
async function reportSlotsImpression() {
    await engagements.reportSlotImpression({
        variation: 1234, // optional
        slotsIds: ['slot-id-1', 'slot-id-2'],
        dayPart: DayPart.DINNER,// optional
        branchId: 'example-branch-id' // optional
    }).then((result) => {
        switch (result.status) {
            case 'SUCCESS':
                //A impression has been reported successfully
                break;
            case 'WARNING':
                result.warnings?.forEach(warning => {
                    // Log the warnings
                });
                break;
            case 'ERROR':
                const error = result.error
                //do something with the error
                break;
        }
    }).catch((error) => {
        //handle error
    });
}
```

### reportPnEngagement

> For App Push Notification campaigns

Returns [DYResult](https://dy.dev/dy-dev/docs/swift-sdk-references#dyresult)

[block:parameters]
{
  "data": {
    "h-0": "Parameter",
    "h-1": "Description",
    "h-2": "Data Structure",
    "0-0": "trackingData <br><span style=\"color:gray; font-size:0.8em;\"><strong>Required</strong></span>",
    "0-1": "Enables Dynamic Yield to track actions attributable to the push notification. Must be extracted from the messaging provider. Learn more about the [tracking link variable](https://support.dynamicyield.com/hc/en-us/articles/13472246286749-Create-a-Reconnect-Campaign#trackinglink).",
    "0-2": "trackingData",
    "1-0": "TrackingData.rri",
    "1-1": "",
    "1-2": "String? = nil",
    "2-0": "TrackingData.sectionID",
    "2-1": "",
    "2-2": "String? = nil",
    "3-0": "TrackingData.userID",
    "3-1": "",
    "3-2": "String? = nil",
    "4-0": "TrackingData.reqTs",
    "4-1": "",
    "4-2": "String? = nil",
    "5-0": "TrackingData.version",
    "5-1": "",
    "5-2": "String? = nil",
    "6-0": "TrackingData.events**(required)**",
    "6-1": "",
    "6-2": "[trackingDataEvent]",
    "7-0": "TrackingDataeEvent.ver",
    "7-1": "",
    "7-2": "String? = nil",
    "8-0": "TrackingDataeEvent.expVisitId",
    "8-1": "",
    "8-2": "String? = nil",
    "9-0": "TrackingDataeEvent.smech",
    "9-1": "",
    "9-2": "String? = nil",
    "10-0": "TrackingDataeEvent.vars",
    "10-1": "",
    "10-2": "[Int]? = nil",
    "11-0": "TrackingDataeEvent.exp",
    "11-1": "",
    "11-2": "String? = nil",
    "12-0": "TrackingDataeEvent.mech",
    "12-1": "",
    "12-2": "String? = nil"
  },
  "cols": 3,
  "rows": 13,
  "align": [
    "left",
    "left",
    "left"
  ]
}
[/block]

```javascript React Native
async function reportPnEngagement() {
    await engagements.reportPnEngagement({
        rri: 'rri',
        sectionID: 'section-id',
        reqTs: 'req-ts',
        userID: 'user-id',
        events: [{
            'ver': 'ver',
            'expVisitId': "expVisitId",
            'smech': "smech",
            'vars': [1, 2, 3],
            'exp': "exp",
            'mech': "mech"
        }]
    }).then((result) => {
        switch (result.status) {
            case 'SUCCESS':
                //A impression has been reported successfully
                break;
            case 'WARNING':
                result.warnings?.forEach(warning => {
                    // Log the warnings
                });
                break;
            case 'ERROR':
                const error = result.error
                //do something with the error
                break;
        }
    }).catch((error) => {
        //handle error
    });
}
```