IIS Recycle Global.asax
-
08-07-2019 - |
Domanda
È possibile catturare un evento di riciclo in global.asax?
So che Application_End verrà attivato, ma c'è un modo per sapere che è stato attivato da un riciclo del pool di applicazioni?
grazie, Lieven Cardoen aka Johlero
Soluzione
Quindi, ecco un'idea di come potrebbe funzionare.
Basato sulla mia risposta precedente (allegare a AppDomain.CurrentDomain.ProcessExit) e commento di stephbu :
Questo intrappolerà il processo più strutturato smontaggio ad es. - ma non ne sono sicuro intrappolerà tutti gli strappi. per esempio. http://blogs.msdn.com/ jmstall / archive / 2006/11/26 / processo-uscita-event.aspx Il processo di riciclo interromperà il processo se sembra essere appeso, il tuo gestore non verrebbe chiamato.
Suggerisco la seguente strategia:
Nel (normale) gestore ProcessExit (che supponiamo non verrà chiamato per il riciclo di un pool di applicazioni), scrivi alcuni file sul disco come " app_domain_end_ok.tmp
" ;.
Quindi in Application_Start del tuo global.asax controlla questo file. Se non esiste, significa che l'applicazione non è stata chiusa in modo pulito (o che è la prima volta che viene avviata). Non dimenticare di eliminare questo file dal disco dopo il controllo.
Non l'ho provato da solo, ma potrebbe valerne la pena.
Altri suggerimenti
Ho trovato questo articolo sul blog di Scott Guthries :
Registrazione degli eventi di arresto dell'applicazione ASP.NET
Qualcuno su un listserv ha chiesto di recente se c'era un modo per capire perché e quando ASP.NET si riavvia domini di applicazione. In particolare, lui cercavo la causa esatta di cosa li stava scatenando sul suo applicazione in una produzione condivisa ambiente ospitato (era a Modifica del file web.config, un global.asax modifica, una modifica della directory app_code, una modifica all'eliminazione della directory, quota max-num-compilation raggiunta, \ bin cambia directory, ecc.).
Thomas nella mia squadra ha un figo snippet di codice che ha scritto che utilizza alcuni trucchi di riflessione privati ??eleganti per acquisire e registrare queste informazioni. È abbastanza facile da riutilizzare e aggiungere in qualsiasi applicazione e può essere utilizzato per registrare le informazioni ovunque tu vuoi (il codice seguente usa l'evento NT Accedi per salvarlo, ma potresti farlo altrettanto inviarlo facilmente a un database o tramite un e-mail a un amministratore). Il codice funziona con ASP.NET V1.1 e ASP.NET V2.0.
Aggiungi semplicemente System.Reflection e Spazi dei nomi System.Diagnostics sul tuo Classe / file Global.asax, quindi aggiungere l'evento Application_End con questo codice:
public void Application_End() {
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);
if (!EventLog.SourceExists(".NET Runtime")) {
EventLog.CreateEventSource(".NET Runtime", "Application");
}
EventLog log = new EventLog();
log.Source = ".NET Runtime";
log.WriteEntry(String.Format(
"\r\n\r\n_shutDownMessage={0}\r\n\r\n_shutDownStack={1}",
shutDownMessage, shutDownStack),
EventLogEntryType.Error);
}
Non ho mai provato questo da solo, ma potresti provare a collegare un gestore di eventi all'evento ProcessExit di AppDomain.
...
AppDomain.CurrentDomain.ProcessExit += new EventHandler(OnExit);
...
void OnExit(object sender, EventArgs e) {
// do something
}
Spero che questo aiuti!
Ho avuto molto più successo con il collegamento all'evento DomainUnload, è stato attivato durante il riciclo di AppPool e l'arresto dell'AppPool stesso.
AppDomain.CurrentDomain.DomainUnload + = this.CurrentDomainOnProcessExit;