using log4net; using System; using System.Collections.Concurrent; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks; namespace LB_SmartVisionCommon { /// /// 异步记录日志类 /// public static class AsyncLogHelper { private static readonly BlockingCollection _logQueue = new BlockingCollection(2000); private static readonly Task _backgroundTask; private static readonly CancellationTokenSource _cancellationTokenSource = new CancellationTokenSource(); static string LineT = "记录信息:"; static readonly ILog _logger = log4net.LogManager.GetLogger(System.Reflection.MethodBase.GetCurrentMethod().DeclaringType); static AsyncLogHelper() { // 启动后台日志处理任务 _backgroundTask = Task.Factory.StartNew( ProcessLogQueue, _cancellationTokenSource.Token, TaskCreationOptions.LongRunning, TaskScheduler.Default); // 注册应用程序退出时的清理 AppDomain.CurrentDomain.ProcessExit += (s, e) => Dispose(); AppDomain.CurrentDomain.DomainUnload += (s, e) => Dispose(); } /// /// Info类型 - 异步记录 /// public static void Info(string message) { EnqueueLog(LogLevel.Info, message); } /// /// Debug类型 - 异步记录 /// public static void Debug(string message) { EnqueueLog(LogLevel.Debug, message); } /// /// Warn类型 - 异步记录 /// public static void Warn(string message) { EnqueueLog(LogLevel.Warn, message); } /// /// Error类型 - 异步记录 /// public static void Error(string message) { EnqueueLog(LogLevel.Error, message); } /// /// Error类型 - 异步记录异常 /// public static void Error(string message, Exception exception) { EnqueueLog(LogLevel.Error, message, exception); } private static void EnqueueLog(LogLevel level, string message, Exception exception = null) { if (!_logQueue.IsAddingCompleted) { var logItem = new LogItem { Level = level, Message = LineT + message, Exception = exception, Timestamp = DateTime.Now }; // 如果队列已满,等待一段时间 if (!_logQueue.TryAdd(logItem, 100)) { // 队列满时的降级处理:同步记录或丢弃 try { WriteLogSync(logItem); } catch { // 忽略同步记录时的异常 } } } } private static void ProcessLogQueue() { foreach (var logItem in _logQueue.GetConsumingEnumerable(_cancellationTokenSource.Token)) { try { WriteLogSync(logItem); } catch (Exception ex) { System.Diagnostics.Debug.WriteLine($"异步日志记录失败: {ex.Message}"); } } } private static void WriteLogSync(LogItem logItem) { switch (logItem.Level) { case LogLevel.Debug: _logger.Debug(logItem.Message, logItem.Exception); break; case LogLevel.Info: _logger.Info(logItem.Message, logItem.Exception); break; case LogLevel.Warn: _logger.Warn(logItem.Message, logItem.Exception); break; case LogLevel.Error: _logger.Error(logItem.Message, logItem.Exception); break; } } /// /// 释放资源,确保所有日志都被处理 /// public static void Dispose() { try { _logQueue.CompleteAdding(); _cancellationTokenSource.CancelAfter(5000); // 5秒后强制取消 // 等待任务完成,最多等待10秒 if (!_backgroundTask.Wait(10000)) { System.Diagnostics.Debug.WriteLine("日志任务未在超时时间内完成"); } } catch (Exception ex) { System.Diagnostics.Debug.WriteLine($"释放日志资源时出错: {ex.Message}"); } } } internal enum LogLevel { Debug, Info, Warn, Error } internal class LogItem { public LogLevel Level { get; set; } public string Message { get; set; } public Exception Exception { get; set; } public DateTime Timestamp { get; set; } } }