2
0
Quellcode durchsuchen

✨ feat(progress): 优化进度条显示和完成检测逻辑

- 添加服务端活动检测机制,区分纯客户端模式和混合模式
- 优化进度计算方式,根据服务端活动状态动态调整权重
- 改进完成检测逻辑,根据不同模式设置不同的完成条件
- 添加3秒无服务端活动自动切换到纯客户端模式的逻辑
- 优化进度条状态显示,增加模式标识和更详细的资源加载信息
- 修复进度可能出现倒退的问题,确保进度条只增不减
- 调整完成检测触发阈值,从95%降低到90%以提前开始检测
- 增加5秒超时强制完成机制,防止进度卡住
yourname vor 7 Monaten
Ursprung
Commit
1e05930c18
1 geänderte Dateien mit 75 neuen und 30 gelöschten Zeilen
  1. 75 30
      vite-plugin-compile-progress.js

+ 75 - 30
vite-plugin-compile-progress.js

@@ -99,6 +99,8 @@ export function progressTrackingPlugin() {
                   let isLoading = true;  
                   let completionTimer = null;  
                   let lastResourceTime = Date.now();  
+                  let hasServerActivity = false;  
+                  let serverActivityTimer = null;  
   
                   // DOM 元素引用  
                   const progressBar = document.getElementById('vite-progress-bar');  
@@ -111,30 +113,52 @@ export function progressTrackingPlugin() {
                     const styleSheets = document.querySelectorAll('link[rel="stylesheet"]').length;  
                     const preloadLinks = document.querySelectorAll('link[rel="preload"], link[rel="modulepreload"]').length;  
                       
-                    // 更保守的预估,避免过度增长  
                     const baseEstimate = scripts + links + styleSheets + preloadLinks;  
-                    const conservativeEstimate = Math.max(baseEstimate + 10, 15); // 只加10个缓冲  
+                    const conservativeEstimate = Math.max(baseEstimate + 10, 15);  
                       
                     return conservativeEstimate;  
                   }  
   
+                  // 检测服务端活动  
+                  function detectServerActivity() {  
+                    hasServerActivity = true;  
+                    if (serverActivityTimer) clearTimeout(serverActivityTimer);  
+                      
+                    // 如果3秒内没有新的服务端活动,认为服务端编译已完成或无需编译  
+                    serverActivityTimer = setTimeout(() => {  
+                      if (serverProgress === 0) {  
+                        console.log('No server compilation detected - using client-only mode');  
+                        hasServerActivity = false;  
+                      }  
+                    }, 3000);  
+                  }  
+  
                   // 检测是否完成加载  
                   function checkCompletion() {  
                     const now = Date.now();  
                     const timeSinceLastResource = now - lastResourceTime;  
                       
-                    // 如果2秒内没有新资源加载,且服务端完成,认为加载完成  
-                    if (serverProgress >= 1.0 && timeSinceLastResource > 2000) {  
-                      console.log('Loading appears to be complete - no new resources for 2 seconds');  
-                      forceComplete();  
-                      return;  
+                    // 根据服务端活动情况调整完成条件  
+                    if (!hasServerActivity) {  
+                      // 无服务端编译时,主要依赖客户端资源  
+                      if (resourcesCompleted >= estimatedTotal * 0.8 && timeSinceLastResource > 2000) {  
+                        console.log('Client-only loading complete');  
+                        forceComplete();  
+                        return;  
+                      }  
+                    } else {  
+                      // 有服务端编译时,需要服务端完成  
+                      if (serverProgress >= 1.0 && timeSinceLastResource > 2000) {  
+                        console.log('Server + client loading complete');  
+                        forceComplete();  
+                        return;  
+                      }  
                     }  
                       
-                    // 如果进度超过98%且3秒内没有新资源,强制完成  
-                    if (serverProgress >= 1.0 && resourcesCompleted >= estimatedTotal * 0.9 && timeSinceLastResource > 3000) {  
-                      console.log('Force completing - high progress with no recent activity');  
+                    // 超时强制完成  
+                    if (timeSinceLastResource > 5000) {  
+                      console.log('Force completing due to timeout');  
                       forceComplete();  
-                      return;  
                     }  
                   }  
   
@@ -158,33 +182,46 @@ export function progressTrackingPlugin() {
                   function updateProgress() {  
                     if (!progressBar || !statusDisplay || !isLoading) return;  
   
-                    // 动态调整权重:服务端完成后,客户端权重增加  
-                    const serverWeight = serverProgress < 1.0 ? 0.6 : 0.3;  
-                    const clientWeight = serverProgress < 1.0 ? 0.4 : 0.7;  
-                      
-                    const serverPart = serverProgress * serverWeight;  
-                    const clientPart = estimatedTotal > 0 ?   
-                      Math.min(resourcesCompleted / estimatedTotal, 1.0) * clientWeight : 0;  
-                      
-                    let totalProgress = Math.min((serverPart + clientPart) * 100, 100);  
+                    let totalProgress;  
                       
-                    // 如果服务端完成且客户端接近完成,给予额外加成  
-                    if (serverProgress >= 1.0 && resourcesCompleted >= estimatedTotal * 0.8) {  
-                      totalProgress = Math.max(totalProgress, 95);  
+                    if (!hasServerActivity && serverProgress === 0) {  
+                      // 无服务端编译活动,100%依赖客户端资源  
+                      const clientProgress = estimatedTotal > 0 ?   
+                        Math.min(resourcesCompleted / estimatedTotal, 1.0) : 0;  
+                      totalProgress = clientProgress * 100;  
+                        
+                      console.log(\`Client-only mode: \${resourcesCompleted}/\${estimatedTotal} resources\`);  
+                    } else {  
+                      // 有服务端编译活动,使用混合权重  
+                      const serverWeight = serverProgress < 1.0 ? 0.6 : 0.3;  
+                      const clientWeight = serverProgress < 1.0 ? 0.4 : 0.7;  
+                        
+                      const serverPart = serverProgress * serverWeight;  
+                      const clientPart = estimatedTotal > 0 ?   
+                        Math.min(resourcesCompleted / estimatedTotal, 1.0) * clientWeight : 0;  
+                        
+                      totalProgress = (serverPart + clientPart) * 100;  
+                        
+                      console.log(\`Mixed mode: Server \${Math.round(serverProgress * 100)}%, Client \${resourcesCompleted}/\${estimatedTotal}\`);  
                     }  
                       
+                    // 确保进度不会倒退  
+                    const currentWidth = parseFloat(progressBar.style.width) || 0;  
+                    totalProgress = Math.max(totalProgress, currentWidth);  
+                      
                     // 更新进度条  
-                    progressBar.style.width = totalProgress + '%';  
+                    progressBar.style.width = Math.min(totalProgress, 100) + '%';  
                       
                     // 更新状态显示  
                     statusDisplay.style.display = 'block';  
+                    const mode = hasServerActivity ? 'Mixed' : 'Client-only';  
                     statusDisplay.textContent =   
-                      \`Loading... \${Math.round(totalProgress)}% (\${resourcesCompleted}/\${estimatedTotal} resources)\`;  
+                      \`Loading... \${Math.round(totalProgress)}% (\${mode}: \${resourcesCompleted}/\${estimatedTotal})\`;  
                       
-                    console.log(\`Progress: Server \${Math.round(serverProgress * 100)}%, Resources \${resourcesCompleted}/\${estimatedTotal}, Total \${Math.round(totalProgress)}%\`);  
+                    console.log(\`Progress: Total \${Math.round(totalProgress)}%\`);  
                       
                     // 如果接近完成,开始检测完成状态  
-                    if (totalProgress >= 95) {  
+                    if (totalProgress >= 90) {  
                       if (completionTimer) clearTimeout(completionTimer);  
                       completionTimer = setTimeout(checkCompletion, 1000);  
                     }  
@@ -192,6 +229,7 @@ export function progressTrackingPlugin() {
   
                   // 监听服务端编译进度  
                   import.meta.hot.on('progress:update', (data) => {  
+                    detectServerActivity();  
                     serverProgress = data.total > 0 ? data.processed / data.total : 0;  
                     updateProgress();  
                   });  
@@ -216,9 +254,9 @@ export function progressTrackingPlugin() {
                             resourcesCompleted++;  
                             lastResourceTime = Date.now();  
                               
-                            // 更保守的总数调整策略  
+                            // 动态调整预估总数  
                             if (resourcesCompleted > estimatedTotal * 0.9) {  
-                              estimatedTotal = Math.max(estimatedTotal, resourcesCompleted + 3); // 只加3个缓冲  
+                              estimatedTotal = Math.max(estimatedTotal, resourcesCompleted + 3);  
                             }  
                               
                             console.log(\`Resource completed: \${entry.name} (type: \${entry.initiatorType})\`);  
@@ -244,12 +282,19 @@ export function progressTrackingPlugin() {
                     }  
                       
                     updateProgress();  
+                      
+                    // 启动服务端活动检测  
+                    setTimeout(() => {  
+                      if (!hasServerActivity) {  
+                        console.log('No server activity detected, switching to client-only mode');  
+                        updateProgress();  
+                      }  
+                    }, 1000);  
                   }  
   
                   // 页面加载完成后的处理  
                   function handlePageLoad() {  
                     setTimeout(() => {  
-                      // 最终调整预估值  
                       if (resourcesCompleted > 0) {  
                         estimatedTotal = Math.max(resourcesCompleted + 2, estimatedTotal);  
                         console.log(\`Final estimated total: \${estimatedTotal}\`);