Showing Url, Location and Carousel Responses in Viber Bot

SUSI Webchat is capable of sending Url, location and carousel responses. In this blog, we will learn about implementing these same responses in SUSI viber bot. We can send text response instead of carousels but it doesn’t attract users and cause difficulties in understanding. In SUSI webchat for query “news” it sends a URL of an article from BBC news which looks like this:

If we send a query “Where is Singapore” it sends location using map response and it looks like this:

For web search SUSI sends carousels which look like this:


To implement these responses in SUSI Viber bot we will send a post request with specific types to the send_message endpoint of Viber chat API https://chatapi.viber.com/pa/send_message. Url, location and carousel responses will be implemented in following way:

  • Url:
    For receiving URL in Viber bot we will post a request with type:’url’ and media:’url to be sent here’. A request will look like code given below.
var options = {
                method: 'POST',
                url: 'https://chatapi.viber.com/pa/send_message',
                headers: headerBody,
                body: {
                    receiver: req.body.sender.id,
                    min_api_version: 1,
                    sender: {
                        name: 'Name of your public Account here',
                        avatar: 'Avatar url for your public account here'
                    },
                    tracking_data: 'tracking data',
                    type: 'url',
                    Media: 'http://www.website.com/go_here'
                },
                json: true
            };
request(options, function(err, res, body) {
                   if (err) throw new Error(err);
                   console.log(body);
               });
  • Location:
    For receiving location with a map on Viber bot we will post a request with type: ‘location’ and location: { lat: latitude, lon: longitude }. In location response, we have to send latitude and longitude values of location to be shown on the map. A request will look like code given below:
var options = {
                method: 'POST',
                url: 'https://chatapi.viber.com/pa/send_message',
                headers: headerBody,
                body: {
                    receiver: req.body.sender.id,
                    min_api_version: 1,
                    sender: {
                        name: 'Name of your public Account here',
                        avatar: 'Avatar url for your public account here'
                    },
                    tracking_data: 'tracking data',
                    type: 'location',
                    location: {
                           lat: latitude,
                           lon: longitude
                       }
                },
                json: true
            };
request(options, function(err, res, body) {
                   if (err) throw new Error(err);
                   console.log(body);
               });

Location response in Viber bot will look like this:

  • Carousel:
    Carousels are horizontal tiles which can be scrolled to view content on them. To receive carousels on Viber bot we will post a request with type: ‘rich_media’ and

    rich_media: {
                       Type: "rich_media",
                       ButtonsGroupColumns: 6,
                       ButtonsGroupRows: 6,
                       BgColor: "#FFFFFF",
                       Buttons: buttons
           }
    

    In rich media “ButtonsGroupColumns” is the number of columns per carousel content block,  “ButtonsGroupRows” is the number of rows per carousel content block and buttons is an array of buttons which contains content to be shown in carousels. A request will look like code given below.

    var options = {
                    method: 'POST',
                    url: 'https://chatapi.viber.com/pa/send_message',
                    headers: headerBody,
                    body: {
                        receiver: req.body.sender.id,
                        min_api_version: 1,
                        sender: {
                            name: 'Name of your public Account here',
                            avatar: 'Avatar url for your public account here'
                        },
                        tracking_data: 'tracking data',
                        type: 'rich_media',
                           rich_media: {
                               Type: "rich_media",
                               ButtonsGroupColumns: 6,
                               ButtonsGroupRows: 6,
                               BgColor: "#FFFFFF",
                               Buttons:{
                                   Columns: 6,
                                   Rows: 3,
                                   Text: 'text to be shown in carousel',
                                   "ActionType": "open-url",
                                   "ActionBody": 'link to be opened on clicking on carousel block',
                                   "TextSize": "medium",
                                   "TextVAlign": "middle",
                                  "TextHAlign": "middle"
                              }            
                           }
                    },
                    json: true
                };
    request(options, function(err, res, body) {
                       if (err) throw new Error(err);
                       console.log(body);
                   });
    

    Carousel response from Viber bot will look like this:

    We have successfully implemented URL, location and carousel response in Viber bot.

    If you want to learn more about Viber chat API refer to https://developers.viber.com/docs/api/rest-bot-api/

    Resources

    Viber Chat API: https://developers.viber.com/docs/api/rest-bot-api/
    Claudia bot builder platform to build Viber bot: https://claudiajs.com/tutorials/viber-chatbot.html
    Viber bot by using PHP: http://thedebuggers.com/build-viber-chat-bot-6-simple-steps/

How to Get Secure Webhook for SUSI Bots in Kubernetes Deployment

Webhook is a user-defined callback which gets triggered by any events in code like receiving a message from a user in SUSI bot is an event. Few bots need webhook URI for callback like in SUSI Viber bot we need to define a webhook URI in the code to receive callbacks and make our Viber bot work. In this blog, we will learn how can we get an SSL activated webhook while deploying our bot to Google container using Kubernetes. We will generate SSL certificate using kube lego service that is included in kubernetes and you will define that in yaml files below. We can also generate SSL certificate using third party services like CloudFlare but by using it we will be dependant on CloudFlare so we will use kube lego.

We will start off by registering a domain first on which we will activate SSL certificate and use that domain as a webhook. Go to freenom and register your account. After logging in, register a free domain of any name and check out that order. Next, you have to set IP for DNS of this domain. To do so we will reserve an IP address in our Google cloud project with this command:

gcloud compute addresses create IPname --region us-central1

You will get a created message. To see your IP go to VPC Network -> External IP addresses. Add this IP to DNS zone of your domain and save it for later use in yaml files that we will use for deployment. Now we will deploy our bot using yaml files but before deployment, we will create a cluster

gcloud container clusters create clusterName

After creating cluster add these yaml files to your bot repository and add your IP address that you have saved above to the yamls/nginx/service.yaml file for “loadBalancerIP” parameter. Replace domain name in yamls/application/ingress-notls.yaml and yamls/application/ingress-tls.yaml with your domain name that you have registered already. Add your email ID to yamls/lego/configmap.yaml for “lego.email” parameter. Replace “image” and “env” parameters in yamls/application/deployment.yaml with your docker image and your environment variables that you are using in your code. After changing yaml files we will use this deploy script to create a deployment. Change paths for yaml files in script according to your yaml files path.

In gcloud shell run the following command to deploy an application using given configurations.

bash ./path-to-deploy-script/deploy.sh create all

This will create the deployment as we have defined in the script. The Kubernetes master creates the load balancer and related Compute Engine forwarding rules, target pools, and firewall rules to make the service fully accessible from outside of Google Cloud Platform. Wait for a few minutes for all the containers to be created and the SSL Certificates to be generated and loaded.

You have successfully created a secure webhook. Test it by opening the domain that you have registered at the start.

Resources

Enabling SSL using CloudFlare: https://jonnyjordan.com/blog/how-to-setup-cloudflare-flexible-ssl-for-wordpress/
https://www.youtube.com/watch?v=qFvwEVkl5gk

How to Make SUSI Bot for Google Hangouts

Google Hangouts is a platform for communication provided by Google. We can also make bots for Google Hangouts. In fact, in this blog, we will make SUSI bot for Google Hangouts. In order to make it we will follow these steps:

  1. Install Node.js from the link below on your computer if you haven’t installed it already.
    https://nodejs.org/en/
  2. Create a folder with any name and open a shell and change your current directory to the new folder you created.
  3. Type npm init in the shell and enter details like name, version and entry point.
  4. Create a file with the same name that you wrote in entry point in an above-given step. i.app.js and it should be in the same folder you created.
  5. Type following commands in command line  npm install –save hangouts-bot. After hangouts-bot is installed, type npm install –save express.  On success, type npm install –save request. When all the modules are installed check your package.json file; therein you’ll see the modules in the dependencies portion.
  6. Your package.json file should look like this.

    {
     "name": "susi_hangout",
     "version": "1.0.0",
     "description": "SUSI AI bot for Google Hangouts",
     "main": "app.js",
     "scripts": {
       "start": "node app.js"
     },
     "author": "",
     "license": "",
     "dependencies": {
       "express": "^4.15.3",
       "hangouts-bot": "^0.2.1",
       "request": "^2.81.0"
     }
    }
    
  7. Copy following code into file you created i.e index.js
    var hangoutsBot = require("hangouts-bot");
    var bot = new hangoutsBot("your-email-here", process.env.password|| config.password);
    var request = require('request');
    var express = require('express');
    
    var app = express();
    app.set('port', 8080);
    
    bot.on('online', function() {
       console.log('online');
    });
    
    bot.on('message', function(from, message) {
       console.log(from + ">> " + message);
    
           var options1 = {
           method: 'GET',
           url: 'http://api.susi.ai/susi/chat.json',
           qs: {
               timezoneOffset: '-330',
               q: message
           }
       };
    
       request(options1, function(error, response, body) {
               if (error) throw new Error(error);
               // answer fetched from susi
               var type = (JSON.parse(body)).answers[0].actions;
               var answer, columns, data, key, i, count;
               if (type.length == 1 && type[0].type == "answer") {
                   answer = (JSON.parse(body)).answers[0].actions[0].expression;
                   bot.sendMessage(from, answer);
               } else if (type.length == 1 && type[0].type == "table") {
                   data = JSON.parse(body).answers[0].data;
                   columns = type[0].columns;
                   key = Object.keys(columns);
                   count = JSON.parse(body).answers[0].metadata.count;
                   console.log(key);
                   for (i = 0; i < count; i++) {
                       answer = "";
                       answer =key[0].toUpperCase() + ": " + data[i][key[0]] + "\n" + key[1].toUpperCase() + ": " + data[i][key[1]] + "\n" + key[2].toUpperCase() + ": " + data[i][key[2]] + "\n\n";
                       bot.sendMessage(from, answer);
                   }
               } else if (type.length == 2 && type[1].type == "rss"){
                 data = (JSON.parse(body)).answers[0].data;
                 columns = type[1];
                 key = Object.keys(columns);
                 for(i = 0; i< 4; i++){
                     if(i == 0){
                         answer = (JSON.parse(body)).answers[0].actions[0].expression;
                         bot.sendMessage(from, answer);
                     } else {
                         answer = "";
                         answer = key[1].toUpperCase() + ": " + data[i][key[1]] + "\n" + key[2].toUpperCase() + ": " + data[i][key[2]] + "\n" + key[3].toUpperCase() + ": " + data[i][key[3]] + "\n\n";
                         bot.sendMessage(from, answer);
                     }
                 }
               } else {
                   answer = "Oops looks like SUSI is taking break try to contact later.";
                   bot.sendMessage(from, answer);
               }
       });
    });
    
    app.listen(app.get('port'));
    
  8. Enter your email in above code.Now, we have to deploy the above-written code onto Heroku, but first, we will make a Github repository and push the files to Github as we will use Github to deploy our code.
    In command line change current directory to folder we created above and  write

    git init
    git add .
    git commit -m”initial”
    git remote add origin <URL for remote repository>
    git remote -v
    git push -u origin master

    You will get URL for the remote repository by making a repository on your Github and copying this link of your repository.

  9. Now we have to deploy this Github repository to Heroku to get URL.
  10. If you don’t have an account on Heroku sign up here https://www.heroku.com/ else just sign in and create a new app.
  11. Deploy your repository onto Heroku from deploy option and choosing Github as a deployment method.
  12. Select automatic deployment so that when you make any changes in the Github repository, they are automatically deployed to heroku.

You have successfully made SUSI Hangout bot. Try massaging it from your other account on https://hangouts.google.com

Resources

Hangouts bot in python: https://github.com/hangoutsbot/hangoutsbot

How to Deploy Node js App to Google Container Engine Using Kubernetes

There are many ways to host node js apps. A popular way is to host your app on Heroku. We can also deploy our app to Google cloud platform on container engine using Kubernetes. In this blog, we will learn how to deploy node js app on container engine with kubernetes. There are many resources on the web but we will use YAML files to create a deployment and to build docker image we will not use Google container registry (GCR) as it will cost us more for the deployment. To deploy we will start by creating an account on Google cloud and you can get a free tier of Google cloud platform worth 300$ for 12 months. After creating account create a project with any name of your choice. Enable Google cloud shell from an icon on right top.

We will also need a docker image of our app for deployment. To create a docker image first create an account on https://www.docker.com and create a repository with any name on it. Now, we will add docker file into our repository so that we can build docker image. Dockerfile will contain this code:

FROM node:boron
# Create app directory
RUN mkdir -p /usr/src/app
WORKDIR /usr/src/app
# Install app dependencies
COPY package.json /usr/src/app
RUN npm install
# Bundle app source
COPY . /usr/src/app
EXPOSE 8080
CMD [ "npm", "start" ]

You can see an example of docker file in SUSI telegram repository. After pushing docker file to your repository we will now build docker image of the app. In Google cloud shell clone, your repository with git clone {your-repository-link here }and change your current directory to the cloned app. We will use –no-cache -t arguments as described above it will be better for building docker image and it will use fewer resources. Run these two commands to build docker image and pushing it to your docker hub.

docker build --no-cache -t {your-docker-username-here}/{repository-name-on-docker here} .

docker push {your-docker-username-here}/{repository-name-on-docker here}


We have successfully created docker image for our app. Now we will deploy our app to container engine using this image. To deploy it we will use configuration files. Add a yaml folder in your repository and we will add four files into it now. In the first file, we will specify the namespace and name it as 00-namespace.yml It will contain following code:

apiVersion: v1
kind: Namespace
metadata:
 name: web

In second file we will configure our namespace that we specified and name it as configmap.yml It will contain following code:

apiVersion: v1
metadata:
 name:{name-of-your-deployment-here}
 namespace: web
kind: ConfigMap

In third file, we will define our deployment and name it as deployment.yml It will contain following code:

kind: Deployment
apiVersion: apps/v1beta1
metadata:
 name: {name-of-your-deployment-here}
 namespace: web
spec:
 replicas: 1
 template:
   metadata:
     labels:
       app: {name-of-your-deployment-here}
   spec:
     containers:
     - name: {name-of-your-deployment-here}
       image: {your-docker-username-here}/{repository-name-on-docker here}:latest
       ports:
       - containerPort: 8080
         protocol: TCP
       envFrom:
       - configMapRef:
           name: {name-of-your-deployment-here}
     restartPolicy: Always

In fourth file, we will define service for our deployment and name it as service.yml It will contain following code:

kind: Service
apiVersion: v1
metadata:
 name: {name-of-your-deployment-here}
 namespace: web
spec:
 ports:
 - port: 8080
   protocol: TCP
   targetPort: 8080
 selector:
   app: {name-of-your-deployment-here}
 type: LoadBalancer

After adding these files to repository we will now deploy our app to a cluster on container engine. Go to Google cloud shell and run the following commands:

gcloud config set compute/zone us-central1-b

This will set zone for our cluster.

gcloud container clusters create {name-your-cluster-here}

Now update in your repository with git pull as we have added new files to it. Run the following command to make your deployment and to see it:

kubectl create -R -f ./yamls

This will create our deployment.

kubectl get services --namespace=web


With above command, you will get external IP for your app and open that IP in your browser with the port. You will see your app.

kubectl get deployments --namespace=web

Run this command if available is 1 then it means your deployment is running the file.

You have successfully deployed your app to container engine using kubernetes.

Resources

Tutorial on Google cloud: https://cloud.google.com/container-engine/docs/tutorials/hello-node
Tutorial by Jatin Shridhar: https://www.sitepoint.com/kubernetes-deploy-node-js-docker-app/

Enhancing SUSI Line Bot UI by Showing Carousels and Location Map

A good UI primarily focuses on attracting large numbers of users and any good UI designer aims to achieve user satisfaction with a user-friendly design. In this blog, we will learn how to show carousels and location map in SUSI line bot to make UI better and easy to use. We can show web search result from SUSI in form of text responses in line bot but it doesn’t follow design rule as it is not a good approach to show more text in constricted space. Users deem such a layout as less attractive. In SUSI webchat, location is returned with a map which looks more promising to users as illustrated below:

Web search is returned as carousels and is viewable as:

We can implement web search in line by sending an array of text responses. We can do this with the code below:

for (var i = 0; i < 5; i++) {
   msg[i] = "";
   msg[i] = {
       type: 'text',
       text: 'text to be sent here'
   }
}
return client.replyMessage(event.replyToken, msg);

If we send web search using text response it looks messy, a user will not like it that much as it is difficult for a user to read and understand a lot of text in one place. You can see it in the screenshot below:

To make it better looking we will implement carousels for web search in SUSI line bot. Carousels are tiles that can be scrolled horizontally to show rich content. We can implement carousels using this code:

for (var i = 1; i < 4; i++) {
   title = 'title of carousel';
   query = title;
   msg = 'description of carousel here';
   link = 'link to be opened here';
   if (title.length >= 40) {
       title = title.substring(0, 36);
       title = title + "...";
   }
   if (msg.length >= 60) {
       msg = msg.substring(0, 56);
       msg = msg + "...";
   }
   carousel[i] = {
       "title": title,
       "text": msg,
       "actions": [{
               "type": "uri",
               "label": "View detail",
               "uri": link
           },
           {
               "type": "message",
               "label": "Ask SUSI again",
               "text": query
           }
       ]
   };
}

In above code, we are checking the length of title and description because line API has a limit for the title up to 40 characters and description up to 60 characters. If limit exceeds we then trim the title or description accordingly and use it. Next, we assign title, description, and link to be opened in action to carousel so that we can use it in below code.

const answer = [{
       type: 'text',
       text: ans
   },
   {
       "type": "template",
       "altText": "this is a carousel template",
       "template": {
           "type": "carousel",
           "columns": [
               carousel[1],
               carousel[2],
               carousel[3]
           ]
       }
   }
]
return client.replyMessage(event.replyToken, answer);

Above code shows an array names answer in which we have added carousels that we have created in last code. After implementing this web search will look like this:

This UI looks neat and easy to read and users will like this. Ask SUSI again will send the title of the carousel to SUSI. To show location map on SUSI line bot just like it is shown on SUSI webchat we will follow this code:

const answer = [{
       type: 'text',
       text: ans
   },
   {
       "type": "location",
       "title": "name of the place here",
       "address": address,
       "latitude": latitude of location here,
       "longitude": longitude of location here
   }
]
return client.replyMessage(event.replyToken, answer);

We will send a location type message which will include latitude and longitude of the location so that Line bot can show location using map. After implementing location type response it will look like this:

On clicking on this location it will open a map inside line app on which we will see a pointer pointing at the location that we have provided.

If you want to learn more about line messaging API refer to this https://devdocs.line.me/en/#messaging-api

Resources
https://devdocs.line.me/en/#messaging-api

Implementing Rich Responses in SUSI Action on Google Assistant

Google Assistant is a personal assistant. This tutorial will tell you how to make a SUSI action on Google, which can only respond to text messages. However, we also need rich responses such as table and rss responses from SUSI API. We can implement following types of rich responses:

  • List
  • Carousel
  • Suggestion Chip


List:
A list will give the user multiple items arranged vertically. In SUSI webchat table type responses are handled with a list and it looks like this:

Now in order to show to list from SUSI Action on Google, we will use first key (i.e Recipe Name in above screenshot) as a title for each item in the list and rest of keys as a description for that item. For building we will use the following code:

assistant.askWithList(assistant.buildRichResponse()
   .addSimpleResponse('Any text you want to send before list'),
   // Build a list
   assistant.buildList(‘Title of the list here’)
   // First item in list
   .addItems(list[1])
   // Second item in list
   .addItems(list[2])
   // Third item in carousel
   .addItems(list[3])
);

In .addItems we will add the object after populating it from data that we will get from SUSI API and we will populate it with following code:

for (var i = 0; i < metadata.count; i++) {
   list[i] = assistant.buildOptionItem('ID for item', ['keyword','keyword','keyword'])
       .setTitle('title of your item in the list here')
       .setDescription('description of item in list')
}

A list should have at least two items in it. List title and descriptions are optional and title of the item in the list is compulsory. We can also set image for list items in following way.

.setImage('link for the image here', 'Image alternate text')

Setting image in the list is optional and image size will be 48×48 pixels.

Carousel:
Carousel messages are cards that we can scroll horizontally. In SUSI webchat RSS type responses are handled with the list and it looks like this:

In order to show carousel from SUSI Action on Google we will use the following code:

assistant.askWithCarousel(assistant.buildRichResponse()
   .addSimpleResponse('Any text you want to send before carousel'),
   // Build a list
   assistant.buildCarousel()
   // First item in carousel
   .addItems(list[1])
   // Second item in carousel
   .addItems(list[2])
   // Third item in carousel
   .addItems(list[3])
);

Again we will populate .addItems() just like we did for the list. Carousel should have at least two tiles. Just like in the list, the title is compulsory and description and image are optional. Image size in the carousel is 128dp x 232dp. You can set image same as we have set image in the list above.

Suggestion Chip:
Suggestion chip is used to add a hint to a response i.e if you want to give the user a list of suggested responses, we can use suggestion chip. To add suggestion chip to any response you just have to add .addSuggestions([Hint1, Hint2, Hint3, Hint4]) to your response code after .addSimpleResponse()  

See how SUSI Action on Google replies to table and RSS type responses in this video https://youtu.be/rjw-Vg4X57g and If you want to learn more about Actions on Google refer to https://developers.google.com/actions/components/

Resources:
Actions on Google: https://developers.google.com/actions/apiai/

How to integrate SUSI AI in Google Assistant

Google Assistant is a personal assistant by Google. Google Assistant can interact with other applications. In fact, we can integrate our own applications with Google Assistant using Actions on Google. In order to integrate SUSI action with Google Assistant we will follow these steps:

  1. Install Node.js from the link below on your computer if you haven’t installed it already. https://nodejs.org/en/
  2. Create a folder with any name and open a shell and change your current directory to the new folder you created. 
  3. Type npm init in the shell and enter details like name, version and entry point. 
  4. Create a file with the same name that you wrote in entry point in above-given step. i.e index.js and it should be in the same folder you created. 
  5. Type following commands in command line  npm install –save actions-on-google. After actions-on-google is installed, type npm install –save express.  On success, type npm install –save request, and at last type npm install –save body-parser. When all the modules are installed check your package.json file; therein you’ll see the modules in the dependencies portion.

    Your package.json file should look like this

    {
     "name": "susi_google",
     "version": "1.0.0",
     "description": "susi on google",
     "main": "app.js",
     "scripts": {
       "start": "node app.js"
     },
     "author": "",
     "license": "ISC",
     "dependencies": {
       "actions-on-google": "^1.1.1",
       "body-parser": "^1.17.2",
       "express": "^4.15.3",
       "request": "^2.81.0"
     }
    }
    
  6. Copy following code into file you created i.e index.js
    // Enable debugging
    process.env.DEBUG = 'actions-on-google:*';
    
    var Assistant = require('actions-on-google').ApiAiApp;
    var express = require('express');
    var bodyParser = require('body-parser');
    
    //defining app and port
    var app = express();
    app.set('port', (process.env.PORT || 8080));
    app.use(bodyParser.json());
    
    const SUSI_INTENT = 'name-of-action-you defined-in-your-intent';
    
    app.post('/webhook', function (request, response) {
     //console.log('headers: ' + JSON.stringify(request.headers));
     //console.log('body: ' + JSON.stringify(request.body));
    
     const assistant = new Assistant({request: request, response: response});
    
     function responseHandler (app) {
       // intent contains the name of the intent you defined in the Actions area of API.AI
       let intent = assistant.getIntent();
       switch (intent) {
         case SUSI_INTENT:
           var query = assistant.getRawInput(SUSI_INTENT);
           console.log(query);
    
           var options = {
           method: 'GET',
           url: 'http://api.asksusi.com/susi/chat.json',
           qs: {
               timezoneOffset: '-330',
               q: query
             }
           };
    
           var request = require('request');
           request(options, function(error, response, body) {
           if (error) throw new Error(error);
    
           var ans = (JSON.parse(body)).answers[0].actions[0].expression;
           assistant.ask(ans);
    
           });
           break;
    
       }
     }
     assistant.handleRequest(responseHandler);
    });
    
    // For starting the server
    var server = app.listen(app.get('port'), function () {
     console.log('App listening on port %s', server.address().port);
    });
    
  7. Now we will make a project on developer’s console of Actions on Google and after that, you will set up action on your project using API.AI
  8. Above step will open API.AI console create an agent there for the project you created above. 
  9. Now we have an agent. In order to create SUSI action on Google, we will define an “intent” from options in the left menu on API.AI, but as we have to receive responses from SUSI API so we have to set up webhook first.

     
  10. See “fulfillment” option in the left menu. Open to enable it and to enter the URL. We have to deploy the above-written code onto Heroku, but first, make a Github repository and push the files in the folder we created above.

    In command line change current directory to folder we created above and  write
    git init
    git add .
    git commit -m”initial”
    git remote add origin <URL for remote repository>
    git remote -v
    git push -u origin master 

    You will get URL for the remote repository by making a repository on your Github and copying this link of your repository.


  11. Now we have to deploy this Github repository to Heroku to get URL. 
  12. If you don’t have an account on Heroku sign up here https://www.heroku.com/ else just sign in and create a new app. 
  13. Deploy your repository onto Heroku from deploy option and choosing GitHub as a deployment method.
  14. Select automatic deployment so that when you make any changes in the Github repository, they are automatically deployed to Heroku.
  15. Open your app from an option on the top right and copy the link of your Heroku app and append it with /webhook and enter this URL into fulfillment URL.

    https://{Your_App_Name}.herokuapp.com/webhook
     
  16. After setting up webhook we will make an intent on API.AI, which will get what user is asking from SUSI. To create an intent, select “intent” from the left menu and create an intent with the information given in screenshot below and save your intent.

     
  17. After creating the intent, your agent is ready. You just have to integrate your agent with Actions on Google. Turn on its integration from the “integration” option in the left menu. 
  18. Your SUSI action on Google Assistant is ready now. To test it click on actions on Google in integration menu and choose “test” option.

  19. You can only test it with the same email you have used for creating the project in step 7. To test it on Google Assistant follow this demo video https://youtu.be/wHwsZOCKaYY

If you want to learn more about action on Google with API.AI refer to this link https://developers.google.com/actions/apiai/

Resources
Actions on Google: https://developers.google.com/actions/apiai/

How to Receive Picture, Video and Link Type Responses from SUSI kik Bot

In this blog, I will explain how to receive picture, video and link messages from SUSI Kik bot. To do so we have to implement these types in our code.

We will start off by making SUSI kik bot first. Follow this tutorial to make SUSI Kik bot. Next, we will implement picture, video, and link type messages from our bot. To implement these message types we need chatID and username of a user who has sent the message to our bot. To get the username of user we will use the following code:

bot.onTextMessage((message) => {
    var chartID = message.chatId;
    var Username;
    bot.getUserProfile(message.from)
        .then((user) => {
            message.reply(`Hey ${user.username}!`);
            Username = user.username;
        });

Now as we have got the chatID and username we will use these and post a request to https://api.kik.com/v1/message to send pictures, video, and link type messages. To post these requests use below code.

1) Picture:

To send picture type message we will define the type to picture,  URL of the picture to be sent to user and username of the user that we got from the code above.

request.post({
   url: "https://api.kik.com/v1/message",
   auth: {
       user: 'your-bot-name',
       pass: 'your-api-key'
   },
   json: {
       "messages": [
       {
           'chatId': chatID,
           'type': 'picture',
           'to': Username,
           'picUrl': answer
       }
       ]
   }
});

2) Video:

To send video type message we will define the type to video, URL of the video to be sent to the user and username of the user that we got from the code above. In this request, we can also set extra attributes like mute and autoplay.

request.post({
   url: "https://api.kik.com/v1/message",
   auth: {
       user: 'your-bot-name',
       pass: 'your-api-key'
   },
   json: {
     "messages": [
       {
           "chatId": "chatID",
           "type": "video",
           "to": "laura",
           "videoUrl": "http://example.kik.com/video.mp4",
           "muted": true,
           "autoplay": true,
           "attribution": "camera"
       }
   ]
   }
});

3) Link:
To send link type message to the user we will define the type of link, URL to be sent to the user and username of the user that we got from the code above.

request.post({
   url: "https://api.kik.com/v1/message",
   auth: {
       user: 'your-bot-name',
       pass: 'your-api-key'
   },
   json: {
     "messages": [
       {
           "chatId": "chatID",
           "type": "link",
           "to": "laura",
           "url": "url-to-send"
       }
   ]
   }
});

If you want to learn more about kik API refer to https://dev.kik.com/#/docs/messaging

Resources
Kik API reference: https://dev.kik.com/#/docs/messaging