Chatbot Sources

A chatbot source represents an integration with the Microsoft Bot Framework. Bots created with the Microsoft Bot Framework can be installed in a variety of different chatroom services (Slack, Teams, Kik, FB Messenger and more) and can relay messages from those chatrooms to a Vantiq node. The events generated by incoming messages can trigger rules which will have access to the complete contents of the message payload. The rule can then modify the text of the message with a response and publish the message to the chatbot source in order to send a reply back to the chatroom from which the message originated.

Integrating with a chatbot requires the setup of several independent pieces, including:

How to Guide

  1. Create a Microsoft account, or use an existing one.
  2. Go to https://dev.botframework.com and register a new bot.
    • Don’t worry about messaging endpoint yet, that depends on the source created later in step 6
    • Save the app id and secret key generated during registration
  3. Finish bot creation and save the bot.
  4. Add any channels to the bot. The bot framework has a customized walk through for setting up each channel type.
  5. Once the bot has been created and added to the chat service, add the bot to any channels/chatrooms on the service from which you wish to receive messages.
    • For most services, this simply involves adding the chatbot user to the chatroom.
  6. Create the Vantiq chatbot source
    • In the source config, set clientId equal to the app id and clientSecret equal to the secret key that were generated in step 2.
  7. Once the source is created, go back to the Microsoft Bot Framework page for managing your bot and update the messaging endpoint URL skipped in step 2.
    • Click “edit” in the details panel and change the messaging endpoint to <Vantiq Server>/private/chatbot/<namespaceName>/<sourceName>

Once the source has been created you can write rules that trigger based on incoming messages like so:

RULE botRule
WHEN MESSAGE ARRIVES FROM <sourceName> AS message

log.info(“Message text: “ + message.text)

// Modify text field to contain response
message.text = “My custom response”

// Send response back to chatroom that inbound message came from
PUBLISH message TO SOURCE <sourceName>

return message

How it works

Integrating with the Chatbot Framework

When a message is written to a chat channel that a Microsoft Bot Framework bot is installed on, the chat service notifies Microsoft of the message, Microsoft then does some normalization on the message it receives, and POSTs a standardized message to the messaging endpoint configured in step 7 of the how-to-guide. We then convert the inbound message in our system into a source event which can trigger rules. These messages are not saved in the Vantiq system anywhere by default, but you can create a type and insert the messages into the type to create a record of all messages that were forwarded to Vantiq by the Bot Framework (be aware of the resources that may be used depending on the frequency and size of messages).

In the body of a rule triggered off by an incoming message, you have access to the entire contents of the normalized message produced by the Bot Framework (an example can be seen below):

{
  "type": "message",
  "id": "4024f72117af4a17b8521bf49bc24270",
  "timestamp": "2016-12-13T21:57:26.0056512Z",
  "serviceUrl": "https://slack.botframework.com",
  "channelId": "slack",
  "from": {
    "id": "XXXXX:TTTTT",
    "name": "jake"
  },
  "conversation": {
    "isGroup": false,
    "id": "BBBBB:TTTTT:CCCCC",
    "name": "vantiq-channel"
  },
  "recipient": {
    "id": "BBBBB:TTTTT",
    "name": "vantiq"
  },
  "text": "@vantiq hello",
  "attachments": [],
  "entities": [
    {
      "mentioned": {
        "id": "BBBBB:TTTTT",
        "name": "vantiq"
      },
      "text": "@vantiq",
      "type": "mention"
    }
  ],
  "channelData": {
    "SlackMessage": {
      "type": "message",
      "channel": "CCCCC",
      "user": "XXXXX",
      "text": "<@U3F2ZFJ6B> hello",
      "ts": "1481666245.000007",
      "team": "TTTTT"
    },
    "ApiToken": "XXXXXXXXXXXXXXXXXXXXXXXXXXXXX"
  }
}

Any of these fields can be used when writing constraints for the rule trigger condition, so it’s possible to write a rule that only triggers off of messages from specific users, or within specific chatrooms using WHEN clauses like:

// Trigger on all incoming messages for the source
WHEN MESSAGE ARRIVES FROM <sourceName> AS message

// Trigger only when a message was the slack user MySlackUserName
WHEN MESSAGE ARRIVES FROM <sourceName> AS message WHERE message.from.name == "MySlackUserName"

// Trigger only on messages that occur in a specific chatroom on slack
WHEN MESSAGE ARRIVES FROM <sourceName> AS message WHERE message.conversation.name == "MyChatroomName" AND message.channelId == "slack"

To generate a response to an inbound message that triggered a rule, simply update the text field of the message with the desired response and publish the message back to the source. Here’s an example:

RULE helloToYouTooRule
WHEN MESSAGE ARRIVES FROM <sourceName> AS message
if (message.text.contains("Hello")) {
    message.text = "Hello to you too!"
    PUBLISH message TO SOURCE <sourceName>
}

This rule will receive every message on every channel the chatbot is installed on. If a message contains “Hello”, the chatbot will then respond back into the chatroom with “Hello to you too!”.

Publishing Arbitrary Chat Messages

It’s also possible to publish a chat message to any existing channel where the chatbot is already a member. To do this, construct an object with the message text, the name of the service (i.e: slack, teams, kik, etc) and the channel name and publish the object to the source, the same way as responding to an incoming message in a rule. See the following procedure for an example:

PROCEDURE sendChatbotMessage
var message = {}
message.text = "Hello World!"
message.service = "slack"
message.channel = "vantiq-channel"
PUBLISH message TO SOURCE testbot

A parameterized version of the above procedure can make it even simpler to send messages out to chat channels from other procedures and rules:

PROCEDURE chatbotTestMessage(text, service, channel)
var message = {}
message.text = text
message.service = service
message.channel = channel
PUBLISH message TO SOURCE testbot

This works by maintaining an internal mapping between unique channel/ service pairs and the bot framework metadata needed to send a message to that specific chat channel. This mapping is updated automatically whenever the chatbot is added to a new chat channel. If there’s a channel with a chatbot already installed but publishing to it doesn’t seem to work it could be that the mapping was never created. To fix this just leave and rejoin the channel as any user and the mapping for that channel will be created.

Creating a Chatbot Source

The following example illustrates how to create a Chatbot source using the REST API. Chatbot sources can also be defined in Modelo by using the Add button to select Source… when in Modelo Development Mode.

POST https://dev.vantiq.com/api/v1/resources/sources
{ 
    "name": "myChatbotSource",
    "type": "CHATBOT",
    "direction": "BOTH",
    "config": {
        "clientId"    : "APP_ID_FROM_BOT_FRAMEWORK",
        "clientSecret": "SECRET_FROM_BOT_FRAMEWORK""
    }
}

To delete a chatbot source named myChatbotSource using the REST API issue the following request:

DELETE https://dev.vantiq.com/api/v1/resources/sources/myChatbotSource