CodebaseAi commited on
Commit
5182442
·
1 Parent(s): b53de1b

Cloud commit

Browse files
backend/app.py CHANGED
@@ -101,8 +101,8 @@ def home():
101
 
102
 
103
  # --- REMOVED: The local run block is removed. Gunicorn will handle startup on Render. ---
104
- # if __name__ == "__main__":
105
- # print("🚀 Starting Adaptive AI NIDS Backend (threading mode)...")
106
  # # Run without debug — debug spawns extra processes and uses more CPU
107
- # socketio.run(app, host="0.0.0.0", port=5000, debug=False)
108
 
 
101
 
102
 
103
  # --- REMOVED: The local run block is removed. Gunicorn will handle startup on Render. ---
104
+ if __name__ == "__main__":
105
+ print("🚀 Starting Adaptive AI NIDS Backend (threading mode)...")
106
  # # Run without debug — debug spawns extra processes and uses more CPU
107
+ socketio.run(app, host="0.0.0.0", port=5000, debug=False)
108
 
frontend/src/App.jsx CHANGED
@@ -1,10 +1,13 @@
1
- import { BrowserRouter as Router, Routes, Route, useLocation } from "react-router-dom";
2
  import { LiveDataProvider } from "./context/DataContext";
3
  import { AuthProvider } from "./context/AuthContext";
4
  import ProtectedRoute from "./components/ProtectedRoute";
5
  import Sidebar from "./components/Sidebar";
6
  import { useState } from "react";
7
 
 
 
 
8
  import AuthPage from "./pages/Login";
9
  import Dashboard from "./pages/Dashboard";
10
  import LiveTraffic from "./components/dashboard/LiveDashboard";
@@ -23,14 +26,15 @@ import SamplePred from "./pages/MLAttackSamplesPage";
23
  import Aichat from "./pages/ChatAssistant";
24
  import MainLayout from "./components/MainLayout";
25
 
26
-
27
- // Layout wrapper
28
  function AppLayout() {
29
  const location = useLocation();
30
  const hideSidebar = location.pathname === "/login";
31
-
32
  const [collapsed, setCollapsed] = useState(false);
33
 
 
 
 
 
34
  return (
35
  <div className="flex min-h-screen text-slate-100 relative bg-transparent">
36
  <ConstellationBackground />
@@ -44,23 +48,33 @@ function AppLayout() {
44
  ${collapsed ? "ml-20" : "ml-64"}
45
  `}
46
  >
47
- <Routes>
48
- <Route path="/login" element={<AuthPage />} />
49
- <Route path="/" element={<ProtectedRoute><MainLayout><Dashboard /></MainLayout></ProtectedRoute>} />
50
- <Route path="/livetraffic" element={<ProtectedRoute><MainLayout><LiveTraffic /></MainLayout></ProtectedRoute>} />
51
- <Route path="/flow" element={<ProtectedRoute><MainLayout><FlowPage /></MainLayout></ProtectedRoute>} />
52
- <Route path="/settings" element={<ProtectedRoute><MainLayout><SettingsPage /></MainLayout></ProtectedRoute>} />
53
- <Route path="/alerts" element={<ProtectedRoute><MainLayout><InfoPage /></MainLayout></ProtectedRoute>} />
54
- <Route path="/traffic" element={<ProtectedRoute><MainLayout><TrafficPage /></MainLayout></ProtectedRoute>} />
55
- <Route path="/samplepred" element={<ProtectedRoute><MainLayout><SamplePred /></MainLayout></ProtectedRoute>} />
56
- <Route path="/incidents" element={<ProtectedRoute><MainLayout><IncidentsPage /></MainLayout></ProtectedRoute>} />
57
- <Route path="/threats" element={<ProtectedRoute><MainLayout><ThreatIntel /></MainLayout></ProtectedRoute>} />
58
- <Route path="/reports" element={<ProtectedRoute><MainLayout><Reports /></MainLayout></ProtectedRoute>} />
59
- <Route path="/system" element={<ProtectedRoute><MainLayout><SystemPage /></MainLayout></ProtectedRoute>} />
60
- <Route path="/response" element={<ProtectedRoute><MainLayout><ResponsePage /></MainLayout></ProtectedRoute>} />
61
- <Route path="/mlmodels" element={<ProtectedRoute><MainLayout><MlmodelPage /></MainLayout></ProtectedRoute>} />
62
- <Route path="/chat" element={<ProtectedRoute><Aichat /></ProtectedRoute>} />
63
- </Routes>
 
 
 
 
 
 
 
 
 
 
64
  </main>
65
  </div>
66
  );
@@ -76,5 +90,4 @@ export default function App() {
76
  </LiveDataProvider>
77
  </AuthProvider>
78
  );
79
- }
80
-
 
1
+ import { BrowserRouter as Router, Routes, Route, useLocation, Navigate } from "react-router-dom";
2
  import { LiveDataProvider } from "./context/DataContext";
3
  import { AuthProvider } from "./context/AuthContext";
4
  import ProtectedRoute from "./components/ProtectedRoute";
5
  import Sidebar from "./components/Sidebar";
6
  import { useState } from "react";
7
 
8
+ // --- IMPORT THE GUARD ---
9
+ import FeatureGuard from "./components/FeatureGuard";
10
+
11
  import AuthPage from "./pages/Login";
12
  import Dashboard from "./pages/Dashboard";
13
  import LiveTraffic from "./components/dashboard/LiveDashboard";
 
26
  import Aichat from "./pages/ChatAssistant";
27
  import MainLayout from "./components/MainLayout";
28
 
 
 
29
  function AppLayout() {
30
  const location = useLocation();
31
  const hideSidebar = location.pathname === "/login";
 
32
  const [collapsed, setCollapsed] = useState(false);
33
 
34
+ // 🛠️ DEFINE LOCAL-ONLY ROUTES HERE
35
+ const localOnlyRoutes = ["/livetraffic", "/flow", "/system", "/traffic"];
36
+ const isProtectedFeature = localOnlyRoutes.includes(location.pathname);
37
+
38
  return (
39
  <div className="flex min-h-screen text-slate-100 relative bg-transparent">
40
  <ConstellationBackground />
 
48
  ${collapsed ? "ml-20" : "ml-64"}
49
  `}
50
  >
51
+ {/* Wrap the Routes in the FeatureGuard.
52
+ It will only trigger the popup if the current path is in localOnlyRoutes
53
+ AND the user is not on localhost.
54
+ */}
55
+ <FeatureGuard requireLocal={isProtectedFeature}>
56
+ <Routes>
57
+ <Route path="/login" element={<AuthPage />} />
58
+ <Route path="/" element={<ProtectedRoute><MainLayout><Dashboard /></MainLayout></ProtectedRoute>} />
59
+
60
+ {/* These routes will now trigger the popup if deployed */}
61
+ <Route path="/livetraffic" element={<ProtectedRoute><MainLayout><LiveTraffic /></MainLayout></ProtectedRoute>} />
62
+ <Route path="/flow" element={<ProtectedRoute><MainLayout><FlowPage /></MainLayout></ProtectedRoute>} />
63
+ <Route path="/system" element={<ProtectedRoute><MainLayout><SystemPage /></MainLayout></ProtectedRoute>} />
64
+ <Route path="/traffic" element={<ProtectedRoute><MainLayout><TrafficPage /></MainLayout></ProtectedRoute>} />
65
+
66
+ {/* These routes work fine in the cloud (Database/AI based) */}
67
+ <Route path="/settings" element={<ProtectedRoute><MainLayout><SettingsPage /></MainLayout></ProtectedRoute>} />
68
+ <Route path="/alerts" element={<ProtectedRoute><MainLayout><InfoPage /></MainLayout></ProtectedRoute>} />
69
+ <Route path="/samplepred" element={<ProtectedRoute><MainLayout><SamplePred /></MainLayout></ProtectedRoute>} />
70
+ <Route path="/incidents" element={<ProtectedRoute><MainLayout><IncidentsPage /></MainLayout></ProtectedRoute>} />
71
+ <Route path="/threats" element={<ProtectedRoute><MainLayout><ThreatIntel /></MainLayout></ProtectedRoute>} />
72
+ <Route path="/reports" element={<ProtectedRoute><MainLayout><Reports /></MainLayout></ProtectedRoute>} />
73
+ <Route path="/response" element={<ProtectedRoute><MainLayout><ResponsePage /></MainLayout></ProtectedRoute>} />
74
+ <Route path="/mlmodels" element={<ProtectedRoute><MainLayout><MlmodelPage /></MainLayout></ProtectedRoute>} />
75
+ <Route path="/chat" element={<ProtectedRoute><Aichat /></ProtectedRoute>} />
76
+ </Routes>
77
+ </FeatureGuard>
78
  </main>
79
  </div>
80
  );
 
90
  </LiveDataProvider>
91
  </AuthProvider>
92
  );
93
+ }
 
frontend/src/api.js CHANGED
@@ -3,19 +3,19 @@
3
  // ===============================================
4
 
5
  const BASE_URL =
6
-   import.meta.env.VITE_API_URL || "http://127.0.0.1:5000";
7
 
8
  // Safe fetch wrapper
9
  async function safeFetch(url, options = {}, timeout = 10000, retries = 1) {
10
-   const controller = new AbortController();
11
-   const id = setTimeout(() => controller.abort(), timeout);
12
 
13
-   try {
14
-     const res = await fetch(url, { ...options, signal: controller.signal });
15
 
16
-     if (!res.ok) {
17
-       const errText = await res.text();
18
-       throw new Error(`HTTP ${res.status}: ${errText}`);
19
      }
20
      return await res.json();
21
    } catch (err) {
@@ -173,8 +173,8 @@ export const offlinePredictAPI = async (file, model) => {
173
 
174
  // ➤ Get PDF forensic report download link
175
  export const downloadOfflineReport = () => {
176
-   // FIX: Using BASE_URL for live deployment
177
-   window.open(`${BASE_URL}/api/offline/report`, "_blank");
178
  };
179
 
180
 
 
3
  // ===============================================
4
 
5
  const BASE_URL =
6
+ import.meta.env.VITE_API_URL || "http://127.0.0.1:5000";
7
 
8
  // Safe fetch wrapper
9
  async function safeFetch(url, options = {}, timeout = 10000, retries = 1) {
10
+ const controller = new AbortController();
11
+ const id = setTimeout(() => controller.abort(), timeout);
12
 
13
+ try {
14
+ const res = await fetch(url, { ...options, signal: controller.signal });
15
 
16
+ if (!res.ok) {
17
+ const errText = await res.text();
18
+ throw new Error(`HTTP ${res.status}: ${errText}`);
19
      }
20
      return await res.json();
21
    } catch (err) {
 
173
 
174
  // ➤ Get PDF forensic report download link
175
  export const downloadOfflineReport = () => {
176
+ // FIX: Using BASE_URL for live deployment
177
+ window.open(`${BASE_URL}/api/offline/report`, "_blank");
178
  };
179
 
180
 
frontend/src/components/FeatureGuard.jsx ADDED
@@ -0,0 +1,63 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ // FeatureGuard.jsx
2
+ import React, { useState, useEffect } from "react";
3
+ import { AlertTriangle, Github, Monitor, Terminal } from "lucide-react";
4
+
5
+ const FeatureGuard = ({ children, requireLocal = false }) => {
6
+ const [isLocal, setIsLocal] = useState(true);
7
+ const [showPopup, setShowPopup] = useState(false);
8
+
9
+ useEffect(() => {
10
+ // Detect environment
11
+ const local = window.location.hostname === "localhost" || window.location.hostname === "127.0.0.1";
12
+ setIsLocal(local);
13
+
14
+ // Only show popup if it's required AND we are not local
15
+ if (requireLocal && !local) {
16
+ setShowPopup(true);
17
+ }
18
+ }, [requireLocal]);
19
+
20
+ // If we are local, or the feature doesn't require local access, show content normally
21
+ if (isLocal || !requireLocal) return <>{children}</>;
22
+
23
+ return (
24
+ <div className="relative min-h-screen">
25
+ {/* Background content is blurred for "Demo" look */}
26
+ <div className="blur-lg pointer-events-none opacity-50">
27
+ {children}
28
+ </div>
29
+
30
+ {showPopup && (
31
+ <div className="fixed inset-0 z-[9999] flex items-center justify-center bg-black/70 backdrop-blur-md p-4">
32
+ <div className="bg-[#0b1120] border-2 border-cyan-500/50 rounded-2xl p-8 max-w-lg w-full shadow-[0_0_50px_rgba(6,182,212,0.4)]">
33
+ <div className="flex items-center gap-3 text-amber-400 mb-4">
34
+ <AlertTriangle size={28} />
35
+ <h2 className="text-2xl font-bold">Local Agent Required</h2>
36
+ </div>
37
+
38
+ <p className="text-gray-300 mb-6">
39
+ This page requires <b>Live Network Sniffing</b>. To protect privacy, browsers cannot access your hardware. Please run the project locally.
40
+ </p>
41
+
42
+ <div className="bg-black/40 rounded-lg p-4 font-mono text-sm border border-cyan-900/50 mb-6">
43
+ <p className="text-emerald-400">$ git clone [Your-Repo-URL]</p>
44
+ <p className="text-blue-400">$ cd nids-project</p>
45
+ <p className="text-purple-400">$ python app.py --mode live</p>
46
+ </div>
47
+
48
+ <div className="flex gap-3">
49
+ <button onClick={() => window.open('https://github.com/your-repo', '_blank')} className="flex-1 bg-cyan-600 py-3 rounded-xl font-bold hover:bg-cyan-500 transition-all flex items-center justify-center gap-2">
50
+ <Github size={18}/> GitHub
51
+ </button>
52
+ <button onClick={() => window.history.back()} className="flex-1 bg-gray-800 py-3 rounded-xl font-bold hover:bg-gray-700 transition-all text-gray-400">
53
+ Go Back
54
+ </button>
55
+ </div>
56
+ </div>
57
+ </div>
58
+ )}
59
+ </div>
60
+ );
61
+ };
62
+
63
+ export default FeatureGuard;