Feature Proposal: Conversational Components
We’re back with another feature proposal. This time we want to talk about Conversational Components.
We’ve been discussing this idea internally for a while, and it has also come up in our community a few times. Here’s a neat quote by @marktucker explaining the gist of the idea: “packaged, multi-turn conversations with accompanying language model, logic, and responses. For example, for In-Skill Purchasing there is a point where the skill developer hands over the conversation to Amazon so that the user confirms a purchase and their account is charged outside the skill code.”
The idea behind these components is to provide solutions for recurring problems you might encounter while creating voice apps.
As an example let’s say at a given time you need your user’s phone number. Instead of setting up the language model, adding the logic to your handler, creating the speech output, etc. you simply install the component and delegate the task to it.
How It Works
First of all, you would have to install the component. These have to be manually installed using npm:
$ npm install <component> --save
After that, you would use a new Jovo CLI command to extract the necessary files from the package into your project, i.e. ./models
, ./src/
$ jovo prepare <component>
We are not sure yet, whether we want to place the files into their respective folders inside a components
sub-directory, or bundle everything up inside a components
directory in the root folder of your project and have sub-directories for each component containing all of its files:
./models/components/<component>
./src/i18n/components/<component>
./src/components/<component>
// OR
./components/<component>/models
./components/<component>/src/i18n
./components/<component>/src
But, after that you would enable the component using the new app.useComponent(componentName)
function:
// src/app.js
app.useComponent('COMPONENT_PHONE_NUMBER');
That’s it for the installation.
Now you could simply delegate the task to the component using the new delegate(componentName, onCompleteIntent)
function:
// src/app.js
PhoneNumberIntent() {
this.delegate('COMPONENT_PHONE_NUMBER', 'CompletedIntent');
},
CompletedIntent() {
}
After the component finished its task, it will route back to the intent specified in onCompleteIntent
and you will be able to access the result of the process using the new $components
object:
CompletedIntent() {
this.$components.COMPONENT_PHONE_NUMBER.$response
}
This response will contain a status property informing you whether the process was SUCCESSFUL
, encountered an ERROR
or was REJECTED
by the user, i.e. user called the StopIntent
at some point. Besides that, it would contain a data
object, which will have the data stored you initially needed. That object will have a different structure depending on the component.
{
"status": "SUCCESSFUL" | "ERROR" | "REJECTED",
"data": {
...
}
}
Third-Party Components
To make it easy for third-party developers to create and share their own components, they will simply be npm packages. The entry point will specify the path to the models
and src
folders, which will be used by the CLI to distribute them to their respective places inside your project using the $ jovo prepare <component>
command.
Problems
One of the most likely problems you will encounter when using components is the corruption of the language model. For example, you’re not allowed to use the same utterance in multiple intents, or you might already have a YesIntent
setup, but the component has its own. In these cases, the CLI would issue a warning, which will help you manually fix the issue.