From aa6da1d02ecc81557211862994c0e7b4d38c35f1 Mon Sep 17 00:00:00 2001 From: ByakuraRinne <gabriel@nazuna.ovh> Date: Tue, 18 Mar 2025 01:30:26 +0100 Subject: [PATCH] mouai pt --- package-lock.json | 128 ++---------------------------- package.json | 1 - src/App.tsx | 22 ++--- src/components/AddServerModal.tsx | 92 ++++++++++++--------- src/lib/db.ts | 31 ++++++++ src/types.ts | 9 ++- 6 files changed, 111 insertions(+), 172 deletions(-) diff --git a/package-lock.json b/package-lock.json index c709eb3..2ef7181 100644 --- a/package-lock.json +++ b/package-lock.json @@ -8,7 +8,6 @@ "name": "proxmox-dashboard", "version": "0.0.0", "dependencies": { - "@supabase/supabase-js": "^2.39.7", "lucide-react": "^0.344.0", "mysql2": "^3.9.2", "react": "^18.3.1", @@ -1217,73 +1216,6 @@ "win32" ] }, - "node_modules/@supabase/auth-js": { - "version": "2.68.0", - "resolved": "https://registry.npmjs.org/@supabase/auth-js/-/auth-js-2.68.0.tgz", - "integrity": "sha512-odG7nb7aOmZPUXk6SwL2JchSsn36Ppx11i2yWMIc/meUO2B2HK9YwZHPK06utD9Ql9ke7JKDbwGin/8prHKxxQ==", - "dependencies": { - "@supabase/node-fetch": "^2.6.14" - } - }, - "node_modules/@supabase/functions-js": { - "version": "2.4.4", - "resolved": "https://registry.npmjs.org/@supabase/functions-js/-/functions-js-2.4.4.tgz", - "integrity": "sha512-WL2p6r4AXNGwop7iwvul2BvOtuJ1YQy8EbOd0dhG1oN1q8el/BIRSFCFnWAMM/vJJlHWLi4ad22sKbKr9mvjoA==", - "dependencies": { - "@supabase/node-fetch": "^2.6.14" - } - }, - "node_modules/@supabase/node-fetch": { - "version": "2.6.15", - "resolved": "https://registry.npmjs.org/@supabase/node-fetch/-/node-fetch-2.6.15.tgz", - "integrity": "sha512-1ibVeYUacxWYi9i0cf5efil6adJ9WRyZBLivgjs+AUpewx1F3xPi7gLgaASI2SmIQxPoCEjAsLAzKPgMJVgOUQ==", - "dependencies": { - "whatwg-url": "^5.0.0" - }, - "engines": { - "node": "4.x || >=6.0.0" - } - }, - "node_modules/@supabase/postgrest-js": { - "version": "1.19.2", - "resolved": "https://registry.npmjs.org/@supabase/postgrest-js/-/postgrest-js-1.19.2.tgz", - "integrity": "sha512-MXRbk4wpwhWl9IN6rIY1mR8uZCCG4MZAEji942ve6nMwIqnBgBnZhZlON6zTTs6fgveMnoCILpZv1+K91jN+ow==", - "dependencies": { - "@supabase/node-fetch": "^2.6.14" - } - }, - "node_modules/@supabase/realtime-js": { - "version": "2.11.2", - "resolved": "https://registry.npmjs.org/@supabase/realtime-js/-/realtime-js-2.11.2.tgz", - "integrity": "sha512-u/XeuL2Y0QEhXSoIPZZwR6wMXgB+RQbJzG9VErA3VghVt7uRfSVsjeqd7m5GhX3JR6dM/WRmLbVR8URpDWG4+w==", - "dependencies": { - "@supabase/node-fetch": "^2.6.14", - "@types/phoenix": "^1.5.4", - "@types/ws": "^8.5.10", - "ws": "^8.18.0" - } - }, - "node_modules/@supabase/storage-js": { - "version": "2.7.1", - "resolved": "https://registry.npmjs.org/@supabase/storage-js/-/storage-js-2.7.1.tgz", - "integrity": "sha512-asYHcyDR1fKqrMpytAS1zjyEfvxuOIp1CIXX7ji4lHHcJKqyk+sLl/Vxgm4sN6u8zvuUtae9e4kDxQP2qrwWBA==", - "dependencies": { - "@supabase/node-fetch": "^2.6.14" - } - }, - "node_modules/@supabase/supabase-js": { - "version": "2.49.1", - "resolved": "https://registry.npmjs.org/@supabase/supabase-js/-/supabase-js-2.49.1.tgz", - "integrity": "sha512-lKaptKQB5/juEF5+jzmBeZlz69MdHZuxf+0f50NwhL+IE//m4ZnOeWlsKRjjsM0fVayZiQKqLvYdBn0RLkhGiQ==", - "dependencies": { - "@supabase/auth-js": "2.68.0", - "@supabase/functions-js": "2.4.4", - "@supabase/node-fetch": "2.6.15", - "@supabase/postgrest-js": "1.19.2", - "@supabase/realtime-js": "2.11.2", - "@supabase/storage-js": "2.7.1" - } - }, "node_modules/@types/babel__core": { "version": "7.20.5", "resolved": "https://registry.npmjs.org/@types/babel__core/-/babel__core-7.20.5.tgz", @@ -1395,15 +1327,13 @@ "version": "22.13.10", "resolved": "https://registry.npmjs.org/@types/node/-/node-22.13.10.tgz", "integrity": "sha512-I6LPUvlRH+O6VRUqYOcMudhaIdUVWfsjnZavnsraHvpBwaEyMN29ry+0UVJhImYL16xsscu0aske3yA+uPOWfw==", + "dev": true, + "optional": true, + "peer": true, "dependencies": { "undici-types": "~6.20.0" } }, - "node_modules/@types/phoenix": { - "version": "1.6.6", - "resolved": "https://registry.npmjs.org/@types/phoenix/-/phoenix-1.6.6.tgz", - "integrity": "sha512-PIzZZlEppgrpoT2QgbnDU+MMzuR6BbCjllj0bM70lWoejMeNJAxCchxnv7J3XFkI8MpygtRpzXrIlmWUBclP5A==" - }, "node_modules/@types/prop-types": { "version": "15.7.13", "resolved": "https://registry.npmjs.org/@types/prop-types/-/prop-types-15.7.13.tgz", @@ -1429,14 +1359,6 @@ "@types/react": "*" } }, - "node_modules/@types/ws": { - "version": "8.18.0", - "resolved": "https://registry.npmjs.org/@types/ws/-/ws-8.18.0.tgz", - "integrity": "sha512-8svvI3hMyvN0kKCJMvTJP/x6Y/EoQbepff882wL+Sn5QsXb3etnamgrJq4isrBxSJj5L2AuXcI0+bgkoAXGUJw==", - "dependencies": { - "@types/node": "*" - } - }, "node_modules/@typescript-eslint/eslint-plugin": { "version": "8.8.1", "resolved": "https://registry.npmjs.org/@typescript-eslint/eslint-plugin/-/eslint-plugin-8.8.1.tgz", @@ -4218,11 +4140,6 @@ "node": ">=8.0" } }, - "node_modules/tr46": { - "version": "0.0.3", - "resolved": "https://registry.npmjs.org/tr46/-/tr46-0.0.3.tgz", - "integrity": "sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==" - }, "node_modules/ts-api-utils": { "version": "1.3.0", "resolved": "https://registry.npmjs.org/ts-api-utils/-/ts-api-utils-1.3.0.tgz", @@ -4292,7 +4209,10 @@ "node_modules/undici-types": { "version": "6.20.0", "resolved": "https://registry.npmjs.org/undici-types/-/undici-types-6.20.0.tgz", - "integrity": "sha512-Ny6QZ2Nju20vw1SRHe3d9jVu6gJ+4e3+MMpqu7pqE5HT6WsTSlce++GQmK5UXS8mzV8DSYHrQH+Xrf2jVcuKNg==" + "integrity": "sha512-Ny6QZ2Nju20vw1SRHe3d9jVu6gJ+4e3+MMpqu7pqE5HT6WsTSlce++GQmK5UXS8mzV8DSYHrQH+Xrf2jVcuKNg==", + "dev": true, + "optional": true, + "peer": true }, "node_modules/update-browserslist-db": { "version": "1.1.1", @@ -4419,20 +4339,6 @@ } } }, - "node_modules/webidl-conversions": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-3.0.1.tgz", - "integrity": "sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==" - }, - "node_modules/whatwg-url": { - "version": "5.0.0", - "resolved": "https://registry.npmjs.org/whatwg-url/-/whatwg-url-5.0.0.tgz", - "integrity": "sha512-saE57nupxk6v3HY35+jzBwYa0rKSy0XR8JSxZPwgLr7ys0IBzhGviA1/TUGJLmSVqs8pb9AnvICXEuOHLprYTw==", - "dependencies": { - "tr46": "~0.0.3", - "webidl-conversions": "^3.0.0" - } - }, "node_modules/which": { "version": "2.0.2", "resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz", @@ -4578,26 +4484,6 @@ "url": "https://github.com/chalk/ansi-styles?sponsor=1" } }, - "node_modules/ws": { - "version": "8.18.1", - "resolved": "https://registry.npmjs.org/ws/-/ws-8.18.1.tgz", - "integrity": "sha512-RKW2aJZMXeMxVpnZ6bck+RswznaxmzdULiBr6KY7XkTnW8uvt0iT9H5DkHUChXrc+uurzwa0rVI16n/Xzjdz1w==", - "engines": { - "node": ">=10.0.0" - }, - "peerDependencies": { - "bufferutil": "^4.0.1", - "utf-8-validate": ">=5.0.2" - }, - "peerDependenciesMeta": { - "bufferutil": { - "optional": true - }, - "utf-8-validate": { - "optional": true - } - } - }, "node_modules/yallist": { "version": "3.1.1", "resolved": "https://registry.npmjs.org/yallist/-/yallist-3.1.1.tgz", diff --git a/package.json b/package.json index 9242d51..6cb8ef0 100644 --- a/package.json +++ b/package.json @@ -10,7 +10,6 @@ "preview": "vite preview" }, "dependencies": { - "@supabase/supabase-js": "^2.39.7", "lucide-react": "^0.344.0", "mysql2": "^3.9.2", "react": "^18.3.1", diff --git a/src/App.tsx b/src/App.tsx index b316c91..e73d18a 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -3,7 +3,7 @@ import { PlusCircle } from 'lucide-react'; import { AddServerModal } from './components/AddServerModal'; import { ServerCard } from './components/ServerCard'; import { Server, ServerMetrics } from './types'; -import { supabase } from './lib/supabase'; +import { getServers } from './lib/db'; function App() { const [servers, setServers] = useState<Server[]>([]); @@ -15,20 +15,22 @@ function App() { }, []); const fetchServers = async () => { - const { data } = await supabase - .from('servers') - .select('*') - .order('created_at', { ascending: true }); - - if (data) { - setServers(data); - data.forEach(server => { - fetchMetrics(server); + try { + const data = await getServers(); + setServers(data as Server[]); + data.forEach((server: Server) => { + if (server.influx_enabled) { + fetchMetrics(server); + } }); + } catch (error) { + console.error('Failed to fetch servers:', error); } }; const fetchMetrics = async (server: Server) => { + if (!server.influx_enabled) return; + // In a real implementation, this would fetch from InfluxDB // For demo purposes, we'll generate mock data const mockMetrics: ServerMetrics[] = Array.from({ length: 20 }).map((_, i) => ({ diff --git a/src/components/AddServerModal.tsx b/src/components/AddServerModal.tsx index 11d9023..78e337a 100644 --- a/src/components/AddServerModal.tsx +++ b/src/components/AddServerModal.tsx @@ -1,6 +1,6 @@ import React, { useState } from 'react'; import { X } from 'lucide-react'; -import { supabase } from '../lib/supabase'; +import { addServer } from '../lib/db'; interface AddServerModalProps { onClose: () => void; @@ -13,6 +13,7 @@ export function AddServerModal({ onClose, onServerAdded }: AddServerModalProps) model: '', cpu_model: '', ram_gb: '', + influx_enabled: false, influx_org: '', influx_token: '', influx_url: '' @@ -21,14 +22,16 @@ export function AddServerModal({ onClose, onServerAdded }: AddServerModalProps) const handleSubmit = async (e: React.FormEvent) => { e.preventDefault(); - const { error } = await supabase.from('servers').insert([{ - ...formData, - ram_gb: parseInt(formData.ram_gb) - }]); - - if (!error) { + try { + await addServer({ + ...formData, + ram_gb: parseInt(formData.ram_gb) + }); onServerAdded(); onClose(); + } catch (error) { + console.error('Failed to add server:', error); + alert('Failed to add server. Please try again.'); } }; @@ -88,39 +91,56 @@ export function AddServerModal({ onClose, onServerAdded }: AddServerModalProps) required /> </div> - - <div> - <label className="block text-sm font-medium text-gray-300">InfluxDB Organization</label> + + <div className="flex items-center space-x-2"> <input - type="text" - className="mt-1 block w-full rounded-md bg-gray-700 border-gray-600 text-white" - value={formData.influx_org} - onChange={(e) => setFormData({ ...formData, influx_org: e.target.value })} - required + type="checkbox" + id="influxEnabled" + className="rounded bg-gray-700 border-gray-600 text-blue-600" + checked={formData.influx_enabled} + onChange={(e) => setFormData({ ...formData, influx_enabled: e.target.checked })} /> + <label htmlFor="influxEnabled" className="text-sm font-medium text-gray-300"> + Enable InfluxDB Metrics + </label> </div> - <div> - <label className="block text-sm font-medium text-gray-300">InfluxDB Token</label> - <input - type="password" - className="mt-1 block w-full rounded-md bg-gray-700 border-gray-600 text-white" - value={formData.influx_token} - onChange={(e) => setFormData({ ...formData, influx_token: e.target.value })} - required - /> - </div> - - <div> - <label className="block text-sm font-medium text-gray-300">InfluxDB URL</label> - <input - type="url" - className="mt-1 block w-full rounded-md bg-gray-700 border-gray-600 text-white" - value={formData.influx_url} - onChange={(e) => setFormData({ ...formData, influx_url: e.target.value })} - required - /> - </div> + {formData.influx_enabled && ( + <> + <div> + <label className="block text-sm font-medium text-gray-300">InfluxDB Organization</label> + <input + type="text" + className="mt-1 block w-full rounded-md bg-gray-700 border-gray-600 text-white" + value={formData.influx_org} + onChange={(e) => setFormData({ ...formData, influx_org: e.target.value })} + required={formData.influx_enabled} + /> + </div> + + <div> + <label className="block text-sm font-medium text-gray-300">InfluxDB Token</label> + <input + type="password" + className="mt-1 block w-full rounded-md bg-gray-700 border-gray-600 text-white" + value={formData.influx_token} + onChange={(e) => setFormData({ ...formData, influx_token: e.target.value })} + required={formData.influx_enabled} + /> + </div> + + <div> + <label className="block text-sm font-medium text-gray-300">InfluxDB URL</label> + <input + type="url" + className="mt-1 block w-full rounded-md bg-gray-700 border-gray-600 text-white" + value={formData.influx_url} + onChange={(e) => setFormData({ ...formData, influx_url: e.target.value })} + required={formData.influx_enabled} + /> + </div> + </> + )} <button type="submit" diff --git a/src/lib/db.ts b/src/lib/db.ts index 996892e..367a1e9 100644 --- a/src/lib/db.ts +++ b/src/lib/db.ts @@ -12,4 +12,35 @@ const pool = mysql.createPool({ queueLimit: 0, }); +export async function getServers() { + const [rows] = await pool.query('SELECT * FROM servers ORDER BY created_at ASC'); + return rows; +} + +export async function addServer(server: { + name: string; + model: string; + cpu_model: string; + ram_gb: number; + influx_enabled: boolean; + influx_org?: string; + influx_token?: string; + influx_url?: string; +}) { + const [result] = await pool.query( + 'INSERT INTO servers (name, model, cpu_model, ram_gb, influx_enabled, influx_org, influx_token, influx_url) VALUES (?, ?, ?, ?, ?, ?, ?, ?)', + [ + server.name, + server.model, + server.cpu_model, + server.ram_gb, + server.influx_enabled, + server.influx_org || null, + server.influx_token || null, + server.influx_url || null, + ] + ); + return result; +} + export default pool; \ No newline at end of file diff --git a/src/types.ts b/src/types.ts index eabeb2f..f9cf0f0 100644 --- a/src/types.ts +++ b/src/types.ts @@ -1,12 +1,13 @@ export interface Server { - id: string; + id: number; name: string; model: string; cpu_model: string; ram_gb: number; - influx_org: string; - influx_token: string; - influx_url: string; + influx_enabled: boolean; + influx_org: string | null; + influx_token: string | null; + influx_url: string | null; created_at: string; }