Introduction

© 2021-2025 Lekab Communication Systems AB. Version 6.0.101, 2025-08-07.

This is a Web Service API with the primary purpose of sending Rich Communication Service (RCS) messages over the Google RBM (Rich Business Messaging) network. Currently, the API contains the basic sending functionality, and it will soon be expanded to callback notification of status of messages and callback delivery of incoming messages to a user-defined webhook url.

There are two main advantages of RCS messages over SMS messages. First, the messages are "rich" in the sense that they can also contain media (image, video, sound) and certain combinations of media and text known as cards and carousels of cards. They can also contain suggestion buttons which can be clicked to generate replies or start actions, like opening a url, calling a number or opening the map at a position. Secondly, the messages are always sent from a registered agent, which has been vetted by Google and the user’s operator for use purpose and cannot be easily "spoofed", so that the end-user knows that the message is from a trusted, known source.

Rich Communication Service messages according to the Universal Profile 2.x RCS standard are currently supported, and Universal Profile 3.0 standard features will be implemented as they are rolled out by Google RBM.

Similar to SMS, an RCS message is received in the standard Messages app and does not need the recipient to download a dedicated app (toggling a setting may be needed). Message reception is today limited to Android phones, but iOS phones are expected to get RCS capability soon. With RCS currently only supported on Android/Google handsets, our service has fallback functionality to the SMS channel, where sending goes through our own SMS gateway and not through Google. We have plans to expand to other channels in the future.

User accounts and billing are integrated with our SMS gateway, and we handle communication with Google and facilitate registration of sending agents with the telephone operators.

Each message can only be of one content type. The service supports the message content types offered by Google at the time of writing: a text of up to 3000 bytes, one piece of media, a single card or a carousel of 2 to 10 cards. Each message can also have a number (currently up to 11) of suggestions.

If a message is sent with instructions to first try the RBM channel, and RBM is not available for that agent to that phone, fallback happens, i.e. the next channel on the list of channels is tried (currently, this will be SMS if present). The user may supply a dedicated SMS message text which will be sent instead of the RBM message upon fallback. If an SMS text is not present, the text-type message content will be used, and if that is also not present due to the RCS message not being of the text type, sending will fail.

We also offer automatic "up-lift" of SMS messages where a user’s messages sent from any of our standard SMS APIs with a specific sender id are sent as RCS text messages from the user’s agent, with fallback to the original SMS if RCS did not work, today probably due to an i(ncompatible) Phone. Up-lift setup and terms of sale are outside the scope of this manual.

Google RBM defines "Basic RBM" as a text-type message without any suggestion buttons, and with a text that fits into 160 bytes of UTF-8 encoding. In that universal standard encoding of the Internet, English letters take 1 byte, European umlauts take 2 bytes, Chinese characters 3 bytes and emojis (as well as Ancient Egyptian hieroglyphs) 4 bytes. The main feature of a Basic RBM is that it is delivered at a lower cost than other RBM messages, and is perfect for the kind of applications where an SMS would be used in the old days of yore. The advantage here with RBM is the spoof-proof sender agent, which lends greater trust to security related messages, for instance, a one-time password login sequence where the message content is a short text string.

The implementation so far includes the endpoint /send, with the obvious purpose.

The endpoint supports only POST calls where the HTTP POST request body is a JSON document and returns responses in the HTTP response body as JSON documents. The standard character encoding of JSON is UTF-8, and the API does not recognize any other encodings (ISO-8859-1, Windows-1252 or other).

The formats of the input and output json documents are described below.

Authentication methods available for requests

Every request to the service must include authentication, i.e. username and password (or equivalent). For POST requests these can be given in the (automatically HTTPS = SSL/TLS encrypted) HTTP headers.

We offer four different alternative ways of supplying these login credentials:

  1. Username and password can be given as standard Basic authentication, in which the header Authorization should have the value Basic + token, where the token is the Base64 encoding of (a UTF-8 byte array representation of) username:password. Here testuser:testpass will be encoded as dGVzdHVzZXI6dGVzdHBhc3M=, and the header Authorization should have the value Basic dGVzdHVzZXI6dGVzdHBhc3M= with a single space between the word Basic and the Base64 token.

  2. Username and password can be given in the HTTP headers, X-Lekab-Userid and X-Lekab-Password, respectively. The values have to be the Base64 encoding of (a UTF-8 byte array representation of) the username or password to allow non-US-ASCII characters. Here testuser will be encoded as dGVzdHVzZXI= and testpass as dGVzdHBhc3M=

  3. An API key obtained from Lekab or by self-service in the web portal can be used as a query parameter key or as the value of the header X-API-Key. The length of the key varies depending on the length of the username (which is contained within the key). TUxVOmRHVnpkSFZ6WlhJOjlKUUczTXU2TVZVU1Exd3Y is a possible example key for the username testuser. The key is independent of the account password.

  4. A Bearer token obtained from our Oauth2 server can be used, where the header Authorization should have the value Bearer token, with a single space between the word Bearer and the token. See below for instructions how to call our oauth server.

It is possible to disallow the username+password based authentication methods by setting the role DISALLOW_BASIC for the API user, forcing the use of either API-key or Oauth authentication.

If any of the alternative methods of authentication are used, parameter values pertaining to other authentication methods should be omitted or set to the empty string "".

How to obtain an oauth token from our oauth server

The /auth/api/v1/token endpoint is used to request an OAuth 2.0 Bearer Token.

POST request examples

Using Basic authentication (username and password in a Base64 from UTF-8 encoded header)

curl -X POST --location "https://secure.lekab.com/auth/api/v1/token" \
    -H "Content-Type: application/x-www-form-urlencoded" \
    -d 'grant_type=client_credentials' \
    --basic --user username:password

Using username and password in body (client_id and client_secret url-encoded from UTF-8)

curl -X POST --location "https://secure.lekab.com/auth/api/v1/token" \
    -H "Content-Type: application/x-www-form-urlencoded" \
    -d 'grant_type=client_credentials&client_id=username&client_secret=password'

Note that both these uses of username:password authentication are available for the call even if the user has the role DISALLOW_BASIC set. We do not support refresh tokens for the oauth server.

Explanation of parameters

POST param query param value Description

grant_type

client_credentials (string)

The requested grant type. Only client_credentials is supported.

client_id

user name (string)

User name if Basic authentication is not used. Url encoded from utf-8 if necessary

client_secret

user password (string)

Password if Basic authentication is not used. Url encoded from utf-8 if necessary

1. The /send endpoint

Used for sending rich messages over the available channels (currently RBM and SMS).

All sending is from the sending user account’s RBM agent, registered and approved by Google and the telephone operators in the destination country. We will assist in the registration and approval process. We can also assign a test agent (where a small number of phone numbers are pre-registered as allowed destinations) for testing. Terms of sale, contracts, approval, credit check etc. are not covered by this manual. We will associate the user account with the RBM agent, so the API sender needs only know the login credentials of the sending user, while we handle all communication with Google.

Channels are specified as a comma (",") separated list starting with the channel to try first. Channels cannot be repeated. Therefore, the currently possible channel specifications are "RBM", "SMS", "RBM,SMS" and "SMS,RBM". It is likely, that "RBM,SMS" (RBM with fallback to SMS) and "RBM" (RBM without fallback) will be of primary interest to API users.

A message can be addressed to a number of recipients, and the channels will be tried as specified for each recipient until a successful sending is achieved. Recipient addresses (addresses are phone numbers for both RBM and SMS) are given separated by semi-colons (";"). In the event that a given recipient has different numbers for different channels, and to later accommodate channels that do not use phone numbers, the address to use in each channel can be given separated by commas. If the number of addresses given for a recipient are fewer than the number of channels specified, the last address is repeated (This is the most common case, where the RBM number given is also used for SMS). Phone numbers must include a country code. We allow up to 400 recipients per HTTP POST call to /send, but recommend substantially fewer. Functionality for accommodating large batch sending is under consideration.

While most parameters for the /send endpoint need only a short description, the actual rich message is a JSON structure with strict rules, and therefore the richMessage field (in the top level of the JSON document which makes up the body of the HTTP POST call) will be explained in its own section below.

1.1. POST request example: a text type message without suggestions

https://secure.lekab.com/rime/send

Sending to one recipient with authentication in the headers and the following as contents of the HTTP body. A typical Basic RBM.

{
   "channels" : "RBM",
   "address" : "46701234567",
   "richMessage" : {
      "text":"Your access key is 12345678"
   }
}

1.2. POST request example: single card type message, suggestions in the card and after

https://secure.lekab.com/rime/send

Sending to two recipients with authentication in the headers and the following as contents of the HTTP body.

{
   "channels" : "RBM,SMS",
   "address" : "46701234567;46702345678",
   "smsText" : "This SMS would have been a RCS card message if your phone allowed it",
   "smsSender" : "MYCOMPANY",
   "richMessage" : {
      "richCard" : {
         "standaloneCard" : {
            "cardOrientation" : "HORIZONTAL",
            "thumbnailImageAlignment" : "LEFT",
            "cardContent" : {
               "title": "A question of zoology",
               "description": "Is this a cat?",
               "media": {
                  "height" : "MEDIUM",
                  "contentInfo": {
                     "fileUrl" : "https://upload.wikimedia.org/wikipedia/commons/2/2b/Mainecoon1.png"
                  }
               },
               "suggestions": [
                  { "reply" : { "text" : "It is a cat!", "postbackData" : "CAT YES"} },
                  { "reply" : { "text" : "No, it is not!", "postbackData" : "CAT NO"} }
               ]
            }
         }
      },
      "suggestions":[
         { "action" : {
            "text" : "Show famous place on map",
            "postbackData" : "TOUR EIFFEL",
            "viewLocationAction" : { "latLong" : {"latitude" : 48.858093, "longitude" : 2.294694}, "label" : "Voila"} }
         }
      ]
   }
}

1.3. Explanation of parameters for /send

POST json key json value

appname

string

Selects one of several sender agents for a user account. Omit this to use default appname "" if we have not supplied an appname to use.

channels

string

channel try order: "RBM", "SMS", RBM,SMS" or "SMS,RBM"

address

string

Recipient id, for RCS and SMS channels: international phone number (country+area+subscriber) no intl prefix like 00 etc To send to several recipients, separate with semicolons. To use different addresses for different channels, separate with commas within each recipient.

smsText

string

text to use instead of rich message if the SMS channel is used

smsSender

string

SMS sender id, required if not two-way SMS, cannot be reserved for other company

smsTwoway

true or false

SMS sender is taken from user’s number pool for receiving answers, default false

richMessage

json object, see below

message to send through rich channel, see below

postbackSuffix

string

User defined string that is sent back to agent when any of the suggestion buttons in this message is pressed

trafficType

string

May be required in the future when sending messages via a multi-use agent, to define which use is selected. Currently one of "AUTHENTICATION", "TRANSACTION", "PROMOTION", "SERVICEREQUEST", "ACKNOWLEDGEMENT". Subject to change according to Google RBM.

ttl

integer

Message time to live in minutes, forwarded to Google or SMS operator when sending

conversationid

string

Feature of our SMS service, where receipts and two-way answers to this message are marked with this id

costcenter

string

For billing, used to separate bill for one account into portions e.g. by department

metadata

string

identifying data not sent to phone but echoed back with status reports and replies

properties

json object/dictionary

{"key1":"value1", "key2":"value2", …​} for future use

1.4. HTTP response to /send

A successful request will return 200 OK and a json document of the following format. Note that the request for sending is successful even if the send status of the message sending turns out to be failed. A successfully sent message may sometimes not be delivered due to external factors (phone turned off, phone subscription expired, no such subscriber, phone lacking capability of receiving channel, opt-out from channel), but such requests will be reported as successful by this endpoint, and the later fortune of the message can instead be followed via the delivery status callbacks to the status webhook url. The Content-Type header of the response is application/json for all responses.

{
  "resultText" : "At least one message sent OK",
  "sent" : [ {
    "result" : "OK",
    "id" : "1225831041592336384",
    "channels" : "RBM,SMS",
    "addresses" : "46701234567,46701234567"
  }, {
    "result" : "OK",
    "id" : "1225831041684611072",
    "channels" : "RBM,SMS",
    "addresses" : "46702345678,46702345678"
  } ]
}

An unsuccessful request will give an appropriate 4xx or 5xx HTTP result code, and a json document of the following form. Any result which is not "OK" is an error and means no message was sent.

{
  "result" : "ERROR",
  "error" : "Unauthorized"
}

In this example, the result code is 401, as appropriate for "Unauthorized". Syntax errors in the message specification will yield 400 and "Validation error".

1.5. Explanation of response to /send

POST json key json value (strings quoted)

resultText

string

"At least one message sent OK" if successful

sent

json list

One list element per recipient

result

string

OK if successful

id

string

id of the message used for future references to this message, e.g. status callbacks

channels

string

Comma separated channels to try sending this message

addresses

string

Comma separated addresses to use for each channel

error

string

error description if not successful

1.6. Example Python 3 code

import json
import requests
import base64

authstringarray=("testuser" + ":" + "testpass").encode('utf-8')
authbase64=base64.b64encode(authstringarray).decode('utf-8')
headers={'Authorization':'Basic ' + authbase64}

sendreq = {}
sendreq["channels"] = "RBM,SMS"
sendreq["address"] = "46701234567;46702345678"
sendreq["richMessage"] = {
   "text":"Can you work extra hours on Christmas Day?",
   "suggestions":[
      { "reply" : { "text" : "Yes" } },
      { "reply" : { "text" : "No" } }
   ]
}
sendreq["metadata"] = 'Xmas 2026 employee 1234'
sendreq_json = json.dumps(sendreq)

url = 'https://secure.lekab.com/rime/send'
response = requests.post(url, data=sendreq_json, headers=headers)
sendresp = response.json()
if sendresp["sent"]:
	for m in sendresp["sent"]:
		print("Successful message id "+ m['id'] + " to " + m['addresses'] + " via " +  m['channels'])
else:
    print("Send error: " + sendresp["error"])

will output

Successful message id 1225831041592336384 to 46701234567,46701234567 via RBM,SMS
Successful message id 1225831041684611072 to 46702345678,46702345678 via RBM,SMS

2. Details of how to construct the richMessage json object

The rules for RCS Business Messages say that each message must have only one content type. This service supports the message content types offered by Google at the time of writing: a text of up to 3000 bytes, one piece of media, a single card or a carousel of 2 to 10 cards. Each message can also have a number (currently up to 11) of suggestions.

This means that the richMessage object can have a maximum of two top level fields, where one gives the content type of the message. This field may be "text" for a text message, "contentInfo" for a media message or "richCard" for a message with a single card or carousel of cards. The optional second field "suggestions" is a list of json objects where each object is a suggestion, i.e. a button to press to reply to the sending agent with a pre-determined text or to start an action on the recipient’s phone, like opening the browser to a url or opening the phone calling app with a phone number filled in. The top level list of suggestions can have a maximum of 11 suggestions, but for most RBM-compatible mobile handsets, we do not recommend more than about 3-4 suggestions due to graphical awkwardness of longer lists. The maximum of 11 suggestions does not include suggestions inside cards, where each card can have up to 4 suggestions.

2.1. Structure of the four message types

2.1.1. Text messages

A text message consists of a text of up to 3000 bytes, and an (optional) list of suggestions. If the message is 160 bytes or shorter and there are no suggestions, it is sent at a lower cost, so called "Basic RBM", if it is longer or has at least one suggestion, the standard message price applies. Note that the text can contain any UTF-8/Unicode characters, including emojis, but the current RCS message standard (Universal Profile 2.x) does not include any formatting (often, confusingly, called "rich text") for specifying font, bold, italic or underline.

{
   "text":"Yes or no, that is the question?",
   "suggestions":[
      { "reply" : { "text" : "😄 YES", "postbackData" : "YES"} },
      { "reply" : { "text" : "NO 😢", "postbackData" : "NO"} }
   ]
}

Fields and subfields:

json key json value

text

string

Message text UTF-8, max 3000 bytes (Basic RBM 160 bytes)

suggestions

Optional JSON list of replies or actions or mixed

0 to 11 suggestions, see below

2.1.2. Media messages

A media message contains a url reference to a server where the piece of media is served. A local media server will be added to this API in the near future. The RBM standard actually includes three different ways of specifying a media message, but two of them refer to messages that are pre-uploaded to Google, and we do not support that uploading process. Therefore, the media url will be contained in a contentInfo object. In addition, an (optional) list of suggestion buttons can be included, but no title text or description text. For such combination messages, the card types are appropriate.

The media in a media file may be a picture (jpeg, png etc.), a sound file (mp3 etc.), a video clip (mp4, etc.) or a PDF file. See separate documentation for allowed types, data and pixel sizes and other limitations. Note that while RBM sending is fully encrypted, Google can read all files sent, with no way of sending files that are encrypted so that Google cannot read them.

{
   "contentInfo" : {
      "fileUrl" : "https://pictureserver.com/dogs/German_Shepherd.jpg",
      "thumbnailUrl" : "https://pictureserver.com/dogs/thumbnails/German_Shepherd_tn.jpg",
      "forceRefresh" : true;
   },
   "suggestions":[
      ...
   ]
}

Fields and subfields:

json key json value

contentInfo

json object

Contains the media reference

fileUrl

string

Url where the media file is served

thumbnailUrl

string

Optional url where a thumbnail file is served

forceRefresh

boolean

Default false, instruct Google to reload the media file if cached from before

suggestions

Optional JSON list of replies or actions or mixed

0 to 11 suggestions, see below

2.1.3. Single card messages

A single card message contains a single card, and an optional list of suggestions. The card can have a title string of up to x characters, a description text of up to y characters, a piece of media specified as a url in a contentInfo object, and an (optional) list of up to 4 internal suggestions inside the card. Depending on the size and type of the media, it is usually displayed in the card as a thumbnail representation which can be clicked to display the media in full-window mode. Exact display geometry is a function of the Messages app version on the phone and is also subject to change.

{
   "richCard" : {
      "standaloneCard" : {
         "cardOrientation" : "HORIZONTAL",
         "thumbnailImageAlignment" : "LEFT",
         "cardContent" : {
            "title": "A nice picture",
            "description": "Is this a cat?",
            "media": {
               "height" : "MEDIUM",
               "contentInfo": {
                  "fileUrl" : "https://upload.wikimedia.org/wikipedia/commons/2/2b/Mainecoon1.png"
               }
            },
            "suggestions": [
               { "reply" : { "text" : "It is a cat!", "postbackData" : "CAT YES"} },
               { "reply" : { "text" : "No, it is not!", "postbackData" : "CAT NO"} }
            ]
         }
      }
   },
   "suggestions":[
      ...
   ]
}

Fields and subfields:

json key json value

richCard

json object

Wraps the card or carousel

standaloneCard

json object

Wraps the single card

cardOrientation

string

Geometry of card display: "HORIZONTAL" or "VERTICAL"

thumbnailImageAlignment

string

Where in the card is media thumbnail: "LEFT" or "RIGHT"

cardContent

json object

Wraps the content of one card (the only one here)

title

string

Title of the card

description

string

Text of the card

media

json object

Wraps media part of content of this card

height

string

Media height "SHORT" (112 DP), "MEDIUM" (168) or "TALL" (264)

contentInfo

json object

Wraps the media urls like in a media message

fileUrl

string

Url where the media file is served

thumbnailUrl

string

Optional url where a thumbnail file is served

forceRefresh

boolean

Default false, instruct Google to reload the media file if cached from before

suggestions

In-card JSON list of replies or actions or mixed

0 to 4 suggestions, see below

suggestions

Optional JSON list of replies or actions or mixed

0 to 11 suggestions, see below

A carousel message contains 2-10 cards which can have the same types of content as the card in the single card message, as well as an (optional) list of suggestions. The carousel displays the cards in a scrollable fashion so that one of the cards is "on top" and visible. Depending on the size and type of the media, it is usually displayed in the card as a thumbnail representation which can be clicked to display the media in full-window mode. Exact display geometry is a function of the Messages app version on the phone and is also subject to change. The Lovecraft-inspired example below has two cards in the list.

{
   "richCard" : {
      "carouselCard" : {
         "cardWidth" : "MEDIUM",
         "cardContents" : [
            {
               "title":"In picturesque Arkham",
               "description":"Cthulhu Hotel service on call",
               "media":{
                  "height" : "MEDIUM",
                  "contentInfo" : {
                     "fileUrl":"https://upload.wikimedia.org/wikipedia/commons/6/63/Octopus_marginatus.jpg"
                  }
               },
               "suggestions":[
                  {
                     "action" : {
                        "text" : "Book a room",
                        "postbackData" : "BOOK CTHULHU",
                        "openUrlAction" : { "url" : "https://creepyhotels.com/cthulhu" }
                     }
                  },
                  {
                     "action" : {
                        "text" : "Call of Cthulhu",
                        "postbackData" : "CALL CTHULHU",
                        "dialAction" : { "phoneNumber" : "+46701234567" } # the called phone does NOT have to be Android
                     }
                  }
               ]
            },
            {
               "title":"Close to Miskatonic U",
               "description":"Tentacle Inn creature comforts",
               "media":{
                  "height" : "MEDIUM",
                  "contentInfo" : {
                     "fileUrl":"https://upload.wikimedia.org/wikipedia/commons/d/dd/Loligo_vulgaris.jpg"
                  }
               },
               "suggestions":[
                  {
                     "action" : {
                        "text" : "Book a room",
                        "postbackData" : "BOOK TENTACLE",
                        "openUrlAction" : { "url" : "https://creepyhotels.com/tentacle" }
                     }
                  },
                  {
                     "action" : {
                        "text" : "Call the hotel",
                        "postbackData" : "CALL TENTACLE",
                        "dialAction" : { "phoneNumber" : "+46702345678" } # the called phone does NOT have to be Android
                     }
                  }
               ]
            }
         ]
      }
   },
   "suggestions" : [
      {
        "reply" : { "text" : "Andover Area", "postbackData" : "MENU ANDOVER"}
      },
      {
        "reply" : { "text" : "Haverhill Area", "postbackData" : "MENU HAVERHILL"}
      },
      {
        "reply" : { "text" : "Salem Area", "postbackData" : "MENU SALEM"}
      }
   ]
}

Fields and subfields:

json key json value

richCard

json object

Wraps the card or carousel

carouselCard

json object

Wraps the carousel

cardWidth

string

Geometry of card display: "SMALL" or "MEDIUM"

cardContents

list of json objects

List of contents of 2-10 cards in carousel

title

string

Url where the media file is served

description

string

Url where the media file is served

media

json object

Wraps media part of content of this card

height

string

Media height "SHORT" (112 DP), "MEDIUM" (168) or "TALL" (264), where TALL is not allowed for carousels with card width SMALL

contentInfo

json object

Wraps the media urls like in a media message

fileUrl

string

Url where the media file is served

thumbnailUrl

string

Optional url where a thumbnail file is served

forceRefresh

boolean

Default false, instruct Google to reload the media file if cached from before

suggestions

In-card JSON list of replies or actions or mixed

0 to 4 suggestions, see below

suggestions

Optional JSON list of replies or actions or mixed

0 to 11 suggestions, see below

2.1.5. Available suggestions for the suggestion list parameters

Suggestions can be either of type reply or of type action, and can be mixed as desired within a suggestions list. A message has a suggestion list of 0 to 11 suggestions at the end of the message, while each card contains a suggestion list of 0 to 4 suggestions. When a user selects a suggestion, an incoming message is sent to the sender agent, where it is stored in our database and forwarded to the sender account by callback to a webhook url (under implementation).

Suggestion reply

Sends an answering message with a preset content to the sender agent.

{
   "reply" : {
      "text" : "Salem Area",
      "postbackData" : "MENU SALEM"
   }
}

Fields and subfields:

json key json value

reply

json object

Wraps the reply

text

string

Button text of the reply suggestion. Also incoming message text if postbackData is empty

postbackData

string

Incoming message text if present

Suggestion dialAction

Opens the telephone app on the recipient’s mobile handset with a given number pre-filled. The phone to call does not have to be Android or even a mobile phone. Also informs the sending agent with an incoming action message.

All actions have the button text field, the postbackData field and the fallbackUrl field where the action is replaced with opening the mobile handset browser at the given url if the mobile handset does not support the originally intended action. Probably the fallbackUrl will not be of much use, since most actions are things mobile handsets usually do. In addition each action has its own xxxAction field defining what action it is and containing the parameters for the specific action.

{
   "action" : {
       "text" : "🦣 Call Erik",
       "dialAction" : { "phoneNumber" : "+46701234567" }
   }
}

Fields and subfields:

json key json value

action

json object

Wraps an action suggestion

text

string

Button text of the action suggestion. Also incoming message text if postbackData is empty

postbackData

string

Incoming message text if present

fallbackUrl

string

Url to open if mobile phone does not support this action (unlikely)

dialAction

json object

Wraps a dialAction suggestion

phoneNumber

string

Number to present in the dialing app

Suggestion viewLocationAction

Opens the user’s default map app and selects the specified location. Also informs the sending agent with an incoming action message.

All actions have the button text field, the postbackData field and the fallbackUrl field where the action is replaced with opening the mobile handset browser at the given url if the mobile handset does not support the originally intended action. Probably the fallbackUrl will not be of much use, since most actions are things mobile handsets usually do. In addition each action has its own xxxAction field defining what action it is and containing the parameters for the specific action.

{
   "action" : {
      "text" : "Famous place",
      "postbackData" : "TOUR EIFFEL",
      "viewLocationAction" : {
         "latLong" : {
            "latitude" : 48.858093,
            "longitude" : 2.294694
         },
         "label" : "Voila"
      }
   }
}

Fields and subfields:

json key json value

action

json object

Wraps an action suggestion

text

string

Button text of the action suggestion. Also incoming message text if postbackData is empty

postbackData

string

Incoming message text if present

fallbackUrl

string

Url to open if mobile phone does not support this action (unlikely)

viewLocationAction

json object

Wraps a viewLocationAction suggestion

latLong

json object

Wraps a latitude+longitude object

latitude

float

Latitude -90.0000 to +90.0000 Southern hemisphere is negative

longitude

float

Longitude -180.0000 to +180.0000 West of Greenwich is negative

label

string

Map marker label

Suggestion createCalendarEventAction

Opens user’s default calendar app and starts the new calendar event flow with the event data pre-filled. Also informs the sending agent with an incoming action message.

All actions have the button text field, the postbackData field and the fallbackUrl field where the action is replaced with opening the mobile handset browser at the given url if the mobile handset does not support the originally intended action. Probably the fallbackUrl will not be of much use, since most actions are things mobile handsets usually do. In addition each action has its own xxxAction field defining what action it is and containing the parameters for the specific action.

{
   "action" : {
      "text" : "Save the date",
      "createCalendarEventAction" : {
         "startTime": "2026-04-30T17:00:00Z",
         "endTime": "2026-04-30T21:00:00Z",
         "title": "Valpurgis night bonfire",
         "description": "A good time will be had by all"
      }
   }
}

Fields and subfields:

json key json value

action

json object

Wraps an action suggestion

text

string

Button text of the action suggestion. Also incoming message text if postbackData is empty

postbackData

string

Incoming message text if present

fallbackUrl

string

Url to open if mobile phone does not support this action (unlikely)

createCalendarEventAction

json object

Wraps a calendarEventAction suggestion

startTime

string

Timestamp in RFC3339 UTC "Zulu" format, with nanosecond resolution and up to nine fractional digits. Examples: "2014-10-02T15:01:23Z" and "2014-10-02T15:01:23.045123456Z"

endTime

string

Timestamp in RFC3339 UTC "Zulu" format, as startTime

title

string

Event title

description

string

Event description

Suggestion openUrlAction

Opens the user’s default web browser app to the given URL. Also informs the sending agent with an incoming action message.

All actions have the button text field, the postbackData field and the fallbackUrl field where the action is replaced with opening the mobile handset browser at the given url if the mobile handset does not support the originally intended action. Probably the fallbackUrl will not be of much use, since most actions are things mobile handsets usually do. In addition each action has its own xxxAction field defining what action it is and containing the parameters for the specific action.

{
   "action" : {
      "text" : "Book the hotel",
      "postbackData" : "BOOK CTHULHU",
      "openUrlAction" : {
         "url" : "https://creepyhotels.com/cthulhu"
      }
   }
}

Fields and subfields:

json key json value

action

json object

Wraps an action suggestion

text

string

Button text of the action suggestion. Also incoming message text if postbackData is empty

postbackData

string

Incoming message text if present

fallbackUrl

string

Url to open if mobile phone does not support this action (absurdly unlikely)

openUrlAction

json object

Wraps an openUrlAction suggestion

url

string

Url to open in browser

Suggestion shareLocationAction

Opens the RCS app’s location chooser so the user can pick a location to send to the agent. Also informs the sending agent with an incoming action message, when the suggestion button is pressed. The location data arrives as a second incoming message of type LOCATION, when the user shares it.

All actions have the button text field, the postbackData field and the fallbackUrl field where the action is replaced with opening the mobile handset browser at the given url if the mobile handset does not support the originally intended action. Probably the fallbackUrl will not be of much use, since most actions are things mobile handsets usually do. In addition each action has its own xxxAction field defining what action it is and containing the parameters for the specific action.

{
   "action" : {
      "text" : "Where are you?",
      "shareLocationAction" : { }
   }
}

Fields and subfields:

json key json value

action

json object

Wraps an action suggestion

text

string

Button text of the action suggestion. Also incoming message text if postbackData is empty

postbackData

string

Incoming message text if present

fallbackUrl

string

Url to open if mobile phone does not support this action (absurdly unlikely)

shareLocationAction

json object

Wraps an openUrlAction suggestion, has no parameters

3. Opting in and out and blocking of numbers

The phone user can always send in a text message to the service with the text "STOP" to get added to the blocklist of that specific sender account. If the user later sends in a text message with the text "START", the blocking is removed.

Google RBM has announced that there will be unsubscribe and resubscribe buttons in the Messages app to achieve the same purpose, but currently any use of such buttons is not forwarded to our system in the Google RBM announced format (or any other format), so we expect that in later versions. The unsubscribe and resubscribe buttons in the current version seem to affect settings inside Google RBM which we currently cannot control or access. So a customer that unsubscribes with a Google button cannot yet resubscribe by sending in "START", but will need to resubscribe with the corresponding Google button.

Opting in and out does not affect our security-related blocking of country codes to which an account cannot send. These blocking rules will be set up so that sending is only attempted to countries where the sending RBM agent is registered, verified and launched. This by default includes the SMS channel, but user accounts could possibly relax the country code blocking rules, to achieve fallback to SMS when RBM sending fails to a foreign country.