From d0ded5cd9bf5070a120bad58b5be21fe2ac6a4ff Mon Sep 17 00:00:00 2001
From: C3032 <C3032@BC3032>
Date: 星期六, 20 十二月 2025 16:41:09 +0800
Subject: [PATCH] test

---
 IDViewer_2D/LogAutoSaveService.cs |  284 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++
 1 files changed, 284 insertions(+), 0 deletions(-)

diff --git a/IDViewer_2D/LogAutoSaveService.cs b/IDViewer_2D/LogAutoSaveService.cs
new file mode 100644
index 0000000..cab1ed5
--- /dev/null
+++ b/IDViewer_2D/LogAutoSaveService.cs
@@ -0,0 +1,284 @@
+using System;
+using System.Collections.Generic;
+using System.Collections.ObjectModel;
+using System.IO;
+using System.Text;
+using System.Threading;
+using System.Threading.Tasks;
+using System.Windows;
+using SmartScanner.ViewModel;
+
+namespace SmartScanner
+{
+    /// <summary>
+    /// 浼樺寲鐨勬棩蹇楄嚜鍔ㄤ繚瀛樻湇鍔�
+    /// 鍔熻兘锛氭壒閲忎繚瀛�48灏忔椂鍐呮瘡涓�鏉℃棩蹇楀埌D鐩�02 LBLog鏂囦欢澶�
+    /// 瑙﹀彂鏉′欢锛氭渶澶�300鏉℃垨鍗佸垎閽熸壒閲忎繚瀛樹竴娆�
+    /// </summary>
+    public class LogAutoSaveService
+    {
+        private readonly ObservableCollection<LogEntry> _logEntries;
+        private Timer _cleanupTimer;
+        private Timer _batchSaveTimer;
+        private const int CLEANUP_INTERVAL_MS = 60 * 60 * 1000; // 1灏忔椂娓呯悊涓�娆�
+        private const int BATCH_SAVE_INTERVAL_MS = 600000; // 鍗佸垎閽熸壒閲忎繚瀛樹竴娆�
+        private const int MAX_BATCH_SIZE = 300; // 鏈�澶�300鏉℃棩蹇楁壒閲忎繚瀛�
+        private readonly string _logDirectory = @"D:\02 LBLog";
+        private bool _isSaving = false;
+        private readonly object _fileLock = new object();
+        private readonly object _bufferLock = new object();
+        private string _currentLogFilePath;
+        private readonly Queue<LogEntry> _logBuffer = new Queue<LogEntry>(); // 鏃ュ織缂撳啿鍖�
+        private int _bufferCount = 0; // 缂撳啿鍖鸿鏁�
+
+        public LogAutoSaveService(ObservableCollection<LogEntry> logEntries)
+        {
+            _logEntries = logEntries ?? throw new ArgumentNullException(nameof(logEntries));
+            
+            // 鍒涘缓鏃ュ織鐩綍
+            if (!Directory.Exists(_logDirectory))
+            {
+                Directory.CreateDirectory(_logDirectory);
+            }
+            
+            // 鍒濆鍖栧綋鍓嶆棩蹇楁枃浠惰矾寰�
+            InitializeCurrentLogFile();
+            
+            // 鍚姩鎵归噺淇濆瓨瀹氭椂鍣�
+            _batchSaveTimer = new Timer(OnBatchSaveTimerElapsed, null, BATCH_SAVE_INTERVAL_MS, BATCH_SAVE_INTERVAL_MS);
+            
+            // 鍚姩娓呯悊瀹氭椂鍣�
+            _cleanupTimer = new Timer(OnCleanupTimerElapsed, null, CLEANUP_INTERVAL_MS, CLEANUP_INTERVAL_MS);
+        }
+
+        /// <summary>
+        /// 鍒濆鍖栧綋鍓嶆棩蹇楁枃浠惰矾寰�
+        /// </summary>
+        private void InitializeCurrentLogFile()
+        {
+            string currentDate = DateTime.Now.ToString("yyyyMMdd");
+            string fileName = $"Log_{currentDate}.txt";
+            _currentLogFilePath = Path.Combine(_logDirectory, fileName);
+        }
+
+        /// <summary>
+        /// 娣诲姞鏃ュ織鍒扮紦鍐插尯锛屽欢杩熸壒閲忎繚瀛�
+        /// </summary>
+        public void LogAdded(LogEntry logEntry)
+        {
+            if (_isSaving) return;
+            
+            lock (_bufferLock)
+            {
+                _logBuffer.Enqueue(logEntry);
+                _bufferCount++;
+                
+                // 濡傛灉缂撳啿鍖鸿揪鍒版渶澶уぇ灏忥紝绔嬪嵆瑙﹀彂淇濆瓨
+                if (_bufferCount >= MAX_BATCH_SIZE)
+                {
+                    Task.Run(() => SaveBatchAsync());
+                }
+            }
+        }
+
+        /// <summary>
+        /// 鎵归噺淇濆瓨瀹氭椂鍣ㄥ洖璋�
+        /// </summary>
+        private void OnBatchSaveTimerElapsed(object state)
+        {
+            if (!_isSaving && _bufferCount > 0)
+            {
+                Task.Run(() => SaveBatchAsync());
+            }
+        }
+
+        /// <summary>
+        /// 寮傛鎵归噺淇濆瓨鏃ュ織
+        /// </summary>
+        private async Task SaveBatchAsync()
+        {
+            if (_isSaving) return;
+            
+            _isSaving = true;
+            
+            try
+            {
+                // 妫�鏌ユ槸鍚﹂渶瑕佸垏鎹㈠埌鏂版枃浠�
+                await CheckAndSwitchLogFileAsync();
+                
+                // 鑾峰彇缂撳啿鍖轰腑鐨勬墍鏈夋棩蹇�
+                List<LogEntry> batchToSave;
+                lock (_bufferLock)
+                {
+                    if (_bufferCount == 0)
+                    {
+                        _isSaving = false;
+                        return;
+                    }
+                    
+                    batchToSave = new List<LogEntry>(_logBuffer);
+                    _logBuffer.Clear();
+                    _bufferCount = 0;
+                }
+                
+                // 鎵归噺淇濆瓨鍒版枃浠�
+                await SaveBatchToFileAsync(batchToSave);
+                
+                Console.WriteLine($"鎵归噺淇濆瓨浜� {batchToSave.Count} 鏉℃棩蹇楀埌鏂囦欢");
+            }
+            catch (Exception ex)
+            {
+                Console.WriteLine($"鎵归噺淇濆瓨澶辫触: {ex.Message}");
+            }
+            finally
+            {
+                _isSaving = false;
+            }
+        }
+
+        /// <summary>
+        /// 鎵归噺淇濆瓨鏃ュ織鍒版枃浠�
+        /// </summary>
+        private async Task SaveBatchToFileAsync(List<LogEntry> batch)
+        {
+            await Task.Run(() =>
+            {
+                lock (_fileLock)
+                {
+                    try
+                    {
+                        using (StreamWriter writer = new StreamWriter(_currentLogFilePath, true, Encoding.UTF8))
+                        {
+                            foreach (var entry in batch)
+                            {
+                                string logLine = $"[{entry.Timestamp:yyyy-MM-dd HH:mm:ss.fff}] [{entry.Level}] {entry.Message}";
+                                writer.WriteLine(logLine);
+                            }
+                        }
+                    }
+                    catch (Exception ex)
+                    {
+                        Console.WriteLine($"鎵归噺淇濆瓨鍒版枃浠跺け璐�: {ex.Message}");
+                    }
+                }
+            });
+        }
+
+        /// <summary>
+        /// 妫�鏌ユ槸鍚﹂渶瑕佸垏鎹㈠埌鏂扮殑鏃ュ織鏂囦欢
+        /// </summary>
+        private async Task CheckAndSwitchLogFileAsync()
+        {
+            await Task.Run(() =>
+            {
+                string currentDate = DateTime.Now.ToString("yyyyMMdd");
+                string fileName = $"Log_{currentDate}.txt";
+                string newFilePath = Path.Combine(_logDirectory, fileName);
+
+                // 濡傛灉鏃ユ湡鍙樺寲锛屽垏鎹㈠埌鏂版枃浠�
+                if (_currentLogFilePath != newFilePath)
+                {
+                    _currentLogFilePath = newFilePath;
+                }
+            });
+        }
+
+        private void OnCleanupTimerElapsed(object state)
+        {
+            // 娓呯悊瓒呰繃48灏忔椂鐨勬棩蹇楁枃浠�
+            if (!_isSaving)
+            {
+                Task.Run(() => CleanupOldLogFilesAsync());
+            }
+        }
+
+        /// <summary>
+        /// 娓呯悊瓒呰繃48灏忔椂鐨勬棩蹇楁枃浠�
+        /// </summary>
+        private async Task CleanupOldLogFilesAsync()
+        {
+            await Task.Run(() =>
+            {
+                try
+                {
+                    if (Directory.Exists(_logDirectory))
+                    {
+                        var files = Directory.GetFiles(_logDirectory, "Log_*.txt");
+                        DateTime cutoffTime = DateTime.Now.AddHours(-48);
+
+                        foreach (string file in files)
+                        {
+                            try
+                            {
+                                FileInfo fileInfo = new FileInfo(file);
+                                if (fileInfo.LastWriteTime < cutoffTime)
+                                {
+                                    File.Delete(file);
+                                    Console.WriteLine($"娓呯悊杩囨湡鏃ュ織鏂囦欢: {file}");
+                                }
+                            }
+                            catch (Exception ex)
+                            {
+                                Console.WriteLine($"娓呯悊鏂囦欢澶辫触 {file}: {ex.Message}");
+                            }
+                        }
+                    }
+                }
+                catch (Exception ex)
+                {
+                    Console.WriteLine($"娓呯悊杩囨湡鏃ュ織鏂囦欢澶辫触: {ex.Message}");
+                }
+            });
+        }
+
+        /// <summary>
+        /// 鎵嬪姩淇濆瓨褰撳墠鎵�鏈夋棩蹇�
+        /// </summary>
+        public void ForceSave()
+        {
+            if (!_isSaving)
+            {
+                Task.Run(() => SaveBatchAsync());
+            }
+        }
+
+        /// <summary>
+        /// 鍋滄鏈嶅姟
+        /// </summary>
+        public void Stop()
+        {
+            _batchSaveTimer?.Dispose();
+            _batchSaveTimer = null;
+            _cleanupTimer?.Dispose();
+            _cleanupTimer = null;
+            
+            // 淇濆瓨鏈�鍚庣殑鏃ュ織
+            if (!_isSaving && _bufferCount > 0)
+            {
+                ForceSave();
+            }
+        }
+
+        /// <summary>
+        /// 鑾峰彇淇濆瓨缁熻淇℃伅
+        /// </summary>
+        public string GetStatus()
+        {
+            try
+            {
+                string currentFileInfo = "";
+                if (File.Exists(_currentLogFilePath))
+                {
+                    FileInfo fileInfo = new FileInfo(_currentLogFilePath);
+                    currentFileInfo = $", 褰撳墠鏂囦欢澶у皬: {fileInfo.Length / 1024} KB";
+                }
+                
+                return $"鑷姩淇濆瓨鏈嶅姟杩愯涓� - 缂撳啿鍖�: {_bufferCount} 鏉currentFileInfo}";
+            }
+            catch
+            {
+                return $"鑷姩淇濆瓨鏈嶅姟杩愯涓� - 缂撳啿鍖�: {_bufferCount} 鏉�";
+            }
+        }
+    }
+}
\ No newline at end of file

--
Gitblit v1.9.3