Skip to content

Commit

Permalink
Merge pull request #19 from alexwohlbruck/develop
Browse files Browse the repository at this point in the history
Develop
  • Loading branch information
alexwohlbruck authored Aug 7, 2017
2 parents 3d47037 + cbbe70c commit 07c0ecf
Show file tree
Hide file tree
Showing 7 changed files with 182 additions and 115 deletions.
28 changes: 28 additions & 0 deletions app/config/app-settings.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
/*
* This file contains global settings for the app configuration
* Use environment variables for secrets and keys!!
* This file is publicly visible (hello if you're reading this :D )
*/

const unsubscribableDates = [
{
start: new Date("August 8, 2017 16:20:00 EDT"),
end: new Date("August 9, 2017 16:20:00 EDT")
}
],

isBetweenDates = function(target, min, max) {
return (min < target) && (target < max);
};

module.exports = {
allowUsersToUnsubscribe: function() {
const now = new Date();

return unsubscribableDates
.map(range => {
return isBetweenDates(now, range.start, range.end);
})
.reduce((sum, value) => sum || value);
}
};
2 changes: 1 addition & 1 deletion app/cron/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,4 +2,4 @@ var cron = require('cron');
var factScraper = require.main.require('./app/cron/fact-scraper');

// Check for new facts once a day
new cron.CronJob('0 0 0 * * *', factScraper.scrape, null, true);
new cron.CronJob('0 0 0 * * *', factScraper.scrape, null, true);
32 changes: 22 additions & 10 deletions app/models/recipient.js
Original file line number Diff line number Diff line change
@@ -1,26 +1,38 @@
var mongoose = require('mongoose');
var Schema = mongoose.Schema;
var strings = require.main.require('./app/config/strings');
const mongoose = require('mongoose');
const Schema = mongoose.Schema;
const strings = require.main.require('./app/config/strings');
const mongooseDelete = require('mongoose-delete');

var RecipientSchema = new Schema({
const RecipientSchema = new Schema({
name: String,
number: {type: String, required: true, validate: validateNumber, unique: true},
number: {
type: String,
required: true,
unique: true,
validate: [
function phoneNumber(string) {
return string.length == 10;
}
]
},
addedBy: {type: Schema.Types.ObjectId, ref: 'User'}
}, {
timestamps: true
});

function validateNumber(string) {
return string.length == 10;
}

RecipientSchema.path('number').validate(function(number, done) {
this.model('Recipient').count({number: number}, function(err, count) {
if (err) return done(err);
done(!count);
});
}, strings.recipient.exists);

var Recipient = mongoose.model('Recipient', RecipientSchema);
/**
* Soft delete implementation
* https://github.com/dsanel/mongoose-delete
*/
RecipientSchema.plugin(mongooseDelete, {overrideMethods: true});

const Recipient = mongoose.model('Recipient', RecipientSchema);

module.exports = Recipient;
57 changes: 32 additions & 25 deletions app/routes/fact.routes.js
Original file line number Diff line number Diff line change
@@ -1,34 +1,41 @@
var express = require('express');
var router = express.Router();
var Fact = require.main.require('./app/models/fact');
var User = require.main.require('./app/models/user');
var Upvote = require.main.require('./app/models/upvote');
var Message = require.main.require('./app/models/message');
var Recipient = require.main.require('./app/models/recipient');
var FactService = require.main.require('./app/services/fact.service');
var apiai = require('apiai-promise');
var keys = require.main.require('./app/config/keys');
var catbot = apiai(keys.apiai.accessToken);
var strings = require.main.require('./app/config/strings.js');
var bluebird = require('bluebird');
const express = require('express');
const router = express.Router();
const Fact = require.main.require('./app/models/fact');
const User = require.main.require('./app/models/user');
const Upvote = require.main.require('./app/models/upvote');
const Message = require.main.require('./app/models/message');
const Recipient = require.main.require('./app/models/recipient');
const FactService = require.main.require('./app/services/fact.service');
const apiai = require('apiai-promise');
const keys = require.main.require('./app/config/keys');
const catbot = apiai(keys.apiai.accessToken);
const strings = require.main.require('./app/config/strings.js');
const Promise = require('bluebird');

// (Tasker route) Text was recieved from recipient, process it and respond
router.get('/text', function(req, res) {

if (!req.query.query) return error({}, "No text query provided");
if (!req.query.number) return error({}, "No phone number provided");

var io = req.app.get('socketio');
const io = req.app.get('socketio');

Recipient.findOne({number: req.query.number})
var overrideMessage;

Recipient.findOneWithDeleted({number: req.query.number})

.then(function(recipient) {

var promises = {};

if (recipient) {

var incoming = new Message({
if (recipient.deleted) {
recipient.restore();
overrideMessage = "Welcome back!";
}

const incoming = new Message({
text: req.query.query,
number: req.query.number,
type: 'incoming'
Expand All @@ -51,7 +58,7 @@ router.get('/text', function(req, res) {

}

return bluebird.props(promises);
return Promise.props(promises);
})

.then(function(result) {
Expand All @@ -68,7 +75,7 @@ router.get('/text', function(req, res) {
response = strings.welcomeMessage;
}

var outgoing = new Message({text: response, number: req.query.number, type: 'outgoing'});
const outgoing = new Message({text: overrideMessage || response, number: req.query.number, type: 'outgoing'});

outgoing.save().then(function(message) {
io.emit('message', {message: message, recipient: result.recipient});
Expand All @@ -77,8 +84,8 @@ router.get('/text', function(req, res) {
});
})

.catch(function(error) {
return error(error.message || null);
.catch(function(err) {
return error(err.message || null);
});

function success(message) {
Expand Down Expand Up @@ -148,9 +155,9 @@ router.post('/submitted', function(req, res) {
if (req.user) {
if (!req.body.text) return res.status(400).json({message: "Provide a cat fact"});

var io = req.app.get('socketio');
const io = req.app.get('socketio');

var fact = new Fact({
const fact = new Fact({
user: req.user._id,
text: req.body.text
});
Expand Down Expand Up @@ -181,9 +188,9 @@ router.post('/submitted/:factID/upvote', function(req, res) {
if (!fact) return res.status(404).json({message: "That fact doesn't exist"});
if (fact.user.equals(req.user._id)) return res.status(400).json({message: "You can't upvote your own fact"});

var io = req.app.get('socketio');
const io = req.app.get('socketio');

var upvote = new Upvote({
const upvote = new Upvote({
user: req.user._id,
fact: req.params.factID
});
Expand All @@ -208,7 +215,7 @@ router.delete('/submitted/:factID/upvote', function(req, res) {
if (req.user) {
if (!req.params.factID) return res.status(400).json({message: "Provide a fact ID"});

var io = req.app.get('socketio');
const io = req.app.get('socketio');

Upvote.findOneAndRemove({fact: req.params.factID, user: req.user._id}).then(function() {
io.emit('fact:unvote', {fact: {_id: req.params.factID}, user: req.user});
Expand Down
143 changes: 81 additions & 62 deletions app/routes/webhook.routes.js
Original file line number Diff line number Diff line change
@@ -1,80 +1,99 @@
var express = require('express');
var router = express.Router();
var bluebird = require('bluebird');
var Recipient = require.main.require('./app/models/recipient');
var strings = require.main.require('./app/config/strings');
var IFTTTService = require.main.require('./app/services/ifttt.service.js');
var FactService = require.main.require('./app/services/fact.service');
const express = require('express');
const router = express.Router();
const Promise = require('bluebird');

const appConfig = require.main.require('./app/config/app-settings');
const Recipient = require.main.require('./app/models/recipient');
const strings = require.main.require('./app/config/strings');
const IFTTTService = require.main.require('./app/services/ifttt.service.js');
const FactService = require.main.require('./app/services/fact.service');

const keys = require.main.require('./app/config/keys');
const apiai = require('apiai-promise');
const catbot = apiai(keys.apiai.accessToken);
const crypto = require('crypto');

var processWebhook = function(req) {
console.log('worked');
var deferred = bluebird.defer();
return new Promise((resolve, reject) => {

if (req.body && req.body.result) {

switch (req.body.result.action) {
case 'fact.get':

FactService.getFact().then(function(fact) {
deferred.resolve(fact);
});

break;

case 'recipient.add':
if (req.body.result.parameters) {
var parameters = req.body.result.parameters,
name = parameters['given-name'] + (parameters['last-name'] ? ' ' + parameters['last-name'] : ''),
number = parameters['phone-number'].replace(/\D/g,'').replace(/^1+/, '');

if (number.length != 10 || number.length != 11)
return deferred.reject({message: strings.invalidNumber});

var recipient = new Recipient({
name: name,
number: number
if (req.body && req.body.result) {

switch (req.body.result.action) {
case 'fact.get':

FactService.getFact().then(function(fact) {
resolve({message: fact});
});

break;

case 'recipient.add':
if (req.body.result.parameters) {
var parameters = req.body.result.parameters,
name = parameters['given-name'] + (parameters['last-name'] ? ' ' + parameters['last-name'] : ''),
number = parameters['phone-number'].replace(/\D/g,'').replace(/^1+/, '');
console.log(number);
if (number.length != 10 && number.length != 11)
return resolve({message: strings.invalidNumber});

var recipient = new Recipient({
name: name,
number: number
});

recipient.save().then(function() {
IFTTTService.sendSingleMessage({
number: number,
msg: strings.welcomeMessage
});

resolve({message: req.body.result.fulfillment.messages[0].speech});

}, function(err) {
reject(err);
});
} else {
reject();
}
break;

case 'recipient.unsubscribe':
if (appConfig.allowUsersToUnsubscribe()) {
const recipientNumber = req.body.sessionId;

recipient.save().then(function() {
IFTTTService.sendSingleMessage({
number: number,
message: strings.welcomeMessage
Recipient.delete({number: recipientNumber}).then(result => {
resolve({message: req.body.result.fulfillment.messages[0].speech});
}, err => {
reject(err);
});
} else {
const randomSessionId = crypto.createHash('md5').update((new Date()).getTime().toString()).digest('hex');

deferred.resolve(req.body.result.fulfullment.messages[0].speech);

}, function(err) {
deferred.reject(err);
});
} else {
deferred.reject();
}
break;

case 'recipient.unsubscribe':
console.log(req);
break;

default:
deferred.reject();
break;
}
} else {
deferred.reject();
}

return deferred.promise;
catbot.textRequest('unsubscribe', {sessionId: randomSessionId}).then(response => {
resolve({message: response.result.fulfillment.speech});
});
}
break;

default:
reject(new Error('No action specified'));
break;
}
} else {
reject(new Error('No request body provided'));
}
});
};


// Route for api.ai webhook
router.post('/', function(req, res) {

processWebhook(req).then(function(message) {
processWebhook(req).then(function(response) {

return res.json({
speech: message,
displayText: message,
speech: response.message,
displayText: response.message,
data: {},
contextOut: [],
source: "Cat Facts"
Expand Down
1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@
"googleapis": "^19.0.0",
"method-override": "^2.3.7",
"mongoose": "^4.10.0",
"mongoose-delete": "^0.4.0",
"mongoose-simple-random": "^0.4.1",
"morgan": "^1.7.0",
"node-ifttt-maker": "^0.1.2",
Expand Down
Loading

0 comments on commit 07c0ecf

Please sign in to comment.