Subscribe

Share

Emerging Technologies

Building Complex Bot Responses with Ease

Learn to love the common response component and render complex and composite responses.

By Frank Nimphius

May/June 2018

The Oracle Intelligent Bots feature of Oracle Mobile Cloud Enterprise uses built-in components to render bot responses in a dialogue flow. Being component-based is an advantage Oracle Intelligent Bots has over its competitors, because it enables bot designers to easily build bot conversations with no code.

The common response (CR) component is a relatively new component in Oracle Intelligent Bots that can render arbitrary complex and composite responses, thus making it even less likely that you’ll need to write code.

About the Common Response Component

With the rise of chatbots, messaging channels such as Facebook Messenger, Slack, and WeChat have become the equivalent of operating systems in client/server computing. Also like operating systems, whereas all messaging channels do the same things, they differ in the UI they can render, the functionality they support, and the message structure—the payload—they require.

The CR component, like the Oracle Intelligent Bots list and text components, is built on top of a new channel-agnostic message model in Oracle Intelligent Bots that abstracts the channel specifics from component developers. For component developers, this new message model means that they can worry less and be more productive.

For more concept and reference information on the CR component, refer to the documentation.

About the Hands-On Instructions

Following the hands-on instructions in this article, you will learn how to use the CR component to build a visually rich select list. To follow the hands-on instructions, you need access to Oracle Mobile Cloud Enterprise, which is available as a free trial.

The starter bot for this article simulates a pizza ordering service. Users can order pizzas by typing, “I like to order a pizza” or “I like to order a pizza supreme.” In the latter case, because the type of pizza is included in the user sentence already, no pizza menu from which the user can select a pizza type is displayed. Similarly, a user may type, “can I see the menu?” for the bot to display a list of pizzas the user can order (as shown in Figure 1).

chatbots figure 1

Figure 1: Pizza menu

For many use cases, the list-style menu displayed by the starter bot may work just fine. For ordering pizza, however, it certainly will not work.

Users expect a richer UI that displays not only the name of a pizza but also a description and an image. In addition, instead of seeing all the pizzas on a single list, users may expect to be able to flip through the menu so they don’t need to scroll (as shown in Figure 2).

chatbots figure 2

Figure 2: CR component displaying the pizza menu

In the hands-on steps for this article, you are going to

  • Import the starter bot from the download for this article
  • Test the functionality of the starter bot to ensure that the importation and training of the bot were successful
  • Define the data for a richer pizza menu locally in a new context variable you create
  • Define a variable used for pagination and initialize it to 0
  • Add the CR component to replace the current list component
  • Run and test the changes

Importing the Starter Bot

The download for this article contains a bot in the starter folder that you need to import to your Oracle Intelligent Bots instance to complete the hands-on steps for this article. To import the bot, download the zip file containing the starter bot and then do the following:

  1. Open a browser, and access the Oracle Mobile Cloud Enterprise home page.
  2. Authenticate with the user credentials you defined when you provisioned the cloud service.
  3. Click the hamburger icon in the upper left to open the Oracle Mobile Cloud Enterprise menu.
  4. Click the Bots menu item (shown in Figure 3), which opens the Oracle Intelligent Bots dashboard in a separate browser window or tab.

    chatbots figure 3

    Figure 3: Oracle Mobile Cloud Enterprise with Oracle Intelligent Bots selected

  5. Click the Import Bot button in the upper right of the dashboard.
  6. In the opened dialog box, navigate to the location to which you extracted the downloaded zip file and open the starter folder.
  7. Select the OracleMagazineOnlinePizzaBot2.zip import file, and click Open.
  8. Close the upload confirmation dialog box, by clicking the X at the right side.
  9. If you already have existing bots defined in your environment, chances are good that you won’t immediately spot the downloaded bot. To find the bot, type OracleMagazine into the Filter field above the green New Bot + icon.
  10. Click the OracleMagazineOnlinePizzaBot2 bot to open it.
  11. Click Train (in the upper right of the screen). Before you click it, Train should show an exclamation point, because the bot is not yet trained after the download and import. After you click Train, a dialog box appears that confirms that the bot has been trained. Training the model is required for the bot to understand free text input.

Note: You cannot import two bots with the same name. If you need to import the starter bot more than once or if you share an Oracle Intelligent Bots instance, rename any previous imports of the starter bot before importing the new bot. You can rename a bot by opening it, clicking the Settings icon, renaming the bot, and exiting the bot.

Testing the Starter Bot

Now that you have imported the bot and trained it, review the starter bot’s functionality.

  1. To run the embedded bot tester, click the test icon (—the right arrow in the upper right of the screen).
  2. In the Message field, type Hi, and press the Enter key.
  3. After the pizza bot welcomes you, type I like to order a pizza and press the Enter key.
  4. Select a pizza from the displayed list.
  5. Choose a size to complete the order.
  6. Click the Reset button in the upper right corner of the tester to start over.
  7. Type I like to order a pizza supreme and press the Enter key. This time the pizza menu is skipped, and you are asked for the size of the pizza you want.
  8. Choose a size to complete the order.
  9. Click the Reset button for one last test.
  10. Type Can I see the menu?, and press the Enter key.
  11. Don’t choose an item from the menu, but instead type I like a pizza pepperoni.
  12. Select a size to finish the order.
  13. Click the test icon again to close the tester.

Defining the New Pizza Menu

The current implementation of the pizza menu reads the pizza types from values saved in the PizzaType custom entity. This, however, doesn’t allow images and additional descriptions as required in this article. So, instead, you will create a context variable to hold the pizza menu definition.

  1. Open the flow editing environment, by clicking the Flows icon () on the left.
  2. Create a new context variable—pizzaMenu: "string"—in the context | variables section of the dialogue flow, right below the cancelOrderYesNo variable. This variable will hold the menu content.
    pizzaMenu: "string"
    
  3. Next, click the + Components button to add a new component to the flow.
  4. In the opened dialog box, select the Variables category and then select Set variable.
  5. Toggle the Remove Comments switch, and click the Apply button.
  6. The previous step created a setVariable: state at the bottom of the editor. Rename the state initializeMenu:.
  7. The initializeMenu: state needs to be moved to the top of the dialogue flow, so copy the initializeMenu: state and its content to the clipboard (Ctrl + C) and then delete it from the dialogue flow.
  8. Navigate to the top of the dialogue flow, and paste the content of the clipboard right below the states: label.
  9. Click the Validate link in the upper right. If validation succeeds, you should see an alert with a green icon. If the icon is red, chances are that the indenting of the pasted content is not correct. In this case, ensure that the initializeMenu: state is indented with two blank spaces, as in the states: label (see Figure 4).

    chatbots figure 4

    Figure 4: System.SetVariable with value property alignment

  10. Set the variable property of the System.SetVariable component to reference the "pizzaMenu" context variable. The initializeMenu: state should look like it does below.
    initializeMenu:
        	  component: "System.SetVariable"
             properties:
               variable: "pizzaMenu"
               value:
    
  11. To set the System.SetVariable value property, open the menu.txt file in the starter folder of the extracted download for this article in a text editor.
  12. Copy all the content to the clipboard, and make sure you don’t miss any leading blank characters.
  13. In the flow editor, highlight the System.SetVariable value property and paste the content from the clipboard so it replaces the value string.
  14. Ensure that the value: string pasted from the clipboard aligns with the variable property as shown in Figure 4.
  15. Click the Validate link in the upper right to ensure proper indenting. Again, if you don’t see an alert with a green icon, you need to adjust the formatting of the added content.

What you just did: You defined a new context variable and added the pizza menu definition to it. When defining the pizza menu items, you used Apache FreeMarker expressions. In a later article, you will learn how to dynamically query the pizza menu from a back-end system by using a custom component service in Oracle Intelligent Bots.

Setting Up for Pagination

Pagination is a feature of the CR component that enables you to specify the start index and the range size for content rendered from an iterator. To prepare for pagination, create a context variable of type "int" to hold the index and initialize it with its first value, 0.

  1. Create a new variable, cardsRangeStart, in the context | variables section at the top of the dialogue flow:
    cardsRangeStart: "int"
    
  2. Next, click the + Components button to add a new component to the flow.
  3. In the opened dialog box, select the Variables category and Set variable.
  4. From the Insert After select list, choose initializeMenu, so that the new component is created below.
  5. Click Apply.
  6. Change the name of the new state from setVariable: to setCardsRangeStart:.
  7. Set the variable property value to "cardsRangeStart" and the value property value to 0:
    setCardsRangeStart:
           component: "System.SetVariable"
           properties:
             variable: "cardsRangeStart"
             value: 0
    
  8. Click Validate to ensure proper indenting. Again, if you don’t see an alert with a green icon, you need to adjust the formatting of the added content.

Adding the CR Component

In this section, you are going to replace the existing pizza menu list, which uses the System.List built-in component, with the System.CommonResponse component.

  1. Scroll down to the startOrder: state.
  2. Before you delete the startOrder: state, notice the pizzaType variable that is updated by the list component and also take note of the iResult variable. Both settings make it possible to not display the pizza menu list when user input strings contain the pizza type for an order. You will implement the same functionality with the CR component.
  3. Delete the startOrder: state and all of its content.
  4. Click + Components at the top of the flow editor, and select the User Interface category in the opened dialog box.
  5. Select the Common response – card entry, and ensure that the Remove Comments toggle is enabled so no component comments get added.
  6. From the Insert After list, choose unresolved as the value. This adds the new CR component into the same spot in the flow editor that the startOrder: state was in.
  7. Click Apply.
  8. Change the generated state name cardResponse: to startOrder: to ensure that the bot conversation flow works as before.

What you just did: You replaced the list component with the CR component. The new card layout enables you to define a title, a description, and an image for each item on the menu. Next you are going to configure the card layout to read its values from the menu variable you defined earlier.

Configuring the CR Component

As you can see from the many properties that got added to the new startOrder: component definition, the common response component is very powerful.

Instead of setting up each property manually, the approach in the following steps loads the configuration from a text file and copies it into the dialogue flow. The “Explaining the CR Component BotML Settings” section below explains what each property is, so you’ll know how to reproduce the bot response in your own bot projects.

  1. Open the startOrder.txt file you find in the starter folder of the extracted download for this article in a text editor.
  2. Copy the whole content to the clipboard, and make sure you don’t miss any leading blank characters.
  3. In the flow editor, delete the startOrder: state and all of its content.
  4. Place the cursor at the beginning of the line that previously held the startOrder: state.
  5. Paste the content from the clipboard. The startOrder: state label should be aligned with the unresolved: state label above.
  6. Click Validate to ensure proper indenting. Again, if you don’t see an alert with a green icon, you need to work on the formatting of the added content.

What you just did: You configured the CR component to display a list of pizzas defined in the pizzaMenu variable. The start index for the cards is set to reference the cardsRangeStart variable so only three pizzas are displayed at a time. Note that the CR component properties that are not used in this sample were removed from the BotML definition.

Testing the Bot

At this point, the bot response has been changed from a simple list menu to one that responds with a rich card layout that users can flip through to select a pizza. Let’s see what it looks like.

  1. Click the tester icon () at the right side of the top menu.
  2. Click the Reset button to ensure a fresh session.
  3. Type Can I see the menu? into the Message field, and press the Enter key.
  4. Click the More Pizzas button to flip to the next three pizzas.
  5. Select a pizza and then a size.
  6. Click the Reset button.
  7. Type I like to order a pizza, and press the Enter key.
  8. Type I want a pepperoni one, and then choose a size to complete the process.
  9. Click the Reset button again.
  10. Now type I want to order a large pepperoni pizza. You should see the order printed immediately.
  11. Close the tester by clicking the tester icon () again.

What you just proved: With the first test, you ensured that the pagination feature worked when you displayed the menu with three pizzas per iteration. In the second test, you showed that you could select a pizza not only by clicking its Order button but also by typing the selection. Finally, in the last test, you showed that both menus are skipped if the user string contains all the information needed for the order.

Explaining the CR Component BotML Settings

Configuring the CR component in the hands-on application steps was done by copy-and-paste, which means that you didn’t learn how the component works.

In this section, you will see all the component properties that were set to achieve the response you just saw in the tester.

To follow this component properties list in the sample application, navigate to the startOrder: state in the flow. The properties are explained from top to bottom.

CR component property Description
variable This references a context of type entity to validate user input. If you, for example, type "salami" when the pizza menu is displayed, the menu will appear again, because the value is not valid for the PizzaType entity.
nlpResultVariable This property references the iResult variable (of type nlpresult). If this property is set, the component—before rendering the menu response—checks whether the user input string contains a valid pizza type. If it does, the menu will not appear.
metadata The metadata section is where you can define the component response, using the various response types, such as card, text, and attachment. This is also where you define the action possible for the cards.
cardLayout The cardLayout property defines whether cards are printed vertically or for horizontal scrolling. Valid values are "vertical" and "horizontal".
actions This property defines actions that are global for all cards. In the example, this setting is used to define the More Pizzas iterator button.
rendered This property defines whether an element is shown in the response. For the More Pizzas button, it uses an Apache FreeMarker expression to hide the button when the last page in the list of pizzas is reached.
payload The payload property of the postback action defines the action string that determines the next transition in the dialogue flow when the button is clicked as well as the variables and values that will be updated. In this case, the cardsRangeStart variable is updated with the next start index.
cards The cards property defines the configuration of a single card. Multiple cards can be configured in BotML or, as in this example, generated from content in an iterator.
title This property is the title of a card. ${pizzaMenu.name} references the current item in an iterator and reads the name attribute from it.
iteratorVariable This property references the pizzaMenu variable, which is an array of objects. For each entry in the array, the cards section prints a card.
rangeStart This property references the cardsRangestart variable to indicate to the CR component where in the iterator it should start printing the cards.
rangeSize This property defines how many cards should be printed, starting from the rangeStart index.
actions This property defines an action for each individual card. In this example, the action is a postback that sets the pizzaType variable’s value to the name of the selected pizza. In addition, it returns "order" as an action to prompt the dialogue flow to navigate to the "askSize:" state.
processUserMessage If set to true, this property ensures that the component will wait for and handle user input.
transitions This section defines where in a conversation the dialogue flow engine transitions to, based on the user interaction in the component. As you see, an action of "order" issued when the Order button is clicked leads the navigation to the askSize: state.

Importing the Solution

This article also provides the completed pizza bot as a download. After you download and extract the completed pizza bot, do the following:

  1. Go to the Oracle Intelligent Bots dashboard.
  2. Click the Import Bot button in the upper right of the dashboard.
  3. In the opened dialog box, navigate to the folder to which you extracted the downloaded zip file. Open the final folder, and select the OracleMagazineOnlinePizzaBot2-final.zip file.
  4. Click Open.
  5. Close the upload confirmation dialog box, by clicking the X at the right side.
  6. If you already have existing bots defined in your environment, chances are good that you won’t immediately spot the downloaded bot. To find the bot, type OracleMagazine into the Filter field above the green New Bot + icon.
  7. Click the OracleMagazineOnlinePizzaBot2 bot to open it.
  8. Click Train (in the upper right of the screen). Before you click it, Train should show an exclamation point, because the bot has not yet been trained after the download and import. After you click Train, a dialog box appears that confirms that the bot has been trained.
  9. Click the test icon to try the downloaded bot.

Conclusion

Both the component-based approach in which you build chatbot conversations in Oracle Intelligent Bots and the CR component deliver big productivity gains to chatbot developers using the Oracle platform. The CR component in particular saves bot designers a lot of programming time they otherwise would have to spend on developing complex and composite responses for each of the channels they support.

In addition to learning how the CR component works, you also learned how to create mockup data in BotML by defining the pizza menu as the content of a context variable. Mockup data is useful when bot design and back-end data system integration are handled by different teams or at different times in a bot development project.

Next Steps

TRY Oracle Mobile Cloud Enterprise and Oracle Intelligent Bots.

LEARN more about
Oracle Mobile Cloud Enterprise and Oracle Intelligent Bots.
Oracle common response component (documentation).

DOWNLOAD the bots for this article
OracleMagazine-OnlinePizzaBot2 (starter).
OracleMagazine-OnlinePizzaBot2 (final).

Photography by Gioia Fabbri, Unsplash