Short Story
I built this app thinking about people in London with Amazon Echo that want to go to theatre for musicals!
Instead of using a website or an app they can simply say "Alexa, ask London Musical give me musical" or "Alexa, ask London Musical what's up tonight".
It's easy, even a grandma or grandpa can do it ;)
Once requested, the echo will read all the musical and theatre available in town.
Software: from scratch
In the past I used Amazon Lambda for building other skills.
This time I wanted to improve my knowledge on a low level side of Alexa platform.
I decided to create the code with nodejs and expressjs to be able to communicate with Alexa Skills Kit.
These 2 links were pretty useful to understand how to write the application:
- https://developer.amazon.com/public/solutions/alexa/alexa-skills-kit/docs/deploying-a-sample-skill-as-a-web-service
- https://developer.amazon.com/public/solutions/alexa/alexa-skills-kit/docs/alexa-skills-kit-interface-reference
The application runs on Heroku.
The code I wrote is able to write voice only response for Alexa.
How the application works (API)
The skill can answer to one intent called ListMusicalIntents.
This intent send back all the musical available in town, reading it from a previosly created file called musicals.
This file is updated daily on the server through a task that get the information from https://developer.londontheatredirect.com/ .
The index.js (see github repository of the project) have one endpoint called "/alexa" where all the post request received from the server sent from amazon echo devices arrive.
app.post('/alexa',function(request,response) {
request.setEncoding(null);
alexaReq.parseRequest(JSON.parse(request.body[0])).then(function(intent) { //vedi riga sopra
console.log(request.body.version);
alexaReq.parseRequest(request.body).then(function(intent) {
console.log("INTENT RECEIVED: " + intent);
if(intent==='ListMusicalsIntent') {
intentListMusicals(response);
} else if(intent==='NoIntent') {
answerMSG(response,"Please ask tell me musicals or give me musicals or what\'s up tonight");
} else if(intent==='AMAZON.HelpIntent') {
defaultAnswer(response);
} else if(intent === 'AMAZON.StopIntent'){
answerMSG(response,"Done");
} else if(intent === 'AMAZON.CancelIntent'){
answerMSG(response,"Done");
} else if(intent === 'AMAZON.SessionEndedRequest'){ //NOT TRUE.. MASQUERADING
response.end();
} else if(intent === 'AMAZON.LaunchIntent'){ //NOT TRUE.. MASQUERADING
defaultAnswer(response);
} else {
console.log("INTENT UNKNOWN: " + intent);
answerMSG(response,"I'm sorry, can't handle this. Please ask tell me musicals");
}
I built 2 classes that are used to understand the request and answer back:
- AlexaRequestParser: read the json format request
- AlexaResponseForger: create simple answer to send back to alexa skill
I've also used the alexa-verifier nodejs module to validate requests: https://github.com/mreinstein/alexa-verifier
Testing
I tested the application:
- directly through https://echosim.io
- writing unit test of my code with chai (and I think I will use another framework for testing in the future :D )
- creating request to the service(also locally on my machine) with curl command like:
curl -v -k http://127.0.0.1:5000/alexa --data-binary '{
"version": "1.0",
"session": {
"new": true,
"sessionId": "session1234",
"application": {
"applicationId": "amzn1.echo-sdk-ams.app.1234"
},
"attributes": {},
"user": {
"userId": null
}
},
"request": {
"type": "LaunchRequest",
"requestId": "request5678",
"timestamp": "2015-05-13T12:34:56Z"
}
}'
Comments