1. 日志目录和文件管理
- 日志目录:日志文件存储在 ./Exceptions 目录下。
- 日志文件定名:日志文件的定名格式为 yyyy_MM_dd.log,表现当天的日期。假如当天的日志文件大小超过 maxFileSizeBytes(3KB),则会创建新的日志文件,文件名格式为 yyyy_MM_dd_P{cnt}.log,此中 cnt 是日志文件的编号。
- 日志文件编码:日志文件使用 UTF-8 编码。
2. 非常日志记录
- WriteExceptionLog(Exception ex) 方法:
该方法用于记录非常信息。首先检查日志目录是否存在,假如不存在则创建。
获取当前日期的日志文件列表,并选择最新的日志文件(按文件名顺序)。
假如日志文件存在且大小超过 maxFileSizeBytes,则创建一个新的日志文件,文件名中包罗 _P{cnt},此中 cnt 是文件的编号。
将非常信息追加到日志文件中,使用 GetLogEntry(ex) 方法天生非常信息的日志条目。
末了调用 CleanupOldLogFiles() 方法清理超过 maxLogFileAgeDays(1天)的旧日志文件。
3. 日志条目天生
- GetLogEntry(Exception ex, int depth = 0) 方法:
– 该方法递归地天生非常信息的日志条目。
– 每层非常信息使用 depth 参数控制缩进,便于阅读。
– 日志条目包括非常时间、非常信息、非常对象和调用堆栈。
– 假如非常有嵌套的内部非常(InnerException),则递归调用 GetLogEntry 方法天生内部非常的日志条目。
4. 旧日志文件清理
- CleanupOldLogFiles() 方法:
– 该方法用于清理超过 maxLogFileAgeDays(1天)的旧日志文件。
–获取日志目录中全部 .log 文件,检查文件的末了修改时间,假如超过 maxLogFileAgeDays,则删除该文件。
5. 非常处置处罚
- 非常处置处罚:在 WriteExceptionLog(Exception ex) 方法中,全部的利用都在 lock 块中举行,确保线程安全。假如发生非常,内部非常会被捕捉但不会记录,制止日志记录自己抛出的非常导致步伐瓦解。
- using System.IO;
- using System.Text;
- using System.Text.RegularExpressions;
- using System.Windows;
- using System.Windows.Shapes;
- namespace DataParser.Helpers;
- public class LogHelper
- {
- private static readonly object objException = new object();
- private static readonly string logDirectory = "./Exceptions";
- private static string curfileName = $"{DateTime.Now:yyyy_MM_dd}.log";
- private static readonly int maxLogFileAgeDays = 1;
- private static readonly long maxFileSizeBytes = 3*1024;
- private static readonly Encoding encoding =Encoding.UTF8;
- static int cnt= 0;
- public static void WriteExceptionLog(Exception ex)
- {
- try
- {
- lock (objException)
- {
- if (!Directory.Exists(logDirectory))
- {
- Directory.CreateDirectory(logDirectory);
- }
- var files = Directory.GetFiles(logDirectory, "*.log")
- .Select(x=>System.IO.Path.GetFileName(x))
- .Where(x => x.Contains($"{DateTime.Now:yyyy_MM_dd}"));
- if(files.Count()>0)
- {
- var tmp = files.OrderBy(x => x.Length);
- curfileName = tmp.Last();
- if (curfileName.Contains("_P"))
- {
- Match match = Regex.Match(curfileName, @"_P(\d+)");
- if (match.Success)
- {
- string str = match.Groups[1].Value;
- int.TryParse(str, out cnt);
- }
- }
- }
- else
- {
- curfileName = $"{DateTime.Now:yyyy_MM_dd}.log";
- }
- string fileName = System.IO.Path.Combine(logDirectory, curfileName);
- string logEntry = GetLogEntry(ex);
- if (File.Exists(fileName) && (new FileInfo(fileName).Length > maxFileSizeBytes))
- {
- cnt++;
- fileName = System.IO.Path.Combine(logDirectory, $"{DateTime.Now:yyyy_MM_dd}_P{cnt}.log");
- }
- else if(!fileName.Contains("_P"))
- {
- cnt = 0;
- }
- File.AppendAllText(fileName, logEntry, encoding);
- CleanupOldLogFiles();
- }
- }
- catch (Exception innerEx)
- {
- }
- }
- private static string GetLogEntry(Exception ex, int depth = 0)
- {
- string indent = new string(' ', depth * 4);
- string logEntry =
- $"{indent}【异常时间】{DateTime.Now}{Environment.NewLine}" +
- $"{indent}【异常信息】{ex.Message}{Environment.NewLine}" +
- $"{indent}【异常对象】{ex.Source}{Environment.NewLine}" +
- $"{indent}【调用堆栈】{Environment.NewLine} {ex.StackTrace?.Trim() ?? "N/A"}{Environment.NewLine}{Environment.NewLine}{Environment.NewLine}";
- if (ex.InnerException != null)
- {
- logEntry += GetLogEntry(ex.InnerException, depth + 1);
- }
- return logEntry;
- }
- private static void CleanupOldLogFiles()
- {
- var files = Directory.GetFiles(logDirectory, "*.log")
- .Select(f => new FileInfo(f))
- .Where(f => (DateTime.Now - f.LastWriteTime).TotalDays > maxLogFileAgeDays);
- foreach (var file in files)
- {
- File.Delete(file.FullName);
- }
- }
- }
复制代码 Rougamo 实现AOP
导包Rougamo.Fody
- using DataParser.Helpers;
- using Rougamo;
- using Rougamo.Context;
- namespace DataParser
- {
- public class ExceptionLogAttribute : MoAttribute
- {
- public override void OnException(MethodContext context)
- {
- LogHelper.WriteExceptionLog(context.Exception);
- context.HandledException(this, null);
- }
- }
- }
复制代码- public partial class MainViewModel:IRougamo<ExceptionLogAttribute>
- {}
复制代码 MainViewModel 类实现了接口 IRougamo<ExceptionLogAttribute>。这意味着在这个类中,全部被 ExceptionLogAttribute 特性标记的方法或类,都会在抛出非常时自动调用 ExceptionLogAttribute 的 OnException 方法
免责声明:如果侵犯了您的权益,请联系站长,我们会及时删除侵权内容,谢谢合作!更多信息从访问主页:qidao123.com:ToB企服之家,中国第一个企服评测及商务社交产业平台。 |