feat: integrate sonner for toast notifications and enhance UI feedback
Added the sonner library for toast notifications across various components, improving user feedback for actions such as saving settings, syncing rules, and handling errors. Updated the layout to include a Toaster component for consistent notification display. Refactored alert messages in the backups, gre, and filters pages to utilize the new notification system, enhancing overall user experience.
This commit is contained in:
1 parent
84ecd4f061
commit
11ad94f67d
33 files changed
+12350
-252
No files matched your search
@@ -20,6 +20,7 @@ import { ingestAlertSignals } from "./signal-ingestor.js"
|
||||
import { getLatestSourceFinishedAt, getSourceWatermark, updateSourceWatermark } from "./source-watermark.js"
|
||||
import { pickTelegramAlertEmoji } from "./telegram-emoji.js"
|
||||
import type { AlertEngineRunResult, RuleEvalHit } from "./types.js"
|
||||
import { appendEvent } from "../../modules/events/service/events-service.js"
|
||||
|
||||
const SNAPSHOT_SOURCE_WAIT_MS = 30_000
|
||||
const SNAPSHOT_SOURCE_POLL_MS = 20
|
||||
@@ -182,6 +183,32 @@ export async function runAlertEngineOnce(): Promise<AlertEngineRunResult> {
|
||||
const outbox = await dispatchPendingOutbox()
|
||||
errors.push(...outbox.errors)
|
||||
|
||||
if (standaloneFires > 0 || groupFires > 0) {
|
||||
appendEvent({
|
||||
level: "info",
|
||||
eventType: "alerts.engine.fired",
|
||||
sourceModule: "alerts",
|
||||
title: "Движок алертов обнаружил события",
|
||||
message: `Правила: ${standaloneFires}, группы: ${groupFires}`,
|
||||
payload: {
|
||||
sampledAt,
|
||||
rulesChecked: hasNewSources ? rules.length : 0,
|
||||
},
|
||||
})
|
||||
}
|
||||
if (errors.length > 0) {
|
||||
appendEvent({
|
||||
level: "warning",
|
||||
eventType: "alerts.engine.errors",
|
||||
sourceModule: "alerts",
|
||||
title: "Ошибки в движке алертов",
|
||||
message: errors[0] ?? "Неизвестная ошибка",
|
||||
payload: {
|
||||
totalErrors: errors.length,
|
||||
},
|
||||
})
|
||||
}
|
||||
|
||||
return {
|
||||
sampledAt,
|
||||
rulesChecked: hasNewSources ? rules.length : 0,
|
||||
|
||||
@@ -43,6 +43,7 @@ import {
|
||||
isSchedulerJobRunning,
|
||||
tryBeginSchedulerJob,
|
||||
} from "./scheduler-running.js"
|
||||
import { appendEvent } from "../modules/events/service/events-service.js"
|
||||
|
||||
export const JOB_KEYS = [
|
||||
"traffic",
|
||||
@@ -138,6 +139,19 @@ async function runSchedulerJobBody(jobKey: SchedulerJobKey): Promise<void> {
|
||||
durationMs: Date.now() - startedAt,
|
||||
result: snapshot ?? null,
|
||||
})
|
||||
appendEvent({
|
||||
level: "info",
|
||||
eventType: "scheduler.job.ok",
|
||||
sourceModule: "scheduler",
|
||||
title: "Задача планировщика завершена",
|
||||
message: `${jobKey}: выполнено за ${Date.now() - startedAt} мс`,
|
||||
entityType: "job",
|
||||
entityId: jobKey,
|
||||
payload: {
|
||||
startedAt: startedIso,
|
||||
finishedAt: finishedIso,
|
||||
},
|
||||
})
|
||||
if (
|
||||
jobKey === "traffic" ||
|
||||
jobKey === "servers_rest_ping" ||
|
||||
@@ -160,6 +174,19 @@ async function runSchedulerJobBody(jobKey: SchedulerJobKey): Promise<void> {
|
||||
durationMs: Date.now() - startedAt,
|
||||
result: snapshot ?? null,
|
||||
})
|
||||
appendEvent({
|
||||
level: "critical",
|
||||
eventType: "scheduler.job.failed",
|
||||
sourceModule: "scheduler",
|
||||
title: "Ошибка задачи планировщика",
|
||||
message: `${jobKey}: ${msg}`,
|
||||
entityType: "job",
|
||||
entityId: jobKey,
|
||||
payload: {
|
||||
startedAt: startedIso,
|
||||
finishedAt: finishedIso,
|
||||
},
|
||||
})
|
||||
throw e
|
||||
}
|
||||
}
|
||||
|
||||
Reference in new issue
Block a user