import { useState, useEffect } from 'react' import { Card, Table, InputNumber, Switch, Typography, message, Space, Tag, Statistic, Row, Col, Button, } from 'antd' import { CheckCircleOutlined, CloseCircleOutlined, ReloadOutlined } from '@ant-design/icons' import api from '../../api/client' const { Title, Text } = Typography interface NodeInfo { id: string name: string host: string hls_port: number api_port: number weight: number enabled: boolean } interface StrategyInfo { strategy: string multicast_enabled: boolean multicast_available: boolean } const strategyLabels: Record = { 'round-robin': 'Round-Robin', 'weighted': 'Weighted', 'least-conn': 'Least-Conn', } export default function NodeManager() { const [nodes, setNodes] = useState([]) const [strategy, setStrategy] = useState(null) const [loading, setLoading] = useState(true) useEffect(() => { loadData() }, []) async function loadData() { setLoading(true) try { const [nodesRes, strategyRes] = await Promise.all([ api.get('/nodes'), api.get('/nodes/strategy'), ]) setNodes(nodesRes.data) setStrategy(strategyRes.data) } catch { message.error('Failed to load') } setLoading(false) } async function updateWeight(nodeId: string, weight: number) { try { await api.put(`/nodes/${nodeId}`, { weight }) message.success('Updated') } catch { message.error('Failed') } } async function toggleNode(nodeId: string, enabled: boolean) { const node = nodes.find((n) => n.id === nodeId) if (!node) return try { await api.put(`/nodes/${nodeId}`, { weight: node.weight, enabled }) setNodes((prev) => prev.map((n) => (n.id === nodeId ? { ...n, enabled } : n))) message.success('Updated') } catch { message.error('Failed') } } const columns = [ { title: 'Name', dataIndex: 'name', key: 'name' }, { title: 'Host', dataIndex: 'host', key: 'host' }, { title: 'HLS Port', dataIndex: 'hls_port', key: 'hls_port', width: 100 }, { title: 'API Port', dataIndex: 'api_port', key: 'api_port', width: 100 }, { title: 'Weight', dataIndex: 'weight', key: 'weight', width: 140, render: (_: number, record: NodeInfo) => ( { const v = val || 0 setNodes((prev) => prev.map((n) => (n.id === record.id ? { ...n, weight: v } : n))) updateWeight(record.id, v) }} size="small" style={{ width: 90 }} /> ), }, { title: 'Enabled', dataIndex: 'enabled', key: 'enabled', width: 80, render: (_: any, record: NodeInfo) => ( toggleNode(record.id, val)} size="small" /> ), }, { title: 'Health', key: 'health', width: 100, render: () => } color="success">Online, }, ] return (
Edge Nodes {strategy && ( )} } onClick={loadData}>Refresh} style={{ borderRadius: 12 }} > ) }