# Technical Guide

## Sending Messages

Messages are sent via MQTT **Topics**. By defualt, there are 4 topic types supported:

* Device
* Store
* Role
* Group

To post messages / notifications to a Topic, BlueFletch Enterprise supports two methods:

* BlueFletch Portal
* Rest API

### BlueFletch Portal <a href="#bluefletch-portal" id="bluefletch-portal"></a>

By using the BlueFletch Portal, an Admin can send messages to a specific topic. Simply log into the [Portal](https://ems.bluefletch.com/login) and navigate to the 'Enterprise Launcher' tab, then 'Notifications'.

<figure><img src="https://799338798-files.gitbook.io/~/files/v0/b/gitbook-x-prod.appspot.com/o/spaces%2FSxhNrDkmDAkv7QEWfOIh%2Fuploads%2FbpKm8lKUw3hbVKCyZuoV%2Fnotifications.png?alt=media&#x26;token=d285d1c1-450f-4c8f-919b-804ebb389635" alt="" width="563"><figcaption></figcaption></figure>

Enter the desired topic and json object of the message, then press **send**. See [Notification Body](https://docs.bluefletch.com/bluefletch-enterprise/product-guides/device-applications/messaging/technical-guide) for the format of the JSON Object.

### Rest API <a href="#rest-api" id="rest-api"></a>

Posting a JSON object to the 'Notify' endpoint will send messages to the Topic.

> *URL* : <https://ems-services-api.bluefletch.com/playbook/apiv1/api/notify>
>
> *Method*: POST
>
> *Parameters* : **topic** a string representing the Topic to post the message.
>
> *Header* : **x-bf-pb-apikey** the organization's [API Key](https://docs.bluefletch.com/bluefletch-enterprise/product-guides/portal/admin/key-management/api-keys)
>
> *Body* : the **JSON object** representing the message to send. See [Notification Body](https://docs.bluefletch.com/bluefletch-enterprise/product-guides/device-applications/messaging/technical-guide) for the format of the JSON Object.

**Example CURL**

```
curl -X POST "https://ems-services-api.bluefletch.com/playbook/apiv1/api/notify?topic=associates"  
          -H "x-bf-pb-apikey: apikeyhere"  -H "accept: */*" 
          -H "Content-Type: application/json" 
          -d "{ \"notificationId\": 6001, 
                \"contentTitle\": \"Customer Phone Call\", 
                \"contentText\": \"Call Jenny\", 
                \"expandedTitle\": \"\",  
                \"expandedText\": [],  
                \"packageName\": \"com.android.dialer\",  
                \"intentAction\": \"android.intent.action.CALL\", 
                \"intentExtras\": [{ \"key\": \"DATA\", \"value\": \"tel:\/\/8675309\" } ], 
                \"autoCancel\": true, 
                \"onGoing\": false, 
                \"useSound\": true, 
                \"useHeadsUp\": false}"
```

### Notification Body <a href="#notification-body" id="notification-body"></a>

| Field          | Description                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                      |
| -------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| notificationId | **number** indicates the Notification Id. Should be unique per notification. Can use the same Id to replace an existing message being displayed                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                  |
| contentTitle   | **string** Title of the message to display                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                       |
| contentText    | **string** Text of the Message body                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                              |
| expandedTitle  | **string** Expanded Text of the Message body                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                     |
| expandedText   | **array** Array of string to display in the expanded message                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                     |
| packageName    | **string** Represents the package to invoke if the message display is press by the user                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                          |
| intentAction   | **string** Represents the ACTION to invoke if the message display is pressed by the user                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                         |
| intentExtras   | **array** Array of Intent Objects to insert within the intent posted when if the message display is pressed by the user                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                          |
| autoCancel     | **boolean** true/false, allow the user to dismiss the message                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                    |
| onGoing        | **boolean** true/false,                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                          |
| useSound       | **boolean** true/false,                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                          |
| useHeadsUp     | **boolean** true/false                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                           |
| soundName      | <p><strong>string</strong> Optional parameter to specify a custom audio file on the device for notifications if <strong>useSound=true AND useHeadsUp=true</strong>. <br><br><em>Example strings:</em> <br>If using local file path: <em><code>"/sdcard/Download/ems/MyRingTone"</code></em>,  where the file  <code>/sdcard/Download/ems/MyRingTone.mp3</code> exists on the device (note to not include the file extension in the field value).<br>If using assets:<br><em><code>"soundName": "assets:message\_tone"</code></em>, where an <a href="../../bluefletch-launcher/configurable-layouts/assets-manager">asset</a> exists in the launcher.json such as<br><code>"message\_tone": "<https://example-file-hosting-site.com/MyRingTone.mp3>"</code>.</p> |

**Intent Object**

| Field | Description                            |
| ----- | -------------------------------------- |
| key   | **string** key of the Intent data      |
| value | **string** value for the intent object |

#### Example Notification Body <a href="#example-notification-body" id="example-notification-body"></a>

```
{
    "notificationId": 6001,
    "contentTitle": "Customer Phone Call",
    "contentText": "Call Jenny",
    "expandedTitle": "",
    "expandedText": [],
    "packageName": "com.android.dialer",
    "intentAction": "android.intent.action.CALL",
    "intentExtras": [
        {
            "key": "DATA",
            "value": "tel://8675309"
        }
    ],
    "autoCancel": true,
    "onGoing": false,
    "useSound": true,
    "useHeadsUp": false
}
```

### Cancelling a Message

If desired to cancel a notification that has been sent, use the following notification format:

```
{
    "notificationId": 6001,
    "notificationAction": "cancel"
}
```

Using the **notificationAction** of "cancel", along with the notification Id of the sent message, will cause the messaging application to remove the message from the device notification tray.

## Configuring the Messaging Client

{% hint style="warning" %}
Configuring the Messaging Client is only required if you are configuring another MQTT broker **in addition to** the BlueFletch MQTT broker cluster.
{% endhint %}

The Messaging application can be configured to connect to one or more MQTT brokers.  The application configuration is declared in the BlueFletch Launcher configuration and the Launcher sends it to the Messaging application.

Messaging by default is configured to connect to the BlueFletch MQTT broker cluster in BlueFletch's Google Cloud Instance.  To add a new broker for the Messaging application to connect to, create a new configuration in Launcher as follows:

Add the `notifications` array at the root level of the launcher.json file:

```json
    "notifications" : [
        {
          "brokerId" : "myCustomBroker",
          "name" : "My Custom Broker",
          "url":  "ssl://<mqttBrokerHost:Port>",
          "urls": "",
          "randomizeUrls" : true,
          "enableOrganizationGroup" : true,
          "useEnhancedMessaging" : true,
          "muteNotificationsOnCall" : true,
          "notificationAcquireWakelocks" : true,
          "receiveOfflineMessages" : false,
          "mqttUserName" : "<mqttUserName>",
          "mqttPassword" :  "<mqttPassword>",
          "enableNotificationsAlwaysOn" : true,
          "enableHeadsUpNotifications" : true,
          "subscribeToIdentityGroups": false
        }

    ]
```

<table><thead><tr><th width="328">Field</th><th>Description</th></tr></thead><tbody><tr><td>brokerId</td><td><strong>string</strong> A free form string ID used by Messaging internally to differentiate brokers.  Must not contain spaces.</td></tr><tr><td>name</td><td><strong>string</strong> Friendly name for this broker connection.  This will be displayed in the Messaging UI.</td></tr><tr><td>url</td><td><strong>string</strong> The full URL (scheme, host and port) for the MQTT broker.  Use this if connecting to one broker, or if you have a load balancer in front of your broker cluster. If there are multiple brokers, this key must still have a string value present, but define the broker list in the <code>"urls"</code> string.<br><br>For secure MQTT, use the ssl:// scheme.</td></tr><tr><td>urls</td><td><p><strong>string</strong> A comma delimited list of URLs corresponding to each server in an MQTT broker cluster. Messaging will select a broker URL for connection at random from the list (or will select in order if <code>"randomizeUrls": false</code>). If this key-value is used, <code>"url"</code> will be ignored but still requires a string value be present.</p><p></p><p>Leave string empty to disable.</p></td></tr><tr><td>randomizeUrls</td><td><strong>boolean</strong> Set to <code>true</code> to randomly pick the server to connect to among the <code>"urls"</code> list, otherwise Messaging will use the servers in the order listed. Default is <code>true</code>.</td></tr><tr><td>enableOrganizationGroup</td><td><strong>boolean</strong> If set to <code>true</code>, Messaging will create a parent topic corresponding to your BFE Organization ID.  This means that to the final topic string will be /&#x3C;orgId>/topicName.   Default is set to <code>true</code>.</td></tr><tr><td>useEnhancedMessaging</td><td><strong>boolean</strong> If set to <code>true</code>, Messaging will create a broadcast intent internally in the device for other applications to receive the message payload directly.</td></tr><tr><td>muteNotificationsOnCall</td><td><strong>boolean</strong> If set to <code>true</code>, Messaging will not make a notification sound if the device is currently on an audio call.</td></tr><tr><td>notificationAcquireWakelocks</td><td><strong>boolean</strong> If set to <code>true</code>, Messaging will wake up the device when a message arrives.</td></tr><tr><td>receiveOfflineMessages</td><td><strong>boolean</strong> (Deprecated) Must always be set to <code>false</code>.</td></tr><tr><td>mqttUserName</td><td><strong>string</strong> The user ID for the MQTT connection.</td></tr><tr><td>mqttPassword</td><td><strong>string</strong> The password for the MQTT connection.</td></tr><tr><td>enableNotificationsAlwaysOn</td><td><strong>boolean</strong> If set to <code>true</code>, will automatically subscribe with the device serial number and site even when no user session is present.</td></tr><tr><td>enableHeadsUpNotifications</td><td><strong>boolean</strong> (Deprecated) Must always be set to <code>true</code>.</td></tr><tr><td>subscribeToIdentityGroups</td><td><strong>boolean</strong> If set to <code>true</code>, Messaging will subscribe to a topic for each identity group the user belongs to.  Note that this may generate a lot of topics in your MQTT broker.</td></tr><tr><td>disableVolumeAdjustment</td><td><strong>boolean</strong> If set to <code>true</code>, the device's volume will <em>not</em> be automatically adjusted to the maximum setting when a new message is received. Default is <code>false</code>. Introduced in Messaging version 3.5.1.</td></tr></tbody></table>
