mirror of
https://github.com/bckelley/cgm-remote-monitor.git
synced 2026-08-24 03:14:12 -05:00
158 lines
4.8 KiB
JavaScript
158 lines
4.8 KiB
JavaScript
'use strict';
|
|
|
|
const _ = require('lodash');
|
|
const crypto = require('crypto');
|
|
const NodeCache = require('node-cache');
|
|
|
|
const times = require('../times');
|
|
|
|
function init (env, ctx) {
|
|
|
|
function pushnotify () {
|
|
return pushnotify;
|
|
}
|
|
var levels = ctx.levels;
|
|
var receipts = new NodeCache({ stdTTL: times.hour().secs, checkperiod: times.mins(5).secs });
|
|
var recentlySent = new NodeCache({ stdTTL: times.mins(15).secs, checkperiod: 20 });
|
|
|
|
pushnotify.emitNotification = function emitNotification (notify) {
|
|
if (notify.clear) {
|
|
cancelPushoverNotifications();
|
|
sendMakerAllClear(notify);
|
|
return;
|
|
}
|
|
|
|
var key = notify.notifyhash || false;
|
|
|
|
if (!key) {
|
|
if (notify.isAnnouncement) {
|
|
//Announcement notifications are sent if they are different from whats been recently sent
|
|
key = notifyToHash(notify);
|
|
} else if (levels.isAlarm(notify.level)) {
|
|
//Alarms can be snoozed
|
|
//for WARN and higher use the plugin name and notification level so that louder alarms aren't triggered too often
|
|
key = notify.plugin.name + '_' + notify.level;
|
|
} else {
|
|
//INFO and lower notifications should be sent as long as they are different from whats been recently sent
|
|
key = notifyToHash(notify);
|
|
}
|
|
}
|
|
|
|
notify.key = key;
|
|
|
|
if (recentlySent.get(key)) {
|
|
console.info('notify: ' + key + ' has ALREADY been sent');
|
|
return;
|
|
} else if (!env.settings.isAlarmEventEnabled(notify)) {
|
|
console.info('notify: ' + key + ' will NOT be sent, it\'s been disabled');
|
|
return;
|
|
}
|
|
|
|
recentlySent.set(key, notify, 30);
|
|
|
|
sendPushoverNotifications(notify);
|
|
sendMakerEvent(notify);
|
|
|
|
};
|
|
|
|
pushnotify.pushoverAck = function pushoverAck (response) {
|
|
if (!response.receipt) { return false; }
|
|
|
|
var notify = receipts.get(response.receipt);
|
|
if (notify) {
|
|
console.info('push ack, response: ', response, ', notify: ', notify);
|
|
var snoozeMins = env.settings.snoozeFirstMinsForAlarmEvent(notify);
|
|
ctx.notifications.ack(notify.level, notify.group, times.mins(snoozeMins).msecs, true);
|
|
receipts.del(response.receipt);
|
|
} else {
|
|
console.info('unable to find notify for pushover ack', response, receipts.keys());
|
|
}
|
|
|
|
return !!notify;
|
|
};
|
|
|
|
function cancelPushoverNotifications () {
|
|
if (ctx.pushover) {
|
|
var receiptKeys = receipts.keys();
|
|
|
|
_.each(receiptKeys, function eachKey (receipt) {
|
|
ctx.pushover.cancelWithReceipt(receipt, function cancelCallback (err) {
|
|
if (err) {
|
|
console.error('error canceling receipt:' + receipt + ', err: ', err);
|
|
} else {
|
|
console.info('got a receipt cancel response for:' + receipt + ', removing from cache');
|
|
receipts.del(receipt);
|
|
}
|
|
});
|
|
});
|
|
}
|
|
}
|
|
|
|
function sendPushoverNotifications (notify) {
|
|
if (ctx.pushover) {
|
|
//add the key to the cache before sending, but with a short TTL
|
|
ctx.pushover.send(notify, function pushoverCallback (err, result) {
|
|
if (err) {
|
|
console.warn('Unable to send pushover', notify, err);
|
|
} else {
|
|
//result comes back as a string here, so fix it
|
|
result = JSON.parse(result);
|
|
//after successfully sent, increase the TTL
|
|
recentlySent.ttl(notify.key, times.mins(15).secs);
|
|
|
|
if (result.receipt) {
|
|
//if this was an emergency alarm, also hold on to the receipt/notify mapping, for later acking
|
|
console.info('storing pushover receipt', result.receipt, notify);
|
|
receipts.set(result.receipt, notify);
|
|
}
|
|
}
|
|
});
|
|
}
|
|
}
|
|
|
|
function sendMakerAllClear (notify) {
|
|
if (ctx.maker) {
|
|
ctx.maker.sendAllClear(notify, function makerCallback (err, result) {
|
|
if (err) {
|
|
console.error('unable to send maker allclear', notify, err);
|
|
} else if (result && result.sent) {
|
|
console.info('sent maker allclear', notify);
|
|
}
|
|
});
|
|
}
|
|
}
|
|
|
|
function sendMakerEvent (notify) {
|
|
if (!ctx.maker) {
|
|
return;
|
|
}
|
|
|
|
var event = {
|
|
name: notify.eventName || notify.plugin.name
|
|
, level: levels.toLowerCase(notify.level)
|
|
, value1: notify.title
|
|
, value2: notify.message && '\n' + notify.message
|
|
, isAnnouncement: notify.isAnnouncement
|
|
};
|
|
ctx.maker.sendEvent(event, function makerCallback (err) {
|
|
if (err) {
|
|
console.error('unable to send maker event', event, err);
|
|
} else {
|
|
console.info('sent maker event: ', event);
|
|
recentlySent.ttl(notify.key, times.mins(15).secs);
|
|
}
|
|
});
|
|
}
|
|
|
|
function notifyToHash (notify) {
|
|
var hash = crypto.createHash('sha1');
|
|
var info = JSON.stringify(_.pick(notify, ['title', 'message']));
|
|
hash.update(info);
|
|
return hash.digest('hex');
|
|
}
|
|
|
|
return pushnotify();
|
|
}
|
|
|
|
module.exports = init;
|