Skip to content

Instantly share code, notes, and snippets.

@mallendeo
Last active October 23, 2016 19:12
Show Gist options
  • Save mallendeo/04af247c6589ab7d2499d8b0e3086f36 to your computer and use it in GitHub Desktop.
Save mallendeo/04af247c6589ab7d2499d8b0e3086f36 to your computer and use it in GitHub Desktop.
Despegar Telegram bot
'use strict'
const fetch = require('node-fetch')
const TelegramBot = require('node-telegram-bot-api')
const bot = new TelegramBot(process.env.TELEGRAM_TOKEN, { polling: true })
const low = require('lowdb')
const fileAsync = require('lowdb/lib/file-async')
const db = low(`${__dirname}/data/db.json`, { storage: fileAsync })
db.defaults({ users: [] }).value()
const intervals = {}
const checkFlights = (departure = 'scl', arrival = 'nyc', maxFare = 200000) => {
const url = `http://www.despegar.cl/vuelos/${departure}/${arrival}/`
return fetch(url)
.then(res => res.text())
.then(html => {
const payload = html.match(/"jsonData" : ([\s\S]*?),\s"fareSelectorType"/)[1]
const data = JSON.parse(payload)
return {
url,
notify: data.items.some(item =>
item.itinerariesBox.emissionPrice.total.fare.raw <= parseInt(maxFare))
}
})
}
bot.onText(/^\/?start$/, (msg, match) => {
bot.sendMessage(msg.from.id,
'Usage: /start {maxFare} {flights}\n' +
'e.g /start 200000 scl mia, scl nyc')
})
bot.onText(/\/?start (\d{1,}) ([\s\S]{1,})/, (msg, match) => {
db.get('users').remove({ id: msg.from.id }).value()
const user = db.get('users')
.push({
id: msg.from.id,
maxFare: match[1],
flights: match[2].split(',').map(f => f.trim().split(' '))
})
.last()
.value()
initUser(user)
})
const stopIntervals = user => {
user.flights && user.flights.forEach(flight => {
const intervalId = `${user.id}${flight[0]}${flight[1]}`
clearInterval(intervals[intervalId])
delete intervals[intervalId]
})
}
bot.onText(/^\/?stop/, msg => {
bot.sendMessage(msg.from.id, 'Done!')
const user = db.get('users').remove({ id: msg.from.id }).value()
stopIntervals(user)
})
const initUser = user => {
bot.sendMessage(user.id, 'Buscando vuelos ✈️')
console.log('init user', user.id)
const notify = (flight, user) => {
return checkFlights(flight[0], flight[1], user.maxFare)
.then(({ notify, url }) => {
if (notify) bot.sendMessage(user.id, url)
})
}
stopIntervals(user)
console.log(user.flights)
user.flights && user.flights.forEach(flight => {
notify(flight, user)
const intervalId = `${user.id}${flight[0]}${flight[1]}`
intervals[intervalId] = setInterval(() =>
notify(flight, user), 10 * 60 * 1000)
})
}
console.log('Starting bot...')
db.get('users').value().forEach(initUser)
{
"name": "despegar-bot",
"version": "1.0.0",
"description": "",
"main": "index.js",
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1"
},
"author": "",
"license": "ISC",
"dependencies": {
"lowdb": "^0.13.1",
"node-fetch": "^1.6.3",
"node-telegram-bot-api": "^0.24.0"
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment