130 lines
2.9 KiB
JavaScript
130 lines
2.9 KiB
JavaScript
const fs = require('fs').promises;
|
|
const fshelpers = require('./fshelpers');
|
|
const crypto = require('crypto');
|
|
const { DateTime } = require('luxon');
|
|
|
|
function checkInitialized()
|
|
{
|
|
if (!global.repositoryData)
|
|
throw new Error('Repository not initialized, call init() first');
|
|
}
|
|
|
|
|
|
async function init(filename, salt)
|
|
{
|
|
if (global.repositoryData)
|
|
throw new Error('Repository is already initialized');
|
|
|
|
global.repositoryData = {
|
|
filename: filename,
|
|
salt: salt,
|
|
notifications: {}
|
|
};
|
|
|
|
if (!(await fshelpers.exists(filename)))
|
|
return;
|
|
|
|
const contents = await fs.readFile(filename, 'utf8');
|
|
global.repositoryData.notifications = JSON.parse(contents.toString());
|
|
}
|
|
|
|
|
|
async function flush()
|
|
{
|
|
const contents = JSON.stringify(global.repositoryData.notifications, null, 2);
|
|
await fs.writeFile(global.repositoryData.filename, contents, 'utf8');
|
|
}
|
|
|
|
|
|
function getNotificationToken(id)
|
|
{
|
|
const hasher = crypto.createHmac("sha256", global.repositoryData.salt);
|
|
return hasher.update(id).digest("hex");
|
|
}
|
|
|
|
|
|
function getUnixTimestamp()
|
|
{
|
|
return Math.floor(DateTime.now().toSeconds());
|
|
}
|
|
|
|
|
|
|
|
// Returns the notification token if it should be sent out or null if the notification is latched
|
|
async function storeNotification(id, title)
|
|
{
|
|
checkInitialized();
|
|
|
|
const now = getUnixTimestamp();
|
|
const token = getNotificationToken(id);
|
|
|
|
if (!global.repositoryData.notifications.hasOwnProperty(token))
|
|
{
|
|
console.info(`New notification with id '${id}' and token '${token}', send permitted`);
|
|
|
|
global.repositoryData.notifications[token] = {
|
|
id: id,
|
|
title: title,
|
|
latched: true,
|
|
latchTime: now,
|
|
resetTime: null,
|
|
reminders: true,
|
|
remindTime: null
|
|
};
|
|
|
|
await flush();
|
|
return token;
|
|
}
|
|
|
|
const notification = global.repositoryData.notifications[token];
|
|
|
|
if (notification.latched)
|
|
{
|
|
console.info(`Notification with id ${id} and token '${token}' is already latched, send blocked`);
|
|
return null;
|
|
}
|
|
|
|
console.info(`Latching notification with id ${id} and token '${token}', send permitted`);
|
|
notification.latched = true;
|
|
notification.latchTime = now;
|
|
|
|
await flush();
|
|
return token;
|
|
}
|
|
|
|
|
|
async function resetNotification(token)
|
|
{
|
|
checkInitialized();
|
|
|
|
const now = getUnixTimestamp();
|
|
|
|
if (!global.repositoryData.notifications.hasOwnProperty(token))
|
|
{
|
|
console.info(`Notification token '${token}' does not exist, reset unneccesary`);
|
|
return;
|
|
}
|
|
|
|
const notification = global.repositoryData.notifications[token];
|
|
|
|
if (!notification.latched)
|
|
{
|
|
console.info(`Notification with id '${notification.id}' and token '${token}' is not latched, reset unneccesary`);
|
|
return;
|
|
}
|
|
|
|
console.info(`Resetting notification with id '${notification.id}' and token '${token}'`);
|
|
notification.latched = false;
|
|
notification.resetTime = now;
|
|
notification.reminders = true;
|
|
notification.remindTime = null;
|
|
|
|
await flush();
|
|
}
|
|
|
|
|
|
module.exports = {
|
|
init,
|
|
storeNotification,
|
|
resetNotification
|
|
} |