From cd2942405aa6bd60525358ea2c5406977cc93b6f Mon Sep 17 00:00:00 2001 From: jialin Date: Thu, 6 Nov 2025 19:22:22 +0800 Subject: [PATCH] feat: cluster_count on dashboard --- src/components/echarts/line-chart.tsx | 5 +- src/pages/dashboard/apis/index.ts | 6 +- .../dashboard/components/dahboard-inner.tsx | 30 ++------- .../components/resource-utilization.tsx | 25 ++++++-- .../dashboard/components/system-load.tsx | 61 ++++++++++++++++--- .../dashboard/config/dashboard-context.ts | 10 ++- src/pages/dashboard/index.tsx | 31 ++++++++-- src/pages/llmodels/forms/advance-config.tsx | 25 +++++++- src/pages/llmodels/forms/index.tsx | 1 - 9 files changed, 143 insertions(+), 51 deletions(-) diff --git a/src/components/echarts/line-chart.tsx b/src/components/echarts/line-chart.tsx index ac514288..f33ecf66 100644 --- a/src/components/echarts/line-chart.tsx +++ b/src/components/echarts/line-chart.tsx @@ -154,7 +154,10 @@ const LineChart: React.FC = (props) => { return ( <> {!seriesData.length ? ( - + ) : ( ( diff --git a/src/pages/dashboard/components/dahboard-inner.tsx b/src/pages/dashboard/components/dahboard-inner.tsx index 46253714..5359ad87 100644 --- a/src/pages/dashboard/components/dahboard-inner.tsx +++ b/src/pages/dashboard/components/dahboard-inner.tsx @@ -1,39 +1,17 @@ -import { memo, useCallback, useEffect, useState } from 'react'; -import { queryDashboardData } from '../apis'; -import DashboardContext from '../config/dashboard-context'; -import { DashboardProps } from '../config/types'; import ActiveTable from './active-table'; import Overview from './over-view'; import SystemLoad from './system-load'; import Usage from './usage'; -const Dashboard: React.FC<{ setLoading: (loading: boolean) => void }> = ({ - setLoading -}) => { - const [data, setData] = useState({} as DashboardProps); - - const getDashboardData = useCallback(async () => { - try { - setLoading(true); - const res = await queryDashboardData(); - setData(res); - setLoading(false); - } catch (error) { - setLoading(false); - setData({} as DashboardProps); - } - }, []); - useEffect(() => { - getDashboardData(); - }, []); +const Dashboard: React.FC = () => { return ( - + <> - + ); }; -export default memo(Dashboard); +export default Dashboard; diff --git a/src/pages/dashboard/components/resource-utilization.tsx b/src/pages/dashboard/components/resource-utilization.tsx index 5ff682d2..891b44fd 100644 --- a/src/pages/dashboard/components/resource-utilization.tsx +++ b/src/pages/dashboard/components/resource-utilization.tsx @@ -2,8 +2,7 @@ import LineChart from '@/components/echarts/line-chart'; import { useIntl } from '@umijs/max'; import dayjs from 'dayjs'; import _ from 'lodash'; -import { memo, useContext, useMemo } from 'react'; -import { DashboardContext } from '../config/dashboard-context'; +import { memo, useMemo } from 'react'; const TypeKeyMap = { cpu: { @@ -32,9 +31,27 @@ const TypeKeyMap = { } }; -const UtilizationOvertime: React.FC = () => { +const UtilizationOvertime: React.FC<{ + data: { + cpu: { + timestamp: number; + value: number; + }[]; + ram: { + timestamp: number; + value: number; + }[]; + gpu: { + timestamp: number; + value: number; + }[]; + vram: { + timestamp: number; + value: number; + }[]; + }; +}> = ({ data }) => { const intl = useIntl(); - const data = useContext(DashboardContext)?.system_load?.history || {}; const typeList = ['gpu', 'cpu', 'ram', 'vram']; diff --git a/src/pages/dashboard/components/system-load.tsx b/src/pages/dashboard/components/system-load.tsx index 78122242..0cb15b8b 100644 --- a/src/pages/dashboard/components/system-load.tsx +++ b/src/pages/dashboard/components/system-load.tsx @@ -1,10 +1,12 @@ import CardWrapper from '@/components/card-wrapper'; import GaugeChart from '@/components/echarts/gauge'; import PageTools from '@/components/page-tools'; +import BaseSelect from '@/components/seal-form/base/select'; +import { queryClusterList } from '@/pages/cluster-management/apis'; import { useIntl } from '@umijs/max'; import { Col, Row } from 'antd'; import _ from 'lodash'; -import { memo, useContext, useMemo } from 'react'; +import { useContext, useEffect, useMemo, useState } from 'react'; import { DashboardContext } from '../config/dashboard-context'; import ResourceUtilization from './resource-utilization'; @@ -14,9 +16,14 @@ const resourceChartHeight = 400; const SystemLoad = () => { const intl = useIntl(); - const data = useContext(DashboardContext)?.system_load?.current || {}; + const { system_load, fetchData } = useContext(DashboardContext); + const [systemLoadData, setSystemLoadData] = useState(system_load || {}); + const [clusterList, setClusterList] = useState[]>( + [] + ); const chartData = useMemo(() => { + const data = systemLoadData?.current || {}; return { gpu: { data: _.round(data.gpu || 0, 1) @@ -31,7 +38,36 @@ const SystemLoad = () => { data: _.round(data.ram || 0, 1) } }; - }, [data]); + }, [systemLoadData?.current]); + + useEffect(() => { + setSystemLoadData(system_load || {}); + }, [system_load]); + + const handleClusterChange = async (value: number) => { + try { + const res: any = await fetchData({ cluster_id: value }); + setSystemLoadData(res.system_load || {}); + } catch (error) { + setSystemLoadData({}); + } + }; + + useEffect(() => { + const fetchClusters = async () => { + try { + const res = await queryClusterList({ page: 1, perPage: 100 }); + const options = res.items.map((cluster) => ({ + label: cluster.name, + value: cluster.id + })); + setClusterList(options); + } catch (error) { + setClusterList([]); + } + }; + fetchClusters(); + }, []); return (
@@ -43,11 +79,22 @@ const SystemLoad = () => { {intl.formatMessage({ id: 'dashboard.systemload' })} } + right={ + + } /> - + @@ -55,7 +102,6 @@ const SystemLoad = () => { { { { { ); }; -export default memo(SystemLoad); +export default SystemLoad; diff --git a/src/pages/dashboard/config/dashboard-context.ts b/src/pages/dashboard/config/dashboard-context.ts index fffb7358..8192e0e7 100644 --- a/src/pages/dashboard/config/dashboard-context.ts +++ b/src/pages/dashboard/config/dashboard-context.ts @@ -2,7 +2,13 @@ import { createContext } from 'react'; import { DashboardProps } from './types'; export const DashboardContext = createContext< - DashboardProps & { fetchData: () => Promise } ->({} as DashboardProps & { fetchData: () => Promise }); + DashboardProps & { + fetchData: (params?: { [key: string]: any }) => Promise; + } +>( + {} as DashboardProps & { + fetchData: (params?: { [key: string]: any }) => Promise; + } +); export default DashboardContext; diff --git a/src/pages/dashboard/index.tsx b/src/pages/dashboard/index.tsx index 3b0caee3..747d8d60 100644 --- a/src/pages/dashboard/index.tsx +++ b/src/pages/dashboard/index.tsx @@ -1,19 +1,42 @@ +import { useMemoizedFn } from 'ahooks'; import { Spin } from 'antd'; -import { useState } from 'react'; +import { useEffect, useState } from 'react'; import PageBox from '../_components/page-box'; +import { queryDashboardData } from './apis'; import DashboardInner from './components/dahboard-inner'; +import DashboardContext from './config/dashboard-context'; +import { DashboardProps } from './config/types'; const Dashboard: React.FC = () => { const [loading, setLoading] = useState(false); + const [data, setData] = useState({} as DashboardProps); + + const getDashboardData = useMemoizedFn(async () => { + try { + setLoading(true); + const res = await queryDashboardData(); + setData(res); + setLoading(false); + } catch (error) { + setLoading(false); + setData({} as DashboardProps); + } + }); + + useEffect(() => { + getDashboardData(); + }, []); return ( - <> + - + - + ); }; diff --git a/src/pages/llmodels/forms/advance-config.tsx b/src/pages/llmodels/forms/advance-config.tsx index ab9c0930..b40f01c2 100644 --- a/src/pages/llmodels/forms/advance-config.tsx +++ b/src/pages/llmodels/forms/advance-config.tsx @@ -4,6 +4,7 @@ import SealSelect from '@/components/seal-form/seal-select'; import { useIntl } from '@umijs/max'; import { Form } from 'antd'; import _ from 'lodash'; +import { useMemo } from 'react'; import { DeployFormKeyMap, modelCategories } from '../config'; import { backendOptionsMap } from '../config/backend-parameters'; import { useFormContext } from '../config/form-context'; @@ -17,7 +18,11 @@ const AdvanceConfig = () => { const form = Form.useFormInstance(); const EnviromentVars = Form.useWatch('env', form); const backend = Form.useWatch('backend', form); - const { onValuesChange, formKey } = useFormContext(); + const { onValuesChange, backendOptions, formKey } = useFormContext(); + + const currentBackendOptions = useMemo(() => { + return backendOptions?.find((item) => item.value === backend); + }, [backend, backendOptions]); const handleEnviromentVarsChange = (labels: Record) => { console.log('handleEnviromentVarsChange', labels); @@ -80,7 +85,23 @@ const AdvanceConfig = () => { onChange={handleEnviromentVarsChange} > - + {(backend === backendOptionsMap.custom || + !currentBackendOptions?.isBuiltIn) && ( + + name="cpu_offloading" + valuePropName="checked" + style={{ marginBottom: 8 }} + > + + + )} {[backendOptionsMap.vllm, backendOptionsMap.ascendMindie].includes( backend ) && ( diff --git a/src/pages/llmodels/forms/index.tsx b/src/pages/llmodels/forms/index.tsx index e6392237..e01c0b86 100644 --- a/src/pages/llmodels/forms/index.tsx +++ b/src/pages/llmodels/forms/index.tsx @@ -366,7 +366,6 @@ const DataForm: React.FC = forwardRef((props, ref) => { replicas: 1, source: props.source, placement_strategy: 'spread', - cpu_offloading: true, scheduleType: ScheduleValueMap.Auto, categories: null, restart_on_error: true,