分析 ASP.Net Application Pool 退出/重启的原因

如果遭遇ASP.Net应用程序莫名其妙退出问题,可以在Global.asax中添加下列代码记录Application Pool退出原因

void Application_End(object sender, EventArgs e)
    {
        HttpRuntime runtime = (HttpRuntime) typeof(System.Web.HttpRuntime).InvokeMember("_theRuntime"
            , BindingFlags.NonPublic | BindingFlags.Static | BindingFlags.GetField
            , null
            , null
            , null
            );
        if (runtime == null) return;
    
        string shutDownMessage = (string)runtime.GetType().InvokeMember("_shutDownMessage"
            , BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.GetField
            , null
            , runtime
            , null
            );

        string shutDownStack = (string)runtime.GetType().InvokeMember("_shutDownStack"
            , BindingFlags.NonPublic | BindingFlags.Instance | BindingFlags.GetField
            , null
            , runtime 
            , null
            );

        EventLog log = new EventLog();
        log.Source = "XXX";
        log.WriteEntry(String.Format("\r\n\r\n_shutDownMessage={0}\r\n\r\n_shutDownStack={1}"
            , shutDownMessage
            , shutDownStack
            )
            , EventLogEntryType.Warning
            );
    }

此代码将退出的原因记录到了XXX这个 Event Source, 所以需要在服务器上创建此 Event Source.

eventcreate /ID 1 /L APPLICATION /T INFORMATION /SO XXX /D "XXX"

当Application Pool正常退出时,日志中就会记录有Application Pool退出的原因。无外乎下面几种情况:

1. web.config被修改 / 2. 即时编译的*.cs文件被修改(一般在App_Code中) / 3.Bin目录被更新 / 4.*.aspx,*.ascx,*.master文件被修改的个数超过阀值 / 5. 长时间的Idle超过阀值

下面的日志显示的是由于App_Code目录被修改导致的退出

The following information was included with the event: 



_shutDownMessage=Change Notification for critical directories.
App_Code dir change or directory rename
HostingEnvironment initiated shutdown
Change Notification for critical directories.
App_Code dir change or directory rename
HostingEnvironment caused shutdown

_shutDownStack=   at System.Environment.GetStackTrace(Exception e, Boolean needFileInfo)
   at System.Environment.get_StackTrace()
   at System.Web.Hosting.HostingEnvironment.InitiateShutdownInternal()
   at System.Web.HttpRuntime.ShutdownAppDomain(String stackTrace)
   at System.Web.HttpRuntime.OnCriticalDirectoryChange(Object sender, FileChangeEvent e)
   at System.Web.FileChangesMonitor.OnCriticaldirChange(Object sender, FileChangeEvent e)
   at System.Web.DirectoryMonitor.FireNotifications()
   at System.Web.Util.WorkItem.CallCallbackWithAssert(WorkItemCallback callback)
   at System.Threading.ExecutionContext.Run(ExecutionContext executionContext, ContextCallback callback, Object state, Boolean ignoreSyncCtx)
   at System.Threading.QueueUserWorkItemCallback.System.Threading.IThreadPoolWorkItem.ExecuteWorkItem()
   at System.Threading.ThreadPoolWorkQueue.Dispatch()
   at System.Threading._ThreadPoolWaitCallback.PerformWaitCallback()

the message resource is present but the message is not found in the string/message table


同时最好加上日志记录Application的启动事件。

protected void Application_Start(object sender, EventArgs e) 
{  
	EventLog log = new EventLog();
        log.Source = "XXX";
        log.WriteEntry("Application Pool Starting..." , EventLogEntryType.Information);
}  

通过 eventvwr, 可以分析Application Pool重启的原因。如果Application Pool是由于崩溃导致异常退出,这个时候Application_End是不会被触发的。但同时在 ASP.Net的系统日志中还是能够查到异常退出的原因。


你可能感兴趣的:(分析 ASP.Net Application Pool 退出/重启的原因)