feat: auto-disable store after notification and improve ntfy payloads
This commit is contained in:
@@ -33,7 +33,8 @@ async function sendNtfyNotification(adminNtfy, userNtfy, payload) {
|
|||||||
const url = `${server}/${topic}`;
|
const url = `${server}/${topic}`;
|
||||||
const headers = {
|
const headers = {
|
||||||
Title: payload.title,
|
Title: payload.title,
|
||||||
Priority: payload.priority || 'default'
|
Priority: payload.priority || 'default',
|
||||||
|
'Content-Type': 'text/plain; charset=utf-8'
|
||||||
};
|
};
|
||||||
if (adminNtfy.username && adminNtfy.password) {
|
if (adminNtfy.username && adminNtfy.password) {
|
||||||
const credentials = Buffer.from(`${adminNtfy.username}:${adminNtfy.password}`).toString('base64');
|
const credentials = Buffer.from(`${adminNtfy.username}:${adminNtfy.password}`).toString('base64');
|
||||||
@@ -51,8 +52,8 @@ async function sendTelegramNotification(adminTelegram, userTelegram, payload) {
|
|||||||
endpoint,
|
endpoint,
|
||||||
{
|
{
|
||||||
chat_id: userTelegram.chatId,
|
chat_id: userTelegram.chatId,
|
||||||
text: `${payload.title}\n${payload.message}`,
|
text: payload.message,
|
||||||
disable_web_page_preview: true
|
disable_web_page_preview: false
|
||||||
},
|
},
|
||||||
{ timeout: 15000 }
|
{ timeout: 15000 }
|
||||||
);
|
);
|
||||||
@@ -71,22 +72,25 @@ async function notifyChannels(profileId, template) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
async function sendSlotNotification({ profileId, storeName, pickupDate, onlyNotify, booked }) {
|
async function sendSlotNotification({ profileId, storeName, pickupDate, onlyNotify, booked, storeId }) {
|
||||||
const dateLabel = formatDateLabel(pickupDate);
|
const dateLabel = formatDateLabel(pickupDate);
|
||||||
const title = onlyNotify
|
const title = onlyNotify
|
||||||
? `Slot verfügbar bei ${storeName}`
|
? `Slot verfügbar bei ${storeName}`
|
||||||
: booked
|
: booked
|
||||||
? `Slot gebucht bei ${storeName}`
|
? `Slot gebucht bei ${storeName}`
|
||||||
: `Slot gefunden bei ${storeName}`;
|
: `Slot gefunden bei ${storeName}`;
|
||||||
const message = onlyNotify
|
const baseMessage = onlyNotify
|
||||||
? `Es wurde ein freier Slot am ${dateLabel} entdeckt.`
|
? `Es wurde ein freier Slot am ${dateLabel} entdeckt.`
|
||||||
: booked
|
: booked
|
||||||
? `Der Slot am ${dateLabel} wurde erfolgreich gebucht.`
|
? `Der Slot am ${dateLabel} wurde erfolgreich gebucht.`
|
||||||
: `Es wurde ein Slot am ${dateLabel} gefunden.`;
|
: `Es wurde ein Slot am ${dateLabel} gefunden.`;
|
||||||
|
const storeLink = storeId ? `https://foodsharing.de/store/${storeId}` : null;
|
||||||
|
const fullMessage = storeLink ? `${title}\n${baseMessage}\n${storeLink}` : `${title}\n${baseMessage}`;
|
||||||
|
|
||||||
await notifyChannels(profileId, {
|
await notifyChannels(profileId, {
|
||||||
title,
|
title,
|
||||||
message,
|
message: fullMessage,
|
||||||
|
link: storeLink,
|
||||||
priority: booked ? 'high' : 'default'
|
priority: booked ? 'high' : 'default'
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -3,6 +3,7 @@ const foodsharingClient = require('./foodsharingClient');
|
|||||||
const sessionStore = require('./sessionStore');
|
const sessionStore = require('./sessionStore');
|
||||||
const { DEFAULT_SETTINGS } = require('./adminConfig');
|
const { DEFAULT_SETTINGS } = require('./adminConfig');
|
||||||
const notificationService = require('./notificationService');
|
const notificationService = require('./notificationService');
|
||||||
|
const { readConfig, writeConfig } = require('./configStore');
|
||||||
|
|
||||||
const weekdayMap = {
|
const weekdayMap = {
|
||||||
Montag: 'Monday',
|
Montag: 'Monday',
|
||||||
@@ -55,6 +56,34 @@ function resolveSettings(settings) {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function deactivateEntryInMemory(entry) {
|
||||||
|
if (entry) {
|
||||||
|
entry.active = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
function persistEntryDeactivation(profileId, entryId) {
|
||||||
|
if (!profileId || !entryId) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
try {
|
||||||
|
const config = readConfig(profileId);
|
||||||
|
let changed = false;
|
||||||
|
const updated = config.map((item) => {
|
||||||
|
if (String(item?.id) === String(entryId) && item?.active !== false) {
|
||||||
|
changed = true;
|
||||||
|
return { ...item, active: false };
|
||||||
|
}
|
||||||
|
return item;
|
||||||
|
});
|
||||||
|
if (changed) {
|
||||||
|
writeConfig(profileId, updated);
|
||||||
|
}
|
||||||
|
} catch (error) {
|
||||||
|
console.error(`[CONFIG] Konnte Eintrag ${entryId} für Profil ${profileId} nicht deaktivieren:`, error.message);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
async function ensureSession(session) {
|
async function ensureSession(session) {
|
||||||
const profileId = session.profile?.id;
|
const profileId = session.profile?.id;
|
||||||
if (!profileId) {
|
if (!profileId) {
|
||||||
@@ -166,8 +195,11 @@ async function processBooking(session, entry, pickup) {
|
|||||||
storeName,
|
storeName,
|
||||||
pickupDate: pickup.date,
|
pickupDate: pickup.date,
|
||||||
onlyNotify: true,
|
onlyNotify: true,
|
||||||
booked: false
|
booked: false,
|
||||||
|
storeId: entry.id
|
||||||
});
|
});
|
||||||
|
deactivateEntryInMemory(entry);
|
||||||
|
persistEntryDeactivation(session.profile.id, entry.id);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -185,14 +217,20 @@ async function processBooking(session, entry, pickup) {
|
|||||||
storeName,
|
storeName,
|
||||||
pickupDate: pickup.date,
|
pickupDate: pickup.date,
|
||||||
onlyNotify: false,
|
onlyNotify: false,
|
||||||
booked: true
|
booked: true,
|
||||||
|
storeId: entry.id
|
||||||
});
|
});
|
||||||
|
deactivateEntryInMemory(entry);
|
||||||
|
persistEntryDeactivation(session.profile.id, entry.id);
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
console.error(`[ERROR] Buchung für ${storeName} am ${readableDate} fehlgeschlagen:`, error.message);
|
console.error(`[ERROR] Buchung für ${storeName} am ${readableDate} fehlgeschlagen:`, error.message);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
async function checkEntry(sessionId, entry, settings) {
|
async function checkEntry(sessionId, entry, settings) {
|
||||||
|
if (entry?.active === false) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
const session = sessionStore.get(sessionId);
|
const session = sessionStore.get(sessionId);
|
||||||
if (!session) {
|
if (!session) {
|
||||||
return;
|
return;
|
||||||
|
|||||||
Reference in New Issue
Block a user