Я использую ASP.NET MVC и создаю общедоступный сайт. Я должен отслеживать пользователей, которые онлайн. Я вижу, что стандартный путь в asp.net выполнения этого состоит в том, чтобы отслеживать LastActivityDate
. Мой вопрос состоит в том, когда я должен обновить это?
Если я обновлю его каждый раз пользовательские щелчки где-нибудь, то я буду чувствовать, что производительность отступает. Однако, если я не делаю этого, люди, что только перемещение вокруг будет перечислено как в режиме офлайн.
Что лучший способ состоит в том, чтобы сделать это в asp.net MVC?
Просто поместите вызов javascript ajax внизу главной страницы, чтобы отслеживать это.
Пока не беспокойтесь о производительности. Если он реализован, и вы видите, что это проблема, вернитесь к поиску лучшего решения. Что-то настолько простое не должно вызывать проблем с производительностью.
Подумайте об этом как об аналитике Google. Он находится внизу миллионов страниц и практически не влияет на работу пользователей с этими сайтами.
Если вы используете InProc SessionState, используйте событие SessionStateModule.End . Это происходит, когда состояние сеанса вытесняется из нижележащего кеш-хранилища. Обычно это происходит после 20 минут бездействия, вы можете установить время в web.config.
Почему бы не реализовать обновление LastActivityDate в виде асинхронного вызова? Таким образом, вы можете сжечь обновление и продолжить обработку.
Я помещаю его в специальную очередь, которая позволяет только одному из заданных ключей находиться в queue (и в этом случае используйте userId в качестве ключа). Затем у меня есть поток с низким приоритетом, который проходит через эту очередь, обновляя базу данных. Таким образом, нет замедления для пользователя, и один пользователь, выполняющий 100 обновлений за одну секунду, не причинит никакого вреда. Если это когда-нибудь станет проблемой, я сделаю эти обновления пакетными обновлениями базы данных, но пока этот подход работает нормально.
Если приложение выйдет из строя, я потеряю несколько секунд последних данных о действиях, но это нормально. Конечно, я также каждый раз обновляю объект User в памяти, чтобы он отражался в пользовательском интерфейсе, даже если он еще не попал в базу данных. Обычно он там еще до того, как получил готовую страницу.
Я не думаю, что будет большая потеря производительности, если вы будете получать информацию о текущем вошедшем в систему пользователю при каждом запросе и обновлять LastActivityDate
каждый раз (если у вас есть осторожность и вы вызываете метод GetUser
для вошедшего в систему пользователя один раз для каждого http-запроса). Таким образом, вы также можете быть уверены, что у вас всегда есть свежие данные пользователя, такие как адрес электронной почты, имя и т. Д. На случай, если он / она обновит эти данные.
Как говорит @Jab, просто реализуйте ее, и если вы считаете это проблемой производительности в будущем - тогда разберитесь с ней.
Вот как я это сделал в своем приложении:
protected void Application_EndRequest()
{
if ((Response.ContentType == "text/html") && (Request.IsAuthenticated))
{
var webUser = Context.User as WebUser;
if (webUser != null)
{
//Update their last activity
webUser.LastActivity = DateTime.UtcNow;
//Update their page hit counter
webUser.ActivityCounter += 1;
//Save them
var webUserRepo = Kernel.Get<IWebUserRepository>(); //Ninject
webUserRepo.Update(webUser);
}
}
}
У меня не было проблем с производительностью.
HTHs,
Чарльз
Хороший вопрос, подумал и над этим, и насколько точными могут быть эти механизмы с учетом производительности, пара идей:
1) Отследить последнее дата входа в систему
2) Используйте LastLoginDate + ожидаемую продолжительность сеанса, чтобы установить какой-то LastOnlineDate, который можно использовать для проверки, находится ли пользователь в сети.