Can I run a sub 5 minute mile

A couple of times I’ve thought about trying to get my best 1 mile below 5 minutes but never dedicated time to it, I’ve always moved on to doing some other training.

The other evening I gave it a go to see what I’m currently capable of. My best is currently 5:27.8 and this test came in at 5:28.8.

Encouraged by this I think I’m going to give this a go over the coming months and see if I can get it under 5 minutes or if not how close I can get.

Adapt Learning Hello World Plugin

This tutorial will not go into depth about some of the code used. The idea is to give an overview of creating a basic Adapt plugin that will output some static text.

The plugin code can be downloaded from gitHub.

The Adapt framework comes with a good selection of components to help you build your e-learning course, then added to this are the contributed plugins. But what if there isn’t quite the thing you need? The good news is that like all good Open Source software you can just make your own.

In this tutorial I’m going to make a very simple bare bones plugin that will allow us to add a component that simply says Hello World.

Before you begin you will need to install the Adapt CLI and Bower.

To give us somewhere to test our plugin we will create a new Adapt course. In terminal run the following command

adapt create course

Accept all of the defaults except the name which we will set to plugin-development.

Once the framework has been downloaded follow the instructions to build and run the course.

cd plugin-development
grunt build
grunt server

You will now have a course running at http://localhost:9001

From within the plugin-development directory navigate to src/extensions and create a new directory called adapt-helloWorld which will contain our plugin.

In a terminal window cd into the adapt-helloWorld directory and run bower init

Name adapt-helloWorld

Description An example Adapt plugin to say Hello World

Main file js/adapt-helloWorld.js

Keywords adapt-plugin,adapt-component

Authors Accept default

License Accept default

Homepage Accept default

Set currently installed components as dependencies No

Add commonly ignored files to ignore list? Yes

Would you like to mark this package as private which prevents it from being accidentally published to the registry? Yes

Looks good? Yes

We now have a bower.json file inside the adapt-helloWorld directory. In addition to the elements Bower has created for us we need to add some extra ones for this to be a valid Adapt component.

Open up bower.json in a text editor and add a comma after the closing square bracket of the ignore array so it looks like this

  "ignore": [
    "**/.*",
    "node_modules",
    "bower_components",
    "src/plugins",
    "test",
    "tests"
  ],
}

We will be adding in four new elements in between the comma we added and the closing curly bracket to ensure we have valid JSON.

Add the following

  "version": "0.0.1",
  "framework": ">=5.0",
  "component": "helloWorld",
  "displayName": "Hello World"

The end of bower.json will now look like this

  "ignore": [
    "**/.*",
    "node_modules",
    "bower_components",
    "src/plugins",
    "test",
    "tests"
  ],
  "version": "0.0.1",
  "framework": ">=5.0",
  "component": "helloWorld",
  "displayName": "Hello World"
}

Adapt follows the Asynchronous module definition (AMD) specification and utilises RequireJS and Backbone for plugin architecture.

Add the following to js/adapt-helloWorld.js

define([
    'core/js/adapt',
    'core/js/views/componentView',
    'core/js/models/componentModel'
], function(Adapt, ComponentView, ComponentModel) {

var HelloWorldView = ComponentView.extend({
    postRender: function() {
        this.setReadyStatus();
        this.setupInviewCompletion();
    }
});

    
    var HelloWorldModel = ComponentModel.extend({
        // Implement your component model
    });

    return Adapt.register('helloWorld', {
        model: HelloWorldModel,
        view: HelloWorldView
    });

});

The first 5 lines use RequireJS to include the module we need to create our plugin.

We then create two variables for the view and the model that extend their respective component bases.

Inside ComponentView.extend we need to add a postRender method that calls two Adapt functions. Without these two calls the course will not load.

The last part of the file registers our plugin with Adapt, passing the view and model variables to it.

We’ll now create a basic template file to add some output.

In the adapt-helloWorld directory create a new directory called templates and inside that create a file called helloWorld.hbs

This is a Handlebars template file which is the templating engine used throughout Adapt. https://handlebarsjs.com/

Add the following to helloWorld.hbs

<div class="component__inner helloWorld__inner">
    {{> component this}}
    <h1>Hello World</h1>
</div>

The wrapper div follows some naming conventions used in other plugin template files.

The second line uses a Handlebars partials, you can read more about those on the official Handlebars site. https://handlebarsjs.com/guide/#partials

Then for good measure we say Hello World in a H1, as it’s very important.

The last thing we need to do to make this a valid Adapt component is to add a properties.schema file. According to the Adapt wiki “properties.schema is a JSON file that is provided by a plug-in. It is the point of contact between the authoring tool, the plug-in, and the course author who configures it.”

You can read more about it’s uses at https://github.com/adaptlearning/adapt_authoring/wiki/Properties-Schema

As we are only making a simple plugin our schema file will also be quite simple. In the adapt-helloWorld directory create the properties.schema file and add the following to it.

{
  "type":"object",
  "$schema": "http://json-schema.org/draft-04/schema",
  "id": "http://jsonschema.net",
  "$ref": "http://localhost/plugins/content/component/model.schema",
  "properties":{
    "_supportedLayout": {
      "type": "string",
      "required": true,
      "enum": ["full-width", "half-width", "both"],
      "default": "both",
      "editorOnly": true
    }
  }
}

The main section to note here is the properties _supportedLayout which includes the three options, inside the enum element, that Adapt uses to layout components.

We are now at the point where we can see our component in action. We will add our component to an existing block.

In your text editor open src/course/en/components.json

After the opening square bracket add

{
    "_id":"c-04",
    "_parentId":"b-05",
    "_type":"component",
    "_component":"helloWorld",
    "_classes":""
},

This will add the helloWorld component to the first block.

If we now run the build and server command again

grunt build
grunt server

And navigate to the Presentation Components page you will see a nice Hello World.

The plugin can also be used in the Adapt Authoring Tool. All we need to do is create a zip file of the adapt-helloWorld directory and then in the Authoring Tool navigate to Plugin Management there will be a green button in the left minute Upload Plugin.

That concludes the introduction to the building blocks of an Adapt plugin.

Adapt Authoring Tool Hello World Part 4: Adding assessment results

Now that we have a course setup and the user can answer some questions and get feedback we’ll add an assessment result to let them now how they did.

In the Adapt Authoring Tool go into our Hello World course and then choose Manage extensions from the left menu.

In the Manage extensions page click the green Add button to the right of Assessment. You should now have two enabled extensions

  1. Assessment
  2. Tutor

Now return to the Course structure and double click on the Take the test and say “Hello World” page.

In the article titled Hello World Test click the cog icon and choose Edit. Scroll down to the section titled Extensions and click on Assessment to expand it.

Update the fields with the following

Enabled: checked

Assessment Name: Hello World Assessment

Pass mark: 50

Show Feedback: checked

Show Marking: checked

Now click the green Save button in the left hand menu which will return us to the Page structure page.

Click Add article at the bottom of the main content area. Change the Article title to Assessment Results and also click the Unlink from title icon next to Display Title. Delete the contents of the Display Title field as we do not want it appearing for the users. Click the green Save button on the left hand menu.

Repeat these steps for the Assessment Block. After that your page should look like the following image.

Add a component to the Assessment block. From the list choose Assessment Results and Add full.

In the Assessment Results Component update the following fields

Title: Assessment Results

Set completion on: pass

Assessment Name: Hello World Assessment

Feedback Text:

{{{feedback}}}

You got a score {{{score}}} out of {{{maxScore}}}

The Feedback Text contains Handlebars syntax that outputs the feedback and a dynamic score that the user obtained.

Still in the Component edit settings we need to add three bands to determine the pass scores.

Under Bands click the blue Add button.

For the first band leave the score at 0 and set the Feedback to

You failed

Then click the blue Ok button

Add two more bands with the following settings

Score: 1
Feedback: You passed with half of the questions correct

Score: 2
Feedback: Well done you said Hello World

You should now have three bands as shown in the below image

Click the green Save button in the left hand menu.

Back on the Page Structure page click the green Preview course button in the left menu. Answer the two questions, try a combination of both correct, neither correct and only one correct and you will see the different fail or pass scores and feedback.

We have now completed a course using the Adapt Authoring Tool.

Adapt Authoring Tool Hello World Part 3: Adding questions

If you’ve been following on from the previous post you will be on the Page Structure page, if not then from the dashboard double click on the Hello World course, then from the Course structure page double click on the Take the test and say “Hello World” page.

You’ll now be back on the Course structure page. Double click on the page box which is now labelled Take the test and say “Hello World!”

We are now on the Page structure page where we can add Articles, Blocks and Components. You can read more about Adapt’s ABC structure on Adapt Learning Blog.

To give ourselves a blank canvas we will first remove the default article, which will also remove its child block and component. Click the bin icon to the right of New Article Title and then click Yes, I’m sure in the confirmation dialog.

Now we can add in our articles, blocks and components.

Click Add article and then double click New Article Title

Change the title value to Hello World Test

Change the Instruction text to Answer all the questions

And then click the green Save button in the top left.

Double click New Block Title

Change the title to Question 1

And then click the green Save button in the top left.

Click on Add component and scroll to the bottom of the list that appears and click on Text Input. You may need to scroll the list down a bit more to see the options that appear for adding the Text Input. From those options choose Add full.

Click the cog icon in the top left of the Text Input component that will now be inside the Question 1 block and click Edit.

Change the Title to What will be our greeting?

Under Input Items click the Add button. For answers enter Hello and then click the blue OK button.

Change attempts to 2 so the user can have another attempt if they get it wrong the first time.

Tick the Allow ‘any case’ answers input so the user can enter hello or Hello.

Feedback

We can add some feedback for our users to help them out during their learning. Update the following fields.

Correct

You are correct we will say Hello

Incorrect

That is not our greeting

Incorrect Not Final

That is not our greeting, please try again

Leave everything else as the defaults and click the green Save button in the top left.

If you now click the green Preview course button and then the View button to take you to the questions you can try adding correct and incorrect answers.

Where’s the feedback?

If you enter an incorrect answer and then click Show feedback you will notice that nothing happens. To fix this we need to enable an extension.

Back in the Authoring Tool select Manage extensions form the left hand menu. Under Available extensions find the Tutor extension and click the green Add button beside it.

 This will now appear in the Enabled extensions at the top of the page.

If you read the description of the Tutor extension you will see it does exactly what we are after “An extension which provides a basic feedback overlay for question components”.

If you now return to our course, preview it and enter an incorrect answer you will see our feedback now appears.

To finish up we will add one more component to utilise a different question format.

Multiple choice

Return to the Page structure page and click on Add block below our Text input.

As we did earlier we will change the block title, this time to Question 2

Click Add component and choose Multiple Choice Question from the list and Add full.

Click the cog icon to edit the Multiple Choice and update the following fields

Title

What are we greeting?

Answers

Sun

Moon

World – Mark this as a correct answer, see the image below

Stars

Sea

Attempts

2

Randomise answers

TRUE

Correct feedback

You are correct we are greeting the world

Incorrect feedback

That is not what we are greeting

Incorrect Not Final feedback

That is not what we are greeting, please try again

If you now preview the course you will see our second question in the format of a multiple choice list.

Now we have a couple of questions for our users the next post will cover letting our user know how they did with by adding an assessment.

Adapt Authoring Tool Hello World Part 2: Course creation and introductory text

As I mentioned in the overview page I won’t be covering the installation of the Adapt Authoring Tool as the documentation covers it thoroughly.

With the Authoring Tool started navigate to the Dashboard which will probably be at http://localhost:5000 if you have followed the installation defaults.

If this is the first time starting it up the Dashboard will be blank.

Click the green Add new course button in the top left.

This takes you to the General settings for the course. Set the following values

Title

Hello World

Subtitle

Welcome to the Adapt Authoring Tool Hello World elearning course.

Body

Why are we saying Hello to the World?

Hello World! Is often the simplest tutorial when learning to create computer programs. Just because we’re using a Graphical User Interface (GUI) to create this course doesn’t mean we can’t stick with convention.

Everything else we will leave as the defaults.

Click the green Save button in the top left which will take you to the Course structure page.

On the Course structure page you will see a single page titled New Menu/Page Title. Click on the cog icon in the top left of the New Menu/Page Title box and select Edit.

Set the title to 

Take the test and say “Hello World”

Then click the green Save button in the top left.

We are now in a position to preview our course so far. Click the green Preview course button in the top left. This will open up a new tab with our course menu page.

In the next post we will look at adding some questions to our course.

Adapt Authoring Tool Hello World Part 1: Storyboard

Like most development that requires logic, whether this is created through code or a user interface, it’s best to have a plan of what you will be producing rather than diving in and ending up with a result that is hard to maintain.

Even though this elearning course is fairly simple we’ll create a storyboard to refer to throughout its creation.

For this I have used Pages and exported it as a PDF. You can download the PDF version and the other assets used in this tutorial as a zip file.

I’ve chosen to keep the storyboard simple here by just using a text document but if you have a Google there are a lot of very good storyboard authoring tools available.

Now we have a storyboard to follow the next post will cover creating the course with introductory text.

Adapt Authoring Tool Hello World

I’ve created a small series of blog posts showing how you can create a simple Adapt elearning course using the Adapt Authoring Tool. These posts assume you have already installed the Authoring Tool. If you have not then please follow the very comprehensive installation instructions.

To start off we will create a storyboard that will guide our development of the course.

Further posts will cover

Arduino Indoor Outdoor Temperatures

There has been many times that I’ve left the house and noticed the difference in temperature between inside and outside my home. I thought a fun project would be to combine an Arduino reading the inside temperature and the outside temperature.

I had a couple ideas on how to do this. The first involved two Arduinos, one inside and one outside, both using TMP36 sensors to monitor the temperatures. The second was a single Arduino inside that recorded the temperature using the sensor and then using the Open Weather Map API to gain the outside temperature.

Both ideas had some pros and cons but I went for option two. It may not be as accurate as having an outside sensor but I think the data reported by the API is good enough that I could see the difference between inside and outside.

The code for this is available in a GitHub repo.

Parts used

Arduino Uno WiFi

TMP36 Sensor

Jumper wires

You’ll also need

A web and database server running PHP and MySQL. In the code used this is an internal server that does not accept requests from outside of the network. If you are going to use a server open to traffic outside of your network you will need to add extra security measures to ensure that unauthorised requests cannot add data.

Setup

Database

Create a database and then run the SQL that is in the data.sql file. This will create a table that stores the indoor and outdoor temperatures as well as a unique id and a created at date and time.

Data receive page

The first part of the script includes the Composer autoload file, the settings file and then uses Guzzle’s HTTP client that will be used to send a get request to Open Weather Map API.

require __DIR__ . '/vendor/autoload.php';

require './settings.inc';

use GuzzleHttp\Client;

There is then the basic security check for the key parameter in the query string.

if (isset($_GET['key']) && $_GET['key'] === BASIC_KEY) {

We create a connection to the database or output the error message and exit if it was not successful.

  try {
    $db = new PDO("mysql:host=" . DB_HOST . ";dbname=" . DB_NAME, DB_USER, DB_PASS);
  } catch (PDOException $e) {
    echo $e->getMessage();
    exit;
  }

The next section of code creates a new Guzzle HTTP client with the base uri set to the Open Weather Map API.

We then set the query string parameters to send and perform a GET request.

The response body is first converted to a string and then JSON decoded for easier use with PHP. This decoded response is a PHP object.

We now access the temperature returned by the API call and use this as our outdoor temperature reading.

$client = new GuzzleHttp\Client(['base_uri' => 'api.openweathermap.org/']);

  $params = [
    'query' => [
      'id' => CITY_ID,
      'appid' => API_KEY,
      'units' => 'metric',
    ],
  ];

  $request = $client->request('GET', 'data/2.5/weather', $params);

  $response = json_decode((string)$request->getBody());

  $outdoorTemperature = $response->main->temp;

The last part of the logic inserts a row into the database. To ensure that the temperature recordings are in the correct format we cast them as floats and user the number_format function to round to two decimal places.

  $data = [
    'indoor_temperature' => number_format((float)$_GET['temp'], 2),
    'outdoor_temperature' => $outdoorTemperature,
  ];

  $sql = "INSERT INTO data (indoor_temperature, outdoor_temperature) VALUES (:indoor_temperature, :outdoor_temperature)";

  $stmt= $db->prepare($sql);

  $stmt->execute($data);

After inserting the row into the database we return a 201 success response code to show that the row has been created.

  // Return a 201 created response.
  header('HTTP/1.1 201 Unauthorized');
  exit;

The last part in the else statement returns a not authorised response header if the query string does not contain the key parameter or if the key parameter is incorrect.

  header('HTTP/1.1 401 Unauthorized');
  exit;

Arduino sketch

The first portion of code includes the library for the Arduino Uno WiFi, this allows us to use the Ciao library for sending HTTP requests. We then declare some constants that will be used when sending the request. You will need to replace the SERVER_ADDRESS and KEY to match those used on your web server for receiving the data. Finally we declare our TMP36 sensor input pin to zero.

#include <UnoWiFiDevEd.h>

#define CONNECTOR "rest"
#define SERVER_ADDRESS "YOUR_SERVER_ADDRESS"
#define METHOD "GET"
#define KEY "YOUR_KEY"

int temperaturePin = 0;

Inside the setup function we initialise the Ciao library ready for use.

void setup() {
  Ciao.begin();
}

Inside our loop function we first calculate a five minute interval as this is how often we want to be taking a recording. We then set the last sampled time to zero so we get a recording on the first time in the loop.

  const unsigned long fiveMinutes = 5 * 60 * 1000UL;
  static unsigned long lastSampleTime = 0 - fiveMinutes;

Next we get the number of milliseconds that have passed and check if five minutes has passed since the last recording. If it has then we add five minutes to our last sampled time ready for the next recording.

unsigned long now = millis();
  if (now - lastSampleTime >= fiveMinutes)
  {
    lastSampleTime += fiveMinutes;

Our next few lines of code take the recording from the sensor and convert it to degrees celsius.

    // Getting the voltage temperature reading from the sensor.
    int temperatureReading = analogRead(temperaturePin);
  
    // Converting that temperature reading to voltage, for 3.3v arduino use 3.3.
    float voltage = temperatureReading * 5.0;
    voltage /= 1024.0;
  
    // Temperature in degrees celsius.
    float temperatureC = (voltage - 0.5) * 100;  // Converting from 10 mv per degree wit 500 mV offset to degrees ((voltage - 500mV) times 100).

The last part of code builds up a URI that we send to the server using the Ciao library.

    // Build the GET request URI
    String uri = "/data.php?key=";
    uri += String(KEY);
    uri += "&temp=";
    uri += String(temperatureC);

    // Send the data to the webserver.
    CiaoData data = Ciao.write(CONNECTOR, SERVER_ADDRESS, uri);

Index page and chart

The last piece of code to look at is the index.php file for the web server. This draws a line chart using the indoor and outdoor temperatures.

We first include the settings file and then make a database connection.

require './settings.inc';

// Try to connect to the database.
try {
  $db = new PDO("mysql:host=" . DB_HOST . ";dbname=" . DB_NAME, DB_USER, DB_PASS);
} catch (PDOException $e) {
  echo $e->getMessage();
  exit;
}

The SQL query gets all of the recordings in the past 24 hours and orders them oldest to newest. We then add all of these results to an array that we will use later to output as JSON.

$query = $db->query("SELECT * FROM data WHERE created_at >= now() - INTERVAL 1 DAY ORDER BY created_at ASC;");

while($row = $query->fetch( PDO::FETCH_ASSOC )){
  $recordings[] = $row;
}

In the head section we set some basic styling for the chart.

  <style>

    body {
      font-family: sans-serif;
      color: #444;
    }

    .line {
      fill: none;
      stroke-width: 3;
    }

    .line__indoor {
      stroke: #ffab00;
    }

    .line__outdoor {
      stroke: #34e823;
    }

    .axis path,
    .axis line {
      fill: none;
      stroke: #000;
      shape-rendering: crispEdges;
    }

    .axis text {
      font-size: 10px;
    }

  </style>

The body has no content, just two script tags. The first tag includes the D3 library.

<script src="https://d3js.org/d3.v5.min.js"></script>

The second script tag has the logic for creating the chart.

We first create a variable to hold the JSON data that we created earlier.

    var recordings = <?php echo json_encode($recordings); ?>;

Then we set some variables for margins, width and height and append an SVG element to the body that will contain the chart.

    // Set variables for margins, width and height.
    var margin = {top: 50, right: 50, bottom: 50, left: 50},
        width = window.innerWidth - margin.left - margin.right,
        height = window.innerHeight - margin.top - margin.bottom;

    // Create an svg element and append it to the body element.
    var svg = d3.select('body').append("svg")
        .attr("width",  width + margin.left + margin.right)
        .attr("height", height + margin.top + margin.bottom)
        .append("g")
        .attr("transform", "translate(" + margin.left + "," + margin.top + ")");

The next section does some setup of a time parse in the format returned from our database and then an array of all of the temperatures so we can get the min and max values.

    var timeConv = d3.timeParse("%Y-%m-%d %H:%M:%S");

    var temperatureRange = [];

    // Create an array of all the temperatures so we can get the min and max values.
    recordings.map(function(recording) {
        temperatureRange.push(recording.indoor_temperature);
        temperatureRange.push(recording.outdoor_temperature);
    });

We then create scales for our X and Y axes using time for the X axis and a linear scale for the temperatures on the Y axis.

For the yScale domain I’ve subtracted 4 from the minimum and added 4 to the maximum so the chart had a bit of breathing room above and below the lines. We then append the axis to the chart.

    var xScale = d3.scaleTime().range([0,width]);
    var yScale = d3.scaleLinear().rangeRound([height, 0]);

    xScale.domain(d3.extent(recordings, function(d){
        return timeConv(d.created_at);
    }));

    yScale.domain([parseFloat(d3.min(temperatureRange)) - 4.00, parseFloat(d3.max(temperatureRange)) + 4]);

    // Create the axis.
    var yaxis = d3.axisLeft().scale(yScale);
    var xaxis = d3.axisBottom().scale(xScale);

    svg.append("g")
        .attr("class", "axis")
        .attr("transform", "translate(0," + height + ")")
        .call(xaxis);

    svg.append("g")
        .attr("class", "axis")
        .call(yaxis);

The last part of the code adds the two lines to the chart and gives them slightly different classes so we can colour the lines differently.

    // Create the indoor line.
    var indoorLine = d3.line()
        .x(function(d) {
            return xScale(timeConv(d.created_at));
        })
        .y(function(d) {
            return yScale(d.indoor_temperature);
        })
        .curve(d3.curveMonotoneX);

    svg.append("path")
        .data([recordings])
        .attr("class", "line line__indoor")
        .attr("d", indoorLine);

    // Create the outdoor line.
    var outdoorLine = d3.line()
        .x(function(d) {
            return xScale(timeConv(d.created_at));
        })
        .y(function(d) {
            return yScale(d.outdoor_temperature);
        })
        .curve(d3.curveMonotoneX);

    svg.append("path")
        .data([recordings])
        .attr("class", "line line__outdoor")
        .attr("d", outdoorLine);

Improving

There are a couple of things I’d like to do to improve this.

  1. Security. To allow the data to be sent to a public facing server some more security steps than a basic key should be used.
  2. Allow different timeframes on the chart, e.g. past X hours, days or weeks. For this I’d need to group the data as showing data for every 5 minutes of an hour over 7 days would clutter a chart.

When to use a custom search solution

This post also appears on the Headscape site.

Website search can often be a thorny subject. Expectations of search capabilities have been set very high by search engines. The default search offered by content management systems (CMSs) is often a bit basic by comparison. For example, the results are often not the most relevant to the search term used because the CMS is only offering a simple “does this page contain this word” method.

Our discovery work for the Competition Appeal Tribunal site revealed a specialised set of search requirements. When working with a CMS, I’m a firm believer that you go with the flow of its strong and weak points, and try not to fight it. With that philosophy in mind, my instinct was not to struggle to make native CMS search fit the requirements but rather to develop a custom solution for this site.

We opted for Elasticsearch, which is described as a “RESTful search and analytics engine”, combined with the very well maintained and documented Elasticsearch PHP library.

As soon as you put some data into Elasticsearch it does a good job of returning relevant results. But where it really excels is when you begin to fine tune it to your needs.

As an example, there is a field on the site that we needed to be able to perform full text searches and sorts. This can be accomplished by duplicating the field into two different “types” allowing one to have all of the full text search capabilities whilst the other is used for sorting.

On another project for US law firm Buckley Sandler (that is built on Drupal), the different content types and fields did not all have the same relevance in search results. By applying a “boost” to specific content types and fields we were able to deliver the most relevant results to users.  Whilst Drupal’s native search API does allow a boost to be applied to certain fields, using Elasticsearch we were able to boost specific content types, individual pages and taxonomy terms.

This level of customisation may not be required on your project, but if it is I highly recommend trying Elasticsearch as I’m confident it can meet your needs.

Chatbots, always available customer support or know nothings?

This post also appears on the Headscape site.

After reading Build Chatbots with PHP by Christoph Rumpel I started making some simple chatbots and quite quickly moved on to more complex interactions. It didn’t take long to get something basic up and running, which in turn, got me really excited about the possibilities.

But – there’s always a ‘but’ isn’t there – it also didn’t take long for the bots to fail to have answers, especially when I showed them to colleagues who didn’t know the precise phrases the bots were listening for.

To try and get over this I used Dialogflow for the backend as it has natural language parsing capabilities. It also has a very nice UI that will allow even non-technical users to build up conversations. After a short tutorial I found Dialogflow easy to use and very powerful for the little effort needed to start using it.

Research

Highlighted by others asking my bot questions it did not understand, it is essential that you do in-depth user research before you launch your bot. The last thing you want is to spend a lot of time and money only for people to never use the chatbot as they had a bad first experience.

Just like any web project, speaking to the people who will be interacting with your site / bot will show you interactions you can never have imagined by yourself.

Monitor

It’s highly likely that you run some analytics or monitoring code on your website to ensure users are moving through the site as expected. You should also be monitoring the chatbot’s interactions to see where users take conversations and if any of these lead to dead ends.

This could be in the form of capturing the sessions with a tool such as Full Story, or logging the conversations to a database that you can then analyse at a later date.

Learn

Machine learning is great but machines also need help as well. Whilst Dialogflow has a machine learning aspect to it there will more than likely be cases where a user asks a question that it cannot learn from. By spotting new forms of interaction early you can return to the research phase to see how others would phrase the same question and then feed these alternatives into the backend.

You may also find people are looking for specific areas of your site and your overall information architecture could do with some readjustment. Or better still, maybe people are coming to you looking for a service or product you do not yet offer but could do, leading to new lines of business.

Chatbots are an exciting development and give the potential to have a form of customer support that’s always on hand. But they are not something that can be set up and never looked at again, otherwise their lack of knowledge can leave users feeling frustrated and abandoning your site.