Android平台下基于MvvmCross和Serilog运行时修改日志配置
解决MvvmCross运行时更新Serilog日志级别不生效的问题
问题根源
MvvmCross的InitializeLoggingServices()仅在应用启动时初始化日志服务,并且会将ILoggerFactory和ILoggerProvider以单例模式注册到IoC容器中。后续调用该方法不会覆盖已注册的实例,所以直接调用无法生效。
两种解决方案
方案一:动态级别控制(推荐)
使用Serilog自带的LoggingLevelSwitch,无需重新创建Logger或修改IoC注册,直接动态调整级别:
- 在Setup类中定义全局级别开关:
private readonly LoggingLevelSwitch _logLevelSwitch = new LoggingLevelSwitch(LogEventLevel.Information); // 默认级别
- 初始化日志工厂时绑定开关:
protected override ILoggerFactory CreateLogFactory() { Serilog.Log.Logger = new LoggerConfiguration() .MinimumLevel.ControlledBy(_logLevelSwitch) .CreateLogger(); return new SerilogLoggerFactory(); }
- 运行时更新级别只需修改开关:
public void UpdateLogLevel(LogEventLevel newLevel) { _logLevelSwitch.MinimumLevel = newLevel; }
这种方式无需操作IoC容器,所有已创建的ILogger实例会自动使用新级别,是最简洁的方案。
方案二:重新注册IoC日志服务
如果必须重新创建LoggerConfiguration,需要手动注销并重新注册IoC中的日志服务:
public void UpdateLogLevel(LogEventLevel newLogLevel) { // 更新全局级别变量 _logEventLevel = newLogLevel; // 重新创建Serilog全局Logger Serilog.Log.Logger = new LoggerConfiguration() .MinimumLevel.Is(_logEventLevel) .CreateLogger(); // 获取MvvmCross IoC容器 var ioc = Mvx.IoCProvider; // 注销并重新注册日志服务 ioc.Unregister<ILoggerFactory>(); ioc.RegisterSingleton<ILoggerFactory>(() => new SerilogLoggerFactory()); ioc.Unregister<ILoggerProvider>(); ioc.RegisterSingleton<ILoggerProvider>(() => new SerilogLoggerProvider()); // 注意:已注入到ViewModel/服务中的旧ILogger实例不会自动更新 // 如果需要这些实例生效,需从IoC重新获取(比如在ViewModel中调用Mvx.IoCProvider.Resolve<ILogger>()) }
注意事项
- 方案二中,已创建的
ILogger实例(比如ViewModel构造函数中注入的)是基于旧级别生成的,不会自动更新,需要手动重新获取。 - 优先使用方案一,因为它更高效且无需修改IoC容器状态。
内容的提问来源于stack exchange,提问作者Remo
相关产品推荐
相关产品推荐

