ASP.NET中存入Application state的日志列表无法在LogHelper类中访问
问题原因
Application 对象是 ASP.NET System.Web.HttpApplicationState 类型的实例,属于Web请求上下文的一部分,只能在ASP.NET页面、HttpModule等直接绑定请求管道的类中直接访问。独立的工具类LogHelper没有默认的上下文引用,因此无法直接调用Application属性。
解决方案
你可以根据业务场景选择以下任意一种方案:
方案1:通过当前HttpContext获取Application状态(最快捷,适合原有逻辑不动的情况)
只需要修改LogHelper中的取值代码,先引入System.Web命名空间,然后通过HttpContext.Current.Application访问存储的值,同时做好类型转换和空值判断即可。
修改后的代码如下:
using System.Web; // 先引入命名空间 namespace Reporting.Helper { public class LogHelper { public static void WriteLog(ApiInfo apiInfo, MethodBase methodBase, string LogType, Exception ex, string logMessage) { // 新增空值判断+类型转换 List<string> allowedLogTypes = HttpContext.Current?.Application["AllowedLogTypes"] as List<string>; // 避免空引用异常,不符合条件直接返回 if (allowedLogTypes == null || !allowedLogTypes.Contains(LogType)) { return; } var logTime = UtilityHelper.CurrentDateTime(); ThreadPool.QueueUserWorkItem(task => { PushAppLogInDB(methodBase, apiInfo, logTime, LogTypes.DEBUG_LOG, logMessage, string.Empty, ex); }); } } }
注意:如果你的日志写入逻辑可能在非请求线程(例如后台任务、异步回调)中执行,
HttpContext.Current可能为null,导致拿不到配置,这种情况更推荐用方案2。
方案2:将允许的日志类型改为静态常量存储(更推荐,适合固定配置场景)
你的allowedLogTypes是应用启动时就从配置读取的固定值,全程不会修改,完全不需要存在Application状态里,直接存为静态变量性能更好、访问更方便,不需要依赖HttpContext。
修改步骤:
- 先修改
LogHelper,新增静态属性存储配置:
namespace Reporting.Helper { public class LogHelper { // 新增静态变量存允许的日志类型 public static List<string> AllowedLogTypes { get; internal set; } public static void WriteLog(ApiInfo apiInfo, MethodBase methodBase, string LogType, Exception ex, string logMessage) { if (AllowedLogTypes == null || !AllowedLogTypes.Contains(LogType)) { return; } // 原有日志逻辑不变 var logTime = UtilityHelper.CurrentDateTime(); ThreadPool.QueueUserWorkItem(task => { PushAppLogInDB(methodBase, apiInfo, logTime, LogTypes.DEBUG_LOG, logMessage, string.Empty, ex); }); } } }
- 修改Global.asax的Application_Start逻辑,替换原来存Application的代码:
// 原有筛选allowedLogTypes的逻辑不变 List<string> allowedLogTypes = new List<string>(); string logTypes= System.Configuration.ConfigurationManager.AppSettings["LogType"]; List<string> lstLogTypes = logTypes.Split('|').ToList<string>(); if (lstLogTypes.Contains(LogTypes.DEBUG_LOG)) { allowedLogTypes.Add(LogTypes.DEBUG_LOG); } if (lstLogTypes.Contains(LogTypes.INFO_LOG)) { allowedLogTypes.Add(LogTypes.INFO_LOG); } if (lstLogTypes.Contains(LogTypes.WARN_LOG)) { allowedLogTypes.Add(LogTypes.WARN_LOG); } // 替换原来Application["AllowedLogTypes"] = allowedLogTypes;这行,直接给静态变量赋值 Reporting.Helper.LogHelper.AllowedLogTypes = allowedLogTypes; GlobalConfiguration.Configure(WebApiConfig.Register);
额外优化提示
你原本Global.asax的代码里写了两次完全相同的if (lstLogTypes.Contains(LogTypes.WARN_LOG))判断,会导致allowedLogTypes里存入两个相同的WARN日志类型,建议删掉重复的判断逻辑。
内容的提问来源于stack exchange,提问作者Slow Death
相关产品推荐
相关产品推荐

