Обнаружение при повторном использовании приложения ASP.NET
Я пытаюсь обнаружить, когда приложение ASP.NET перерабатывается из-за изменения файла web.config или пула приложений IIS, который вручную перерабатывается.
Первоначально я думал, что метод ASP.NET Application_End будет работать, и попробовал следующее:
protected void Application_End(object sender, EventArgs e)
{
File.AppendAllText("log.txt", DateTime.Now + "\n");
}
Файл был создан при первом изменении файла web.config, но последующие изменения не активировали событие. Аналогичным образом, при тестировании в IIS первый ручной пул пула приложений создавал файл, но более поздние - не так, как если бы событие Application_End срабатывало только один раз.
Как я буду обнаруживать каждый раз, когда пул/приложение перерабатывает?
Ответы
Ответ 1
Ниже может быть немного взлома, но вы можете использовать приложение Cache
, чтобы понять это. Каждый раз, когда загружается страница, вы можете проверить кеш для определенного ключа, если ключ не существует, вы можете считать его "переработкой", а затем добавить ключ. Не лучший метод, но может работать только на то, что вам нужно.
Eg. На вашей базовой странице Page_Load
или где-нибудь, которая будет работать с каждым запросом, вы можете сделать следующее:
if (HttpContext.Current.Cache["RecycleCheck"] != null)
{
// Add flag to cache
HttpContext.Current.Cache.Insert("RecycleCheck", "1", null,
DateTime.UtcNow.AddDays(2), // 2 days (most will recycle by then)
System.Web.Caching.Cache.NoSlidingExpiration);
// Do what you need because a recycle has happened
}
Этот метод не будет воспринимать его, поскольку происходит повторное использование. Он будет идентифицировать только рециркуляцию по первому запросу после повторного использования.
Application_Start
будет самым надежным местом для этого, но он страдает от той же проблемы, что и взлом с тем фактом, что это происходит после повторного использования по первому запросу.
Ответ 2
Хороший ответ на этот вопрос был предоставлен в следующем вопросе: как определить, что текущий пул приложений завершается.
Чтобы отслеживать переработку пула приложений, вам необходимо реализовать интерфейс IRegisteredObject, вызвать ApplicationManager.CreateObject для создания экземпляра вашего объекта и затем зарегистрировать его с помощью HostingEnvironment.RegisterObject во время запуска вашего приложения.
Когда этот объект IRegisteredObject.Stop(bool) реализуется с параметром false, это уведомление о том, что домен приложения закрыт и что объект должен быть незарегистрирован (вроде как глобальный dispose) с вызовом в HostingEnvironment.UnregisterObject.
Итак, используя это событие, вы можете отслеживать, когда пул приложений перерабатывается.
Ответ 3
Почему бы вам не сделать что-то подобное. Отрегулируйте частоту задания таймера, чтобы повысить точность определения при повторном использовании appPool.
private readonly Timer timer = new Timer();
private DateTime start;
private string logFile;
void Application_Start(object sender, EventArgs e)
{
start= DateTime.Now;
logFile = Server.MapPath(
string.Concat("Log-",start.ToString("yyyyMMdd-HHmmss.fff"),".txt"));
timer.Interval = 1000;
timer.Elapsed += (s, ee)
=> File.WriteAllText(logFile,
string.Concat("App Start :", start, " Last Alive: ", DateTime.Now));
timer.Start();
}