Improve chat flow with answers
This commit is contained in:
@@ -1,6 +0,0 @@
|
||||
const intents = require('./intents')
|
||||
|
||||
module.exports = async (message, recipient) => {
|
||||
const run = intents.get(message)
|
||||
run(message, recipient)
|
||||
}
|
||||
@@ -7,7 +7,7 @@ FB.setAccessToken(process.env.FB_ACCESS_TOKEN)
|
||||
const fbParser = require('claudia-bot-builder/lib/facebook/parse')
|
||||
const fbValidate = require('claudia-bot-builder/lib/facebook/validate-integrity')
|
||||
|
||||
const conversation = require('./conversation')
|
||||
const {run} = require('./intents')
|
||||
|
||||
/**
|
||||
* In-Memory cache for FB graph results
|
||||
@@ -63,7 +63,7 @@ const respond = async (req, res) => {
|
||||
recipients[message.sender] = recipient
|
||||
|
||||
try {
|
||||
await conversation(message, recipient)
|
||||
await run(message, recipient)
|
||||
} catch (err) {
|
||||
console.error(err)
|
||||
res.end(err.message)
|
||||
|
||||
@@ -3,6 +3,9 @@ const fbReply = require('claudia-bot-builder/lib/facebook/reply')
|
||||
const send = (recipientId, message) =>
|
||||
fbReply(recipientId, message, process.env.FB_ACCESS_TOKEN)
|
||||
|
||||
const noop = () => {}
|
||||
|
||||
module.exports = {
|
||||
send,
|
||||
noop,
|
||||
}
|
||||
|
||||
@@ -1,14 +1,20 @@
|
||||
const flatten = require('flatten')
|
||||
const fbTemplate = require('claudia-bot-builder/lib/facebook/format-message')
|
||||
const {send} = require('./common')
|
||||
|
||||
const run = (msg, recipient) => {
|
||||
const reply = new fbTemplate.Text(`
|
||||
This is a \`Text\` message
|
||||
`).get()
|
||||
send(recipient.id, reply)
|
||||
const INTENT_DEBUG_START = 'intent_debug_start'
|
||||
|
||||
const run = (msg, recipient, data) => {
|
||||
const text = flatten(data)
|
||||
.map(d => JSON.stringify(d, null, 2))
|
||||
.join(', ')
|
||||
send(recipient.id, new fbTemplate.Text(`DEBUG: \`${text}\``).get())
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
keywords: ['debug'],
|
||||
run,
|
||||
}
|
||||
module.exports = [
|
||||
{
|
||||
id: 'debug',
|
||||
keywords: [INTENT_DEBUG_START, 'debug'],
|
||||
run,
|
||||
},
|
||||
]
|
||||
|
||||
@@ -1,16 +1,32 @@
|
||||
const huh = require('huh')
|
||||
const fbTemplate = require('claudia-bot-builder/lib/facebook/format-message')
|
||||
const {send} = require('./common')
|
||||
|
||||
const uncapitalize = str => str.charAt(0).toLowerCase() + str.slice(1)
|
||||
|
||||
const run = (msg, recipient) => {
|
||||
const reply = new fbTemplate.Text(
|
||||
`Sorry, ${
|
||||
recipient.first_name
|
||||
}. I am a young Bot and still learning. Type "Start" to show the start over.`
|
||||
).get()
|
||||
send(recipient.id, reply)
|
||||
send(recipient.id, [
|
||||
new fbTemplate.ChatAction('mark_seen').get(),
|
||||
new fbTemplate.ChatAction('typing_on').get(),
|
||||
new fbTemplate.Text(
|
||||
`Sorry, ${
|
||||
recipient.first_name
|
||||
}. I didn't understand that, probably because of ${uncapitalize(
|
||||
huh.get()
|
||||
)}`
|
||||
).get(),
|
||||
new fbTemplate.ChatAction('typing_on').get(),
|
||||
new fbTemplate.Pause(1000).get(),
|
||||
new fbTemplate.Text(
|
||||
`I'll improve in time, don't worry. Meanwhile, you can type 'start' to start the show over.`
|
||||
).get(),
|
||||
])
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
keywords: [],
|
||||
run,
|
||||
}
|
||||
module.exports = [
|
||||
{
|
||||
id: 'default',
|
||||
keywords: [],
|
||||
run,
|
||||
},
|
||||
]
|
||||
|
||||
@@ -1,17 +1,90 @@
|
||||
const fbTemplate = require('claudia-bot-builder/lib/facebook/format-message')
|
||||
const {send} = require('./common')
|
||||
|
||||
const INTENT_DRINK_START = 'intent_drink_start'
|
||||
const INTENT_DRINK_YES = 'intent_drink_yes'
|
||||
const INTENT_DRINK_NO = 'intent_drink_no'
|
||||
const INTENT_DRINK_FAVORITE = 'intent_drink_favorite'
|
||||
|
||||
const run = (msg, recipient) => {
|
||||
const reply = new fbTemplate.Text(`
|
||||
send(recipient.id, [
|
||||
new fbTemplate.ChatAction('mark_seen').get(),
|
||||
new fbTemplate.ChatAction('typing_on').get(),
|
||||
new fbTemplate.Pause(500).get(),
|
||||
new fbTemplate.Text(`
|
||||
So, you'd like to drink?
|
||||
`)
|
||||
.addQuickReply('YES!', 'YES')
|
||||
.addQuickReply('No, not particulary', 'NO')
|
||||
.get()
|
||||
send(recipient.id, reply)
|
||||
.addQuickReply('YES!', INTENT_DRINK_YES)
|
||||
.addQuickReply('No, not particulary', INTENT_DRINK_NO)
|
||||
.get(),
|
||||
])
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
keywords: ['drink', 'dring', 'water', 'gimmme'],
|
||||
run,
|
||||
const runYes = (msg, recipient) => {
|
||||
send(recipient.id, [
|
||||
new fbTemplate.ChatAction('mark_seen').get(),
|
||||
new fbTemplate.ChatAction('typing_on').get(),
|
||||
new fbTemplate.Pause(500).get(),
|
||||
new fbTemplate.Text(`
|
||||
YEAH, me too.
|
||||
`).get(),
|
||||
new fbTemplate.ChatAction('mark_seen').get(),
|
||||
new fbTemplate.ChatAction('typing_on').get(),
|
||||
new fbTemplate.Pause(1000).get(),
|
||||
new fbTemplate.Text(`
|
||||
What's your favorite drink?
|
||||
`)
|
||||
.addQuickReply('Absinthe', INTENT_DRINK_FAVORITE)
|
||||
.addQuickReply('Beer', INTENT_DRINK_FAVORITE)
|
||||
.addQuickReply('Brandy', INTENT_DRINK_FAVORITE)
|
||||
.addQuickReply('Cachaça', INTENT_DRINK_FAVORITE)
|
||||
.addQuickReply('Gin', INTENT_DRINK_FAVORITE)
|
||||
.addQuickReply('Ouzo', INTENT_DRINK_FAVORITE)
|
||||
.addQuickReply('Rum', INTENT_DRINK_FAVORITE)
|
||||
.addQuickReply('Sake', INTENT_DRINK_FAVORITE)
|
||||
.get(),
|
||||
])
|
||||
}
|
||||
|
||||
const runFavorite = (msg, recipient) => {
|
||||
send(recipient.id, [
|
||||
new fbTemplate.ChatAction('mark_seen').get(),
|
||||
new fbTemplate.ChatAction('typing_on').get(),
|
||||
new fbTemplate.Pause(500).get(),
|
||||
new fbTemplate.Text(
|
||||
`Hmmm... I don't like ${
|
||||
msg.originalRequest.message.text
|
||||
}, but I like water!`
|
||||
).get(),
|
||||
])
|
||||
}
|
||||
|
||||
const runNo = (msg, recipient) => {
|
||||
send(recipient.id, [
|
||||
new fbTemplate.ChatAction('mark_seen').get(),
|
||||
new fbTemplate.ChatAction('typing_on').get(),
|
||||
new fbTemplate.Pause(500).get(),
|
||||
new fbTemplate.Text(`
|
||||
That's a shame, but do drink water!
|
||||
`).get(),
|
||||
])
|
||||
}
|
||||
|
||||
module.exports = [
|
||||
{
|
||||
keywords: [INTENT_DRINK_START, 'drink', 'dring', 'water', 'gimmme'],
|
||||
run,
|
||||
},
|
||||
{
|
||||
keywords: [INTENT_DRINK_YES],
|
||||
run: runYes,
|
||||
},
|
||||
{
|
||||
keywords: [INTENT_DRINK_NO],
|
||||
run: runNo,
|
||||
},
|
||||
{
|
||||
keywords: [INTENT_DRINK_FAVORITE],
|
||||
run: runFavorite,
|
||||
},
|
||||
]
|
||||
|
||||
@@ -1,20 +1,40 @@
|
||||
const flatten = require('flatten')
|
||||
|
||||
const load = intents => flatten(intents.map(name => require(`./${name}`)))
|
||||
|
||||
const intents = load(['default', 'start', 'drink', 'debug'])
|
||||
|
||||
const normalize = str => str.toLowerCase()
|
||||
|
||||
const intents = {
|
||||
default: require('./default'),
|
||||
start: require('./start'),
|
||||
drink: require('./drink'),
|
||||
debug: require('./debug'),
|
||||
}
|
||||
const matchIntent = str =>
|
||||
intents
|
||||
.map(i => (i.keywords.indexOf(normalize(str)) > -1 ? i.run : false))
|
||||
.find(f => f !== false)
|
||||
|
||||
const get = msg => {
|
||||
const text = normalize(msg.text)
|
||||
const intent = Object.keys(intents).find(
|
||||
k => intents[k].keywords.indexOf(text) !== -1
|
||||
)
|
||||
return intent ? intents[intent].run : intents.default.run
|
||||
const defaultIntent = intents.find(i => i.id === 'default').run
|
||||
let intent = matchIntent(msg.text)
|
||||
|
||||
if (!intent) {
|
||||
if (msg.quick_reply) {
|
||||
intent = matchIntent(msg.quick_reply.payload)
|
||||
}
|
||||
}
|
||||
|
||||
return intent || defaultIntent
|
||||
}
|
||||
|
||||
const run = (msg, recipient) => {
|
||||
const debugIntent = intents.find(i => i.id === 'debug').run
|
||||
const intent = get(msg)
|
||||
|
||||
if (intent === debugIntent) {
|
||||
return debugIntent(msg, recipient, intents)
|
||||
}
|
||||
|
||||
return intent(msg, recipient)
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
get,
|
||||
run,
|
||||
}
|
||||
|
||||
@@ -1,14 +1,64 @@
|
||||
const fbTemplate = require('claudia-bot-builder/lib/facebook/format-message')
|
||||
const {send} = require('./common')
|
||||
const {send, noop} = require('./common')
|
||||
|
||||
const INTENT_START_START = 'intent_start_start'
|
||||
const INTENT_START_ABOUT = 'intent_start_about'
|
||||
const INTENT_START_CHANGE_ALERTS = 'intent_change_alert'
|
||||
|
||||
const run = (msg, recipient) => {
|
||||
const reply = new fbTemplate.Text(`
|
||||
send(recipient.id, [
|
||||
new fbTemplate.ChatAction('mark_seen').get(),
|
||||
new fbTemplate.ChatAction('typing_on').get(),
|
||||
new fbTemplate.Pause(500).get(),
|
||||
new fbTemplate.Text(`
|
||||
This is your menu. You can reach it by writing Menu, or Help, or Start
|
||||
`).get()
|
||||
send(recipient.id, reply)
|
||||
`)
|
||||
.addQuickReply('About vodopija-bot', INTENT_START_ABOUT)
|
||||
.addQuickReply('Change alerts', INTENT_START_CHANGE_ALERTS)
|
||||
.get(),
|
||||
])
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
keywords: ['start', 'menu', 'help'],
|
||||
run,
|
||||
const runAbout = (msg, recipient) => {
|
||||
send(recipient.id, [
|
||||
new fbTemplate.ChatAction('mark_seen').get(),
|
||||
new fbTemplate.ChatAction('typing_on').get(),
|
||||
new fbTemplate.Text(`Thanks for asking 🙂`).get(),
|
||||
new fbTemplate.ChatAction('typing_on').get(),
|
||||
new fbTemplate.Pause(500).get(),
|
||||
new fbTemplate.Text(
|
||||
`vodolija-bot was created by Marko Marković as a test for SPARTANS AI LTD.`
|
||||
).get(),
|
||||
new fbTemplate.ChatAction('typing_on').get(),
|
||||
new fbTemplate.Pause(1000).get(),
|
||||
new fbTemplate.Text(
|
||||
`Its goal is to help you drink more water for a healthier life.`
|
||||
).get(),
|
||||
new fbTemplate.ChatAction('typing_on').get(),
|
||||
new fbTemplate.Pause(1000).get(),
|
||||
new fbTemplate.Text(`
|
||||
It features:
|
||||
☑ Daily water reminders
|
||||
☑ Personalized AI recommendations
|
||||
☑ Number of cups of water drank this week
|
||||
☑ Tips about water drinking
|
||||
`)
|
||||
.addQuickReply('Back', INTENT_START_START)
|
||||
.get(),
|
||||
])
|
||||
}
|
||||
|
||||
module.exports = [
|
||||
{
|
||||
keywords: [INTENT_START_START, 'start', 'menu', 'help'],
|
||||
run,
|
||||
},
|
||||
{
|
||||
keywords: [INTENT_START_ABOUT],
|
||||
run: runAbout,
|
||||
},
|
||||
{
|
||||
keywords: [INTENT_START_CHANGE_ALERTS],
|
||||
run: noop,
|
||||
},
|
||||
]
|
||||
|
||||
@@ -14,6 +14,8 @@
|
||||
},
|
||||
"dependencies": {
|
||||
"claudia-bot-builder": "4.0.0",
|
||||
"flatten": "1.0.2",
|
||||
"huh": "2.0.1",
|
||||
"micro": "9.1.4",
|
||||
"microrouter": "3.1.2"
|
||||
},
|
||||
|
||||
@@ -1127,6 +1127,10 @@ flat-cache@^1.2.1:
|
||||
graceful-fs "^4.1.2"
|
||||
write "^0.2.1"
|
||||
|
||||
flatten@1.0.2:
|
||||
version "1.0.2"
|
||||
resolved "https://registry.yarnpkg.com/flatten/-/flatten-1.0.2.tgz#dae46a9d78fbe25292258cc1e780a41d95c03782"
|
||||
|
||||
for-in@^1.0.2:
|
||||
version "1.0.2"
|
||||
resolved "https://registry.yarnpkg.com/for-in/-/for-in-1.0.2.tgz#81068d295a8142ec0ac726c6e2200c30fb6d5e80"
|
||||
@@ -1384,6 +1388,10 @@ http-signature@~1.2.0:
|
||||
jsprim "^1.2.2"
|
||||
sshpk "^1.7.0"
|
||||
|
||||
huh@2.0.1:
|
||||
version "2.0.1"
|
||||
resolved "https://registry.yarnpkg.com/huh/-/huh-2.0.1.tgz#08d5836a47e3f301ad50899d4788721b0ac15486"
|
||||
|
||||
iconv-lite@0.4.19:
|
||||
version "0.4.19"
|
||||
resolved "https://registry.yarnpkg.com/iconv-lite/-/iconv-lite-0.4.19.tgz#f7468f60135f5e5dad3399c0a81be9a1603a082b"
|
||||
|
||||
Reference in New Issue
Block a user