From 47df2e2aa67e40f9f14446e609d571a16016e47a Mon Sep 17 00:00:00 2001 From: iven Date: Mon, 27 Apr 2026 10:11:12 +0800 Subject: [PATCH] =?UTF-8?q?perf(web):=20manualChunks=20=E6=8B=86=E5=88=86?= =?UTF-8?q?=20heavy=20deps=20+=20lazy=20ProcessDesigner/ProcessViewer?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - vite.config.ts 添加 vendor-charts/plots/graphs, vendor-flow, vendor-editor 独立 chunk - vendor-antd 从 3000kB 降至 1532kB,charts 独立 1459kB - ProcessDesigner/ProcessViewer 改为 React.lazy 按需加载 - 移除 PluginGraphPage 遗留的 animFrameRef 未使用变量 --- apps/web/src/pages/PluginGraphPage.tsx | 1 - apps/web/src/pages/workflow/InstanceMonitor.tsx | 11 +++++++---- .../src/pages/workflow/ProcessDefinitions.tsx | 17 ++++++++++------- apps/web/vite.config.ts | 9 +++++++++ 4 files changed, 26 insertions(+), 12 deletions(-) diff --git a/apps/web/src/pages/PluginGraphPage.tsx b/apps/web/src/pages/PluginGraphPage.tsx index ffa9a7d..5bafec2 100644 --- a/apps/web/src/pages/PluginGraphPage.tsx +++ b/apps/web/src/pages/PluginGraphPage.tsx @@ -59,7 +59,6 @@ export function PluginGraphPage() { const { token } = theme.useToken(); const canvasRef = useRef(null); const containerRef = useRef(null); - const animFrameRef = useRef(0); const nodePositionsRef = useRef>(new Map()); const visibleNodesRef = useRef([]); const visibleEdgesRef = useRef([]); diff --git a/apps/web/src/pages/workflow/InstanceMonitor.tsx b/apps/web/src/pages/workflow/InstanceMonitor.tsx index 2e0913f..628983b 100644 --- a/apps/web/src/pages/workflow/InstanceMonitor.tsx +++ b/apps/web/src/pages/workflow/InstanceMonitor.tsx @@ -1,5 +1,5 @@ -import { useEffect, useCallback, useState, useRef } from 'react'; -import { Button, message, Modal, Table, Tag } from 'antd'; +import { useEffect, useCallback, useState, useRef, lazy, Suspense } from 'react'; +import { Button, message, Modal, Spin, Table, Tag } from 'antd'; import { EyeOutlined, PauseCircleOutlined, PlayCircleOutlined, StopOutlined } from '@ant-design/icons'; import type { ColumnsType } from 'antd/es/table'; import { @@ -10,7 +10,8 @@ import { type ProcessInstanceInfo, } from '../../api/workflowInstances'; import { getProcessDefinition, type NodeDef, type EdgeDef } from '../../api/workflowDefinitions'; -import ProcessViewer from './ProcessViewer'; + +const ProcessViewer = lazy(() => import('./ProcessViewer')); import { useThemeMode } from '../../hooks/useThemeMode'; const statusStyles: Record = { @@ -289,7 +290,9 @@ export default function InstanceMonitor() { width={720} loading={viewerLoading} > - + }> + + ); diff --git a/apps/web/src/pages/workflow/ProcessDefinitions.tsx b/apps/web/src/pages/workflow/ProcessDefinitions.tsx index 989c3bd..663b068 100644 --- a/apps/web/src/pages/workflow/ProcessDefinitions.tsx +++ b/apps/web/src/pages/workflow/ProcessDefinitions.tsx @@ -1,5 +1,5 @@ -import { useEffect, useState, useCallback } from 'react'; -import { Button, message, Modal, Space, Table, Tag } from 'antd'; +import { useEffect, useState, useCallback, lazy, Suspense } from 'react'; +import { Button, message, Modal, Space, Spin, Table, Tag } from 'antd'; import { PlusOutlined } from '@ant-design/icons'; import type { ColumnsType } from 'antd/es/table'; import { @@ -10,7 +10,8 @@ import { type ProcessDefinitionInfo, type CreateProcessDefinitionRequest, } from '../../api/workflowDefinitions'; -import ProcessDesigner from './ProcessDesigner'; + +const ProcessDesigner = lazy(() => import('./ProcessDesigner')); import { useThemeMode } from '../../hooks/useThemeMode'; const statusColors: Record = { @@ -190,10 +191,12 @@ export default function ProcessDefinitions() { width={1200} destroyOnClose > - + }> + + ); diff --git a/apps/web/vite.config.ts b/apps/web/vite.config.ts index 4ffe889..2def0b2 100644 --- a/apps/web/vite.config.ts +++ b/apps/web/vite.config.ts @@ -26,6 +26,15 @@ export default defineConfig({ if (id.includes("node_modules/react-dom") || id.includes("node_modules/react/") || id.includes("node_modules/react-router-dom")) { return "vendor-react"; } + if (id.includes("node_modules/@ant-design/charts") || id.includes("node_modules/@ant-design/plots") || id.includes("node_modules/@ant-design/graphs")) { + return "vendor-charts"; + } + if (id.includes("node_modules/@xyflow/react")) { + return "vendor-flow"; + } + if (id.includes("node_modules/@wangeditor/") || id.includes("node_modules/wangeditor/")) { + return "vendor-editor"; + } if (id.includes("node_modules/antd") || id.includes("node_modules/@ant-design")) { return "vendor-antd"; }