Since LUIS was first previewed, it’s certainly changed a lot! General availability for LUIS was announced back in December last month, with an expanded limit to 500 intents and 100 entities per application, support for new regions, availability in 7 new regions (South Central US, East US, West US 2, East Asia, North Europe, Brazil South, Australia East), as well as increased support for different languages. If you’re interested and haven’t already, click here to read the full announcement.
This post is going to provide a quick guide through the new LUIS portal, and will demonstrate how to create a new LUIS application in addition to showing you how to use list entities. List entities allow you to define related words and synonyms for a specific entities you want a resolution for – if that sentence is a unclear, don’t worry about it, it will make much more sense by the end of this article. The scenario we’ll be using for this sample application is a food ordering application for a restaurant.
In order to follow along, all you’ll need is a Microsoft account and you can sign into the LUIS portal and get started right away.
Creating our LUIS Application
As soon as you’re signed in, you’ll be directed to My Apps in the LUIS portal. On the upper left, click on Create new app as shown below.
When you are satisfied, simply click on done. Your new LUIS application will be ready to train. Select the newly created application, and you’ll be re-directed to the app’s build tab where we can define new intents and entities, as shown below.
By default, you will always start with an intent of None. Moving on, let’s add our first intent!
Adding Intents
The intent of a LUIS application defines a certain task or action your users would want to perform. To start, lets add some simple CRUD operations (create, read, update, delete) for this restaurant app. Under the App Assets field to the left, select intents, and create new intent. Simply define a name for the intent, and hit done when you’re satisfied.
We define our first intent as AddItem, this is the intent we’ll be focusing on for the remainder of this guide.
Defining the rest of the intents for this application might look something like below:
We’ve added some intents to update an item, clear the order, delete an item, view the current order, and checkout. For experienced LUIS users, you might be tempted to go ahead and start adding some utterances for the intents we just created. Instead, let’s define some entities for this restaurant application and continue with creating utterances later.
Creating the Entities
Whereas intents defined certain actions, an entity describes information relevant to certain intents. They represent the nouns, and the things in the LUIS application. For example, for a LUIS app for an alarm bot, a user might say “set an alarm for 5 pm”. The intent might be SetAlarm, whereas the entity refers to the specific time for that alarm to be set. You can define your own entities, as well as select from a list of common pre-built entities to use.
For a comprehensive list of pre-built entities, click here.
In this application, we’ll be using one of each, first we will create a list entity called FoodName, and add a Number entity from the list of pre-builts.
Under App Assets, this time select Entities as shown above. Similar to creating a new intent, select Create new entity.
Unlike intents, with entities you can also define a type. By default, a type of Simple will be preselected if you don’t specify otherwise in the drop down. We name this new entity FoodName, and select type List from the type menu.
For a comprehensive list of entity types, click here.
Now, to add the pre-built number entity. From the entity menu, select Add prebuilt domain entity as shown below.
Next, using the check box, select the number entity. Take note that there are various other prebuilt entities available, such as temperature, dimension, and currency (money).
Click ‘done’, and the pre-built entity will be added for your application.
Revisiting our custom Entity
As mentioned in the beginning of the article, a ‘list entity allows you to define related words and synonyms for a specific entities you want a resolution for’. Restaurants typically provide menus which provide information about what they serve. Customers generally look at a menu, and make a decision on what to order, however a user may not always explicitly say the exact menu item that they’re referring to. For example, let’s say a restaurant serves an item called ‘Bone-In Natural Cut Ribeye’. When ordering, a customer might simply say, “I’ll have the rib eye”. How can this be resolved?
With intents, we provide many sample utterances to train our LUIS model so that it can recognize intents in any number of ways a user may want to trigger it. We can use list entities to provide other alternative names (synonyms) for LUIS to recognize this entity. Back in the FoodName list entity we created early, we’ll add some values which represent menu items for this hypothetical restaurant. These values will appear under the normalized value column of the entity. For the sample, we’ve added Cheese burger, Greek Salad, Rib Eye Steak, etc.
Next, we define manually define various synonyms for each value – these can be different ways a user may refer (either by speech or text) to one value, including common typos, other names, expressing multiples, etc.
With the list entity defined as above, if a user says “mutton curry”, our LUIS model will process the user’s query and provide a resolution for a FoodItem with the value of ‘Curried Lamb’.
Providing Utterances
Next we need to provide utterances to train our natural language model. Utterances are simply sample phrases that a user might say in the context of your application, and we’ll train it to recognize specific entities for certain intents. For example, in the intent AddItem, we added a sample utterance “I would like two cheese burgers“. Automatically, ‘two’ was recognized as a number pre-built entity which we enabled earlier, however we need to tag our custom FoodItem entity. Selecting ‘cheese burger’, we can tag it as an entity of FoodName, and set it as a synonym for the value Cheese Burger (lower case cheese burger wasn’t recognized) as shown below.
As you provide more and more utterances, your natural language model will become better and more accurate. With enough data, LUIS can automatically tag the appropriate entities. If a mistake is made and an incorrect entity is tagged, you can always edit it manually and re-train your model.
Training and publishing our LUIS app
Next, we need to do is train our model. In the top right, if you have any changes that haven’t yet been provided to your application, there will be a red circle next to the train button. Simply click Train and the service will do the rest. When your changes have been successfully incorporated, and your model re-trained, a green circle will appear, indicating that no new changes have been added. Please note that your model cannot have any untrained changes
When your model is trained and up-to-date, you can then open the test panel and provide some utterances to your LUIS model:
Lastly, we need to publish our application! Select the publish tab on the top right, and you’ll be re-directed to a view similar to below:
Here you can view your publish settings, as well as your LUIS App ID and Password. You will need these to access your LUIS app from your client applications.
Please note that you can also type in queries directly to your production endpoint, and you’ll get a JSON response from LUIS. To demonstrate this, we’ll copy paste the URL highlighted above under the endpoint column (note that the app ID and keys are removed for this image) into an internet browser, and type the query – “two horiatiki salads please.” Horiatiki salad is a synonym (source) which we provided in our list entity for the value of ‘Greek Salad.’ Below is the full JSON response for the query, you’ll notice our intent resolution of ‘AddItem’ along with our two entities of FoodName, and builtin.number, along with their resolutions.
{ "query": "two horiatiki salads please", "topScoringIntent": { "intent": "AddItem", "score": 0.832546 }, "intents": [ { "intent": "AddItem", "score": 0.832546 }, { "intent": "ClearCart", "score": 0.04075234 }, { "intent": "DeleteItem", "score": 0.0365081131 }, { "intent": "CheckOut", "score": 0.03454889 }, { "intent": "UpdateItem", "score": 0.0191788059 }, { "intent": "None", "score": 0.0165171754 }, { "intent": "ViewCart", "score": 0.0110074291 } ], "entities": [ { "entity": "horiatiki salads", "type": "FoodName", "startIndex": 4, "endIndex": 19, "resolution": { "values": [ "Greek Salad" ] } }, { "entity": "two", "type": "builtin.number", "startIndex": 0, "endIndex": 2, "resolution": { "value": "2" } } ] }
In addition to allowing users to express different menu items under different synonyms, we also have the ability to verify if a food item is a specific menu item. We can do this by ensuring that the values under our FoodItem entity also match the actual names of menu items for our restaurant. If it’s a valid item, we can add the item to their order, otherwise we can prompt the user that the restaurant doesn’t serve such a thing.
We hope this helps you become more acquainted with LUIS!
Happy Making!
Matthew Shim from the Bot Framework Team.