feat: otomatik e-posta bildirimi
Kullanıcı kriter kaydediyor; sunucu periyodik olarak eşleşen YENİ ihaleleri bulup özet e-posta gönderiyor. - server/notify-store.mjs: abonelik deposu (SQLite, kalıcı volume'de) kriterler: il · sektör · alım türü · anahtar kelime · favori kurumlar - server/notifier.mjs: eşleştirme + gönderim motoru · aynı ihale iki kez bildirilmez (sonGorulenler takibi) · ilk abonelikte geçmiş bildirilmez, yalnızca temel alınır (spam önleme) · sonuçlanmış/arşiv kayıtları bildirime girmez - /api/notify/subscriptions (GET/POST/DELETE) + /api/notify/run (admin, anlık test) - scheduler: NOTIFY_INTERVAL_SAAT (varsayılan 6) ile periyodik tur - NotifySubscriptions paneli: kriter ekle/sil, 'ekrandaki filtreleri kullan' - tendersPayload ortak yardımcısına çıkarıldı (API ve bildirim aynı veriyi kullanır)
This commit is contained in:
+29
-1
@@ -14,6 +14,7 @@ import os from 'node:os';
|
||||
import path from 'node:path';
|
||||
import { fileURLToPath } from 'node:url';
|
||||
import { historyStats } from './history-store.mjs';
|
||||
import { bildirimleriIsle } from './notifier.mjs';
|
||||
|
||||
const __dirname = path.dirname(fileURLToPath(import.meta.url));
|
||||
|
||||
@@ -137,7 +138,24 @@ export function schedulerStatus() {
|
||||
};
|
||||
}
|
||||
|
||||
export function startScheduler() {
|
||||
// --- Otomatik e-posta bildirimi ---
|
||||
let bildirimCalisiyor = false;
|
||||
|
||||
async function bildirimTuru(tenderGetir) {
|
||||
if (bildirimCalisiyor) return;
|
||||
bildirimCalisiyor = true;
|
||||
try {
|
||||
const s = await bildirimleriIsle(tenderGetir);
|
||||
if (s.atlandi) console.log(`[scheduler] bildirim atlandı: ${s.atlandi}`);
|
||||
else console.log(`[scheduler] bildirim turu: ${s.abonelik} abonelik, ${s.gonderilen || 0} e-posta, ${s.hata || 0} hata`);
|
||||
} catch (e) {
|
||||
console.warn('[scheduler] bildirim hatası:', e.message);
|
||||
} finally {
|
||||
bildirimCalisiyor = false;
|
||||
}
|
||||
}
|
||||
|
||||
export function startScheduler({ tenderGetir } = {}) {
|
||||
if (process.env.SCAN_ENABLED === '0') {
|
||||
console.log('[scheduler] devre dışı (SCAN_ENABLED=0)');
|
||||
return;
|
||||
@@ -158,4 +176,14 @@ export function startScheduler() {
|
||||
setTimeout(dtTara, 4 * 60 * 1000).unref?.();
|
||||
setInterval(dtTara, Math.max(1, dtSaat) * 3600 * 1000).unref?.();
|
||||
}
|
||||
|
||||
// Otomatik e-posta bildirimi
|
||||
if (process.env.NOTIFY_ENABLED === '0' || !tenderGetir) {
|
||||
console.log('[scheduler] otomatik e-posta bildirimi devre dışı');
|
||||
} else {
|
||||
const nSaat = Number(process.env.NOTIFY_INTERVAL_SAAT || 6);
|
||||
console.log(`[scheduler] otomatik e-posta bildirimi her ${nSaat} saatte bir kontrol edilecek`);
|
||||
setTimeout(() => bildirimTuru(tenderGetir), 6 * 60 * 1000).unref?.();
|
||||
setInterval(() => bildirimTuru(tenderGetir), Math.max(1, nSaat) * 3600 * 1000).unref?.();
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user