End-to-end chatbot creation in node.js with Bot Framework v4 & QnA Maker

Katia Gil Guzman
14 min readFeb 6, 2019

--

You want to start building chatbots but get lost in documentation, and don’t really know what to look for nor where to start? Well, look no further: this tutorial will teach you how to build a bot end-to-end, using Microsoft’s Bot Framework v4 (node.js) and QnA Maker.

Read through this, follow the steps, and at the end you will find yourself with a working bot, that you can then publish on your website, messenger, slack… or whichever channel you prefer. All of this can be done in less than 1 hour.

Intro

In this tutorial, we’re going to build a bot which can answer questions. It can be useful if what you’re looking to do is providing information for users in a direct and simple way, instead of having them search for it.

If you’re interested in building a bot that can store user data, understand natural language or conduct dialogs, you’ll have to wait a bit for my next tutorials.

If a simple bot which can answer questions is exactly what you need, then keep on reading!

Note: There are several ways of building a bot with Bot Framework v4 and QnA Maker. What is described in this tutorial is what I consider the easiest way.

For this tutorial you will need an Azure account. If you don’t already have one, you can create one for free here. You will have to enter your credit card info but don’t worry, an account is free as long as you don’t use paid services — which we won’t do here.

Step 1: Creating a QnA Maker service

To build this bot, we’re going to use QnA Maker, which is part of the Azure Cognitive Services. This service allows to create – as the name suggests – question and answer bots by providing answers to a set of questions.

  • Go to the Azure portal and sign in
  • Click on Create a resource (top-left corner)
  • Search for QnA Maker
  • Click on Create (bottom of the page)

You should now see this:

  • Choose a unique name and app name (the two can be the same)
  • Select your preferred subscription
  • Select F0 as the management pricing tier and F as the search pricing tier – unless you want to pay for an unlimited version, but for the purposes of this tutorial the free version is enough
  • Create or select an existing resource group
  • Choose your preferred location – the one closest to you – for your search and website location (the service itself is only available in West US for now, so you can’t change that)
  • Disable App Insights as we won’t need it in this tutorial

You should now have something similar to this:

Make a note of this:

We will have to come back to it later to make sure everything stays free.

Finally, click on Create and wait a couple of minutes for everything to be deployed — you will be notified when it’s done.

Now, let’s take a look at what exactly was just deployed.

Search (at the top of the portal) for the resource group you selected for the creation of the service, to display all the resources it contains.

4 resources have actually been created:

  1. A QnA Service (one of the Cognitive Services)
  2. An App Service Plan
  3. An App Service
  4. A Search Service

The App Service is what will host our QnA Service so that it’s accessible through an endpoint, and it relies on an App Service Plan. A Search Service is also used by QnA Maker to search through the content.

By default, the App Service Plan that was created is on a S1 pricing tier, which is not free, so we have to change that:

  • Click on the App Service Plan
  • Click on Scale Up under Settings (left menu)
  • Click on Dev/Test and select the F1 pricing Tier before clicking on Apply

After a couple of minutes, if you go into Overview, you should see that the App Service Plan Pricing Tier has changed and is now set to Free: 0 Small

Step 2: Linking a knowledge base

To store all the information your bot has access to, you will need a QnA Maker knowledge base, that links answers to potential questions.

  • Go to qnamaker.ai and sign in
  • Click on Create a knowledge base
  • Go directly to step 2 (we’ve completed what they call step 1 in the first step of this tutorial) and select your tenant, subscription and the QnA service you just created
  • Choose a name for your knowledge base (step 3). It doesn’t have to be a unique name, and you can use the same as me: DemoKB
  • If you have files containing a set of questions and answers, or a link to a website with an FAQ for example, you can populate your knowledge base with these, but it’s optional
  • If you want to have pre-defined questions and answers that will allow your bot to do basic chit-chat, you can choose between 3 personalities. Personally, I’m going for “The Friend”, but feel free to choose whichever you prefer
  • Click on Create your KB and wait for a couple of minutes

After the knowledge base was created, you should be redirected to this:

With the chit-chat option, our knowledge base is already populated with 97 “QnA pairs”. Pairs are composed of several similar questions and a matching answer.

You can now add all the QnA pairs you need manually.

  • Click on Add QnA pair
  • Click on the + sign to add examples of questions users might ask for the same answer — add at least 3 utterances so that your bot has more material to train on
  • Add an answer
  • Once you’re finished, click on Save and train

The service will train to recognize the example questions you provided and match them with an answer. Keep in mind that there’s a whole layer of natural language processing underneath, so that even with a few utterances your bot can recognize similar questions and determine what the user is the most likely to have asked. So even if the user says something that doesn’t match exactly one of your example questions, QnA Maker will still find the matching answer.

After the service is trained, you can test it:

  • Click on Test
  • Ask questions and look at the answers (try and make spelling and syntax errors to see how it affects comprehension)

If you click on Inspect, you can see the confidence score with which an answer was matched to the question.

If the behavior isn’t what you expected, you can add alternative phrasing to improve the performance.

When you’re satisfied, click on Publish:

Click again on the Publish button, et voilà! Your knowledge base is now accessible to the whole internet.

Make a note of your knowledge base ID, your hostname, and your endpoint key, we are going to need them later. You can find them in the example HTTP request QnA Maker gives you:

POST /knowledgebases/<kbID>/generateAnswer
Host: <hostName>/qnamaker
Authorization: EndpointKey <endpointKey>
Content-Type: application/json
{"question":"<Your question>"}

Step 3: Creating the bot

Now that our QnA Service is ready, we can create the actual bot, which will handle the conversation and use the QnA Service to match answers to user input.

To host the bot, we need to create a web app.

  • Go back to the Azure portal
  • Click on Create a resource
  • Search for Web App Bot
  • Click on the Create button

You should see this:

  • Choose a unique name for your bot and your app
  • Select your subscription, resource group (you can choose the same as for your QnA Maker Service) and your preferred location
  • Select the F0 pricing tier
  • Click on the bot template area to change the template
  • In the panel that has opened, select the v4 version of the SDK, node.js as the language and the Echo Bot template, then confirm by clicking the Select button

The Basic Bot template includes LUIS, another Cognitive Service, which we won’t cover in this tutorial. The template we’ll use here generates a bot that will simply echo what the users says, but we will make modifications to it and add our QnA Maker service.

  • Back in the Web App Bot creation panel, select the App Service Plan that was created with your QnA Maker service
  • For the Azure Storage, leave the Create New option selected
  • Turn off Application Insights, we won’t use it in this tutorial
  • When you’re done, click on Create

Wait for the deployment to complete (it usually takes about 5 minutes), you will be notified when it’s done.

If we go into our resource group, we can see that 3 new resources have been added:

  1. The Web App Bot which will contain our bot logic
  2. A new App Service which will host our bot and make it accessible through an endpoint
  3. A Storage Account which can be used to store information

Step 4: Setting up the bot development environment

To customize the bot template and have our bot do exactly what we want it to, we’ll have to modify the source code. And in order to do that, we need to set up a development environment. Once you have done this once, you don’t have to do it again when developing other bots.

I won’t get into details about how to install all the tools for each OS but it’s pretty straightforward, you can just follow the links.

npm install -g msbot
  • If you don’t already have a code editor on your computer, download VS Code

Now let’s test our bot locally.

  • Go back to the Azure portal and find your web app bot resource: go to the resource group and click on the web app bot name, or directly search for it in the search field at the top of the page
  • Click on Build in the left menu, under Bot Management
  • Click on the Download source code button
  • Once your source code is downloaded, unzip it and open your bot’s folder in your preferred code editor
  • Create a new file at the root of the folder named “.env”
  • Go back to your web app bot resource on Azure
  • Go to Application Settings in the left menu under App Service Settings
  • Scroll down to find the botFilePath and botFileSecret values
  • Write the following in the .env file:
botFilePath=./your_bot_name.bot
botFileSecret=""

(replace the value of the botFilePath by the one you found in your bot’s App Settings)

  • Go to your bot’s folder, open a terminal (on Windows: Shift + Right Click + Open Powershell window here) and run the command to install restify and botbuilder-ai (our bot app needs this to run properly):
npm install --save restify botbuilder-ai

By default, the .bot file, that we need to modify, is encrypted. To de-encrypt it, run the following command (still in the bot’s folder):

msbot secret -b YOUR_BOT_NAME.bot --secret "YOUR_SECRET" --clear

where YOUR_BOT_NAME.bot is the name of your .bot file, and YOUR_SECRET is the botFileSecret you got from the Application Settings.

You should get the following as a result:

You can now run the bot with this command:

node .\index.js

If there are no issues, you’ll see this — otherwise, go through the previous steps again and make sure everything is in order:

Now that your bot is running, you can test it using the Bot Framework Emulator:

  • Open the Bot Framework Emulator
  • Click on the Open Bot button
  • Find your bot’s folder and open the .bot file

You should now be looking at this:

If you try talking to the bot, as it is the Echo Bot template that we haven’t modified yet, you get this kind of answers:

Step 5: Building the bot logic

To change the behavior of our bot and connect it to our QnA service, we need to change its source code. It’s now time to look at what it is made of and make our modifications!

  • Go back to the code editor with your bot’s folder opened and open the .bot file
  • Add this code at the end of the services block, right before the closing square bracket
,{
'type': 'qna',
'name': 'DemoKB',
'kbId': 'YOUR_KBID',
'subscriptionKey': 'YOUR_SUBSCRIPTION_KEY',
'endpointKey': 'YOUR_ENDPOINT_KEY',
'hostname': 'YOUR_HOSTNAME',
'id': '117'
}

To find your subscription key:

  • Go to the Azure portal and search for your QnA Maker service
  • Click on Keys in the left menu under Resource Management
  • You can use either Key 1 or Key 2 as your subscription key

You should have your kbId, endpoint key and hostname from the 2nd step of this tutorial. The name of your knowledge base is what you put as name when you created it — if you’ve done the same as me, it is “DemoKB”.

Now that we’ve added the reference to our QnA Maker service, we’ll modify the code to access it.

  • Open the index.js file and after the line…
const BOT_CONFIGURATION = (process.env.NODE_ENV || DEV_ENVIRONMENT);

… add the following code:

  • Replace ‘<YOUR_KB_NAME>’ with the name of your knowledge base (DemoKB if you chose the same as me)
  • Replace EchoBot by QnAMakerBot at the following line:
const { EchoBot } = require('./bot');
  • Delete this line…
const bot = new EchoBot(conversationState);

… as well as this one:

const endpointConfig = botConfig.findServiceByNameOrId(BOT_CONFIGURATION);
  • Open the bot.js file and replace everything with this:

(Source: QnA Maker documentation)

Save, and test your bot by opening the .bot file in the Emulator, after running the node .\index.js command.

If you want to change the welcome message, find this line in bot.js

await turnContext.sendActivity('Welcome to the QnA Maker sample! Ask me a question and I will try to answer it.');

and change the text.

You can also change the default message when no matching answer is found at this line:

await turnContext.sendActivity('No QnA Maker answers were found. This example uses a QnA Maker Knowledge Base that focuses on smart light bulbs. To see QnA Maker in action, ask the bot questions like "Why won\'t it turn on?" or "I need help."');

Step 6: Deploying the bot to Azure

Now that our bot is ready and that we’ve tested it locally, we can deploy it back to Azure.

First thing we are going to do is re-encrypt our .bot file, so that no one can access the precious information it contains (we don’t want our bot to be used by someone else, do we?)

Still in your bot’s folder, run the command:

msbot secret --new

You’ll get a message like this one:

Copy the secret that was generated (/!\ very important, otherwise you won’t be able to do anything with your bot) and paste it in the .env file as your new botFileSecret, then save.

To make sure that it works, start your bot again (node .\index.js) and test it in the Emulator.

Now, we’re going to use the Azure CLI to deploy it to Azure.

Connect to your Azure subscription with the login command:

az login

(this will redirect you to your browser to enter your Azure credentials)

Then set your subscription:

az account set --subscription "<subscriptionID>"

You can find your Subscription ID by going to the Azure portal, searching for your Azure subscription (with the search field or All Services > Subscriptions) — mine is called “Pass Azure” for example.

The Subscription ID is displayed in the Overview tab.

You can now publish your bot with the following command:

az bot publish --name <bot-resource-name> --resource-group <resource-group-name> --code-dir '.' --verbose

<bot-resource-name> is the name of your bot (the name of your .bot file is <bot-resource-name>.bot), and <resource-group-name> the name of the Resource Group you selected during the creation of your web app bot.

You should get the following success message:

To make sure your bot was deployed correctly, you can go to the Azure portal, find your web app bot resource and test it directly from the portal. But first, find the Application Settings of your web app bot, scroll down and update your botFileSecret with the new one. Then, click on Test in web chat in the menu, under Bot Management, and try chatting with your bot.

And… It’s done! You’re finished with the creation of your bot. The best part is that you can now update your QnA service directly from the QnA Maker portal directly and not touch the code again.

Next step: Publishing to various channels

You can now publish your bot to several channels and make it available to end users. Since there are different ways to publish depending on the channel, this part will be covered in separate tutorials.

But whichever channel you choose, it all starts in the Channels tab, in the menu of your web app bot, under Bot Management.

I will update this post regularly and add links to tutorials explaining how to publish to some of these channels. In the meantime, you can take a look at the documentation.

Download the source code directly: GitHub

--

--