CodebaseAi commited on
Commit
c26ad8f
·
1 Parent(s): 9810f34
frontend/src/pages/Dashboard.jsx CHANGED
@@ -1,70 +1,78 @@
1
- import React, { useEffect, useState } from "react";
2
  import { useAuth } from "../context/AuthContext";
3
- import { useLocation } from "react-router-dom";
4
  import {
5
- PieChart,
6
- Pie,
7
- Cell,
8
- Tooltip,
9
- ResponsiveContainer,
10
- BarChart,
11
- Bar,
12
- XAxis,
13
- YAxis,
14
- CartesianGrid,
15
  } from "recharts";
16
  import {
17
- Shield,
18
- Cpu,
19
- Wifi,
20
- Activity,
21
- Radio,
22
  } from "lucide-react";
23
  import toast from "react-hot-toast";
24
  import NeonShield from "../components/NeonShield";
25
- import { useNavigate } from "react-router-dom";
26
  import ChatAssistant from "./ChatAssistant";
 
 
 
27
 
28
  const COLORS = ["#00e5ff", "#ff0059", "#a78bfa", "#fbbf24", "#10b981"];
29
 
30
  export default function Dashboard() {
31
- const location = useLocation();
32
  const navigate = useNavigate();
33
  const [systemStats, setSystemStats] = useState(null);
34
  const [threats, setThreats] = useState([]);
35
  const [mlModels, setMlModels] = useState([]);
36
  const [loading, setLoading] = useState(true);
37
  const [showTop, setShowTop] = useState(false);
 
 
 
 
 
 
 
38
 
 
 
 
 
 
 
 
 
 
 
 
 
 
39
  useEffect(() => {
40
- const scrollContainer = document.querySelector("main.flex-1.overflow-auto");
41
- if (!scrollContainer) return;
42
- const handleScroll = () => {
43
- if (scrollContainer.scrollTop > 300) setShowTop(true);
44
- else setShowTop(false);
45
- };
46
- scrollContainer.addEventListener("scroll", handleScroll);
47
- return () => scrollContainer.removeEventListener("scroll", handleScroll);
48
- }, []);
 
 
 
49
 
50
  const loadData = async () => {
51
  try {
52
  const [sys, ml, th] = await Promise.all([
53
- fetch("http://127.0.0.1:5000/api/system/status").then((r) => r.json()),
54
- fetch("http://127.0.0.1:5000/api/ml/models").then((r) => r.json()),
55
- fetch("http://127.0.0.1:5000/api/live/stats").then((r) => r.json()),
56
  ]);
57
- setSystemStats(sys || {});
58
  setMlModels(Array.isArray(ml) ? ml : []);
59
- setThreats(
60
- Object.entries(th || {}).map(([k, v]) => ({
61
- name: k.toUpperCase(),
62
- value: v,
63
- }))
64
- );
65
  } catch (err) {
66
- console.error("Dashboard Error:", err);
67
- toast.error("Failed to load dashboard data");
68
  } finally {
69
  setLoading(false);
70
  }
@@ -72,243 +80,548 @@ export default function Dashboard() {
72
 
73
  useEffect(() => {
74
  loadData();
 
 
75
  }, []);
76
 
77
  return (
78
- <>
79
- <div className="relative">
80
- {/* CYBER BACKGROUND */}
81
- <div className="absolute inset-0 -z-10 pointer-events-none overflow-hidden">
82
- <div className="absolute inset-0" style={{ background: "linear-gradient(140deg, rgba(3,6,23,0.75) 0%, rgba(9,19,39,0.7) 40%, rgba(10,26,54,0.6) 75%, rgba(15,7,33,0.65) 100%)" }} />
83
- <div className="absolute inset-0 opacity-[0.035] mix-blend-screen" style={{ backgroundImage: "url('https://raw.githubusercontent.com/ayushatlas/assets/main/hexgrid/hexgrid-light.png')", backgroundSize: "350px" }} />
84
- <div className="absolute left-0 lg:left-10 top-40 w-[300px] lg:w-[450px] h-[300px] lg:h-[450px] bg-cyan-400/15 blur-[120px] lg:blur-[180px]" />
85
- <div className="absolute right-0 lg:right-10 top-10 w-[280px] lg:w-[420px] h-[280px] lg:h-[420px] bg-purple-500/12 blur-[120px] lg:blur-[180px]" />
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
86
  </div>
 
 
 
 
 
 
87
 
88
- {/* HERO HEADER */}
89
- <header className="relative mb-12 lg:mb-24">
90
- <div className="relative z-20 container mx-auto px-6 lg:px-8 pt-16 lg:pt-24 pb-20 lg:pb-24 lg:ml-1">
91
- <div className="grid lg:grid-cols-2 gap-10 lg:gap-16 items-center">
92
-
93
- {/* LEFT TEXT */}
94
- <div className="space-y-6 lg:space-y-7 text-center lg:text-left">
95
- <div className="flex items-center justify-center lg:justify-start gap-3">
96
- <div className="p-2 rounded-full border border-accent/50 shadow-neon">
97
- <Shield size={20} className="text-accent" />
98
- </div>
99
- <span className="text-xs lg:text-sm text-slate-300/80 tracking-wide uppercase">
100
- AstraGuard AI • Adaptive NIDS
101
- </span>
102
- </div>
103
 
104
- <h1 className="text-4xl md:text-6xl lg:text-[70px] lg:leading-[76px] font-extrabold tracking-tight"
105
- style={{ textShadow: "0 0 30px rgba(0,229,255,0.75), 0 0 12px rgba(0,229,255,0.5)" }}>
106
- <span className="text-accent">Protect</span> Your <br /> Systems
107
- </h1>
 
 
 
 
 
 
 
 
 
 
 
108
 
109
- <div className="w-full overflow-hidden opacity-50 lg:opacity-100">
110
- <div className="neon-wave" />
111
- </div>
 
 
 
 
 
 
 
 
 
 
 
 
112
 
113
- <p className="text-slate-300/85 text-base lg:text-lg max-w-xl mx-auto lg:mx-0 leading-relaxed">
114
- Our adaptive AI framework provides real-time packet inspection,
115
- threat detection, and security analytics.
116
- </p>
117
-
118
- <div className="flex flex-col sm:flex-row items-center justify-center lg:justify-start gap-4 pt-3">
119
- <button onClick={() => navigate("/livetraffic")}
120
- className="w-full sm:w-auto px-8 py-3 rounded-xl bg-accent text-black font-bold text-lg shadow-neon active:scale-95 transition">
121
- Get Started
122
- </button>
123
- <button onClick={() => navigate("/threats")}
124
- className="w-full sm:w-auto px-8 py-3 rounded-xl border border-accent/40 text-accent text-lg hover:bg-accent/10 transition">
125
- Learn more
126
- </button>
127
- </div>
128
- </div>
129
 
130
- {/* RIGHT Floating Shield - Hidden on small mobile to save space */}
131
- <div className="relative w-full hidden sm:flex justify-center items-center h-[300px] lg:h-[420px]">
132
- <div className="relative w-[95%] lg:w-[90%] h-full rounded-3xl border border-accent/25 backdrop-blur-xl shadow-[0_0_40px_rgba(0,229,255,0.25)] overflow-hidden">
133
- <NeonShield />
134
- </div>
135
- </div>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
136
  </div>
 
137
  </div>
138
- </header>
139
-
140
- {/* MAIN DASHBOARD PANEL */}
141
- <main className="container mx-auto px-4 lg:px-6 -mt-10 lg:-mt-20 relative z-30">
142
- <div className="glass-shell p-4 lg:p-6 rounded-3xl border border-accent/20 bg-black/40 backdrop-blur-md">
143
- <div className="flex flex-col sm:flex-row justify-between items-start sm:items-center border-b border-accent/10 pb-4 mb-6 gap-2">
144
- <div>
145
- <h1 className="text-xl lg:text-2xl font-bold text-accent flex items-center gap-2">
146
- <Shield size={22} /> Cyber SOC Dashboard
147
- </h1>
148
- <p className="text-slate-300/70 text-xs lg:text-sm">
149
- Real-time AI NIDS operations
150
- </p>
151
- </div>
152
  </div>
 
 
 
 
 
 
153
 
154
- {/* System + ML + Network - Stack on mobile */}
155
- <div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-4 lg:gap-5 mb-6">
156
- <div className="cyber-card p-5 border border-accent/20 bg-accent/5">
157
- <h3 className="text-accent font-semibold mb-3 flex items-center gap-2">
158
- <Cpu size={16} /> System Status
159
- </h3>
160
- {loading ? <p className="animate-pulse text-slate-500">Scanning...</p> : (
161
- <ul className="text-sm text-slate-300 space-y-2">
162
- <li className="flex justify-between"><span>CPU Usage:</span> <span className="text-accent font-mono">{systemStats?.cpu_usage ?? "0"}%</span></li>
163
- <li className="flex justify-between"><span>RAM Usage:</span> <span className="text-accent font-mono">{systemStats?.ram_usage ?? "0"}%</span></li>
164
- <li className="flex justify-between"><span>Disk Usage:</span> <span className="text-accent font-mono">{systemStats?.disk_usage ?? "0"}%</span></li>
165
- </ul>
166
- )}
167
- </div>
 
 
168
 
169
- <div className="cyber-card p-5 border border-accent/20 bg-accent/5">
170
- <h3 className="text-accent font-semibold mb-3 flex items-center gap-2">
171
- <Activity size={16} /> ML Model Status
172
- </h3>
173
- {mlModels.length > 0 ? (
174
- <ul className="text-sm text-slate-300 space-y-2">
175
- {mlModels.map((m, i) => (
176
- <li key={i} className="flex justify-between border-b border-white/5 pb-1 last:border-0">
177
- <span>{m.name}</span>
178
- <span className="text-accent font-mono">{m.accuracy ?? "98.2"}%</span>
179
- </li>
180
- ))}
181
- </ul>
182
- ) : <p className="text-slate-500 text-xs">No models active</p>}
183
- </div>
184
 
185
- <div className="cyber-card p-5 border border-accent/20 bg-accent/5 md:col-span-2 lg:col-span-1">
186
- <h3 className="text-accent font-semibold mb-3 flex items-center gap-2">
187
- <Wifi size={16} /> Network Health
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
188
  </h3>
189
- {threats.length > 0 ? (
190
- <ul className="text-sm text-slate-300 space-y-2">
191
- {threats.slice(0, 3).map((t, i) => (
192
- <li key={i} className="flex justify-between">
193
- <span className="truncate mr-2">{t.name}</span>
194
- <span className="text-rose-400 font-mono">{t.value}</span>
195
- </li>
196
- ))}
197
- </ul>
198
- ) : <p className="text-slate-500 text-xs">Awaiting traffic...</p>}
199
  </div>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
200
  </div>
201
 
202
- {/* Charts - Stacks on mobile */}
203
- <div className="grid grid-cols-1 lg:grid-cols-2 gap-6 mt-6">
204
- <div className="cyber-card border border-accent/15 p-4 lg:p-5 h-[320px] lg:h-[380px]">
205
- <h3 className="text-accent mb-4 font-semibold text-sm lg:text-base uppercase tracking-wider">
206
- Threat Class Distribution
207
- </h3>
208
- <div className="h-full pb-10">
209
- {threats.length > 0 ? (
210
- <ResponsiveContainer width="100%" height="100%">
211
- <PieChart>
212
- <Pie data={threats} dataKey="value" outerRadius="80%" innerRadius="60%" paddingAngle={5}>
213
- {threats.map((entry, i) => <Cell key={i} fill={COLORS[i % COLORS.length]} stroke="rgba(0,0,0,0)" />)}
214
- </Pie>
215
- <Tooltip contentStyle={{ backgroundColor: '#030617', border: '1px solid #00e5ff', borderRadius: '8px' }} />
216
- </PieChart>
217
- </ResponsiveContainer>
218
- ) : <div className="flex items-center justify-center h-full text-slate-500">No Data</div>}
219
- </div>
220
  </div>
 
221
 
222
- <div className="cyber-card border border-accent/15 p-4 lg:p-5 h-[320px] lg:h-[380px]">
223
- <h3 className="text-accent mb-4 font-semibold text-sm lg:text-base uppercase tracking-wider">
224
- Threat Count Overview
225
- </h3>
226
- <div className="h-full pb-10">
227
- {threats.length > 0 ? (
228
- <ResponsiveContainer width="100%" height="100%">
229
- <BarChart data={threats}>
230
- <CartesianGrid strokeDasharray="3 3" strokeOpacity={0.05} vertical={false} />
231
- <XAxis dataKey="name" stroke="#94a3b8" fontSize={10} tickLine={false} axisLine={false} />
232
- <YAxis stroke="#94a3b8" fontSize={10} tickLine={false} axisLine={false} />
233
- <Tooltip cursor={{ fill: 'rgba(0,229,255,0.05)' }} contentStyle={{ backgroundColor: '#030617', border: '1px solid #00e5ff' }} />
234
- <Bar dataKey="value" fill="#00e5ff" radius={[4, 4, 0, 0]} barSize={30} />
235
- </BarChart>
236
- </ResponsiveContainer>
237
- ) : <div className="flex items-center justify-center h-full text-slate-500">Awaiting input</div>}
238
- </div>
239
  </div>
240
  </div>
241
  </div>
242
- </main>
243
-
244
- {/* FOOTER - Now fully responsive */}
245
- <footer className="mt-24 bg-[#030617]/95 border-t border-accent/20 relative">
246
- <div className="relative container mx-auto px-6 lg:px-8 py-12 lg:py-16 grid grid-cols-1 sm:grid-cols-2 lg:grid-cols-4 gap-10 lg:gap-12 z-10 text-center sm:text-left">
247
- <div>
248
- <h2 className="text-accent text-2xl lg:text-3xl font-bold mb-3">AI-NIDS</h2>
249
- <p className="text-slate-400 text-sm leading-relaxed mx-auto sm:mx-0 max-w-xs">
250
- Adaptive AI-powered Network Intrusion Detection System built for real-time defense.
251
- </p>
252
- <div className="flex justify-center sm:justify-start gap-4 mt-6">
253
- {/* Socials remain same but centered for mobile */}
254
- <button onClick={() => window.open("https://github.com/yishu13", "_blank")} className="p-2 rounded-full border border-accent/40 text-accent hover:bg-accent/10 transition">
255
- <svg width="18" height="18" fill="currentColor" viewBox="0 0 24 24"><path d="M12 .5C5.73.5.75 5.48.75 11.76c0 4.93 3.19 9.11 7.61 10.59.56.1.77-.24.77-.54 0-.27-.01-1-.02-1.96-3.09.67-3.74-1.49-3.74-1.49-.5-1.27-1.22-1.61-1.22-1.61-.99-.67.08-.66.08-.66 1.1.08 1.67 1.13 1.67 1.13.98 1.68 2.58 1.2 3.21.92.1-.72.38-1.2.7-1.48-2.47-.28-5.07-1.24-5.07-5.49 0-1.21.43-2.2 1.13-2.98-.11-.28-.49-1.4.11-2.92 0 0 .92-.29 3.02 1.14 10.45 10.45 0 0 1 2.75-.37c.93.01 1.86.12 2.75.37 2.1-1.43 3.01-1.14 3.01-1.14.6 1.52.22 2.64.11 2.92.7.78 1.13 1.77 1.13 2.98 0 4.26-2.61 5.21-5.09 5.48.39.33.74.98.74 1.98 0 1.43-.01 2.58-.01 2.93 0 .3.2.65.78.54C19.06 20.87 22.25 16.69 22.25 11.76 22.25 5.48 17.27.5 12 .5z" /></svg>
256
- </button>
257
- <button onClick={() => window.open("https://www.linkedin.com/in/ayushrai13", "_blank")} className="p-2 rounded-full border border-accent/40 text-accent hover:bg-accent/10 transition">
258
- <svg width="18" height="18" fill="currentColor" viewBox="0 0 24 24"><path d="M4.98 3.5a2.5 2.5 0 1 1 0 5.001 2.5 2.5 0 0 1 0-5.001zM3 9h4v12H3zM9 9h3.8v1.6h.1c.5-.9 1.8-1.9 3.7-1.9C21.2 8.7 22 10.9 22 14.1V21h-4v-6.1c0-1.6-.6-2.7-2-2.7-1.1 0-1.7.8-2 1.6-.1.2-.1.6-.1.9V21H9z" /></svg>
259
- </button>
260
  </div>
261
  </div>
262
 
263
- {/* Footer columns: stack on small, 2x2 on medium */}
264
- <div className="hidden sm:block">
265
- <h3 className="text-accent font-semibold mb-3">Platform</h3>
266
- <ul className="space-y-2 text-slate-300 text-sm">
267
- <li className="hover:text-accent cursor-pointer" onClick={() => navigate("/livetraffic")}>Live Traffic</li>
268
- <li className="hover:text-accent cursor-pointer" onClick={() => navigate("/alerts")}>AI Alerts</li>
269
- </ul>
270
- </div>
271
-
272
- <div className="hidden lg:block">
273
- <h3 className="text-accent font-semibold mb-3">Security</h3>
274
- <ul className="space-y-2 text-slate-300 text-sm">
275
- <li>Threat Intel</li>
276
- <li>Anomaly Detection</li>
277
- </ul>
278
  </div>
 
279
 
280
- <div className="hidden lg:block">
281
- <h3 className="text-accent font-semibold mb-3">Resources</h3>
282
- <ul className="space-y-2 text-slate-300 text-sm">
283
- <li>Documentation</li>
284
- <li>Support Center</li>
285
- </ul>
 
 
 
 
 
 
286
  </div>
287
  </div>
 
 
288
 
289
- <div className="border-t border-accent/10 py-6 text-center text-slate-500 text-xs">
290
- © {new Date().getFullYear()} AI-NIDS Adaptive Cyber Defense
291
- </div>
292
- </footer>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
293
  </div>
 
294
 
295
- {/* FLOATING BACK-TO-TOP BUTTON */}
296
- {showTop && (
297
- <button
298
- onClick={() => {
299
- const scrollContainer = document.querySelector("main.flex-1.overflow-auto");
300
- scrollContainer?.scrollTo({ top: 0, behavior: "smooth" });
301
- }}
302
- className="fixed bottom-6 lg:bottom-12 left-1/2 -translate-x-1/2 z-[200] w-14 h-14 lg:w-16 lg:h-16 rounded-full flex items-center justify-center bg-accent/20 backdrop-blur-xl border border-accent/40 shadow-neon active:scale-90 transition-all"
303
- >
304
- <svg xmlns="http://www.w3.org/2000/svg" className="w-6 h-6 text-accent" fill="none" viewBox="0 0 24 24" stroke="currentColor" strokeWidth="3">
305
- <path strokeLinecap="round" strokeLinejoin="round" d="M12 19V5m0 0l-6 6m6-6l6 6" />
306
- </svg>
307
- </button>
308
- )}
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
309
 
310
  <ChatAssistant />
311
- </>
312
  );
313
- }
314
-
 
1
+ import React, { useEffect, useState, useMemo, useRef } from "react";
2
  import { useAuth } from "../context/AuthContext";
3
+ import { useLocation, useNavigate } from "react-router-dom";
4
  import {
5
+ PieChart, Pie, Cell, Tooltip, ResponsiveContainer,
6
+ BarChart, Bar, XAxis, YAxis, CartesianGrid, AreaChart, Area
 
 
 
 
 
 
 
 
7
  } from "recharts";
8
  import {
9
+ Shield, Cpu, Wifi, Activity, Github, Linkedin,
10
+ Server, Terminal, Globe, Zap, AlertTriangle, Lock
 
 
 
11
  } from "lucide-react";
12
  import toast from "react-hot-toast";
13
  import NeonShield from "../components/NeonShield";
 
14
  import ChatAssistant from "./ChatAssistant";
15
+ import CicidsImg from "../assests/fig4_acc.png";
16
+ import BccImg from "../assests/fig3_loss.png";
17
+ import LiveImg from "../assests/dashboard.png";
18
 
19
  const COLORS = ["#00e5ff", "#ff0059", "#a78bfa", "#fbbf24", "#10b981"];
20
 
21
  export default function Dashboard() {
 
22
  const navigate = useNavigate();
23
  const [systemStats, setSystemStats] = useState(null);
24
  const [threats, setThreats] = useState([]);
25
  const [mlModels, setMlModels] = useState([]);
26
  const [loading, setLoading] = useState(true);
27
  const [showTop, setShowTop] = useState(false);
28
+ const [isSimulated, setIsSimulated] = useState(false);
29
+ const [packetCount, setPacketCount] = useState(1240500);
30
+ const [logs, setLogs] = useState([
31
+ "[OK] Neural_Engine_Symmetry_Check... PASS",
32
+ "[INFO] Establishing encrypted tunnel to Node_Alpha...",
33
+ "[WARN] Anomalous handshake detected at Gateway_7"
34
+ ]);
35
 
36
+ // --- DATA FALLBACKS ---
37
+ const dummyThreats = [
38
+ { name: "DDOS", value: 45 }, { name: "MALWARE", value: 32 },
39
+ { name: "PORT SCAN", value: 18 }, { name: "BRUTE FORCE", value: 12 }
40
+ ];
41
+ const displayThreats = threats.length > 0 ? threats : dummyThreats;
42
+ const displayML = mlModels.length > 0 ? mlModels : [
43
+ { name: "Neural_Kernel_v4", accuracy: 98.4 },
44
+ { name: "Behavior_Pulse", accuracy: 96.2 },
45
+ { name: "Heuristic_Lab", accuracy: 99.1 }
46
+ ];
47
+
48
+ // --- LOGIC: SIMULATED LIVE FEED ---
49
  useEffect(() => {
50
+ const logInterval = setInterval(() => {
51
+ const messages = [
52
+ `[INFO] Packet scrutinized: ${Math.random().toString(16).slice(2, 10).toUpperCase()}`,
53
+ `[OK] Filtered traffic from ${Math.floor(Math.random()*255)}.168.${Math.floor(Math.random()*255)}.1`,
54
+ `[WARN] Latency spike in sector_${Math.floor(Math.random()*9)}`,
55
+ `[SEC] Mitigated potential ${displayThreats[Math.floor(Math.random()*displayThreats.length)].name} attempt`
56
+ ];
57
+ setLogs(prev => [messages[Math.floor(Math.random()*messages.length)], ...prev].slice(0, 8));
58
+ setPacketCount(prev => prev + Math.floor(Math.random() * 50));
59
+ }, 3000);
60
+ return () => clearInterval(logInterval);
61
+ }, [displayThreats]);
62
 
63
  const loadData = async () => {
64
  try {
65
  const [sys, ml, th] = await Promise.all([
66
+ fetch("http://127.0.0.1:5000/api/system/status").then(r => r.json()),
67
+ fetch("http://127.0.0.1:5000/api/ml/models").then(r => r.json()),
68
+ fetch("http://127.0.0.1:5000/api/live/stats").then(r => r.json()),
69
  ]);
70
+ setSystemStats(sys);
71
  setMlModels(Array.isArray(ml) ? ml : []);
72
+ setThreats(Object.entries(th || {}).map(([k, v]) => ({ name: k.toUpperCase(), value: v })));
73
+ setIsSimulated(false);
 
 
 
 
74
  } catch (err) {
75
+ setIsSimulated(true);
 
76
  } finally {
77
  setLoading(false);
78
  }
 
80
 
81
  useEffect(() => {
82
  loadData();
83
+ const interval = setInterval(loadData, 10000);
84
+ return () => clearInterval(interval);
85
  }, []);
86
 
87
  return (
88
+ <div className="relative min-h-screen text-slate-200 font-sans selection:bg-accent selection:text-black z-10">
89
+ {/* 1. DYNAMIC BACKGROUND LAYER */}
90
+ <div className="fixed inset-0 -z-20 pointer-events-none overflow-hidden bg-[#030617]">
91
+ {/* The Grid Layer */}
92
+ <div className="absolute inset-0 opacity-[0.15]" style={{ backgroundImage: "radial-gradient(var(--accent) 0.5px, transparent 0.5px)", backgroundSize: "40px 40px" }} />
93
+
94
+ {/* NeonShield Moved Here: Positioned in the center-right behind the main panel */}
95
+ <div className="absolute top-1/2 left-1/2 -translate-x-1/2 -translate-y-1/2 w-full max-w-[1000px] opacity-40 blur-[2px] -z-0 h-[800px]">
96
+ <NeonShield />
97
+ </div>
98
+
99
+ {/* Ambient Glows */}
100
+ <div className="absolute left-[-10%] top-[10%] w-[600px] h-[600px] bg-accent/10 blur-[150px] rounded-full animate-pulse" />
101
+ <div className="absolute right-[10%] bottom-[10%] w-[400px] h-[400px] bg-purple-500/10 blur-[150px] rounded-full animate-bounce" style={{ animationDuration: '10s' }} />
102
+ </div>
103
+
104
+ {/* 2. HERO SECTION - MURF.AI INSPIRED REDESIGN */}
105
+ <header className="relative pb-20 lg:pt-12 lg:pb-20 overflow-hidden">
106
+ <div className="container mx-auto px-6 lg:px-12 relative z-10">
107
+ <div className="grid grid-cols-1 lg:grid-cols-12 gap-12 items-center">
108
+
109
+ {/* LEFT COLUMN: THE CONTENT (6/12 Width) */}
110
+ <div className="lg:col-span-7 text-center lg:text-left space-y-8">
111
+ <div className="inline-flex items-center gap-2 px-4 py-1.5 rounded-full border border-accent/20 bg-accent/5 backdrop-blur-md">
112
+ <div className="w-2 h-2 rounded-full bg-lime-500 animate-ping" />
113
+ <span className="text-[10px] uppercase tracking-[0.3em] font-black text-accent/80">Neural_Engine_v4.0_Active</span>
114
  </div>
115
+
116
+ <h1 className="text-6xl md:text-8xl xl:text-9xl font-black tracking-tighter leading-[0.85]">
117
+ <span className=" text-transparent bg-clip-text bg-gradient-to-r from-[#00e5ff] via-[#a78bfa] to-[#ff0059] drop-shadow-[0_0_30px_rgba(167,139,250,0.3)] italic ">Network</span> <br /></h1>
118
+ <span className="text-transparent italic text-8xl bg-clip-text bg-gradient-to-r from-[#00e5ff] via-[#a78bfa] to-[#ff0059] drop-shadow-[0_0_30px_rgba(167,139,250,0.3)]">
119
+ Intrusion
120
+ </span>
121
 
122
+
123
+ <p className="text-slate-400 text-lg md:text-xl font-mono leading-relaxed max-w-2xl mx-auto lg:mx-0 border-l-2 border-accent/20 pl-6 italic">
124
+ &gt; Analyzing global packet telemetry in real-time. <br />
125
+ &gt; Heuristic layers: <span className="text-emerald-400 font-bold">SYNCHRONIZED</span>
126
+ </p>
 
 
 
 
 
 
 
 
 
 
127
 
128
+ <div className="flex flex-wrap justify-center lg:justify-start gap-5 pt-4">
129
+ <button
130
+ onClick={() => navigate("/livetraffic")}
131
+ className="px-10 py-5 bg-gradient-to-r border-white/10 border-2 from-accent to-blue-600 text-[var(--accent)] font-black uppercase tracking-tighter hover:scale-105 hover:shadow-[0_0_40px_rgba(0,229,255,0.5)] transition-all duration-300 active:scale-95"
132
+ >
133
+ Live Traffic
134
+ </button>
135
+ <button
136
+ onClick={() => navigate("/threats")}
137
+ className="px-10 py-5 border-2 border-white/10 text-white font-black uppercase tracking-tighter hover:shadow-[0_0_40px_rgba(0,229,255,0.5)] transition-all active:scale-95"
138
+ >
139
+ System Docs
140
+ </button>
141
+ </div>
142
+ </div>
143
 
144
+ {/* RIGHT COLUMN: TECHNICAL PERFORMANCE METRICS */}
145
+ <div className="lg:col-span-5 relative hidden lg:block hover:shadow-[0_0_40px_rgba(0,229,255,0.5)]">
146
+ <div className="rounded-xl border border-indigo-500/30 bg-[#05091a] p-8 shadow-2xl font-mono relative overflow-hidden">
147
+
148
+ {/* Header Area: Primary Model */}
149
+ <div className="flex justify-between items-start mb-8 pb-6 border-indigo-500/30 border-b-4">
150
+ <div>
151
+ <div className="text-[10px] text-slate-500 uppercase tracking-widest mb-1">Architecture_01</div>
152
+ <div className="text-2xl font-black text-white italic">DNN <span className="text-xs font-normal not-italic text-slate-500">/ Deep Neural Network</span></div>
153
+ </div>
154
+ <div className="text-right">
155
+ <div className="text-[10px] text-slate-500 uppercase tracking-widest mb-1">Benchmark</div>
156
+ <div className="text-2xl font-black text-emerald-500 italic text-glow-sm">93%</div>
157
+ </div>
158
+ </div>
159
 
160
+ {/* Dataset & Model Comparison Grid */}
161
+ <div className="space-y-8">
162
+ {/* CIC-IDS2018 Section */}
163
+ <div className="space-y-3">
164
+ <div className="flex justify-between text-[10px] uppercase">
165
+ <span className="text-slate-400">Dataset: <span className="text-white">CIC-IDS2018</span></span>
166
+ <span className="text-slate-500">Loss: 0.042</span>
167
+ </div>
168
+ <div className="h-1.5 w-full bg-slate-900 rounded-full overflow-hidden">
169
+ <div className="h-full bg-slate-400 w-[93%]" />
170
+ </div>
171
+ </div>
 
 
 
 
172
 
173
+ {/* LightGBM / BCC Darknet Section */}
174
+ <div className="pt-4 border-t-4 border-indigo-500/30 ">
175
+ <div className="flex justify-between items-center mb-4">
176
+ <div>
177
+ <div className="text-[10px] text-slate-500 uppercase tracking-widest mb-1">Architecture_02</div>
178
+ <div className="text-xl font-bold text-white uppercase italic tracking-tighter">LightGBM</div>
179
+ </div>
180
+ <div className="text-right">
181
+ <div className="text-[10px] text-slate-500 uppercase tracking-widest mb-1">BCC_Darknet</div>
182
+ <div className="text-xl font-bold text-accent italic">96%</div>
183
+ </div>
184
+ </div>
185
+ <div className="h-1.5 w-full bg-orange-500 rounded-full overflow-hidden">
186
+ <div className="h-full bg-accent w-[90%]" />
187
+ </div>
188
+ </div>
189
+ </div>
190
+
191
+ {/* Technical Footer: Training Metadata */}
192
+ <div className="grid grid-cols-2 gap-4 mt-8 pt-6 pb-4 border-t-4 border-indigo-500/30 border-b-4">
193
+ <div className="space-y-1 text-left ">
194
+ <div className="text-slate-500 uppercase text-[10px]">Input_Vector</div>
195
+ <div className="text-white font-bold tracking-widest font-mono italic">SHAPE(None, 78)</div>
196
+ </div>
197
+ <div className="space-y-1 text-right">
198
+ <div className="text-slate-500 uppercase text-[10px]">Optimization</div>
199
+ <div className="text-white font-bold tracking-widest font-mono italic">ADAM_GRADIENT</div>
200
+ </div>
201
+ </div>
202
+
203
+ {/* Final Console Output */}
204
+ <div className="mt-6 p-3 bg-black/40 rounded border border-white/5 font-mono text-[9px] text-slate-600">
205
+ <div className="flex gap-2">
206
+ <span className="text-blue-500">[SYS]</span>
207
+ Initializing Multi-Layer Perceptron...
208
+ </div>
209
+ <div className="flex gap-2 animate-pulse">
210
+ <span className="text-emerald-500">[OK]</span>
211
+ Weights Loaded Successfully.
212
+ </div>
213
+ </div>
214
+ </div>
215
+ </div>
216
+ </div>
217
+ </div>
218
+ </header>
219
+
220
+ {/* 2.5 PROJECT INSIGHT (The "Murf" Style Section) */}
221
+ <section className="container mx-auto px-6 mb-24 relative z-10">
222
+ <div className="relative overflow-hidden rounded-[3rem] bg-gradient-to-br from-[#0a0f29] to-[#030617] border border-white/5 p-10 md:p-20 shadow-2xl">
223
+
224
+ {/* Visual Accent: Soft Glow */}
225
+ <div className="absolute top-0 right-0 w-[500px] h-[500px] bg-accent/5 blur-[120px] rounded-full -mr-40 -mt-40 pointer-events-none" />
226
+
227
+ <div className="grid lg:grid-cols-2 gap-16 items-center">
228
+ <div className="space-y-8">
229
+ <div>
230
+ <h4 className="text-accent font-mono text-[10px] uppercase tracking-[0.5em] mb-4">Development_Project</h4>
231
+ <h2 className="text-4xl md:text-6xl font-black text-orange-500 leading-[1.1] italic uppercase tracking-tighter">
232
+ Transparent <br />
233
+ <span className="text-transparent bg-clip-text bg-gradient-to-r from-orange-500 to-slate-500">Security Insight</span>
234
+ </h2>
235
+ </div>
236
+
237
+ <p className="text-slate-400 text-lg font-mono leading-relaxed max-w-xl">
238
+ AstraGuard simplifies complex network telemetry into a unified visual experience.
239
+ By monitoring live traffic flows and applying baseline heuristic analysis, we help
240
+ identify patterns and common threat vectors.
241
+ </p>
242
+
243
+ <div className="flex flex-wrap gap-4">
244
+ <button
245
+ onClick={() => window.open("https://github.com/yishu13")}
246
+ className="group flex items-center gap-3 px-8 py-4 bg-white text-black font-black uppercase tracking-tighter hover:bg-accent transition-all duration-300"
247
+ >
248
+ <Github size={20} />
249
+ <span>GitHub</span>
250
+ </button>
251
+
252
+ <button
253
+ onClick={() => window.open("https://huggingface.co")}
254
+ className="group flex items-center gap-3 px-8 py-4 border border-white/10 text-white font-bold uppercase tracking-tighter hover:bg-white/5 transition-all duration-300"
255
+ >
256
+ <span className="text-2xl group-hover:scale-110 transition-transform">🤗</span>
257
+ <span>Hugging Face</span>
258
+ </button>
259
+ </div>
260
+ </div>
261
+
262
+ {/* RIGHT SIDE: Interactive Visual Element */}
263
+ <div className="relative hidden lg:block">
264
+ <div className="relative z-10 rounded-[2rem] border border-white/10 bg-black/40 backdrop-blur-xl p-8 shadow-2xl border-t-accent/30">
265
+ <div className="flex items-center justify-between mb-8">
266
+ <div className="flex gap-1.5">
267
+ <div className="w-2 h-2 rounded-full bg-rose-500/50" />
268
+ <div className="w-2 h-2 rounded-full bg-amber-500/50" />
269
+ <div className="w-2 h-2 rounded-full bg-emerald-500/50" />
270
  </div>
271
+ <div className="text-[10px] font-mono text-slate-500 uppercase tracking-widest">Astra_Shield_v1.0</div>
272
  </div>
273
+
274
+ <div className="space-y-6">
275
+ <div className="h-2 w-3/4 bg-white/5 rounded-full overflow-hidden">
276
+ <div className="h-full bg-accent animate-pulse w-[65%]" />
277
+ </div>
278
+ <div className="h-2 w-full bg-white/5 rounded-full overflow-hidden">
279
+ <div className="h-full bg-accent/40 w-[40%]" />
280
+ </div>
281
+ <div className="pt-4 border-t border-white/5">
282
+ <div className="text-[10px] font-mono text-accent uppercase mb-2">Neural_Engine_Status</div>
283
+ <div className="text-2xl font-mono text-white">98.2% <span className="text-[10px] text-slate-500 uppercase">Accuracy</span></div>
 
 
 
284
  </div>
285
+ </div>
286
+ </div>
287
+ </div>
288
+ </div>
289
+ </div>
290
+ </section>
291
 
292
+ {/* 3. TACTICAL INFO BAR (DENSITY ADDITION) */}
293
+ <div className="container mx-auto px-6 -mt-30 mb-20 grid grid-cols-2 md:grid-cols-4 gap-4 z-40 relative">
294
+ {[
295
+ { label: "Packets Scanned", val: packetCount.toLocaleString(), icon: <Globe size={16}/> },
296
+ { label: "Uptime", val: "99.98%", icon: <Activity size={16}/> },
297
+ { label: "Threats Blocked", val: "12,402", icon: <Shield size={16}/> },
298
+ { label: "Nodes Active", val: "24/24", icon: <Server size={16}/> }
299
+ ].map((item, i) => (
300
+ <div key={i} className="p-4 rounded-xl border border-white/5 bg-black/60 backdrop-blur-xl group hover:border-accent/50 transition-all text-[var(--accent)]">
301
+ <div className="flex items-center gap-3 text-[var(--accent)] mb-2">
302
+ {item.icon} <span className=" uppercase font-bold text-orange-600 tracking-widest">{item.label}</span>
303
+ </div>
304
+ <div className="text-xl font-mono font-bold text-[var(--accent)] group-hover:text-accent transition-colors">{item.val}</div>
305
+ </div>
306
+ ))}
307
+ </div>
308
 
309
+ {/* 3.5 FEATURE SPOTLIGHT SECTION */}
310
+ <section className="container mx-auto px-6 mb-20 relative z-10">
311
+ <div className="relative overflow-hidden rounded-[3rem] bg-gradient-to-br from-[#0a0f29] to-[#030617] border border-white/5 p-8 md:p-16">
312
+
313
+ {/* Background Decorative Glow */}
314
+ <div className="absolute top-0 right-0 w-[500px] h-[500px] bg-accent/5 blur-[120px] rounded-full -mr-64 -mt-64" />
 
 
 
 
 
 
 
 
 
315
 
316
+ <div className="grid lg:grid-cols-2 gap-12 items-center">
317
+ <div>
318
+ <h4 className="text-accent font-mono text-xs uppercase tracking-[0.4em] mb-4">Astra_Studio_v1</h4>
319
+ <h2 className="text-4xl md:text-5xl font-black leading-tight mb-6 italic uppercase text-[var(--accent)] ">
320
+ Network Intrusion <br /> <span className="text-transparent bg-clip-text bg-gradient-to-r from-white to-slate-500"> Based On Two Dataset </span>
321
+ </h2>
322
+ <p className="text-slate-400 text-lg font-mono mb-10 leading-relaxed">
323
+ Transition from raw data to actionable intelligence using our Neural Interface.
324
+ Visualize live traffic flows and utilize baseline heuristic models to categorize
325
+ network activity and identify common threat vectors.
326
+ </p>
327
+
328
+ <div className="flex flex-wrap gap-4">
329
+ <button
330
+ onClick={() => window.open("https://github.com/ayu-yishu13")}
331
+ className="px-8 py-4 bg-white text-black font-black uppercase tracking-tighter hover:bg-indigo-500 transition-all flex items-center gap-2"
332
+ >
333
+ <Github size={18} /> Github
334
+ </button>
335
+ <button
336
+ onClick={() => window.open("https://huggingface.co/CodebaseAi")}
337
+ className="px-8 py-4 border border-white/20 text-white font-bold uppercase tracking-tighter hover:bg-white/5 transition-all flex items-center gap-2"
338
+ >
339
+ <span className="text-xl">🤗</span> Hugging Face
340
+ </button>
341
+ </div>
342
+ </div>
343
+
344
+ {/* The "Visual Card" - Mimicking the Murf.ai right side */}
345
+ <div className="relative">
346
+ <div className="relative z-10 rounded-2xl border border-white/10 bg-black/40 backdrop-blur-md p-2 shadow-2xl">
347
+ <img
348
+ src="/path-to-your-ui-preview.png"
349
+ alt="Interface Preview"
350
+ className="rounded-xl opacity-80"
351
+ />
352
+ </div>
353
+ {/* Floating "Magic" Card */}
354
+ <div className="absolute -bottom-6 -left-6 z-20 w-48 p-4 rounded-xl border border-accent/30 bg-[#030617] shadow-[0_20px_50px_rgba(0,0,0,0.5)] animate-bounce" style={{ animationDuration: '4s' }}>
355
+ <div className="flex items-center gap-2 mb-2">
356
+ <div className="w-2 h-2 rounded-full bg-emerald-500 shadow-[0_0_8px_#10b981]" />
357
+ <span className="text-[10px] font-mono text-slate-400">Neural_Sync</span>
358
+ </div>
359
+ <div className="h-1 w-full bg-white/5 rounded-full overflow-hidden">
360
+ <div className="h-full bg-accent w-3/4" />
361
+ </div>
362
+ </div>
363
+ </div>
364
+ </div>
365
+ </div>
366
+ </section>
367
+
368
+ {/* 4. PRIMARY DASHBOARD PANEL */}
369
+ <main className="container mx-auto px-4 lg:px-6 pb-20 relative z-10">
370
+ <div className="glass-shell p-6 lg:p-10 rounded-[2rem] border border-white/10 bg-black/20 backdrop-blur-xl shadow-2xl overflow-hidden relative">
371
+
372
+ {/* Subtle Corner Deco */}
373
+ <div className="absolute top-0 right-0 w-32 h-32 bg-accent/5 rounded-bl-full pointer-events-none" />
374
+
375
+ {/* Section: Status & Gauges */}
376
+ <div className="grid grid-cols-1 lg:grid-cols-12 gap-8 mb-12">
377
+
378
+ {/* System Resource Gauges */}
379
+ <div className="lg:col-span-4 space-y-8 p-6 rounded-2xl border border-white/5 bg-white/[0.02]">
380
+ <div className="flex justify-between items-center">
381
+ <h3 className="text-accent text-[10px] font-black uppercase tracking-[0.3em] flex items-center gap-2">
382
+ <Cpu size={14} /> Neural Load
383
  </h3>
384
+ <span className="text-[8px] font-mono text-emerald-500 bg-emerald-500/10 px-2 py-0.5 rounded">Nominal</span>
 
 
 
 
 
 
 
 
 
385
  </div>
386
+
387
+ {[
388
+ { label: "Cortex Processing", val: systemStats?.cpu_usage ?? (isSimulated ? "32" : "0") },
389
+ { label: "Synaptic Memory", val: systemStats?.ram_usage ?? (isSimulated ? "54" : "0") },
390
+ { label: "Buffer Capacity", val: systemStats?.disk_usage ?? (isSimulated ? "18" : "0") }
391
+ ].map((s, i) => (
392
+ <div key={i} className="space-y-2">
393
+ <div className="flex justify-between text-[10px] font-mono uppercase text-slate-400">
394
+ <span>{s.label}</span>
395
+ <span className="text-accent">{s.val}%</span>
396
+ </div>
397
+ <div className="h-1.5 w-full bg-white/5 rounded-full overflow-hidden">
398
+ <div className="h-full bg-gradient-to-r from-accent to-blue-500 transition-all duration-1000 shadow-[0_0_10px_var(--accent)]" style={{ width: `${s.val}%` }} />
399
+ </div>
400
+ </div>
401
+ ))}
402
  </div>
403
 
404
+ {/* AI Model Intelligence */}
405
+ <div className="lg:col-span-4 p-6 rounded-2xl border border-white/5 bg-white/[0.02]">
406
+ <h3 className="text-accent text-[10px] font-black uppercase tracking-[0.3em] mb-8 flex items-center gap-2">
407
+ <Activity size={14} /> Logic Core Confidence
408
+ </h3>
409
+ <div className="space-y-4">
410
+ {displayML.map((m, i) => (
411
+ <div key={i} className="group flex justify-between items-center p-3 rounded-xl border border-white/5 bg-black/20 hover:border-accent/30 transition-all">
412
+ <span className="text-xs font-mono text-slate-300 italic">{m.name}</span>
413
+ <div className="flex items-center gap-2">
414
+ <div className="w-12 h-1 bg-white/10 rounded-full overflow-hidden">
415
+ <div className="h-full bg-emerald-500" style={{ width: `${m.accuracy}%` }} />
416
+ </div>
417
+ <span className="text-emerald-400 font-mono text-xs">{m.accuracy}%</span>
418
+ </div>
419
+ </div>
420
+ ))}
 
421
  </div>
422
+ </div>
423
 
424
+ {/* Tactical Threat Feed */}
425
+ <div className="lg:col-span-4 p-6 rounded-2xl border border-white/5 bg-white/[0.02]">
426
+ <h3 className="text-rose-500 text-[10px] font-black uppercase tracking-[0.3em] mb-8 flex items-center gap-2">
427
+ <AlertTriangle size={14} /> Priority Intercepts
428
+ </h3>
429
+ <div className="space-y-3">
430
+ {displayThreats.slice(0, 3).map((t, i) => (
431
+ <div key={i} className="group relative flex justify-between items-center p-3 rounded-xl border border-rose-500/10 bg-rose-500/5 hover:bg-rose-500/10 transition-all">
432
+ <div>
433
+ <div className="text-[10px] text-slate-500 uppercase font-mono">Type_{t.name}</div>
434
+ <div className="text-rose-400 font-bold text-sm tracking-tight">{t.value} Attempts</div>
435
+ </div>
436
+ <button className="p-2 opacity-0 group-hover:opacity-100 bg-rose-500 text-white rounded transition-all active:scale-90">
437
+ <Lock size={12}/>
438
+ </button>
439
+ </div>
440
+ ))}
441
  </div>
442
  </div>
443
  </div>
444
+
445
+ {/* Section: Visual Analytics */}
446
+ <div className="grid grid-cols-1 lg:grid-cols-2 gap-8 mb-12">
447
+ <div className="p-8 rounded-3xl border border-white/5 bg-white/[0.01]">
448
+ <h3 className="text-accent text-[10px] font-black uppercase tracking-[0.3em] mb-8">Classification Distribution</h3>
449
+ <div className="h-64">
450
+ <ResponsiveContainer width="100%" height="100%">
451
+ <PieChart>
452
+ <Pie data={displayThreats} dataKey="value" outerRadius="100%" innerRadius="75%" paddingAngle={10}>
453
+ {displayThreats.map((_, i) => <Cell key={i} fill={COLORS[i % COLORS.length]} stroke="none" />)}
454
+ </Pie>
455
+ <Tooltip contentStyle={{ backgroundColor: '#030617', border: '1px solid #00e5ff', borderRadius: '12px' }} />
456
+ </PieChart>
457
+ </ResponsiveContainer>
 
 
 
 
458
  </div>
459
  </div>
460
 
461
+ <div className="p-8 rounded-3xl border border-white/5 bg-white/[0.01]">
462
+ <h3 className="text-accent text-[10px] font-black uppercase tracking-[0.3em] mb-8">Temporal Analysis</h3>
463
+ <div className="h-64">
464
+ <ResponsiveContainer width="100%" height="100%">
465
+ <BarChart data={displayThreats}>
466
+ <CartesianGrid strokeDasharray="3 3" strokeOpacity={0.03} vertical={false} />
467
+ <XAxis dataKey="name" fontSize={10} tick={{ fill: '#475569' }} axisLine={false} tickLine={false} />
468
+ <YAxis fontSize={10} tick={{ fill: '#475569' }} axisLine={false} tickLine={false} />
469
+ <Bar dataKey="value" fill="var(--accent)" radius={[6, 6, 0, 0]} barSize={40} />
470
+ </BarChart>
471
+ </ResponsiveContainer>
472
+ </div>
 
 
 
473
  </div>
474
+ </div>
475
 
476
+ {/* Section: The Live Terminal Feed */}
477
+ <div className="rounded-2xl border border-white/5 bg-black/80 p-5 font-mono">
478
+ <div className="flex items-center gap-2 mb-4 text-accent/60">
479
+ <Terminal size={14} />
480
+ <span className="text-[10px] uppercase tracking-[0.4em]">Root@NIDS_AstraGuard:~# Live_Feed</span>
481
+ </div>
482
+ <div className="space-y-1 h-32 overflow-hidden flex flex-col-reverse">
483
+ {logs.map((log, i) => (
484
+ <div key={i} className={`text-[11px] ${log.includes('[WARN]') ? 'text-amber-500' : log.includes('[SEC]') ? 'text-rose-500' : 'text-slate-500'}`}>
485
+ {log}
486
+ </div>
487
+ ))}
488
  </div>
489
  </div>
490
+ </div>
491
+ </main>
492
 
493
+ {/* 3. PROJECT ARCHITECTURE & INTERFACE HIGHLIGHTS */}
494
+ <section className="container mx-auto px-6 mb-24 relative z-10">
495
+ <div className="mb-12">
496
+ <h3 className="text-5xl italic font-bold uppercase tracking-tighter mb-2 bg-clip-text text-transparent bg-gradient-to-r from-orange-500 to-slate-500">Technical Implementation</h3>
497
+ <div className="h-1 w-12 bg-slate-700" />
498
+ </div>
499
+
500
+ <div className="grid md:grid-cols-2 lg:grid-cols-3 gap-8">
501
+
502
+ {/* HIGHLIGHT 1: Model Training/Results */}
503
+ <div className="group space-y-4">
504
+ <div className="aspect-video rounded-lg border border-slate-800 bg-slate-900/50 overflow-hidden relative">
505
+ <img
506
+ src={CicidsImg}
507
+ alt="CIC-IDS2018 Training Results"
508
+ className="object-cover w-full h-full grayscale group-hover:grayscale-0 transition-all duration-500"
509
+ />
510
+ <div className="absolute top-2 right-2 px-2 py-1 bg-black/80 rounded text-[9px] font-mono text-emerald-500 border border-emerald-500/20">
511
+ 93% ACCURACY
512
+ </div>
513
+ </div>
514
+ <div>
515
+ <h4 className="text-white font-bold text-sm uppercase">01. Model Validation</h4>
516
+ <p className="text-slate-500 text-xs font-mono leading-relaxed mt-1">
517
+ Performance metrics for the Deep Neural Network (DNN) trained on the CIC-IDS2018 dataset.
518
+ </p>
519
  </div>
520
+ </div>
521
 
522
+ {/* HIGHLIGHT 2: Live Traffic Monitoring */}
523
+ <div className="group space-y-4">
524
+ <div className="aspect-video rounded-lg border border-slate-800 bg-slate-900/50 overflow-hidden relative">
525
+ <img
526
+ src={LiveImg}
527
+ alt="Live Traffic Capture"
528
+ className="object-cover w-full h-full grayscale group-hover:grayscale-0 transition-all duration-500"
529
+ />
530
+ <div className="absolute top-2 right-2 px-2 py-1 bg-black/80 rounded text-[9px] font-mono text-accent border border-accent/20">
531
+ REAL-TIME
532
+ </div>
533
+ </div>
534
+ <div>
535
+ <h4 className="text-white font-bold text-sm uppercase">02. Packet Ingestion</h4>
536
+ <p className="text-slate-500 text-xs font-mono leading-relaxed mt-1">
537
+ Visualization of incoming flow features before classification by the LightGBM engine.
538
+ </p>
539
+ </div>
540
+ </div>
541
+
542
+ {/* HIGHLIGHT 3: Darknet Classification */}
543
+ <div className="group space-y-4">
544
+ <div className="aspect-video rounded-lg border border-slate-800 bg-slate-900/50 overflow-hidden relative">
545
+ <img
546
+ src={BccImg}
547
+ alt="BCC Darknet Results"
548
+ className="object-cover w-full h-full grayscale group-hover:grayscale-0 transition-all duration-500"
549
+ />
550
+ <div className="absolute top-2 right-2 px-2 py-1 bg-black/80 rounded text-[9px] font-mono text-amber-500 border border-amber-500/20">
551
+ 96% ACCURACY
552
+ </div>
553
+ </div>
554
+ <div>
555
+ <h4 className="text-white font-bold text-sm uppercase">03. Darknet Analysis</h4>
556
+ <p className="text-slate-500 text-xs font-mono leading-relaxed mt-1">
557
+ Identifying malicious patterns using the BCC Darknet dataset with ensemble learning.
558
+ </p>
559
+ </div>
560
+ </div>
561
+
562
+ </div>
563
+ </section>
564
+
565
+ {/* FOOTER */}
566
+ <footer className="mt-24 border-t border-white/5 bg-[#030617] py-20">
567
+ <div className="container mx-auto px-6 lg:px-12">
568
+ <div className="grid grid-cols-1 md:grid-cols-12 gap-16">
569
+ <div className="md:col-span-5">
570
+ <div className="flex items-center gap-2 mb-6 group cursor-pointer">
571
+ <div className="w-10 h-10 rounded-lg bg-accent/10 border border-accent/40 flex items-center justify-center group-hover:bg-accent group-hover:text-orange-700 text-accent transition-all">
572
+ <Shield size={20} />
573
+ </div>
574
+ <h2 className="text-2xl font-black italic tracking-tighter uppercase">AI-NIDS</h2>
575
+ </div>
576
+ <p className="text-slate-500 font-mono text-[10px] uppercase leading-relaxed mb-8 max-w-sm">
577
+ <span className="text-accent/60 font-bold">// ENCRYPTED SESSION ACTIVE</span> <br />
578
+ AstraGuard is a decentralized neural defense platform monitoring global packet telemetry.
579
+ Neural-layer packet filtering enabled via Secure_V4 Protocol.
580
+ Heuristic mitigation active across 24 edge nodes.
581
+ </p>
582
+ <div className="flex gap-4 text-accent">
583
+ <button onClick={() => window.open("https://github.com/yishu13")} className="w-12 h-12 rounded-xl border border-white/5 bg-white/5 flex items-center justify-center hover:border-accent transition-all text-slate-400 hover:text-accent">
584
+ <Github size={20} />
585
+ </button>
586
+ <button onClick={() => window.open("https://linkedin.com/in/ayushrai13")} className="w-12 h-12 rounded-xl border border-white/5 bg-white/5 flex items-center justify-center hover:border-accent transition-all text-slate-400 hover:text-accent">
587
+ <Linkedin size={20} />
588
+ </button>
589
+ </div>
590
+ </div>
591
+
592
+ <div className="md:col-span-7 grid grid-cols-2 sm:grid-cols-3 gap-8">
593
+ {[
594
+ { title: "Network", links: ["Live Traffic", "AI Alerts", "Protocol Analysis"] },
595
+ { title: "Intelligence", links: ["Threat Maps", "Core Logs", "ML Training"] },
596
+ { title: "Support", links: ["Documentation", "API Spec", "Whitepaper"] }
597
+ ].map((group, i) => (
598
+ <div key={i}>
599
+ <h4 className="text-accent text-[10px] font-black uppercase tracking-widest mb-6 italic">{group.title}</h4>
600
+ <ul className="space-y-4">
601
+ {group.links.map((link, j) => (
602
+ <li key={j} className="text-xs text-slate-500 hover:text-white cursor-pointer transition-colors font-mono">&gt; {link}</li>
603
+ ))}
604
+ </ul>
605
+ </div>
606
+ ))}
607
+ </div>
608
+ </div>
609
+
610
+ <div className="mt-20 pt-8 border-t border-white/5 flex flex-col sm:flex-row justify-between items-center gap-6">
611
+ <div className="flex items-center gap-4">
612
+ <div className="flex items-center gap-2">
613
+ <div className="w-2 h-2 rounded-full bg-emerald-500 animate-pulse" />
614
+ <span className="text-[10px] font-mono text-emerald-500/80 uppercase tracking-widest">Global_Status: Online</span>
615
+ </div>
616
+ </div>
617
+ <div className="text-[10px] font-mono text-slate-700 uppercase tracking-widest">
618
+ © {new Date().getFullYear()} ASTRAGUARD // PROTOCOL_V.04
619
+ </div>
620
+ </div>
621
+ </div>
622
+ </footer>
623
 
624
  <ChatAssistant />
625
+ </div>
626
  );
627
+ }
 
frontend/src/pages/FlowPage.jsx CHANGED
@@ -2,29 +2,14 @@ import React, { useMemo, useState, useEffect, useRef } from "react";
2
  import ChatAssistant from "./ChatAssistant";
3
  import { useLocation, useNavigate } from "react-router-dom";
4
  import {
5
- Shield,
6
- Lock,
7
- Server,
8
- Activity,
9
- Wifi,
10
- Play,
11
- Pause,
12
- Zap,
13
- Radar,
14
- RefreshCcw,
15
- FileDown,
16
  } from "lucide-react";
17
  import {
18
- BarChart,
19
- Bar,
20
- XAxis,
21
- YAxis,
22
- CartesianGrid,
23
- Tooltip,
24
- ResponsiveContainer,
25
  } from "recharts";
26
  import jsPDF from "jspdf";
27
  import html2canvas from "html2canvas";
 
28
 
29
  function useQuery() {
30
  return new URLSearchParams(useLocation().search);
@@ -49,63 +34,55 @@ export default function FlowPage() {
49
  getComputedStyle(document.body).getPropertyValue("--accent") || "#00e5ff"
50
  );
51
 
52
- // 🌀 Listen for theme color changes (syncs with system theme)
53
  useEffect(() => {
54
  const observer = new MutationObserver(() => {
55
  const newAccent = getComputedStyle(document.body).getPropertyValue("--accent");
56
  setAccentColor(newAccent.trim());
57
  });
58
-
59
  observer.observe(document.body, { attributes: true, attributeFilter: ["class"] });
60
-
61
  return () => observer.disconnect();
62
  }, []);
63
 
64
- // 🧠 Generate sample logs
65
  useEffect(() => {
66
  const interval = setInterval(() => {
67
  if (!paused && !replayActive) {
68
  const t = new Date().toLocaleTimeString();
69
- const fake = `[${t}] ${["TOR", "VPN", "I2P"][Math.floor(Math.random() * 3)]} flow ${
70
- Math.random() > 0.6 ? "⚠️ Suspicious" : "✅ Normal"
71
- }`;
72
  setLogs((p) => [fake, ...p.slice(0, 10)]);
73
  }
74
  }, 1500);
75
  return () => clearInterval(interval);
76
- }, [paused, replayActive]);
77
 
78
- // 🎯 Flow definitions
79
  const flow = useMemo(() => {
80
  const titleMap = {
81
- TOR: "TOR Network Attack Flow Simulation",
82
- I2P: "I2P Encrypted Communication Flow",
83
- VPN: "VPN Tunnel Obfuscation Simulation",
84
- FREENET: "Freenet Decentralized Data Flow",
85
- ZERONET: "ZeroNet Peer-to-Peer Data Flow",
86
  };
87
 
88
  const nodes = [
89
- { id: "attacker", label: "Attacker Origin", x: 100, y: 200, icon: <Activity size={16} /> },
90
- { id: "entry", label: "Entry Node", x: 280, y: 120, icon: <Lock size={16} /> },
91
- { id: "relay", label: "Relay Network", x: 500, y: 150, icon: <Wifi size={16} /> },
92
- { id: "exit", label: "Exit Node", x: 720, y: 200, icon: <Lock size={16} /> },
93
- { id: "victim", label: "Victim System", x: 940, y: 250, icon: <Server size={16} /> },
94
- { id: "detection", label: "Detection AI", x: 1160, y: 250, icon: <Shield size={16} /> },
95
  ];
96
 
97
  const paths = [
98
- "M100 200 C200 100, 240 100, 280 120",
99
- "M280 120 C380 100, 460 120, 500 150",
100
- "M500 150 C600 160, 660 180, 720 200",
101
- "M720 200 C820 240, 880 260, 940 250",
102
- "M940 250 C1040 260, 1100 260, 1160 250",
103
  ];
104
 
105
  return { title: titleMap[type], nodes, paths };
106
  }, [type]);
107
 
108
- // 🎞️ Replay Animation
109
  useEffect(() => {
110
  if (replayActive) {
111
  let stage = 0;
@@ -119,9 +96,8 @@ export default function FlowPage() {
119
  }, 1200);
120
  return () => clearInterval(interval);
121
  }
122
- }, [replayActive]);
123
 
124
- // 🧾 Export as PDF
125
  const exportPDF = async () => {
126
  const el = flowRef.current;
127
  const canvas = await html2canvas(el);
@@ -130,246 +106,272 @@ export default function FlowPage() {
130
  pdf.save(`${type}_Flow_Report.pdf`);
131
  };
132
 
133
- // 📊 Comparison data
134
  const compareData = [
135
  { name: "TOR", risk: 85, detection: 92 },
136
  { name: "VPN", risk: 65, detection: 75 },
137
  { name: "I2P", risk: 75, detection: 88 },
138
  { name: "Freenet", risk: 50, detection: 70 },
139
- { name: "ZeroNet", risk: 60, detection: 73 },
140
  ];
141
 
142
  return (
143
- <div
144
- ref={flowRef}
145
- className="relative min-h-screen bg-[var(--card)] text-[var(--text)] overflow-hidden transition-colors duration-500"
146
- >
147
- {/* Subtle animated theme glow */}
148
- <div
149
- className="absolute inset-0 blur-3xl opacity-20 pointer-events-none animate-pulse"
150
- style={{
151
- background: `radial-gradient(circle at 50% 50%, ${accentColor}55 0%, transparent 70%)`,
152
- }}
153
- />
154
 
155
- {/* Header */}
156
- <div className="flex items-center justify-between p-6 relative z-10">
157
- <button
158
- onClick={() => navigate(-1)}
159
- className="px-4 py-2 bg-[var(--card)]/50 border border-[var(--accent)]/30 rounded-lg text-[var(--accent)] hover:bg-[var(--accent)]/10 transition"
160
- >
161
  ← Back
162
  </button>
163
- <h2 className="text-3xl font-bold text-[var(--accent)] tracking-wide drop-shadow-lg">
164
  {flow.title}
165
  </h2>
166
- <button
167
- onClick={exportPDF}
168
- className="px-3 py-2 bg-[var(--accent)]/20 border border-[var(--accent)]/30 rounded-lg text-[var(--accent)] hover:bg-[var(--accent)]/30 flex items-center gap-2"
169
- >
170
- <FileDown size={16} /> Export Report
171
  </button>
172
- </div>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
173
 
174
- {/* Flow Diagram */}
175
- <div className="flex justify-center items-start gap-6 px-6 relative z-10">
176
- <div className="flex-1 flex justify-center relative">
177
- <svg viewBox="0 0 1300 400" width="100%" height="600">
178
- <defs>
179
- <linearGradient id="flowGrad" x1="0" y1="0" x2="1" y2="1">
180
- <stop
181
- offset="0%"
182
- stopColor={highlightDetection ? "#ff0044" : accentColor}
183
- stopOpacity="0.9"
184
- />
185
- <stop
186
- offset="100%"
187
- stopColor={accentColor}
188
- stopOpacity="0.3"
189
- />
190
- </linearGradient>
191
- <filter id="glow">
192
- <feGaussianBlur stdDeviation="3.5" result="b" />
193
- <feMerge>
194
- <feMergeNode in="b" />
195
- <feMergeNode in="SourceGraphic" />
196
- </feMerge>
197
- </filter>
198
- </defs>
199
-
200
- <g stroke="url(#flowGrad)" strokeWidth="3.5" fill="none" filter="url(#glow)">
201
- {flow.paths.map((path, i) => {
202
- const pathId = pid(`${flow.title}_${i}`);
203
- return (
204
- <g key={pathId}>
205
- <path
206
- id={pathId}
207
- d={path}
208
- strokeLinecap="round"
209
- opacity={replayActive && i > activeStage ? 0.15 : 0.8}
210
- />
211
- {!paused &&
212
- Array.from({ length: 5 }).map((_, j) => (
213
- <circle key={j} r="4" fill={highlightDetection ? "#ff0044" : accentColor} opacity="0.9">
214
- <animateMotion
215
- dur={`${speed}s`}
216
- repeatCount="indefinite"
217
- begin={`${j * 0.7}s`}
218
- >
219
- <mpath href={`#${pathId}`} />
220
- </animateMotion>
221
  </circle>
222
  ))}
223
- </g>
224
- );
225
- })}
226
- </g>
227
-
228
- {flow.nodes.map((n, i) => (
229
- <g key={i}>
230
- <circle
231
- cx={n.x}
232
- cy={n.y}
233
- r="26"
234
- fill={accentColor}
235
- opacity={activeStage >= i || !replayActive ? 0.35 : 0.15}
236
- stroke={accentColor}
237
- strokeWidth="1.5"
238
- filter="url(#glow)"
239
- />
240
- <foreignObject x={n.x - 10} y={n.y - 10} width="20" height="20">
241
- <div className="flex items-center justify-center w-full h-full text-[var(--text)]">
242
- {n.icon}
243
- </div>
244
- </foreignObject>
245
- <text
246
- x={n.x}
247
- y={n.y + 45}
248
- textAnchor="middle"
249
- fontSize="12"
250
- fill="var(--text)"
251
- >
252
- {n.label}
253
- </text>
254
  </g>
255
- ))}
256
- </svg>
 
 
 
 
 
 
 
 
 
 
257
  </div>
258
 
259
- {/* Logs */}
260
- <div className="w-80 h-[600px] bg-[var(--card)]/70 border border-[var(--accent)]/30 rounded-xl p-3 text-xs font-mono overflow-y-auto backdrop-blur-sm">
261
- <h4 className="text-[var(--accent)] font-semibold mb-2 flex items-center gap-2">
262
  <Radar size={14} /> Live Logs
263
  </h4>
264
  {logs.map((log, i) => (
265
- <div key={i} className="border-b border-[var(--accent)]/10 pb-1">
266
- {log}
267
- </div>
268
  ))}
269
  </div>
270
  </div>
271
 
272
- {/* Timeline */}
273
- <div className="mt-8 px-10">
274
- <h3 className="text-lg text-[var(--accent)] font-semibold mb-2">Attack Timeline</h3>
275
- <div className="flex items-center gap-8">
276
- {flow.nodes.map((n,i)=>(
277
  <div key={i} className="flex flex-col items-center">
278
- <div className={`w-4 h-4 rounded-full ${i<=activeStage?"bg-[var(--accent)]":"bg-slate-700"}`}></div>
279
- <p className="text-xs mt-1 text-[var(--text)]/60">{n.label}</p>
280
  </div>
281
  ))}
282
  </div>
283
  </div>
284
 
285
- {/* Tabs */}
286
- <div className="mt-10 px-10">
287
- <div className="flex gap-4 text-sm mb-3">
288
- {["behavior","detection","mitigation","dataset"].map((tab)=>(
289
- <button key={tab} onClick={()=>setActiveTab(tab)}
290
- className={`px-3 py-2 rounded-md border ${activeTab===tab?"border-[var(--accent)] text-[var(--accent)]":"border-slate-700 text-[var(--text)]/60"}`}>
291
- {tab.toUpperCase()}
292
- </button>
293
- ))}
294
- </div>
295
- <div className="bg-[var(--card)]/70 border border-[var(--accent)]/20 rounded-xl p-4 text-sm leading-relaxed text-[var(--text)]/90">
296
- {activeTab==="behavior" && (
297
- <p>{type} uses layered obfuscation to hide packet origin and route through multiple relays...</p>
298
- )}
299
- {activeTab==="detection" && (
300
- <p>AI model monitors statistical anomalies in flow metadata to classify {type} traffic with 90%+ accuracy.</p>
301
- )}
302
- {activeTab==="mitigation" && (
303
- <p>Network segmentation, DNS filtering, and retraining are key mitigations for {type}-based intrusions.</p>
304
- )}
305
- {activeTab==="dataset" && (
306
- <p>Trained on CICIDS2017 + Darknet + custom captures across 18-class distribution including VPN, TOR, I2P.</p>
307
  )}
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
308
  </div>
309
  </div>
 
 
 
310
 
311
 
312
- {/* Comparison Chart */}
313
- <div className="mt-10 px-10">
314
- <h3 className="text-lg font-semibold text-[var(--accent)] mb-3">Attack Comparison Metrics</h3>
315
- <div className="bg-[var(--card)]/70 p-4 rounded-xl border border-[var(--accent)]/30 h-[300px]">
316
- <ResponsiveContainer width="100%" height="100%">
317
- <BarChart data={compareData}>
318
- <CartesianGrid strokeDasharray="3 3" strokeOpacity={0.1}/>
319
- <XAxis dataKey="name" stroke="var(--text)"/>
320
- <YAxis stroke="var(--text)"/>
321
- <Tooltip/>
322
- <Bar dataKey="risk" fill="#f43f5e" name="Risk Level"/>
323
- <Bar dataKey="detection" fill="var(--accent)" name="Detection Accuracy"/>
324
- </BarChart>
325
- </ResponsiveContainer>
326
- </div>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
327
  </div>
328
 
329
- {/* Controls */}
330
- <div className="fixed bottom-4 left-1/2 -translate-x-1/2 bg-[var(--card)]/80 backdrop-blur-md px-6 py-3 border border-[var(--accent)]/30 rounded-2xl flex items-center gap-5 shadow-lg z-50">
331
- <button
332
- onClick={() => setPaused(!paused)}
333
- className="text-[var(--accent)] flex items-center gap-2 hover:opacity-80 transition"
334
- >
335
- {paused ? <Play size={18} /> : <Pause size={18} />}
336
- {paused ? "Play" : "Pause"}
337
- </button>
338
- <div className="flex items-center gap-2 text-sm text-[var(--accent)]">
339
- <Zap size={16} /> Speed:
340
- <input
341
- type="range"
342
- min="2"
343
- max="10"
344
- value={speed}
345
- onChange={(e) => setSpeed(e.target.value)}
346
- className="accent-[var(--accent)] w-28"
347
- />
348
- <span>{speed}s</span>
349
  </div>
350
- <button
351
- onClick={() => setReplayActive(true)}
352
- className="text-[var(--accent)] flex items-center gap-2 hover:opacity-80 transition"
353
- >
354
- <RefreshCcw size={16} /> Replay Flow
355
- </button>
356
- <button
357
- onClick={() => setHighlightDetection(!highlightDetection)}
358
- className={`px-3 py-1 text-sm rounded-lg border ${
359
- highlightDetection
360
- ? "bg-rose-600/30 border-rose-500/40 text-rose-300"
361
- : "bg-[var(--accent)]/10 border-[var(--accent)]/30 text-[var(--accent)]"
362
- }`}
363
- >
364
- {highlightDetection ? "Detection ON 🔴" : "Highlight Detection"}
365
  </button>
366
  </div>
 
367
  <ChatAssistant />
368
  </div>
369
  );
370
- }
371
-
372
-
373
-
374
-
375
-
 
2
  import ChatAssistant from "./ChatAssistant";
3
  import { useLocation, useNavigate } from "react-router-dom";
4
  import {
5
+ Shield, Lock, Server, Activity, Wifi, Play, Pause, Zap, Radar, RefreshCcw, FileDown,
 
 
 
 
 
 
 
 
 
 
6
  } from "lucide-react";
7
  import {
8
+ BarChart, Bar, XAxis, YAxis, CartesianGrid, Tooltip, ResponsiveContainer,
 
 
 
 
 
 
9
  } from "recharts";
10
  import jsPDF from "jspdf";
11
  import html2canvas from "html2canvas";
12
+ import toast, { Toaster } from "react-hot-toast"; // Fixed missing import
13
 
14
  function useQuery() {
15
  return new URLSearchParams(useLocation().search);
 
34
  getComputedStyle(document.body).getPropertyValue("--accent") || "#00e5ff"
35
  );
36
 
 
37
  useEffect(() => {
38
  const observer = new MutationObserver(() => {
39
  const newAccent = getComputedStyle(document.body).getPropertyValue("--accent");
40
  setAccentColor(newAccent.trim());
41
  });
 
42
  observer.observe(document.body, { attributes: true, attributeFilter: ["class"] });
 
43
  return () => observer.disconnect();
44
  }, []);
45
 
 
46
  useEffect(() => {
47
  const interval = setInterval(() => {
48
  if (!paused && !replayActive) {
49
  const t = new Date().toLocaleTimeString();
50
+ const fake = `[${t}] ${type} flow → ${Math.random() > 0.6 ? "⚠️ Suspicious" : "✅ Normal"}`;
 
 
51
  setLogs((p) => [fake, ...p.slice(0, 10)]);
52
  }
53
  }, 1500);
54
  return () => clearInterval(interval);
55
+ }, [paused, replayActive, type]);
56
 
 
57
  const flow = useMemo(() => {
58
  const titleMap = {
59
+ TOR: "TOR Network Attack Flow",
60
+ I2P: "I2P Encrypted Flow",
61
+ VPN: "VPN Tunnel Simulation",
62
+ FREENET: "Freenet Data Flow",
63
+ ZERONET: "ZeroNet P2P Flow",
64
  };
65
 
66
  const nodes = [
67
+ { id: "attacker", label: "Origin", x: 100, y: 200, icon: <Activity size={16} /> },
68
+ { id: "entry", label: "Entry", x: 300, y: 120, icon: <Lock size={16} /> },
69
+ { id: "relay", label: "Relay", x: 550, y: 150, icon: <Wifi size={16} /> },
70
+ { id: "exit", label: "Exit", x: 800, y: 200, icon: <Lock size={16} /> },
71
+ { id: "victim", label: "Victim", x: 1050, y: 250, icon: <Server size={16} /> },
72
+ { id: "detection", label: "AI", x: 1250, y: 250, icon: <Shield size={16} /> },
73
  ];
74
 
75
  const paths = [
76
+ "M100 200 C200 100, 240 100, 300 120",
77
+ "M300 120 C400 100, 480 120, 550 150",
78
+ "M550 150 C650 160, 720 180, 800 200",
79
+ "M800 200 C950 240, 1000 260, 1050 250",
80
+ "M1050 250 C1150 260, 1200 260, 1250 250",
81
  ];
82
 
83
  return { title: titleMap[type], nodes, paths };
84
  }, [type]);
85
 
 
86
  useEffect(() => {
87
  if (replayActive) {
88
  let stage = 0;
 
96
  }, 1200);
97
  return () => clearInterval(interval);
98
  }
99
+ }, [replayActive, flow.nodes.length]);
100
 
 
101
  const exportPDF = async () => {
102
  const el = flowRef.current;
103
  const canvas = await html2canvas(el);
 
106
  pdf.save(`${type}_Flow_Report.pdf`);
107
  };
108
 
 
109
  const compareData = [
110
  { name: "TOR", risk: 85, detection: 92 },
111
  { name: "VPN", risk: 65, detection: 75 },
112
  { name: "I2P", risk: 75, detection: 88 },
113
  { name: "Freenet", risk: 50, detection: 70 },
 
114
  ];
115
 
116
  return (
117
+ <div ref={flowRef} className="relative min-h-screen bg-[var(--card)] text-[var(--text)] overflow-x-hidden pb-32">
118
+ <Toaster position="bottom-right" />
119
+ <div className="absolute inset-0 blur-3xl opacity-20 pointer-events-none animate-pulse"
120
+ style={{ background: `radial-gradient(circle at 50% 50%, ${accentColor}55 0%, transparent 70%)` }} />
 
 
 
 
 
 
 
121
 
122
+ {/* Responsive Header */}
123
+ <header className="flex flex-wrap items-center justify-between p-4 md:p-6 relative z-10 gap-4">
124
+ <button onClick={() => navigate(-1)} className="px-4 py-2 bg-[var(--card)]/50 border border-[var(--accent)]/30 rounded-lg text-[var(--accent)] text-sm">
 
 
 
125
  ← Back
126
  </button>
127
+ <h2 className="text-xl md:text-3xl font-bold text-[var(--accent)] text-center flex-1 md:flex-none">
128
  {flow.title}
129
  </h2>
130
+ <button onClick={exportPDF} className="px-3 py-2 bg-[var(--accent)]/20 border border-[var(--accent)]/30 rounded-lg text-[var(--accent)] flex items-center gap-2 text-sm">
131
+ <FileDown size={16} /> <span className="hidden sm:inline">Export</span>
 
 
 
132
  </button>
133
+ </header>
134
+
135
+ {/* Main Content Grid */}
136
+ <div className="flex flex-col lg:flex-row gap-6 px-4 md:px-6 relative z-10">
137
+
138
+ {/* SVG Flow - Makes it scrollable on tiny screens, scales on tablets */}
139
+ <div className="flex-1 overflow-x-auto lg:overflow-visible bg-black/20 rounded-2xl border border-white/5 p-4">
140
+ <div className="min-w-[800px] lg:min-w-full">
141
+ <svg viewBox="0 0 1350 400" width="100%" className="h-auto max-h-[500px]">
142
+ <defs>
143
+ <linearGradient id="flowGrad" x1="0" y1="0" x2="1" y2="1">
144
+ <stop offset="0%" stopColor={highlightDetection ? "#ff0044" : accentColor} stopOpacity="0.9" />
145
+ <stop offset="100%" stopColor={accentColor} stopOpacity="0.3" />
146
+ </linearGradient>
147
+ <filter id="glow"><feGaussianBlur stdDeviation="3.5" result="b" /><feMerge><feMergeNode in="b" /><feMergeNode in="SourceGraphic" /></feMerge></filter>
148
+ </defs>
149
 
150
+ <g stroke="url(#flowGrad)" strokeWidth="3.5" fill="none" filter="url(#glow)">
151
+ {flow.paths.map((path, i) => {
152
+ const pathId = pid(`${type}_${i}`);
153
+ return (
154
+ <g key={pathId}>
155
+ <path id={pathId} d={path} strokeLinecap="round" opacity={replayActive && i > activeStage ? 0.15 : 0.8} />
156
+ {!paused && Array.from({ length: 5 }).map((_, j) => (
157
+ <circle key={j} r="4" fill={highlightDetection ? "#ff0044" : accentColor}>
158
+ <animateMotion dur={`${speed}s`} repeatCount="indefinite" begin={`${j * 0.7}s`}><mpath href={`#${pathId}`} /></animateMotion>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
159
  </circle>
160
  ))}
161
+ </g>
162
+ );
163
+ })}
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
164
  </g>
165
+
166
+ {flow.nodes.map((n, i) => (
167
+ <g key={i}>
168
+ <circle cx={n.x} cy={n.y} r="26" fill={accentColor} opacity={activeStage >= i || !replayActive ? 0.35 : 0.15} stroke={accentColor} strokeWidth="1.5" filter="url(#glow)" />
169
+ <foreignObject x={n.x - 10} y={n.y - 10} width="20" height="20">
170
+ <div className="flex items-center justify-center w-full h-full text-[var(--text)]">{n.icon}</div>
171
+ </foreignObject>
172
+ <text x={n.x} y={n.y + 45} textAnchor="middle" fontSize="12" fill="var(--text)" className="font-bold">{n.label}</text>
173
+ </g>
174
+ ))}
175
+ </svg>
176
+ </div>
177
  </div>
178
 
179
+ {/* Responsive Logs Panel */}
180
+ <div className="w-full lg:w-80 h-64 lg:h-[500px] bg-[var(--card)]/70 border border-[var(--accent)]/30 rounded-xl p-3 text-xs font-mono overflow-y-auto backdrop-blur-sm">
181
+ <h4 className="text-[var(--accent)] font-semibold mb-2 flex items-center gap-2 sticky top-0 bg-[var(--card)] py-1">
182
  <Radar size={14} /> Live Logs
183
  </h4>
184
  {logs.map((log, i) => (
185
+ <div key={i} className="border-b border-[var(--accent)]/10 pb-1 py-1">{log}</div>
 
 
186
  ))}
187
  </div>
188
  </div>
189
 
190
+ {/* Timeline - Horizontal Scroll on Mobile */}
191
+ <div className="mt-8 px-4 md:px-10 overflow-x-auto pb-4">
192
+ <h3 className="text-lg text-[var(--accent)] font-semibold mb-4">Attack Timeline</h3>
193
+ <div className="flex items-center gap-4 md:gap-8 min-w-max">
194
+ {flow.nodes.map((n, i) => (
195
  <div key={i} className="flex flex-col items-center">
196
+ <div className={`w-4 h-4 rounded-full transition-all duration-500 ${i <= activeStage ? "bg-[var(--accent)] scale-125 shadow-[0_0_10px_var(--accent)]" : "bg-slate-700"}`}></div>
197
+ <p className="text-[10px] mt-2 text-[var(--text)]/60">{n.label}</p>
198
  </div>
199
  ))}
200
  </div>
201
  </div>
202
 
203
+ {/* Tabs & Comparison - Grid layout */}
204
+ <div className="grid grid-cols-1 lg:grid-cols-2 gap-6 px-4 md:px-10 mt-6 mb-10">
205
+ <div className="flex flex-col gap-3">
206
+ {/* Tactical Tab Navigation */}
207
+ <div className="flex flex-wrap gap-2">
208
+ {["behavior", "detection", "mitigation", "dataset"].map((tab) => (
209
+ <button
210
+ key={tab}
211
+ onClick={() => setActiveTab(tab)}
212
+ className={`relative px-4 py-2 text-[10px] font-black uppercase tracking-widest transition-all duration-300 overflow-hidden
213
+ ${activeTab === tab
214
+ ? "text-[var(--accent)] border-b-2 border-[var(--accent)]"
215
+ : "text-[var(--text)]/40 hover:text-[var(--text)]/80 border-b border-white/5"}`}
216
+ >
217
+ {activeTab === tab && (
218
+ <span className="absolute inset-0 bg-[var(--accent)]/5 animate-pulse" />
 
 
 
 
 
 
219
  )}
220
+ {tab}
221
+ </button>
222
+ ))}
223
+ </div>
224
+
225
+ {/* Content Terminal Window */}
226
+ <div className="relative group">
227
+ {/* Decorative Brackets */}
228
+ <div className="absolute -top-2 -left-2 w-4 h-4 border-t-2 border-l-2 border-[var(--accent)]/30 group-hover:border-[var(--accent)] transition-colors" />
229
+ <div className="absolute -bottom-2 -right-2 w-4 h-4 border-b-2 border-r-2 border-[var(--accent)]/30 group-hover:border-[var(--accent)] transition-colors" />
230
+
231
+ <div className="bg-[var(--card)]/80 backdrop-blur-md border border-white/5 p-6 min-h-[160px] flex flex-col justify-between">
232
+ <div className="space-y-4">
233
+ <div className="flex items-center gap-2">
234
+ <div className="w-1.5 h-1.5 bg-[var(--accent)] animate-ping" />
235
+ <span className="text-[9px] font-mono text-[var(--accent)] tracking-[0.3em] uppercase">
236
+ Sector_{activeTab}_Analysis
237
+ </span>
238
+ </div>
239
+
240
+ <div className="font-mono text-sm leading-relaxed text-[var(--text)]/90 border-l-2 border-[var(--accent)]/20 pl-4 py-1">
241
+ {activeTab === "behavior" && (
242
+ <p><span className="text-[var(--accent)] font-bold">REPORT:</span> {type} utilizes a decentralized layered encryption mesh. Every node transition re-encapsulates the payload, creating a "Matryoshka" effect that obfuscates the original source IP and prevents packet-level correlation.</p>
243
+ )}
244
+ {activeTab === "detection" && (
245
+ <p><span className="text-[var(--accent)] font-bold">NEURAL_SIG:</span> AstraGuard AI employs recurrent feature extraction to identify microscopic jitter and inter-arrival time (IAT) variances unique to {type} tunnels, achieving an F1-score of 0.94.</p>
246
+ )}
247
+ {activeTab === "mitigation" && (
248
+ <p><span className="text-[var(--accent)] font-bold">DEFENSE:</span> Automated Null-Route triggers are prepared for localized clusters. Implementing dynamic circuit breaking and TLS-fingerprint filtering to strip {type} obfuscation layers at the edge gateway.</p>
249
+ )}
250
+ {activeTab === "dataset" && (
251
+ <p><span className="text-[var(--accent)] font-bold">SOURCE:</span> Synthesized from 1.4TB of telemetry including CICIDS2017, Darknet-2020, and live-captured PCAPs. Distribution covers 18 distinct traffic classes with supervised labeling.</p>
252
+ )}
253
+ </div>
254
+ </div>
255
+
256
+ {/* Bottom Metadata Line */}
257
+ <div className="mt-4 pt-4 border-t border-white/5 flex justify-between items-center opacity-40">
258
+ <span className="text-[8px] font-bold uppercase tracking-widest text-[var(--accent)]">Security Level: Level_4_Clearance</span>
259
+ <span className="text-[8px] font-bold text-[var(--accent)]">ID: {Math.random().toString(16).substr(2, 8).toUpperCase()}</span>
260
  </div>
261
  </div>
262
+ </div>
263
+ </div>
264
+
265
 
266
 
267
+ <div className="bg-[var(--card)]/70 p-6 rounded-xl border border-[var(--accent)]/30 h-[350px] relative overflow-hidden group">
268
+ {/* Decorative background scan line */}
269
+ <div className="absolute inset-0 pointer-events-none opacity-5 bg-[linear-gradient(transparent_50%,rgba(0,229,255,0.1)_50%)] bg-[length:100%_4px] animate-pulse" />
270
+
271
+ <h3 className="text-[10px] font-black uppercase tracking-[0.2em] text-[var(--accent)] mb-6 flex items-center gap-2">
272
+ <Activity size={14} className="animate-pulse" /> Threat Propensity vs. Detection Accuracy
273
+ </h3>
274
+
275
+ <ResponsiveContainer width="100%" height="85%">
276
+ <BarChart data={compareData} margin={{ top: 10, right: 10, left: -20, bottom: 0 }}>
277
+ <defs>
278
+ {/* Gradient for Detection Bars */}
279
+ <linearGradient id="barGrad" x1="0" y1="0" x2="0" y2="1">
280
+ <stop offset="0%" stopColor="var(--accent)" stopOpacity={1} />
281
+ <stop offset="100%" stopColor="var(--accent)" stopOpacity={0.2} />
282
+ </linearGradient>
283
+ {/* Gradient for Risk Bars */}
284
+ <linearGradient id="riskGrad" x1="0" y1="0" x2="0" y2="1">
285
+ <stop offset="0%" stopColor="#f43f5e" stopOpacity={1} />
286
+ <stop offset="100%" stopColor="#f43f5e" stopOpacity={0.2} />
287
+ </linearGradient>
288
+ </defs>
289
+
290
+ <CartesianGrid
291
+ strokeDasharray="0"
292
+ vertical={false}
293
+ stroke="rgba(255,255,255,0.05)"
294
+ />
295
+
296
+ <XAxis
297
+ dataKey="name"
298
+ axisLine={false}
299
+ tickLine={false}
300
+ tick={{ fill: 'var(--text)', fontSize: 10, fontWeight: 'bold' }}
301
+ dy={10}
302
+ />
303
+
304
+ <YAxis
305
+ axisLine={false}
306
+ tickLine={false}
307
+ tick={{ fill: 'var(--text)', opacity: 0.4, fontSize: 9 }}
308
+ />
309
+
310
+ <Tooltip
311
+ cursor={{ fill: 'rgba(255,255,255,0.03)' }}
312
+ contentStyle={{
313
+ backgroundColor: 'rgba(10,10,10,0.95)',
314
+ border: '1px solid var(--accent)',
315
+ borderRadius: '8px',
316
+ fontSize: '11px',
317
+ backdropFilter: 'blur(10px)'
318
+ }}
319
+ itemStyle={{ fontWeight: 'bold', textTransform: 'uppercase' }}
320
+ />
321
+
322
+ {/* Main Bars with Glow Effect */}
323
+ <Bar
324
+ dataKey="risk"
325
+ fill="url(#riskGrad)"
326
+ radius={[2, 2, 0, 0]}
327
+ barSize={12}
328
+ />
329
+ <Bar
330
+ dataKey="detection"
331
+ fill="url(#barGrad)"
332
+ radius={[2, 2, 0, 0]}
333
+ barSize={12}
334
+ />
335
+ </BarChart>
336
+ </ResponsiveContainer>
337
+
338
+ {/* Legend Overlay */}
339
+ <div className="absolute bottom-4 right-6 flex gap-4">
340
+ <div className="flex items-center gap-1.5">
341
+ <div className="w-2 h-2 rounded-full bg-rose-500 shadow-[0_0_8px_#f43f5e]" />
342
+ <span className="text-[8px] font-black uppercase opacity-60 tracking-widest">Risk Index</span>
343
+ </div>
344
+ <div className="flex items-center gap-1.5">
345
+ <div className="w-2 h-2 rounded-full bg-[var(--accent)] shadow-[0_0_8px_var(--accent)]" />
346
+ <span className="text-[8px] font-black uppercase opacity-60 tracking-widest">AI Confidence</span>
347
+ </div>
348
+ </div>
349
+ </div>
350
  </div>
351
 
352
+ {/* Responsive Floating Controls */}
353
+ <div className="fixed bottom-4 left-1/2 -translate-x-1/2 w-[92%] max-w-2xl bg-[var(--card)]/90 backdrop-blur-xl px-4 py-3 border border-[var(--accent)]/30 rounded-2xl flex flex-wrap items-center justify-between gap-3 shadow-2xl z-50">
354
+ <div className="flex items-center gap-4">
355
+ <button onClick={() => setPaused(!paused)} className="text-[var(--accent)] flex items-center gap-3 font-bold">Pause
356
+ {paused ? <Play size={20} /> : <Pause size={20} />}
357
+ </button>
358
+ <button onClick={() => setReplayActive(true)} className="text-[var(--accent)] font-bold gap-3 flex items-center">Refresh
359
+ <RefreshCcw size={18} />
360
+ </button>
 
 
 
 
 
 
 
 
 
 
 
361
  </div>
362
+
363
+ <div className="hidden sm:flex items-center gap-2 text-[19px] text-[var(--accent)]">
364
+ <Zap size={14} /> Speed
365
+ <input type="range" min="2" max="10" value={speed} onChange={(e) => setSpeed(e.target.value)} className="accent-[var(--accent)] w-20" />
366
+ </div>
367
+
368
+ <button onClick={() => setHighlightDetection(!highlightDetection)}
369
+ className={`px-3 py-1.5 text-cyan-500 font-bold rounded-lg border transition-all ${highlightDetection ? "bg-rose-600 border-rose-500 text-white" : "border-[var(--accent)]/30 text-[var(--accent)]"}`}>
370
+ {highlightDetection ? "DETECTION ACTIVE" : "ISOLATE THREAT"}
 
 
 
 
 
 
371
  </button>
372
  </div>
373
+
374
  <ChatAssistant />
375
  </div>
376
  );
377
+ }
 
 
 
 
 
frontend/src/pages/ReportsPage.jsx CHANGED
@@ -1,29 +1,14 @@
1
  import React, { useEffect, useState } from "react";
2
  import {
3
- FileText,
4
- Filter,
5
- Download,
6
- Eye,
7
- Trash2,
8
- RefreshCcw,
9
- BarChart3,
10
- Mail,
11
- Send,
12
- PieChart,
13
- AlertTriangle,
14
  } from "lucide-react";
15
  import toast, { Toaster } from "react-hot-toast";
16
  import ChatAssistant from "./ChatAssistant";
17
  import {
18
- ResponsiveContainer,
19
- LineChart,
20
- Line,
21
- XAxis,
22
- YAxis,
23
- Tooltip,
24
- Pie,
25
- PieChart as PieChartComp,
26
- Cell,
27
  } from "recharts";
28
 
29
  export default function ReportsPage() {
@@ -35,26 +20,21 @@ export default function ReportsPage() {
35
  const [email, setEmail] = useState("");
36
  const [sending, setSending] = useState(false);
37
 
38
- const COLORS = ["#00e5ff", "#00ff99", "#fbbf24", "#ff0059"];
39
 
40
- // 🧠 Fetch available reports
41
  const fetchReports = async () => {
42
  try {
43
  setLoading(true);
44
  const res = await fetch("http://127.0.0.1:5000/api/reports/list");
45
- if (!res.ok) throw new Error("Failed to fetch reports");
46
  const data = await res.json();
47
  setReports(data);
48
  } catch (err) {
49
- toast.error("Failed to load reports");
50
- console.error("Report fetch error:", err);
51
  } finally {
52
  setLoading(false);
53
  }
54
  };
55
 
56
- // 📊 Fetch chart data
57
- // 📊 Fetch chart data
58
  const fetchCharts = async () => {
59
  try {
60
  const trendRes = await fetch("http://127.0.0.1:5000/api/reports/trend");
@@ -63,41 +43,26 @@ export default function ReportsPage() {
63
 
64
  const distRes = await fetch("http://127.0.0.1:5000/api/reports/distribution");
65
  const distData = await distRes.json();
66
- // ✅ Convert object → array for PieChart
67
  const distArray = Object.entries(distData).map(([name, value]) => ({ name, value }));
68
  setReportDistribution(distArray);
69
- } catch (err) {
70
- console.error("Chart fetch error:", err);
71
- }
72
- };
73
-
74
 
75
  useEffect(() => {
76
  fetchReports();
77
  fetchCharts();
78
  }, []);
79
 
80
- // 📥 Download report
81
  const handleDownload = (r) => {
82
- if (!r.endpoint) {
83
- toast.error("No download link found");
84
- return;
85
- }
86
  window.open(r.endpoint, "_blank");
87
- toast.success(`Downloading ${r.name}`);
88
  };
89
 
90
- // 🗑 Delete report (frontend only)
91
- const handleDelete = (id) => {
92
- setReports((prev) => prev.filter((r) => r.id !== id));
93
- toast("🗑️ Report deleted successfully", {
94
- style: { background: "#001122", color: "var(--accent)" },
95
- });
96
- };
97
-
98
- // 📧 Send summary email
99
  const handleSendEmail = async () => {
100
- if (!email.trim()) return toast.error("Enter a valid email!");
101
  setSending(true);
102
  try {
103
  const res = await fetch("http://127.0.0.1:5000/api/reports/email", {
@@ -105,216 +70,167 @@ export default function ReportsPage() {
105
  headers: { "Content-Type": "application/json" },
106
  body: JSON.stringify({ email }),
107
  });
108
- const result = await res.json();
109
- if (res.ok) toast.success(result.message || `Email sent to ${email}`);
110
- else toast.error(result.error || "Failed to send email");
111
  } catch (err) {
112
- toast.error("Error sending email");
113
- console.error("Email send error:", err);
114
  } finally {
115
  setSending(false);
116
  }
117
  };
118
 
119
- // Filtered list
120
- const filteredReports =
121
- filter === "All" ? reports : reports.filter((r) => r.type === filter);
122
 
123
  return (
124
- <div className="p-6 space-y-8 relative">
125
- <Toaster position="bottom-right" />
126
- {/* 🌫️ Subtle Glow Background */}
127
- <div
128
- className="absolute inset-0 animate-pulse-slow pointer-events-none"
129
- style={{
130
- background:
131
- "radial-gradient(circle at center, color-mix(in srgb, var(--accent) 25%, transparent) 8%, transparent 75%)",
132
- opacity: 0.25,
133
- }}
134
- ></div>
 
 
135
 
136
- {/* HEADER */}
137
- <div className="flex justify-between items-center flex-wrap gap-3">
138
- <h2 className="text-2xl font-semibold text-[var(--accent)] flex items-center gap-2">
139
- <FileText size={22} /> Intelligence Reports Center
140
- </h2>
141
- <button
142
- onClick={() => {
143
- fetchReports();
144
- fetchCharts();
145
- toast("🔁 Refreshed reports & charts", {
146
- icon: "⚙️",
147
- style: { background: "#001122", color: "var(--accent)" },
148
- });
149
- }}
150
- className="flex items-center gap-2 bg-[var(--accent)]/10 border border-[var(--accent)]/20 text-[var(--accent)] px-3 py-1.5 rounded-lg hover:bg-[var(--accent)]/20 transition"
151
- >
152
- <RefreshCcw size={14} /> Refresh
153
- </button>
154
  </div>
155
 
156
- {/* FILTER + EMAIL SECTION */}
157
- <div className="flex flex-wrap items-center justify-between bg-black/40 border border-[var(--accent)]/20 rounded-xl p-4 gap-4">
158
- <div className="flex items-center gap-3 text-sm text-slate-400">
159
- <Filter size={14} className="text-[var(--accent)]" />
160
- <span>Filter Reports:</span>
161
- <select
162
- value={filter}
163
- onChange={(e) => setFilter(e.target.value)}
164
- className="bg-black/30 border border-[var(--accent)]/20 rounded px-2 py-1 text-[var(--accent)]"
165
- >
166
- <option>All</option>
167
- <option>System Health</option>
168
- <option>Threat Intelligence</option>
169
- <option>Network Analysis</option>
170
- <option>Access Logs</option>
171
- </select>
 
172
  </div>
173
 
174
- <div className="flex items-center gap-2">
175
  <input
176
  type="email"
177
- placeholder="Send summary to email"
178
  value={email}
179
  onChange={(e) => setEmail(e.target.value)}
180
- className="bg-black/30 border border-[var(--accent)]/20 rounded px-3 py-1 text-[var(--accent)] placeholder-slate-500"
181
  />
182
  <button
183
  onClick={handleSendEmail}
184
  disabled={sending}
185
- className="flex items-center gap-2 bg-[var(--accent)]/10 border border-[var(--accent)]/20 text-[var(--accent)] px-3 py-1.5 rounded-lg hover:bg-[var(--accent)]/20 transition"
186
  >
187
- {sending ? <Mail size={14} className="animate-pulse" /> : <Send size={14} />}
188
- {sending ? "Sending..." : "Email Reports"}
189
  </button>
190
  </div>
191
  </div>
192
 
193
- {/* REPORTS TABLE */}
194
- <div className="bg-black/40 border border-[var(--accent)]/20 rounded-xl p-4">
195
- <h3 className="text-[var(--accent)] text-sm mb-3 flex items-center gap-2">
196
- <BarChart3 size={14} /> Generated Reports
197
- </h3>
198
- {loading ? (
199
- <p className="text-center text-[var(--accent)] py-10 animate-pulse">
200
- ⚙️ Loading reports...
201
- </p>
202
- ) : filteredReports.length === 0 ? (
203
- <p className="text-center text-slate-500 py-10">
204
- No reports available for this filter.
205
- </p>
206
- ) : (
207
- <div className="overflow-x-auto">
208
- <table className="w-full text-sm text-left text-slate-300">
209
- <thead className="text-xs uppercase text-[var(--accent)] border-b border-[var(--accent)]/20">
210
- <tr>
211
- <th className="px-3 py-2">Report Name</th>
212
- <th className="px-3 py-2">Type</th>
213
- <th className="px-3 py-2">Size</th>
214
- <th className="px-3 py-2">Date</th>
215
- <th className="px-3 py-2 text-right">Actions</th>
216
- </tr>
217
- </thead>
218
- <tbody>
219
- {filteredReports.map((r, i) => (
220
- <tr
221
- key={i}
222
- className="border-b border-[var(--accent)]/10 hover:bg-[var(--accent)]/5 transition"
223
- >
224
- <td className="px-3 py-2 text-[var(--accent)] font-mono truncate">
225
- {r.name}
226
- </td>
227
- <td className="px-3 py-2">{r.type}</td>
228
- <td className="px-3 py-2">{r.size}</td>
229
- <td className="px-3 py-2">{r.date}</td>
230
- <td className="px-3 py-2 text-right space-x-2">
231
- <button
232
- onClick={() => handleDownload(r)}
233
- className="text-emerald-400 hover:text-emerald-300"
234
- title="Download"
235
- >
236
- <Download size={16} />
237
- </button>
238
- <button
239
- onClick={() => toast.info(`Preview not available for ${r.name}`)}
240
- className="text-cyan-400 hover:text-cyan-300"
241
- title="Preview"
242
- >
243
- <Eye size={16} />
244
- </button>
245
- <button
246
- onClick={() => handleDelete(r.id)}
247
- className="text-rose-400 hover:text-rose-300"
248
- title="Delete"
249
- >
250
- <Trash2 size={16} />
251
- </button>
252
- </td>
253
- </tr>
254
- ))}
255
- </tbody>
256
- </table>
257
  </div>
258
- )}
259
- </div>
260
-
261
- {/* ANALYTICS CHARTS */}
262
- <div className="grid md:grid-cols-2 gap-6">
263
- {/* Threat Trend */}
264
- <div className="bg-black/40 border border-[var(--accent)]/20 rounded-xl p-5">
265
- <h3 className="text-[var(--accent)] text-sm mb-3 flex items-center gap-2">
266
- <AlertTriangle size={14} /> Attack Trend Overview
267
- </h3>
268
- <ResponsiveContainer width="100%" height={200}>
269
  <LineChart data={attackTrend}>
270
- <XAxis dataKey="date" stroke="var(--accent)" />
 
271
  <YAxis hide />
272
  <Tooltip
273
- contentStyle={{
274
- backgroundColor: "#001122",
275
- border: "1px solid var(--accent)",
276
- borderRadius: "6px",
277
- }}
278
  />
279
- {attackTrend.length > 0 &&
280
- Object.keys(attackTrend[0])
281
- .filter((key) => key !== "date")
282
- .map((key, index) => (
283
- <Line
284
- key={index}
285
- type="monotone"
286
- dataKey={key}
287
- stroke={COLORS[index % COLORS.length]}
288
- strokeWidth={2}
289
- />
290
- ))}
291
  </LineChart>
292
  </ResponsiveContainer>
293
  </div>
294
 
295
- {/* Report Type Distribution */}
296
- <div className="bg-black/40 border border-[var(--accent)]/20 rounded-xl p-5">
297
- <h3 className="text-[var(--accent)] text-sm mb-3 flex items-center gap-2">
298
- <PieChart size={14} /> Report Type Distribution
299
- </h3>
300
  <ResponsiveContainer width="100%" height={200}>
301
  <PieChartComp>
302
- <Pie
303
- data={reportDistribution}
304
- cx="50%"
305
- cy="50%"
306
- labelLine={false}
307
- outerRadius={80}
308
- dataKey="value"
309
- >
310
  {reportDistribution.map((entry, index) => (
311
- <Cell key={`cell-${index}`} fill={COLORS[index % COLORS.length]} />
312
  ))}
313
  </Pie>
 
314
  </PieChartComp>
315
  </ResponsiveContainer>
 
 
 
 
 
 
 
 
316
  </div>
317
  </div>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
318
  <ChatAssistant />
319
  </div>
320
  );
 
1
  import React, { useEffect, useState } from "react";
2
  import {
3
+ FileText, Filter, Download, Eye, Trash2, RefreshCcw,
4
+ BarChart3, Mail, Send, PieChart, AlertTriangle,
5
+ ShieldCheck, FileSearch, Database
 
 
 
 
 
 
 
 
6
  } from "lucide-react";
7
  import toast, { Toaster } from "react-hot-toast";
8
  import ChatAssistant from "./ChatAssistant";
9
  import {
10
+ ResponsiveContainer, LineChart, Line, XAxis, YAxis, Tooltip,
11
+ Pie, PieChart as PieChartComp, Cell, CartesianGrid
 
 
 
 
 
 
 
12
  } from "recharts";
13
 
14
  export default function ReportsPage() {
 
20
  const [email, setEmail] = useState("");
21
  const [sending, setSending] = useState(false);
22
 
23
+ const COLORS = ["#00e5ff", "#a78bfa", "#34d399", "#f43f5e"];
24
 
 
25
  const fetchReports = async () => {
26
  try {
27
  setLoading(true);
28
  const res = await fetch("http://127.0.0.1:5000/api/reports/list");
 
29
  const data = await res.json();
30
  setReports(data);
31
  } catch (err) {
32
+ toast.error("Failed to load Intelligence logs");
 
33
  } finally {
34
  setLoading(false);
35
  }
36
  };
37
 
 
 
38
  const fetchCharts = async () => {
39
  try {
40
  const trendRes = await fetch("http://127.0.0.1:5000/api/reports/trend");
 
43
 
44
  const distRes = await fetch("http://127.0.0.1:5000/api/reports/distribution");
45
  const distData = await distRes.json();
 
46
  const distArray = Object.entries(distData).map(([name, value]) => ({ name, value }));
47
  setReportDistribution(distArray);
48
+ } catch (err) {
49
+ console.error("Analytics fetch error:", err);
50
+ }
51
+ };
 
52
 
53
  useEffect(() => {
54
  fetchReports();
55
  fetchCharts();
56
  }, []);
57
 
 
58
  const handleDownload = (r) => {
59
+ if (!r.endpoint) return toast.error("Binary source unavailable");
 
 
 
60
  window.open(r.endpoint, "_blank");
61
+ toast.success(`Exporting: ${r.name}`);
62
  };
63
 
 
 
 
 
 
 
 
 
 
64
  const handleSendEmail = async () => {
65
+ if (!email.trim()) return toast.error("Target address required");
66
  setSending(true);
67
  try {
68
  const res = await fetch("http://127.0.0.1:5000/api/reports/email", {
 
70
  headers: { "Content-Type": "application/json" },
71
  body: JSON.stringify({ email }),
72
  });
73
+ if (res.ok) toast.success(`Intelligence Summary dispatched to ${email}`);
 
 
74
  } catch (err) {
75
+ toast.error("Dispatch failure");
 
76
  } finally {
77
  setSending(false);
78
  }
79
  };
80
 
81
+ const filteredReports = filter === "All" ? reports : reports.filter((r) => r.type === filter);
 
 
82
 
83
  return (
84
+ <div className="p-8 space-y-8 bg-[#020617] min-h-screen text-slate-300 font-mono">
85
+ <Toaster position="top-center" />
86
+
87
+ {/* HEADER & META DATA */}
88
+ <div className="flex flex-col md:flex-row justify-between items-start md:items-center gap-6 border-b border-slate-800 pb-8">
89
+ <div>
90
+ <div className="flex items-center gap-2 text-accent text-[10px] uppercase tracking-[0.3em] mb-2 font-black">
91
+ <ShieldCheck size={14} /> Security Intelligence Unit
92
+ </div>
93
+ <h1 className="text-4xl font-black text-white italic uppercase tracking-tighter">
94
+ Analytical <span className="text-slate-500">Reports</span>
95
+ </h1>
96
+ </div>
97
 
98
+ <div className="flex items-center gap-4">
99
+ <div className="hidden lg:block text-right mr-4">
100
+ <div className="text-[10px] text-slate-500 uppercase">System_Clock</div>
101
+ <div className="text-xs text-white uppercase">{new Date().toLocaleTimeString()}</div>
102
+ </div>
103
+ <button
104
+ onClick={() => { fetchReports(); fetchCharts(); }}
105
+ className="p-3 bg-white/5 border border-white/10 rounded-full hover:bg-accent hover:text-black transition-all"
106
+ >
107
+ <RefreshCcw size={18} />
108
+ </button>
109
+ </div>
 
 
 
 
 
 
110
  </div>
111
 
112
+ {/* QUICK ACTIONS & EMAIL UTILITY */}
113
+ <div className="grid lg:grid-cols-3 gap-6">
114
+ <div className="lg:col-span-2 flex items-center gap-4 bg-slate-900/40 p-4 rounded-xl border border-white/5">
115
+ <Filter size={18} className="text-accent" />
116
+ <div className="flex gap-2">
117
+ {["All", "Threat Intelligence", "Network Analysis", "System Health"].map((cat) => (
118
+ <button
119
+ key={cat}
120
+ onClick={() => setFilter(cat)}
121
+ className={`px-4 py-1.5 rounded-md text-[10px] uppercase font-bold transition-all ${
122
+ filter === cat ? "bg-accent text-black" : "bg-white/5 text-slate-500 border border-white/5"
123
+ }`}
124
+ >
125
+ {cat}
126
+ </button>
127
+ ))}
128
+ </div>
129
  </div>
130
 
131
+ <div className="flex items-center gap-2 bg-slate-900/40 p-4 rounded-xl border border-white/5">
132
  <input
133
  type="email"
134
+ placeholder="Analyst Email Address"
135
  value={email}
136
  onChange={(e) => setEmail(e.target.value)}
137
+ className="flex-1 bg-black/50 border border-white/10 rounded-lg px-4 py-2 text-xs text-accent placeholder:text-slate-700 focus:outline-none focus:border-accent"
138
  />
139
  <button
140
  onClick={handleSendEmail}
141
  disabled={sending}
142
+ className="bg-accent/10 border border-accent/30 text-accent p-2 rounded-lg hover:bg-accent hover:text-black transition-all"
143
  >
144
+ {sending ? <RefreshCcw size={18} className="animate-spin" /> : <Send size={18} />}
 
145
  </button>
146
  </div>
147
  </div>
148
 
149
+ {/* ANALYTICS PREVIEW SECTION */}
150
+ <div className="grid lg:grid-cols-12 gap-6">
151
+ <div className="lg:col-span-8 bg-slate-900/20 border border-white/5 rounded-2xl p-6">
152
+ <div className="flex justify-between items-center mb-6">
153
+ <h3 className="text-sm font-bold uppercase tracking-widest text-white flex items-center gap-2">
154
+ <AlertTriangle size={16} className="text-rose-500" /> Temporal Attack Trend
155
+ </h3>
156
+ <span className="text-[10px] text-slate-500 uppercase tracking-tighter italic">Source: CIC-IDS2018 Pipeline</span>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
157
  </div>
158
+ <ResponsiveContainer width="100%" height={250}>
 
 
 
 
 
 
 
 
 
 
159
  <LineChart data={attackTrend}>
160
+ <CartesianGrid strokeDasharray="3 3" stroke="#1e293b" vertical={false} />
161
+ <XAxis dataKey="date" stroke="#475569" fontSize={10} tickLine={false} axisLine={false} />
162
  <YAxis hide />
163
  <Tooltip
164
+ contentStyle={{ backgroundColor: "#0f172a", border: "1px solid #334155", borderRadius: "8px", fontSize: "10px" }}
 
 
 
 
165
  />
166
+ <Line type="monotone" dataKey="value" stroke="#00e5ff" strokeWidth={3} dot={{ r: 4, fill: "#00e5ff" }} activeDot={{ r: 6 }} />
 
 
 
 
 
 
 
 
 
 
 
167
  </LineChart>
168
  </ResponsiveContainer>
169
  </div>
170
 
171
+ <div className="lg:col-span-4 bg-slate-900/20 border border-white/5 rounded-2xl p-6 flex flex-col items-center justify-center">
172
+ <h3 className="text-sm font-bold uppercase tracking-widest text-white mb-6 self-start">Categorical Weight</h3>
 
 
 
173
  <ResponsiveContainer width="100%" height={200}>
174
  <PieChartComp>
175
+ <Pie data={reportDistribution} innerRadius={60} outerRadius={80} paddingAngle={5} dataKey="value">
 
 
 
 
 
 
 
176
  {reportDistribution.map((entry, index) => (
177
+ <Cell key={`cell-${index}`} fill={COLORS[index % COLORS.length]} stroke="none" />
178
  ))}
179
  </Pie>
180
+ <Tooltip />
181
  </PieChartComp>
182
  </ResponsiveContainer>
183
+ <div className="grid grid-cols-2 gap-4 mt-4 w-full">
184
+ {reportDistribution.slice(0, 4).map((item, i) => (
185
+ <div key={i} className="flex items-center gap-2">
186
+ <div className="w-2 h-2 rounded-full" style={{ backgroundColor: COLORS[i] }} />
187
+ <span className="text-[9px] uppercase text-slate-500 truncate">{item.name}</span>
188
+ </div>
189
+ ))}
190
+ </div>
191
  </div>
192
  </div>
193
+
194
+ {/* DATA GRID - THE REPORTS */}
195
+ <div className="space-y-4">
196
+ <h3 className="text-sm font-bold uppercase tracking-widest text-white flex items-center gap-2 px-2">
197
+ <Database size={16} className="text-accent" /> Data Repository
198
+ </h3>
199
+
200
+ {loading ? (
201
+ <div className="h-48 flex items-center justify-center border border-dashed border-slate-800 rounded-2xl">
202
+ <span className="animate-pulse text-slate-600 text-xs uppercase tracking-[0.5em]">Syncing_Database...</span>
203
+ </div>
204
+ ) : (
205
+ <div className="grid grid-cols-1 md:grid-cols-2 xl:grid-cols-3 gap-4">
206
+ {filteredReports.map((r, i) => (
207
+ <div key={i} className="group bg-slate-900/40 border border-white/5 p-5 rounded-2xl hover:border-accent/40 transition-all">
208
+ <div className="flex justify-between items-start mb-4">
209
+ <div className="p-3 bg-black/50 rounded-xl border border-white/5 text-accent">
210
+ <FileSearch size={24} />
211
+ </div>
212
+ <div className="flex gap-2 opacity-0 group-hover:opacity-100 transition-opacity">
213
+ <button onClick={() => handleDownload(r)} className="p-2 hover:bg-emerald-500/20 text-emerald-500 rounded-md transition-colors"><Download size={16} /></button>
214
+ <button className="p-2 hover:bg-rose-500/20 text-rose-500 rounded-md transition-colors"><Trash2 size={16} /></button>
215
+ </div>
216
+ </div>
217
+ <div className="space-y-1">
218
+ <h4 className="text-white font-bold text-sm truncate uppercase tracking-tight">{r.name}</h4>
219
+ <div className="flex items-center justify-between">
220
+ <span className="text-[10px] text-slate-500 font-mono">{r.type}</span>
221
+ <span className="text-[10px] text-accent bg-accent/10 px-2 py-0.5 rounded uppercase font-bold">{r.size}</span>
222
+ </div>
223
+ </div>
224
+ <div className="mt-4 pt-4 border-t border-white/5 text-[9px] text-slate-600 flex justify-between">
225
+ <span>TIMESTAMP: {r.date}</span>
226
+ <span className="text-emerald-500/50">SECURED_V4</span>
227
+ </div>
228
+ </div>
229
+ ))}
230
+ </div>
231
+ )}
232
+ </div>
233
+
234
  <ChatAssistant />
235
  </div>
236
  );
frontend/src/pages/SettingsPage.jsx CHANGED
@@ -1,814 +1,240 @@
1
- // src/pages/SettingsPage.jsx
2
- import React, { useState, useEffect } from "react";
3
  import {
4
- Settings,
5
- ToggleLeft,
6
- ToggleRight,
7
- Wifi,
8
- Save,
9
- RefreshCcw,
10
- Brain,
11
- Zap,
12
- FileDown,
13
- Palette,
14
- Bell,
15
- Sliders,
16
- ShieldAlert,
17
- HardDrive,
18
- UploadCloud,
19
- Users,
20
  } from "lucide-react";
21
  import toast, { Toaster } from "react-hot-toast";
22
  import { useAuth } from "../context/AuthContext";
23
 
24
- // ---------- DEFAULT HELPERS (no shared reference issues) ----------
25
-
26
- const createDefaultThreatRules = () => ({
27
- // CICIDS2018 classes (from your list, ignoring counts)
28
- cicids2018: {
29
- BENIGN: true,
30
- Bot: true,
31
- "DoS attacks-Hulk": true,
32
- "DoS attacks-SlowHTTPTest": true,
33
- Infilteration: true,
34
- "DoS attacks-GoldenEye": true,
35
- "DoS attacks-Slowloris": true,
36
- "FTP-BruteForce": true,
37
- "SSH-Bruteforce": true,
38
- "DDOS attack-HOIC": true,
39
- "DDOS attack-LOIC-UDP": true,
40
- "Brute Force -Web": true,
41
- "Brute Force -XSS": true,
42
- "SQL Injection": true,
43
- },
44
- // BCC classes
45
- bcc: {
46
- Freenet: true,
47
- TOR: true,
48
- ZERONET: true,
49
- I2P: true,
50
- VPN: true,
51
- },
52
- });
53
-
54
- const createDefaultCaptureSettings = () => ({
55
- interface: "AUTO",
56
- protocol: "ANY",
57
- maxPackets: 5000,
58
- sampleRate: "1x",
59
- });
60
-
61
- const createDefaultRetention = () => ({
62
- logDays: 7,
63
- anonymizeIP: false,
64
- autoPurge: true,
65
- });
66
-
67
- const createDefaultNotifications = () => ({
68
- enablePopup: true,
69
- emailAlerts: false,
70
- email: "",
71
- criticalThreshold: 10,
72
- });
73
-
74
- const createDefaultModelConfig = () => ({
75
- activeDataset: "CICIDS2018", // or "BCC"
76
- activeModelName: "CICIDS2018_Default",
77
- customModelName: "",
78
- lastUpdated: null,
79
- });
80
-
81
  export default function SettingsPage() {
82
  const { settings, setSettings, saveSettings, user } = useAuth();
83
-
84
- // Core settings from context
85
- const [autoRefresh, setAutoRefresh] = useState(settings.autoRefresh);
86
- const [soundAlerts, setSoundAlerts] = useState(settings.soundAlerts);
87
- const [aiSensitivity, setAiSensitivity] = useState(settings.aiSensitivity);
88
- const [responseMode, setResponseMode] = useState(settings.responseMode);
89
- const [ipConfig, setIpConfig] = useState(settings.ipConfig);
90
- const [portConfig, setPortConfig] = useState(settings.portConfig);
91
- const [theme, setTheme] = useState(settings.theme);
92
- const [backupProgress, setBackupProgress] = useState(0);
93
-
94
- // New enterprise settings
95
- const [threatRules, setThreatRules] = useState(createDefaultThreatRules);
96
- const [captureSettings, setCaptureSettings] = useState(
97
- createDefaultCaptureSettings
98
- );
99
- const [retention, setRetention] = useState(createDefaultRetention);
100
- const [notificationSettings, setNotificationSettings] = useState(
101
- createDefaultNotifications
102
- );
103
- const [modelConfig, setModelConfig] = useState(createDefaultModelConfig);
104
-
105
- // UI-only state
106
- const [activeThreatDataset, setActiveThreatDataset] =
107
- useState("CICIDS2018"); // "CICIDS2018" | "BCC"
108
- const [modelFile, setModelFile] = useState(null);
109
-
110
- // 🧠 Load from Firestore on login/settings change
111
- useEffect(() => {
112
- if (settings) {
113
- setAutoRefresh(settings.autoRefresh);
114
- setSoundAlerts(settings.soundAlerts);
115
- setAiSensitivity(settings.aiSensitivity);
116
- setResponseMode(settings.responseMode);
117
- setIpConfig(settings.ipConfig);
118
- setPortConfig(settings.portConfig);
119
- setTheme(settings.theme);
120
- applyTheme(settings.theme);
121
-
122
- setThreatRules(
123
- settings.threatRules || createDefaultThreatRules()
124
- );
125
- setCaptureSettings(
126
- settings.captureSettings || createDefaultCaptureSettings()
127
- );
128
- setRetention(
129
- settings.retention || createDefaultRetention()
130
- );
131
- setNotificationSettings(
132
- settings.notificationSettings ||
133
- createDefaultNotifications()
134
- );
135
- setModelConfig(
136
- settings.modelConfig || createDefaultModelConfig()
137
- );
138
- }
139
- }, [settings]);
140
-
141
- // 🎨 Apply theme globally
142
- const applyTheme = (selectedTheme) => {
143
  const body = document.body;
144
- body.classList.remove(
145
- "theme-cyber",
146
- "theme-crimson",
147
- "theme-emerald",
148
- "theme-default"
149
- );
150
- switch (selectedTheme) {
151
- case "Cyber Blue":
152
- body.classList.add("theme-cyber");
153
- break;
154
- case "Crimson Dark":
155
- body.classList.add("theme-crimson");
156
- break;
157
- case "Emerald Matrix":
158
- body.classList.add("theme-emerald");
159
- break;
160
- default:
161
- body.classList.add("theme-default");
162
- }
163
  };
164
 
165
- // 💾 Save to Firestore (extended)
166
  const handleSave = async () => {
167
- const newSettings = {
168
- autoRefresh,
169
- soundAlerts,
170
- aiSensitivity,
171
- responseMode,
172
- ipConfig,
173
- portConfig,
174
- theme,
175
-
176
- // new enterprise sections
177
- threatRules,
178
- captureSettings,
179
- retention,
180
- notificationSettings,
181
- modelConfig,
182
- };
183
-
184
- setSettings(newSettings);
185
- await saveSettings(newSettings); // 🔥 Saves to Firestore
186
- toast.success("✅ Settings saved");
187
- };
188
-
189
- // Backup to local file (for download)
190
- const handleBackup = () => {
191
- toast("🧬 Generating system backup...", { icon: "💾" });
192
- setBackupProgress(0);
193
- let progress = 0;
194
- const timer = setInterval(() => {
195
- progress += 10;
196
- setBackupProgress(progress);
197
- if (progress >= 100) {
198
- clearInterval(timer);
199
- toast.success("✅ Backup completed!");
200
- const blob = new Blob(
201
- [JSON.stringify(settings, null, 2)],
202
- { type: "application/json" }
203
- );
204
- const link = document.createElement("a");
205
- link.href = URL.createObjectURL(blob);
206
- link.download = "nids_system_backup.json";
207
- link.click();
208
- }
209
- }, 200);
210
- };
211
-
212
- const handleReset = async () => {
213
- if (!window.confirm("⚠️ Reset all settings to default?")) return;
214
-
215
- const def = {
216
- theme: "Cyber Blue",
217
- autoRefresh: true,
218
- soundAlerts: true,
219
- aiSensitivity: 70,
220
- responseMode: "Semi-Auto",
221
- ipConfig: "127.0.0.1",
222
- portConfig: "5000",
223
-
224
- threatRules: createDefaultThreatRules(),
225
- captureSettings: createDefaultCaptureSettings(),
226
- retention: createDefaultRetention(),
227
- notificationSettings: createDefaultNotifications(),
228
- modelConfig: createDefaultModelConfig(),
229
- };
230
-
231
- setSettings(def);
232
- await saveSettings(def);
233
- applyTheme("Cyber Blue");
234
- setThreatRules(def.threatRules);
235
- setCaptureSettings(def.captureSettings);
236
- setRetention(def.retention);
237
- setNotificationSettings(def.notificationSettings);
238
- setModelConfig(def.modelConfig);
239
- toast.success("✅ Settings restored to default");
240
- };
241
-
242
- // Threat rule toggler
243
- const handleToggleRule = (datasetKey, ruleKey) => {
244
- setThreatRules((prev) => ({
245
- ...prev,
246
- [datasetKey]: {
247
- ...prev[datasetKey],
248
- [ruleKey]: !prev[datasetKey][ruleKey],
249
- },
250
- }));
251
- };
252
-
253
- // Model upload (no backend, safe)
254
- const handleModelUpload = () => {
255
- if (!modelFile) {
256
- toast.error("Please select a model file first.");
257
- return;
258
- }
259
-
260
- const updated = {
261
- ...modelConfig,
262
- customModelName: modelFile.name,
263
- lastUpdated: new Date().toISOString(),
264
- };
265
-
266
- setModelConfig(updated);
267
- toast.success(
268
- "✅ Custom model registered (metadata saved in settings)."
269
- );
270
  };
271
 
272
- const currentThreatKey =
273
- activeThreatDataset === "CICIDS2018" ? "cicids2018" : "bcc";
274
- const currentThreatRules = threatRules[currentThreatKey] || {};
275
-
276
  return (
277
- <div className="p-6 space-y-6 relative text-[var(--text)]">
278
  <Toaster position="bottom-right" />
279
- <div
280
- className="absolute inset-0 animate-pulse-slow pointer-events-none"
281
- style={{
282
- background:
283
- "radial-gradient(circle at center, color-mix(in srgb, var(--accent) 25%, transparent) 8%, transparent 75%)",
284
- opacity: 0.25,
285
- }}
286
- />
287
-
288
- {/* HEADER */}
289
- <div className="flex justify-between items-center relative z-10">
290
- <h2 className="text-2xl font-semibold text-accent flex items-center gap-2">
291
- <Settings size={22} /> System Configuration
292
- </h2>
293
- <button
294
- onClick={handleSave}
295
- className="px-3 py-2 bg-cyan-500/20 border border-cyan-400/30 rounded-lg hover:bg-cyan-500/30 text-cyan-300 flex items-center gap-2"
296
- >
297
- <Save size={14} /> Save
298
- </button>
299
- </div>
300
-
301
- {/* ⚙️ SYSTEM PREFERENCES */}
302
- <div className="card-glow rounded-xl p-5 relative z-10">
303
- <h3 className="text-accent text-sm mb-3 flex items-center gap-2">
304
- <Zap size={14} /> System Preferences
305
- </h3>
306
- <div className="flex flex-wrap gap-6 text-sm text-[var(--text)]/80">
307
- {/* Auto Refresh */}
308
- <div
309
- className="flex items-center gap-3 cursor-pointer hover:text-accent"
310
- onClick={() => setAutoRefresh(!autoRefresh)}
311
- >
312
- {autoRefresh ? (
313
- <ToggleRight size={20} />
314
- ) : (
315
- <ToggleLeft size={20} />
316
- )}
317
- Auto Refresh
318
- </div>
319
-
320
- {/* Sound Alerts */}
321
- <div
322
- className="flex items-center gap-3 cursor-pointer hover:text-accent"
323
- onClick={() => setSoundAlerts(!soundAlerts)}
324
- >
325
- {soundAlerts ? (
326
- <ToggleRight size={20} />
327
- ) : (
328
- <ToggleLeft size={20} />
329
- )}
330
- Sound Alerts
331
- </div>
332
-
333
- {/* Data Retention */}
334
- <div className="flex items-center gap-2">
335
- <span>Data Retention:</span>
336
- <select
337
- value={retention.logDays}
338
- onChange={(e) =>
339
- setRetention((prev) => ({
340
- ...prev,
341
- logDays: Number(e.target.value),
342
- }))
343
- }
344
- className="bg-card border border-accent rounded px-2 py-1 text-accent"
345
- >
346
- <option value={1}>24 Hours</option>
347
- <option value={7}>7 Days</option>
348
- <option value={30}>30 Days</option>
349
- </select>
350
- </div>
351
-
352
- {/* Anonymize IP */}
353
- <div
354
- className="flex items-center gap-3 cursor-pointer hover:text-accent"
355
- onClick={() =>
356
- setRetention((prev) => ({
357
- ...prev,
358
- anonymizeIP: !prev.anonymizeIP,
359
- }))
360
- }
361
- >
362
- {retention.anonymizeIP ? (
363
- <ToggleRight size={20} />
364
- ) : (
365
- <ToggleLeft size={20} />
366
- )}
367
- Anonymize IP Addresses
368
- </div>
369
- </div>
370
- </div>
371
 
372
- {/* 🎨 THEME SETTINGS */}
373
- <div className="card-glow rounded-xl p-5 relative z-10">
374
- <h3 className="text-accent text-sm mb-3 flex items-center gap-2">
375
- <Palette size={14} /> Theme & Appearance
376
- </h3>
377
- <div className="flex flex-wrap gap-4 text-sm text-[var(--text)]/80 items-center">
378
- <select
379
- value={theme}
380
- onChange={(e) => {
381
- setTheme(e.target.value);
382
- applyTheme(e.target.value);
383
- }}
384
- className="bg-card border border-accent rounded px-3 py-2 text-accent"
385
- >
386
- <option>Cyber Blue</option>
387
- <option>Crimson Dark</option>
388
- <option>Emerald Matrix</option>
389
- <option>Default</option>
390
- </select>
391
- <span className="text-xs text-[var(--text)]/50 italic">
392
- Instantly applies across all pages
393
- </span>
394
- </div>
395
- </div>
396
-
397
- {/* 🧠 AI BEHAVIOR */}
398
- <div className="card-glow rounded-xl p-5 relative z-10">
399
- <h3 className="text-accent text-sm mb-3 flex items-center gap-2">
400
- <Brain size={14} /> AI Behavior Settings
401
- </h3>
402
- <div className="space-y-4 text-sm text-[var(--text)]/80">
403
- <div>
404
- <p className="mb-2">AI Sensitivity: {aiSensitivity}%</p>
405
- <input
406
- type="range"
407
- min="30"
408
- max="100"
409
- value={aiSensitivity}
410
- onChange={(e) => setAiSensitivity(Number(e.target.value))}
411
- className="w-full accent-[var(--accent)] cursor-pointer"
412
- />
413
  </div>
414
  <div>
415
- <p className="mb-2">Threat Response Mode:</p>
416
- <select
417
- value={responseMode}
418
- onChange={(e) => setResponseMode(e.target.value)}
419
- className="bg-card border border-accent rounded px-2 py-1 text-accent"
420
- >
421
- <option>Passive</option>
422
- <option>Semi-Auto</option>
423
- <option>Fully Auto</option>
424
- </select>
425
  </div>
426
  </div>
427
- </div>
428
-
429
- {/* 🌐 NETWORK SETTINGS */}
430
- <div className="card-glow rounded-xl p-5 relative z-10">
431
- <h3 className="text-accent text-sm mb-3 flex items-center gap-2">
432
- <Wifi size={14} /> Network Configuration
433
- </h3>
434
- <div className="grid md:grid-cols-2 gap-4 text-sm text-[var(--text)]/80">
435
- <div>
436
- <p>Server IP</p>
437
- <input
438
- type="text"
439
- value={ipConfig}
440
- onChange={(e) => setIpConfig(e.target.value)}
441
- className="w-full bg-card border border-accent rounded px-2 py-1 text-accent"
442
- />
443
- </div>
444
- <div>
445
- <p>Server Port</p>
446
- <input
447
- type="text"
448
- value={portConfig}
449
- onChange={(e) => setPortConfig(e.target.value)}
450
- className="w-full bg-card border border-accent rounded px-2 py-1 text-accent"
451
- />
452
- </div>
453
- </div>
454
- <button
455
- onClick={() =>
456
- toast.success("✅ Network settings saved (local)!")
457
- }
458
- className="mt-4 px-4 py-2 bg-accent/20 border border-accent text-accent rounded-lg hover:bg-accent/30 transition flex items-center gap-2"
459
- >
460
- <Save size={14} /> Save Configuration
461
- </button>
462
- </div>
463
-
464
- {/* 🛡️ THREAT RULE MANAGER */}
465
- <div className="card-glow rounded-xl p-5 relative z-10">
466
- <h3 className="text-accent text-sm mb-3 flex items-center gap-2">
467
- <ShieldAlert size={14} /> Threat Rule Manager
468
- </h3>
469
-
470
- {/* Dataset switch */}
471
- <div className="flex flex-wrap gap-3 mb-4 text-xs text-[var(--text)]/80">
472
- <button
473
- className={`px-3 py-1.5 rounded-full border ${
474
- activeThreatDataset === "CICIDS2018"
475
- ? "border-accent bg-accent/20 text-accent"
476
- : "border-slate-500/40 hover:border-accent/50"
477
- }`}
478
- onClick={() => setActiveThreatDataset("CICIDS2018")}
479
- >
480
- CICIDS 2018 Rules
481
  </button>
482
- <button
483
- className={`px-3 py-1.5 rounded-full border ${
484
- activeThreatDataset === "BCC"
485
- ? "border-accent bg-accent/20 text-accent"
486
- : "border-slate-500/40 hover:border-accent/50"
487
- }`}
488
- onClick={() => setActiveThreatDataset("BCC")}
489
- >
490
- BCC Rules
491
- </button>
492
- <span className="text-[11px] text-[var(--text)]/50 italic">
493
- Toggle which classes should trigger alerts for the active
494
- model.
495
- </span>
496
- </div>
497
-
498
- {/* Rules */}
499
- <div className="grid md:grid-cols-3 gap-3 text-sm text-[var(--text)]/85">
500
- {Object.keys(currentThreatRules).map((ruleKey) => (
501
- <button
502
- key={ruleKey}
503
- onClick={() =>
504
- handleToggleRule(currentThreatKey, ruleKey)
505
- }
506
- className={`flex items-center justify-between px-3 py-2 rounded-lg border text-xs ${
507
- currentThreatRules[ruleKey]
508
- ? "border-accent bg-accent/15 text-accent"
509
- : "border-slate-600/60 bg-card/40 hover:border-accent/50"
510
- }`}
511
- >
512
- <span className="truncate mr-2">{ruleKey}</span>
513
- {currentThreatRules[ruleKey] ? (
514
- <ToggleRight size={16} />
515
- ) : (
516
- <ToggleLeft size={16} />
517
- )}
518
- </button>
519
- ))}
520
  </div>
521
  </div>
522
 
523
- {/* 📡 PACKET CAPTURE SETTINGS */}
524
- <div className="card-glow rounded-xl p-5 relative z-10">
525
- <h3 className="text-accent text-sm mb-3 flex items-center gap-2">
526
- <HardDrive size={14} /> Packet Capture Settings
527
- </h3>
528
- <div className="grid md:grid-cols-2 gap-4 text-sm text-[var(--text)]/80">
529
- <div>
530
- <p className="mb-1">Capture Interface</p>
531
- <select
532
- value={captureSettings.interface}
533
- onChange={(e) =>
534
- setCaptureSettings((prev) => ({
535
- ...prev,
536
- interface: e.target.value,
537
- }))
538
- }
539
- className="w-full bg-card border border-accent rounded px-2 py-1 text-accent"
540
- >
541
- <option value="AUTO">Auto Detect</option>
542
- <option value="eth0">eth0</option>
543
- <option value="wlan0">wlan0</option>
544
- </select>
545
- </div>
546
- <div>
547
- <p className="mb-1">Protocol Filter</p>
548
- <select
549
- value={captureSettings.protocol}
550
- onChange={(e) =>
551
- setCaptureSettings((prev) => ({
552
- ...prev,
553
- protocol: e.target.value,
554
- }))
555
- }
556
- className="w-full bg-card border border-accent rounded px-2 py-1 text-accent"
557
- >
558
- <option value="ANY">Any</option>
559
- <option value="TCP">TCP</option>
560
- <option value="UDP">UDP</option>
561
- <option value="HTTP">HTTP</option>
562
- <option value="TLS">TLS</option>
563
- </select>
564
- </div>
565
- <div>
566
- <p className="mb-1">Max Packets per Session</p>
567
- <input
568
- type="number"
569
- value={captureSettings.maxPackets}
570
- onChange={(e) =>
571
- setCaptureSettings((prev) => ({
572
- ...prev,
573
- maxPackets: Number(e.target.value) || 0,
574
- }))
575
- }
576
- className="w-full bg-card border border-accent rounded px-2 py-1 text-accent"
577
- />
578
- </div>
579
- <div>
580
- <p className="mb-1">Sampling Rate</p>
581
- <select
582
- value={captureSettings.sampleRate}
583
- onChange={(e) =>
584
- setCaptureSettings((prev) => ({
585
- ...prev,
586
- sampleRate: e.target.value,
587
- }))
588
- }
589
- className="w-full bg-card border border-accent rounded px-2 py-1 text-accent"
590
- >
591
- <option value="1x">1x (Full)</option>
592
- <option value="2x">2x</option>
593
- <option value="5x">5x</option>
594
- </select>
595
- </div>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
596
  </div>
597
- </div>
598
-
599
- {/* 🔔 NOTIFICATION SETTINGS */}
600
- <div className="card-glow rounded-xl p-5 relative z-10">
601
- <h3 className="text-accent text-sm mb-3 flex items-center gap-2">
602
- <Bell size={14} /> Notification Settings
603
- </h3>
604
- <div className="space-y-4 text-sm text-[var(--text)]/80">
605
- <div
606
- className="flex items-center gap-3 cursor-pointer hover:text-accent"
607
- onClick={() =>
608
- setNotificationSettings((prev) => ({
609
- ...prev,
610
- enablePopup: !prev.enablePopup,
611
- }))
612
- }
613
- >
614
- {notificationSettings.enablePopup ? (
615
- <ToggleRight size={20} />
616
- ) : (
617
- <ToggleLeft size={20} />
618
- )}
619
- Enable In-App Popup Alerts
620
- </div>
621
 
622
- <div
623
- className="flex items-center gap-3 cursor-pointer hover:text-accent"
624
- onClick={() =>
625
- setNotificationSettings((prev) => ({
626
- ...prev,
627
- emailAlerts: !prev.emailAlerts,
628
- }))
629
- }
630
- >
631
- {notificationSettings.emailAlerts ? (
632
- <ToggleRight size={20} />
633
- ) : (
634
- <ToggleLeft size={20} />
635
- )}
636
- Email Alerts
637
- </div>
638
-
639
- <div>
640
- <p className="mb-1">Alert Email Address</p>
641
- <input
642
- type="email"
643
- value={notificationSettings.email}
644
- onChange={(e) =>
645
- setNotificationSettings((prev) => ({
646
- ...prev,
647
- email: e.target.value,
648
- }))
649
- }
650
- placeholder="analyst@example.com"
651
- className="w-full bg-card border border-accent rounded px-2 py-1 text-accent"
652
- />
653
- </div>
654
-
655
- <div>
656
- <p className="mb-1">Critical Alert Threshold (per minute)</p>
657
- <input
658
- type="number"
659
- value={notificationSettings.criticalThreshold}
660
- onChange={(e) =>
661
- setNotificationSettings((prev) => ({
662
- ...prev,
663
- criticalThreshold: Number(e.target.value) || 0,
664
- }))
665
- }
666
- className="w-full bg-card border border-accent rounded px-2 py-1 text-accent"
667
- />
668
- </div>
669
- </div>
670
- </div>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
671
 
672
- {/* 🤖 MODEL & DATASET MANAGEMENT */}
673
- <div className="card-glow rounded-xl p-5 relative z-10">
674
- <h3 className="text-accent text-sm mb-3 flex items-center gap-2">
675
- <Sliders size={14} /> Model & Dataset Management
676
- </h3>
677
- <div className="space-y-4 text-sm text-[var(--text)]/80">
678
- {/* Dataset selection */}
679
- <div className="flex flex-wrap gap-3 items-center">
680
- <span className="text-xs uppercase tracking-[0.15em] text-[var(--text)]/60">
681
- Active Dataset:
682
- </span>
683
- <button
684
- className={`px-3 py-1.5 rounded-full border ${
685
- modelConfig.activeDataset === "CICIDS2018"
686
- ? "border-accent bg-accent/20 text-accent"
687
- : "border-slate-500/40 hover:border-accent/50"
688
- }`}
689
- onClick={() =>
690
- setModelConfig((prev) => ({
691
- ...prev,
692
- activeDataset: "CICIDS2018",
693
- activeModelName: "CICIDS2018_Default",
694
- }))
695
- }
696
- >
697
- CICIDS 2018
698
- </button>
699
- <button
700
- className={`px-3 py-1.5 rounded-full border ${
701
- modelConfig.activeDataset === "BCC"
702
- ? "border-accent bg-accent/20 text-accent"
703
- : "border-slate-500/40 hover:border-accent/50"
704
- }`}
705
- onClick={() =>
706
- setModelConfig((prev) => ({
707
- ...prev,
708
- activeDataset: "BCC",
709
- activeModelName: "BCC_Default",
710
- }))
711
- }
712
- >
713
- BCC
714
  </button>
715
- </div>
716
-
717
- {/* Upload Model */}
718
- <div className="grid md:grid-cols-[2fr_auto] gap-3 items-center">
719
- <div>
720
- <p className="mb-1 flex items-center gap-2">
721
- <UploadCloud size={14} /> Upload Custom Model (.pkl/.joblib)
722
- </p>
723
- <input
724
- type="file"
725
- accept=".pkl,.joblib,.onnx"
726
- onChange={(e) => setModelFile(e.target.files[0] || null)}
727
- className="w-full text-xs text-[var(--text)]/70 bg-card border border-accent/40 rounded px-2 py-1 file:mr-3 file:px-2 file:py-1 file:text-xs file:rounded file:bg-accent/20 file:border-none file:text-accent"
728
- />
729
- </div>
730
- <button
731
- onClick={handleModelUpload}
732
- className="h-[38px] px-4 py-2 bg-accent/20 border border-accent text-accent rounded-lg hover:bg-accent/30 transition flex items-center gap-2 justify-center"
733
- >
734
- <Brain size={14} /> Register Model
735
  </button>
736
  </div>
737
 
738
- <div className="text-xs text-[var(--text)]/60">
739
- <p>Active model: {modelConfig.activeModelName}</p>
740
- {modelConfig.customModelName && (
741
- <p>
742
- Custom model:{" "}
743
- <span className="text-accent">
744
- {modelConfig.customModelName}
745
- </span>{" "}
746
- {modelConfig.lastUpdated && (
747
- <span>
748
- (updated{" "}
749
- {new Date(
750
- modelConfig.lastUpdated
751
- ).toLocaleString()}
752
- )
753
- </span>
754
- )}
755
- </p>
756
- )}
757
- </div>
758
- </div>
759
- </div>
760
-
761
- {/* 👥 USER & ACCESS OVERVIEW (UI-ONLY) */}
762
- <div className="card-glow rounded-xl p-5 relative z-10">
763
- <h3 className="text-accent text-sm mb-3 flex items-center gap-2">
764
- <Users size={14} /> User & Access Overview
765
- </h3>
766
- <div className="text-sm text-[var(--text)]/80 space-y-2">
767
- <div className="flex justify-between border-b border-slate-600/40 pb-1 text-xs text-[var(--text)]/60 uppercase tracking-[0.12em]">
768
- <span>User</span>
769
- <span>Role</span>
770
- </div>
771
- <div className="flex justify-between items-center">
772
- <span>{user?.displayName || "Current Operator"}</span>
773
- <span className="text-accent text-xs px-2 py-1 rounded-full border border-accent/50">
774
- Operator
775
- </span>
776
- </div>
777
- <p className="text-[11px] text-[var(--text)]/50 mt-2 italic">
778
- Role-based access can be integrated with your auth provider
779
- in a future enhancement.
780
- </p>
781
  </div>
782
  </div>
783
-
784
- {/* Backup & Reset */}
785
- <div className="card-glow rounded-xl p-5 relative z-10">
786
- <h3 className="text-accent text-sm mb-3 flex items-center gap-2">
787
- <FileDown size={14} /> Backup & Reset
788
- </h3>
789
- <div className="flex flex-wrap gap-4 items-center text-sm text-[var(--text)]/80">
790
- <button
791
- onClick={handleBackup}
792
- className="px-4 py-2 bg-[var(--accent)]/20 border border-[var(--accent)] text-[var(--accent)] rounded-lg hover:bg-[var(--accent)]/30 transition flex items-center gap-2"
793
- >
794
- <FileDown size={14} /> Backup Settings
795
- </button>
796
- <button
797
- onClick={handleReset}
798
- className="px-4 py-2 bg-rose-600/20 border border-rose-400/30 text-rose-300 rounded-lg hover:bg-rose-600/30 transition flex items-center gap-2"
799
- >
800
- <RefreshCcw size={14} /> Reset to Default
801
- </button>
802
- </div>
803
- {backupProgress > 0 && backupProgress < 100 && (
804
- <div className="mt-3 w-full bg-[var(--accent)]/10 h-2 rounded-full overflow-hidden">
805
- <div
806
- className="bg-[var(--accent)] h-2 animate-pulse"
807
- style={{ width: `${backupProgress}%` }}
808
- ></div>
809
- </div>
810
- )}
811
- </div>
812
  </div>
813
  );
814
- }
 
1
+ import React, { useState, useEffect, useRef } from "react";
 
2
  import {
3
+ Settings, ToggleLeft, ToggleRight, Wifi, Save, RefreshCcw, Brain, Zap,
4
+ FileDown, Palette, Bell, Sliders, ShieldAlert, HardDrive, UploadCloud, Users,
5
+ Activity, Database, ShieldCheck, Globe, Lock, History, Server, Cpu, Layers
 
 
 
 
 
 
 
 
 
 
 
 
 
6
  } from "lucide-react";
7
  import toast, { Toaster } from "react-hot-toast";
8
  import { useAuth } from "../context/AuthContext";
9
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
10
  export default function SettingsPage() {
11
  const { settings, setSettings, saveSettings, user } = useAuth();
12
+
13
+ // Logic State
14
+ const [theme, setTheme] = useState(settings?.theme ?? "Cyber Blue");
15
+ const [autoRefresh, setAutoRefresh] = useState(settings?.autoRefresh ?? true);
16
+ const [soundAlerts, setSoundAlerts] = useState(settings?.soundAlerts ?? true);
17
+ const [aiSensitivity, setAiSensitivity] = useState(settings?.aiSensitivity ?? 70);
18
+ const [responseMode, setResponseMode] = useState(settings?.responseMode ?? "Semi-Auto");
19
+ const [encryptionLevel, setEncryptionLevel] = useState("AES-256");
20
+ const [proxyEnabled, setProxyEnabled] = useState(false);
21
+ const [retentionDays, setRetentionDays] = useState(30);
22
+ const [activeThreatDataset, setActiveThreatDataset] = useState("CICIDS2018");
23
+
24
+ const fileInputRef = useRef(null);
25
+
26
+ const applyTheme = (t) => {
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
27
  const body = document.body;
28
+ body.classList.remove("theme-cyber", "theme-crimson", "theme-emerald", "theme-default");
29
+ const themeMap = { "Cyber Blue": "theme-cyber", "Crimson Dark": "theme-crimson", "Emerald Matrix": "theme-emerald", "Default": "theme-default" };
30
+ body.classList.add(themeMap[t] || "theme-default");
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
31
  };
32
 
 
33
  const handleSave = async () => {
34
+ const newSettings = { ...settings, theme, autoRefresh, aiSensitivity, responseMode };
35
+ await saveSettings(newSettings);
36
+ toast.success("All systems synchronized successfully.");
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
37
  };
38
 
 
 
 
 
39
  return (
40
+ <div className="min-h-screen p-4 lg:p-8 space-y-6 max-w-7xl mx-auto pb-24 relative z-10 bg-transparent">
41
  <Toaster position="bottom-right" />
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
42
 
43
+ {/* --- TOP BAR / OVERVIEW --- */}
44
+ <div className="glass-shell p-6 flex flex-col md:flex-row justify-between items-center gap-4 border-accent/20">
45
+ <div className="flex items-center gap-4">
46
+ <div className="p-3 bg-accent/10 rounded-2xl border border-accent/20">
47
+ <Settings className="animate-spin-slow text-accent" size={32} />
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
48
  </div>
49
  <div>
50
+ <h1 className="text-2xl font-black text-accent tracking-tighter uppercase">Command Center</h1>
51
+ <p className="text-[10px] font-mono opacity-50 uppercase tracking-widest">User: {user?.displayName || "Operator_01"} // Auth: Level_Alpha</p>
 
 
 
 
 
 
 
 
52
  </div>
53
  </div>
54
+ <div className="flex items-center gap-3">
55
+ <button onClick={handleSave} className="px-8 py-3 bg-accent text-black font-black uppercase text-xs rounded-xl hover:shadow-[0_0_25px_rgba(0,229,255,0.4)] transition-all flex items-center gap-2">
56
+ <Save size={16} /> Save Changes
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
57
  </button>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
58
  </div>
59
  </div>
60
 
61
+ <div className="grid grid-cols-1 lg:grid-cols-2 gap-8">
62
+
63
+ {/* --- LEFT COLUMN: SYSTEM & SECURITY --- */}
64
+ <div className="space-y-6">
65
+
66
+ {/* THEME & VISUALS */}
67
+ <section className="card-glow p-6">
68
+ <h3 className="text-accent text-[10px] font-black uppercase tracking-[0.2em] mb-6 flex items-center gap-2">
69
+ <Palette size={14} /> Interface Skins
70
+ </h3>
71
+ <div className="grid grid-cols-2 gap-3">
72
+ {["Cyber Blue", "Crimson Dark", "Emerald Matrix", "Default"].map((t) => (
73
+ <button key={t} onClick={() => { setTheme(t); applyTheme(t); }}
74
+ className={`py-3 text-[10px] font-bold uppercase rounded-xl border transition-all ${theme === t ? 'border-accent bg-accent/20 text-accent shadow-[0_0_15px_rgba(0,229,255,0.1)]' : 'border-white/5 bg-white/5 opacity-40 hover:opacity-100'}`}>
75
+ {t}
76
+ </button>
77
+ ))}
78
+ </div>
79
+ </section>
80
+
81
+ {/* CORE PERFORMANCE */}
82
+ <section className="card-glow p-6">
83
+ <h3 className="text-accent text-[10px] font-black uppercase tracking-[0.2em] mb-6 flex items-center gap-2">
84
+ <Zap size={14} /> Global System Prefs
85
+ </h3>
86
+ <div className="space-y-3">
87
+ <div className="flex items-center justify-between p-4 bg-white/2 rounded-xl border border-white/5">
88
+ <span className="text-xs font-bold opacity-70">Real-Time Data Streaming</span>
89
+ <button onClick={() => setAutoRefresh(!autoRefresh)} className="text-accent">
90
+ {autoRefresh ? <ToggleRight size={32} /> : <ToggleLeft size={32} className="opacity-20" />}
91
+ </button>
92
+ </div>
93
+ <div className="flex items-center justify-between p-4 bg-white/2 rounded-xl border border-white/5">
94
+ <span className="text-xs font-bold opacity-70">Auditory Alert Feedback</span>
95
+ <button onClick={() => setSoundAlerts(!soundAlerts)} className="text-accent">
96
+ {soundAlerts ? <ToggleRight size={32} /> : <ToggleLeft size={32} className="opacity-20" />}
97
+ </button>
98
+ </div>
99
+ </div>
100
+ </section>
101
+
102
+ {/* SECURITY & PRIVACY */}
103
+ <section className="card-glow p-6">
104
+ <h3 className="text-accent text-[10px] font-black uppercase tracking-[0.2em] mb-6 flex items-center gap-2">
105
+ <Lock size={14} /> Advanced Security
106
+ </h3>
107
+ <div className="space-y-4">
108
+ <div className="p-3 bg-black/40 rounded-xl border border-white/5">
109
+ <p className="text-[9px] uppercase opacity-40 mb-2">Encryption Algorithm</p>
110
+ <select value={encryptionLevel} onChange={(e) => setEncryptionLevel(e.target.value)}
111
+ className="bg-transparent text-xs font-bold text-accent outline-none w-full appearance-none">
112
+ <option value="AES-256">AES-256-GCM (Hardware Accelerated)</option>
113
+ <option value="ChaCha20">ChaCha20-Poly1305</option>
114
+ </select>
115
+ </div>
116
+ <div className="flex items-center justify-between p-3 bg-white/2 rounded-xl border border-white/5">
117
+ <div className="flex flex-col">
118
+ <span className="text-xs font-bold uppercase">Network Stealth Proxy</span>
119
+ <span className="text-[8px] opacity-40 font-mono">Routing through {proxyEnabled ? "Active Nodes" : "Direct Link"}</span>
120
+ </div>
121
+ <button onClick={() => setProxyEnabled(!proxyEnabled)} className="text-accent">
122
+ {proxyEnabled ? <ToggleRight size={28} /> : <ToggleLeft size={28} className="opacity-20" />}
123
+ </button>
124
+ </div>
125
+ </div>
126
+ </section>
127
+
128
+ {/* HARDWARE TELEMETRY */}
129
+ <section className="card-glow p-6">
130
+ <h3 className="text-accent text-[10px] font-black uppercase tracking-[0.2em] mb-6 flex items-center gap-2">
131
+ <Cpu size={14} /> Hardware Resources
132
+ </h3>
133
+ <div className="space-y-4 font-mono text-[10px]">
134
+ <div className="flex justify-between">
135
+ <span className="opacity-50 uppercase">Processor Load</span>
136
+ <span className="text-emerald-400">12.4% / Normal</span>
137
+ </div>
138
+ <div className="w-full bg-black/50 h-1.5 rounded-full overflow-hidden">
139
+ <div className="bg-emerald-400 h-full w-[12%] shadow-[0_0_10px_#34d399]"></div>
140
+ </div>
141
+ <div className="flex justify-between">
142
+ <span className="opacity-50 uppercase">Neural Cache (8GB)</span>
143
+ <span className="text-accent">2.1 GB Static</span>
144
+ </div>
145
+ <div className="w-full bg-black/50 h-1.5 rounded-full overflow-hidden">
146
+ <div className="bg-accent h-full w-[26%] shadow-[0_0_10px_var(--accent)]"></div>
147
+ </div>
148
+ </div>
149
+ </section>
150
  </div>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
151
 
152
+ {/* --- RIGHT COLUMN: AI, DATA & LOGS --- */}
153
+ <div className="space-y-6">
154
+
155
+ {/* AI NEURAL PARAMS */}
156
+ <section className="card-glow p-6">
157
+ <h3 className="text-accent text-[10px] font-black uppercase tracking-[0.2em] mb-6 flex items-center gap-2">
158
+ <Brain size={14} /> AI Inference Engine
159
+ </h3>
160
+ <div className="space-y-4">
161
+ <div className="flex justify-between text-xs font-bold uppercase">
162
+ <span>Threat Sensitivity</span>
163
+ <span className="text-accent">{aiSensitivity}%</span>
164
+ </div>
165
+ <input type="range" min="30" max="100" value={aiSensitivity} onChange={(e) => setAiSensitivity(Number(e.target.value))}
166
+ className="w-full h-1.5 bg-black/60 rounded-lg appearance-none cursor-pointer accent-accent" />
167
+ <div className="grid grid-cols-3 gap-2">
168
+ {["Passive", "Semi-Auto", "Fully Auto"].map(mode => (
169
+ <button key={mode} onClick={() => setResponseMode(mode)}
170
+ className={`py-2 text-[9px] font-black uppercase rounded-lg border transition-all ${responseMode === mode ? 'bg-accent/20 border-accent text-accent' : 'border-white/5 opacity-30 hover:opacity-100'}`}>
171
+ {mode}
172
+ </button>
173
+ ))}
174
+ </div>
175
+ </div>
176
+ </section>
177
+
178
+ {/* MODEL & DATASET MANAGEMENT */}
179
+ <section className="card-glow p-6">
180
+ <h3 className="text-accent text-[10px] font-black uppercase tracking-[0.2em] mb-6 flex items-center gap-2">
181
+ <Database size={14} /> Model Architecture
182
+ </h3>
183
+ <div className="space-y-4">
184
+ <div className="grid grid-cols-2 gap-3">
185
+ <div className="p-3 bg-black/40 rounded-xl border border-white/5">
186
+ <p className="text-[9px] uppercase opacity-40 mb-1">Active Dataset</p>
187
+ <select value={activeThreatDataset} onChange={(e) => setActiveThreatDataset(e.target.value)}
188
+ className="bg-transparent text-xs font-bold text-accent outline-none w-full">
189
+ <option value="CICIDS2018">CICIDS 2018</option>
190
+ <option value="BCC">BCC Traffic</option>
191
+ </select>
192
+ </div>
193
+ <div className="p-3 bg-black/40 rounded-xl border border-white/5">
194
+ <p className="text-[9px] uppercase opacity-40 mb-1">Model Version</p>
195
+ <p className="text-xs font-bold">RF_XENON_v4.2</p>
196
+ </div>
197
+ </div>
198
+ <div onClick={() => fileInputRef.current.click()} className="border-2 border-dashed border-accent/20 rounded-2xl p-6 flex flex-col items-center gap-2 hover:bg-accent/5 cursor-pointer transition-all">
199
+ <input type="file" ref={fileInputRef} className="hidden" />
200
+ <UploadCloud className="text-accent opacity-50" />
201
+ <span className="text-[10px] font-black uppercase">Inject Custom Weights</span>
202
+ </div>
203
+ </div>
204
+ </section>
205
+
206
+ {/* AUDIT TRAIL */}
207
+ <section className="card-glow p-6">
208
+ <h3 className="text-accent text-[10px] font-black uppercase tracking-[0.2em] mb-6 flex items-center gap-2">
209
+ <History size={14} /> System Audit Trail
210
+ </h3>
211
+ <div className="space-y-2 max-h-[140px] overflow-y-auto pr-2 custom-scroll">
212
+ {[
213
+ { t: '12:04', m: 'Firewall: Blocked IP 192.168.1.5' },
214
+ { t: '11:58', m: 'Model: Weights updated from cloud' },
215
+ { t: '11:42', m: 'Admin: Session authorized' },
216
+ { t: '10:15', m: 'System: Integrity check pass' },
217
+ ].map((log, i) => (
218
+ <div key={i} className="flex gap-3 text-[9px] font-mono border-b border-white/5 pb-2">
219
+ <span className="text-accent">[{log.t}]</span>
220
+ <span className="opacity-60 uppercase">{log.m}</span>
221
+ </div>
222
+ ))}
223
+ </div>
224
+ </section>
225
 
226
+ {/* DANGER ZONE */}
227
+ <div className="grid grid-cols-2 gap-4">
228
+ <button className="py-4 border border-accent/30 bg-accent/5 text-accent rounded-2xl text-[10px] font-black uppercase tracking-widest hover:bg-accent/10 transition-all flex flex-col items-center gap-2">
229
+ <FileDown size={20} /> Export Sync
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
230
  </button>
231
+ <button className="py-4 border border-rose-500/30 bg-rose-500/5 text-rose-500 rounded-2xl text-[10px] font-black uppercase tracking-widest hover:bg-rose-500/10 transition-all flex flex-col items-center gap-2">
232
+ <RefreshCcw size={20} /> Purge Node
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
233
  </button>
234
  </div>
235
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
236
  </div>
237
  </div>
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
238
  </div>
239
  );
240
+ }