feat: K8s 集群同步功能 + 表单简化

- 新增手动同步按钮(卡片下拉菜单「同步」)
- 新建集群后自动触发同步(延迟500ms等列表刷新)
- 同步后刷新集群列表,节点/Pod/Deployment 数据写入 DB
- 集群表单:名称即code,正则校验英文/数字/连字符
This commit is contained in:
attacker committed 2026-06-21 10:53:30 +00:00
1 parent e5276161ea
commit 9dbb7e9fc4
1 file changed
+41 -1
@@ -29,6 +29,7 @@ import {
Container,
} from 'lucide-react';
import { kubernetesApi } from '@/services/api';
import { toast } from 'sonner';
import type { KubernetesCluster } from '@/types';
import { KubernetesClusterDetail } from './KubernetesClusterDetail';
import { KubernetesClusterDialog } from './KubernetesClusterDialog';
@@ -65,6 +66,24 @@ export function KubernetesClusters() {
loadData();
}, []);
// 新建后自动同步
const [pendingSyncId, setPendingSyncId] = useState<number | null>(null);
const handleSaved = () => {
loadData().then(() => {
if (!editingCluster) {
// 新建集群后,等列表刷新完再取最新一条同步
setTimeout(async () => {
const res: any = await kubernetesApi.getClusters();
const list = res?.list || [];
if (list.length > 0) {
handleSync(list[list.length - 1].id, true);
}
}, 500);
}
});
};
const handleDelete = async (id: string) => {
try {
await kubernetesApi.deleteCluster(id);
@@ -74,6 +93,17 @@ export function KubernetesClusters() {
}
};
const handleSync = async (id: number | string, silent?: boolean) => {
try {
if (!silent) toast.info('正在同步集群资源...');
const res: any = await kubernetesApi.syncCluster(id);
if (!silent) toast.success(res?.message || '同步完成');
loadData();
} catch (e: any) {
if (!silent) toast.error(e?.message || '同步失败');
}
};
const filteredClusters = clusters.filter(
(cluster) =>
(cluster.name || '').toLowerCase().includes(searchQuery.toLowerCase()) ||
@@ -280,6 +310,16 @@ export function KubernetesClusters() {
<Settings className="h-4 w-4 mr-2" />
配置
</DropdownMenuItem>
<DropdownMenuItem
className="text-cyan-400 focus:bg-slate-700 focus:text-cyan-300"
onClick={(e) => {
e.stopPropagation();
handleSync(cluster.id);
}}
>
<RefreshCw className="h-4 w-4 mr-2" />
同步
</DropdownMenuItem>
<DropdownMenuItem
className="text-emerald-400 focus:bg-slate-700 focus:text-emerald-300"
onClick={(e) => {
@@ -377,7 +417,7 @@ export function KubernetesClusters() {
open={dialogOpen}
onOpenChange={setDialogOpen}
editingCluster={editingCluster}
onSaved={loadData}
onSaved={handleSaved}
/>
{/* kubectl 终端 */}