浏览代码

feat(dashboard): remove Active VLANs overview table and expand Interfaces Overview to full width

Proxmox Router 1 周之前
父节点
当前提交
6550a81890
共有 2 个文件被更改,包括 51 次插入 和 61 次删除
  1. 28 31
      internal/web/static/app.js
  2. 23 30
      internal/web/static/index.html

+ 28 - 31
internal/web/static/app.js

@@ -496,43 +496,40 @@ function renderDashboard() {
   });
 
   const ifaceTbody = document.getElementById('quick-interfaces-table');
-  ifaceTbody.innerHTML = '';
-  (state.interfaces || []).slice(0, 6).forEach(i => {
-    const isUp = i.state === 'UP';
-    const tr = document.createElement('tr');
-    tr.className = 'hover:bg-slate-800/40 transition cursor-pointer';
-    tr.onclick = () => openIfaceModal(i.name);
-    tr.innerHTML = `
-      <td class="py-2.5 font-bold text-white flex items-center gap-2">
-        <span class="w-1.5 h-1.5 rounded-full ${isUp ? 'bg-emerald-400' : 'bg-rose-400'}"></span>
-        <span>${i.name}</span>
-      </td>
-      <td class="py-2.5 text-slate-300 font-sans"><span class="px-1.5 py-0.5 rounded text-[10px] bg-slate-800 text-slate-300">${i.role || 'LAN'}</span></td>
-      <td class="py-2.5 text-slate-300">${i.ipv4 && i.ipv4.length > 0 ? i.ipv4[0] : '<span class="text-slate-600">-</span>'}</td>
-      <td class="py-2.5 text-right font-sans font-semibold ${isUp ? 'text-emerald-400' : 'text-rose-400'}">${i.state}</td>
-    `;
-    ifaceTbody.appendChild(tr);
-  });
-
-  const vlanTbody = document.getElementById('quick-vlans-table');
-  vlanTbody.innerHTML = '';
-  const vlans = state.vlans || [];
-  if (vlans.length === 0) {
-    vlanTbody.innerHTML = `<tr><td colspan="4" class="py-4 text-center text-slate-500 font-sans">No VLANs configured. Click "+ Add" above to create one.</td></tr>`;
-  } else {
-    vlans.slice(0, 6).forEach(v => {
+  if (ifaceTbody) {
+    ifaceTbody.innerHTML = '';
+    (state.interfaces || []).forEach(i => {
+      const isUp = i.state === 'UP';
       const tr = document.createElement('tr');
       tr.className = 'hover:bg-slate-800/40 transition cursor-pointer';
-      tr.onclick = () => openIfaceModal(v.name);
+      tr.onclick = () => openIfaceModal(i.name);
+      const rxStr = i.rate?.rx_human || '0 B/s';
+      const txStr = i.rate?.tx_human || '0 B/s';
       tr.innerHTML = `
-        <td class="py-2.5"><span class="px-2 py-0.5 rounded text-[11px] bg-cyan-950 text-cyan-400 border border-cyan-800 font-bold">VLAN ${v.vlan_id}</span></td>
-        <td class="py-2.5 text-white font-bold">${v.name}</td>
-        <td class="py-2.5 text-slate-300">${v.ipv4 && v.ipv4.length > 0 ? v.ipv4[0] : '<span class="text-slate-600">Unnumbered</span>'}</td>
-        <td class="py-2.5 text-right text-slate-400">${v.parent_name || 'eth0'}</td>
+        <td class="py-2.5 font-bold text-white flex items-center gap-2">
+          <span class="w-2 h-2 rounded-full ${isUp ? 'bg-emerald-400 shadow-sm shadow-emerald-400/50' : 'bg-rose-400'}"></span>
+          <span>${i.name}</span>
+        </td>
+        <td class="py-2.5 text-slate-300 font-sans">
+          <span class="px-2 py-0.5 rounded text-[10px] bg-slate-800 text-slate-300 font-medium">${i.role || i.type || 'Ethernet'}</span>
+        </td>
+        <td class="py-2.5 text-slate-400 text-[11px] font-mono">${i.mac || '-'}</td>
+        <td class="py-2.5 text-slate-200 font-semibold">${i.ipv4 && i.ipv4.length > 0 ? i.ipv4.join(', ') : '<span class="text-slate-600 font-normal">Unassigned</span>'}</td>
+        <td class="py-2.5 text-slate-300 text-[11px] font-mono">
+          <span class="text-emerald-400">↓ ${rxStr}</span> <span class="text-slate-600">•</span> <span class="text-cyan-400">↑ ${txStr}</span>
+        </td>
+        <td class="py-2.5 text-right font-sans font-semibold">
+          <span class="px-2 py-0.5 rounded text-[10px] ${isUp ? 'bg-emerald-500/10 text-emerald-400 border border-emerald-500/20' : 'bg-rose-500/10 text-rose-400 border border-rose-500/20'}">${i.state}</span>
+        </td>
       `;
-      vlanTbody.appendChild(tr);
+      ifaceTbody.appendChild(tr);
     });
   }
+
+  const vlanTbody = document.getElementById('quick-vlans-table');
+  if (vlanTbody) {
+    vlanTbody.innerHTML = '';
+  }
 }
 
 // Expand / Collapse Handlers

+ 23 - 30
internal/web/static/index.html

@@ -449,36 +449,29 @@
             <div id="port-matrix" class="grid grid-cols-2 sm:grid-cols-3 md:grid-cols-4 lg:grid-cols-6 gap-3"></div>
           </div>
 
-          <!-- Quick Overview Tables -->
-          <div class="grid grid-cols-1 lg:grid-cols-2 gap-6">
-            <div class="bg-slate-900/90 border border-slate-800 rounded-xl p-5">
-              <div class="flex items-center justify-between mb-4">
-                <h3 class="text-sm font-bold text-white">Interfaces Overview</h3>
-                <button onclick="navigate('interfaces')" class="text-xs text-brand-400 hover:text-brand-300 font-medium">View All →</button>
-              </div>
-              <div class="overflow-x-auto">
-                <table class="w-full text-left text-xs">
-                  <thead class="text-slate-400 border-b border-slate-800">
-                    <tr><th class="pb-2">Interface</th><th class="pb-2">Role</th><th class="pb-2">IP</th><th class="pb-2 text-right">Status</th></tr>
-                  </thead>
-                  <tbody id="quick-interfaces-table" class="divide-y divide-slate-800/60 font-mono"></tbody>
-                </table>
-              </div>
+          <!-- Quick Overview: Interfaces -->
+          <div class="bg-slate-900/90 border border-slate-800 rounded-xl p-5">
+            <div class="flex items-center justify-between mb-4">
+              <h3 class="text-sm font-bold text-white flex items-center gap-2">
+                <span>Interfaces Overview</span>
+                <span class="text-[10px] bg-slate-800 text-slate-400 font-normal px-2 py-0.5 rounded-full">Active Ports & Addresses</span>
+              </h3>
+              <button onclick="navigate('interfaces')" class="text-xs text-brand-400 hover:text-brand-300 font-medium">View All Interfaces →</button>
             </div>
-
-            <div class="bg-slate-900/90 border border-slate-800 rounded-xl p-5">
-              <div class="flex items-center justify-between mb-4">
-                <h3 class="text-sm font-bold text-white">Active VLANs</h3>
-                <button onclick="navigate('vlans')" class="text-xs text-cyan-400 hover:text-cyan-300 font-medium">Manage →</button>
-              </div>
-              <div class="overflow-x-auto">
-                <table class="w-full text-left text-xs">
-                  <thead class="text-slate-400 border-b border-slate-800">
-                    <tr><th class="pb-2">VLAN</th><th class="pb-2">Device</th><th class="pb-2">Subnet</th><th class="pb-2 text-right">Parent</th></tr>
-                  </thead>
-                  <tbody id="quick-vlans-table" class="divide-y divide-slate-800/60 font-mono"></tbody>
-                </table>
-              </div>
+            <div class="overflow-x-auto">
+              <table class="w-full text-left text-xs">
+                <thead class="text-slate-400 border-b border-slate-800 text-[11px] uppercase tracking-wider">
+                  <tr>
+                    <th class="pb-2.5">Interface</th>
+                    <th class="pb-2.5">Role / Type</th>
+                    <th class="pb-2.5">MAC Address</th>
+                    <th class="pb-2.5">IP Address</th>
+                    <th class="pb-2.5">Live Traffic</th>
+                    <th class="pb-2.5 text-right">Status</th>
+                  </tr>
+                </thead>
+                <tbody id="quick-interfaces-table" class="divide-y divide-slate-800/60 font-mono"></tbody>
+              </table>
             </div>
           </div>
         </section>
@@ -5202,6 +5195,6 @@
     </div>
   </div>
 
-  <script src="app.js?v=4.2"></script>
+  <script src="app.js?v=4.3"></script>
 </body>
 </html>