UNPKG

3.71 kBJavaScriptView Raw
1// Copyright Michael Rhodes. 2017,2018. All Rights Reserved.
2// This file is licensed under the MIT License.
3// License text available at https://opensource.org/licenses/MIT
4
5var debug = require('debug')('antisocial-friends');
6var VError = require('verror').VError;
7var WError = require('verror').WError;
8var async = require('async');
9
10module.exports = function mountFriendWebhook(antisocialApp) {
11
12 var router = antisocialApp.router;
13 var config = antisocialApp.config;
14 var db = antisocialApp.db;
15 var authUserMiddleware = antisocialApp.authUserMiddleware;
16
17 var webhookRegex = /^\/([a-zA-Z0-9\-.]+)\/friend-webhook$/;
18
19 debug('mounting GET /username/friend-webhook', webhookRegex);
20
21 router.post(webhookRegex, function handleFriendRequest(req, res) {
22 var matches = req.path.match(webhookRegex);
23 var username = matches[1];
24
25 async.waterfall([
26 function getUser(cb) {
27 debug('/friend-webhook getUser');
28 db.getInstances('users', [{
29 'property': 'username',
30 'value': username
31 }], function (err, userInstances) {
32 if (err) {
33 return cb(new VError(err, 'user not found'));
34 }
35
36 if (userInstances.length > 1) {
37 return cb(new VError('more than one user matching username'));
38 }
39
40 if (!userInstances.length) {
41 return cb(new VError('user not found'));
42 }
43
44 var user = userInstances[0];
45
46 cb(err, user);
47 });
48 },
49 function getFriendByAccessToken(user, cb) {
50 debug('/friend-webhook getFriendByAccessToken');
51 db.getInstances('friends', [{
52 'property': 'userId',
53 'value': user.id
54 }, {
55 'property': 'localAccessToken',
56 'value': req.body.accessToken
57 }], function (err, friendInstances) {
58 if (err) {
59 return cb(new VError(err, 'error reading friends'));
60 }
61
62 if (!friendInstances.length) {
63 return cb(new VError(err, 'friend not found'));
64 }
65
66 cb(err, user, friendInstances[0]);
67 });
68 },
69 function updateFriend(user, friend, cb) {
70 debug('/friend-webhook updateFriend action ' + req.body.action);
71
72 if (req.body.action === 'friend-request-accepted') {
73 // mark friend as accepted
74 friend.audiences.push('friends');
75 var update = {
76 'status': 'accepted',
77 'audiences': friend.audiences
78 };
79
80 db.updateInstance('friends', friend.id, update, function (err, friend) {
81 if (err) {
82 var e = new VError(err, '/friend-webhook friend-request-accepted error');
83 return cb(e, friend);
84 }
85
86 antisocialApp.emit('new-friend', {
87 'info': {
88 'friend': friend,
89 'user': user
90 }
91 });
92
93 cb(null, friend);
94 });
95 }
96 else if (req.body.action === 'friend-update') {
97
98 antisocialApp.emit('friend-updated', {
99 'info': {
100 'friend': friend,
101 'user': user
102 }
103 });
104
105 cb(null, friend);
106 }
107 else if (req.body.action === 'friend-request-declined' || req.body.action === 'request-friend-cancel' || req.body.action === 'friend-delete') {
108
109 antisocialApp.emit('friend-deleted', {
110 'info': {
111 'friend': JSON.parse(JSON.stringify(friend)),
112 'user': user
113 }
114 });
115
116 db.deleteInstance('friends', friend.id, function (err, friend) {
117 if (err) {
118 var e = new VError(err, '/friend-webhook friend-request-declined error');
119 return cb(e);
120 }
121
122 cb(null);
123 });
124 }
125 else {
126 return cb(new VError('unknown webhook action'));
127 }
128 }
129 ], function (err) {
130 if (err) {
131 var e = new WError(err, '/friend-webook failed');
132 return res.send({
133 'status': 'error',
134 'reason': e.message,
135 'details': e.cause().message
136 });
137 }
138 res.send({
139 'status': 'ok'
140 });
141 });
142 });
143};