require ('isomorphic-fetch'); const config = require ('../config/config'); var request = require ('request'); var databaseHelper = require ('./database'); var getBuildStatus = function (skillID) { fetch ( `https://api.amazonalexa.com/v0/skills/${skillID}/interactionModel/locales/en-US/status`, { method: 'GET', headers: { Authorization: config.TOKEN, }, } ).then (result => { return result.text (); }); }; var refreshTokens = function () { return new Promise ((resolve, reject) => { var options = { method: 'POST', url: 'https://api.amazon.com/auth/o2/token', headers: { 'cache-control': 'no-cache', 'content-type': 'application/x-www-form-urlencoded', }, form: { grant_type: 'refresh_token', refresh_token: config.REFRESH_TOKEN, client_id: config.CLIENT_ID, client_secret: config.CLIENT_SECRET, }, }; request (options, function (error, response, body) { if (error) { reject (error); } else { parsedResponse = JSON.parse (body); if (parsedResponse.refresh_token) { databaseHelper .updateTokens ( parsedResponse.refresh_token, parsedResponse.access_token, parsedResponse.expires_in ) .then (() => { resolve (); }) .catch (e => { reject (e); }); } else { reject (body); } } }); }); }; var generateInteractionModel = function (skill) { let result = {}; let allIntents = []; skill.intents.map (intent => { allIntents.push ({name: intent.intentName, samples: intent.questions}); }); //Built-In like intents (Amazon built-in don't work, probably something related to existance of dialog intent allIntents.push ({ name: 'HelpIntent', samples: ['Help', 'Can you help me', 'I need help'], slots: [], }, { name: 'CancelIntent', samples: ['Cancel', 'Stop', 'Please stop'], slots: [], }, { name: 'YesIntent', samples: [ 'Yes', 'Yes please', 'I would like that', 'Yes I would like that', ], slots: [], }, { name: 'NoIntent', samples: ['No', 'No thank you'], slots: [], }); //Special intent for sending message (Dialog) allIntents.push ({ name: 'SendMessageIntent', samples: [ 'I would like to send a message', 'I want to send a message', 'Send message', ], slots: [ { name: 'Name', type: 'AMAZON.US_FIRST_NAME', samples: ['My name is {Name}', 'I am {Name}', '{Name}'], }, { name: 'Email', type: 'EmailSlot', samples: ['My email is {Email}', '{Email}'], }, { name: 'Message', type: 'MessageSlot', samples: ['{Message}'], }, ], }); let customSlotTypes = [ { name: 'EmailSlot', values: [ { id: null, name: { value: 'bla@bla.bla', synonyms: [], }, }, { id: null, name: { value: 'bla.bla@bla.bla.bla', synonyms: [], }, }, { id: null, name: { value: 'bla_bla@bla.bla', synonyms: [], }, }, ], }, { name: 'MessageSlot', values: [ { id: null, name: { value: 'Quick brown fox jumps over lazy dog', synonyms: [], }, }, { id: null, name: { value: 'Quick brown fox jumps over lazy dog. Quick brown fox jumps over lazy dog.', synonyms: [], }, }, { id: null, name: { value: 'Quick brown fox jumps over lazy dog. Quick brown fox jumps over lazy dog. Quick brown fox jumps over lazy dog.', synonyms: [], }, }, ], }, ]; let dialogPrompts = [ { id: 'Elicit.Intent-SendMessageIntent.IntentSlot-Name', variations: [ { type: 'PlainText', value: 'What is your name ?', }, { type: 'PlainText', value: 'Tell me your name', }, ], }, { id: 'Elicit.Intent-SendMessageIntent.IntentSlot-Email', variations: [ { type: 'PlainText', value: 'What is your email ?', }, { type: 'PlainText', value: 'Tell me your email', }, ], }, { id: 'Elicit.Intent-SendMessageIntent.IntentSlot-Message', variations: [ { type: 'PlainText', value: 'What is your message', }, ], }, ]; let dialogIntents = [ { name: 'SendMessageIntent', confirmationRequired: false, prompts: {}, slots: [ { name: 'Name', type: 'AMAZON.US_FIRST_NAME', elicitationRequired: true, confirmationRequired: false, prompts: { elicitation: 'Elicit.Intent-SendMessageIntent.IntentSlot-Name', }, }, { name: 'Email', type: 'EmailSlot', elicitationRequired: true, confirmationRequired: false, prompts: { elicitation: 'Elicit.Intent-SendMessageIntent.IntentSlot-Email', }, }, { name: 'Message', type: 'MessageSlot', elicitationRequired: true, confirmationRequired: false, prompts: { elicitation: 'Elicit.Intent-SendMessageIntent.IntentSlot-Message', }, }, ], }, ]; result.interactionModel = {}; result.interactionModel.languageModel = { invocationName: skill.invocationName, types: customSlotTypes, intents: allIntents, }; result.interactionModel.prompts = dialogPrompts; result.interactionModel.dialog = {}; result.interactionModel.dialog.intents = dialogIntents; return JSON.stringify (result); }; var uploadSkill = function (skill) { let generatedInteractionModel = generateInteractionModel (skill); console.log(skill.skillID); return fetch ( `https://api.amazonalexa.com/v1/skills/${skill.skillID}/stages/development/interactionModel/locales/en-US`, { method: 'PUT', headers: { Authorization: config.TOKEN, }, body: generatedInteractionModel, } ); }; module.exports = { updateSkill: function (skill) { return new Promise ((resolve, reject) => { if (new Date () / 1000 > config.TOKEN_EXPIRES_IN) { refreshTokens () .then (() => { uploadSkill (skill).then (response => { resolve (response.status); }); }) .catch (e => { reject (e); }); } else { uploadSkill (skill) .then (response => { resolve (response.status); }) .catch (e => { reject (e); }); } }); }, };