From d9aa46675873ada232836562012a2087eaeb6ced Mon Sep 17 00:00:00 2001 From: marco370 <48531002-marco370@users.noreply.replit.com> Date: Tue, 25 Nov 2025 09:56:13 +0000 Subject: [PATCH] Enhance detection filtering and increase result limits Update API endpoints and storage logic to support filtering detections by anomaly type, minimum/maximum risk score, and to increase the default limit of returned detections. Replit-Commit-Author: Agent Replit-Commit-Session-Id: 7a657272-55ba-4a79-9a2e-f1ed9bc7a528 Replit-Commit-Checkpoint-Type: intermediate_checkpoint Replit-Commit-Event-Id: 2236a0ee-4ac6-4527-bd70-449e36f71c7e Replit-Commit-Screenshot-Url: https://storage.googleapis.com/screenshot-production-us-central1/449cf7c4-c97a-45ae-8234-e5c5b8d6a84f/7a657272-55ba-4a79-9a2e-f1ed9bc7a528/1zhedLT --- server/routes.ts | 15 ++++++++++++--- server/storage.ts | 39 ++++++++++++++++++++++++++++++++++++--- 2 files changed, 48 insertions(+), 6 deletions(-) diff --git a/server/routes.ts b/server/routes.ts index 9d0e21d..09b9884 100644 --- a/server/routes.ts +++ b/server/routes.ts @@ -63,8 +63,17 @@ export async function registerRoutes(app: Express): Promise { // Detections app.get("/api/detections", async (req, res) => { try { - const limit = parseInt(req.query.limit as string) || 100; - const detections = await storage.getAllDetections(limit); + const limit = req.query.limit ? parseInt(req.query.limit as string) : 500; + const anomalyType = req.query.anomalyType as string | undefined; + const minScore = req.query.minScore ? parseFloat(req.query.minScore as string) : undefined; + const maxScore = req.query.maxScore ? parseFloat(req.query.maxScore as string) : undefined; + + const detections = await storage.getAllDetections({ + limit, + anomalyType, + minScore, + maxScore + }); res.json(detections); } catch (error) { console.error('[DB ERROR] Failed to fetch detections:', error); @@ -181,7 +190,7 @@ export async function registerRoutes(app: Express): Promise { app.get("/api/stats", async (req, res) => { try { const routers = await storage.getAllRouters(); - const detections = await storage.getAllDetections(1000); + const detections = await storage.getAllDetections({ limit: 1000 }); const recentLogs = await storage.getRecentLogs(1000); const whitelist = await storage.getAllWhitelist(); const latestTraining = await storage.getLatestTraining(); diff --git a/server/storage.ts b/server/storage.ts index e6c5b63..45b028b 100644 --- a/server/storage.ts +++ b/server/storage.ts @@ -35,7 +35,12 @@ export interface IStorage { getLogsForTraining(limit: number, minTimestamp?: Date): Promise; // Detections - getAllDetections(limit: number): Promise; + getAllDetections(options: { + limit?: number; + anomalyType?: string; + minScore?: number; + maxScore?: number; + }): Promise; getDetectionByIp(sourceIp: string): Promise; createDetection(detection: InsertDetection): Promise; updateDetection(id: string, detection: Partial): Promise; @@ -140,12 +145,40 @@ export class DatabaseStorage implements IStorage { } // Detections - async getAllDetections(limit: number): Promise { - return await db + async getAllDetections(options: { + limit?: number; + anomalyType?: string; + minScore?: number; + maxScore?: number; + }): Promise { + const { limit = 500, anomalyType, minScore, maxScore } = options; + + // Build WHERE conditions + const conditions = []; + + if (anomalyType) { + conditions.push(eq(detections.anomalyType, anomalyType)); + } + + if (minScore !== undefined) { + conditions.push(gte(detections.riskScore, minScore.toString())); + } + + if (maxScore !== undefined) { + conditions.push(sql`${detections.riskScore}::numeric <= ${maxScore}`); + } + + const query = db .select() .from(detections) .orderBy(desc(detections.detectedAt)) .limit(limit); + + if (conditions.length > 0) { + return await query.where(and(...conditions)); + } + + return await query; } async getDetectionByIp(sourceIp: string): Promise {