Можно ли зарегистрироваться на сервисные события PreShutdown, используя .Net? - PullRequest
7 голосов
/ 16 сентября 2011

Я столкнулся с ситуацией, когда развернул службу .Net (C #) на сервере Win 2008R2.Служба зависит от MSMQ.При выключении необходимо отправить пару быстрых сообщений перед завершением.Это прекрасно работает с событиями OnStop (), запускаемыми вручную, но когда сервер выключается и SCM вызывает OnShutdown (), я обнаружил, что MSMQ уже завершил работу и моя служба не может правильно очистить.Моему сервису нужно всего 2-5 секунд, чтобы работать.

Я понимаю (сейчас), что сервисные зависимости относятся только к запуску, так что это не помогает.Сегодня я потратил некоторое время, пытаясь выяснить, как зарегистрировать свой сервис, чтобы принимать новые (начиная с Vista) доступные события SERVICE_ACCEPT_PRESHUTDOWN и работать с функцией PreShutDownOrder (http://blogs.technet.com/b/askperf/archive/2008/02/04/ws2008-service-shutdown-and-crash-handling.aspx),, но это не поддерживается в ServiceBase, как реализовано внасколько я могу судить, это фреймворк.

Я пытался вручную установить его с помощью функции SetServiceStatus (), но, похоже, он не работает.

_serviceHandle = this.ServiceHandle;
SERVICE_STATUS serviceStatus = new SERVICE_STATUS();
serviceStatus.currentState = (int)State.SERVICE_RUNNING;
serviceStatus.controlsAccepted = (int)(ControlsAccepted.SERVICE_ACCEPT_PRESHUTDOWN | ControlsAccepted.SERVICE_ACCEPT_STOP);
serviceStatus.waitHint = 0;
serviceStatus.checkPoint = 0;
bool setStatus = SetServiceStatus(_serviceHandle, ref serviceStatus);
int error = Marshal.GetLastWin32Error();

Это возвращает статус ошибки 13, когда вы звоните GetLastError();

Есть какие-нибудь идеи о том, как подключиться к событиям предварительной очистки?

Ответы [ 5 ]

2 голосов
/ 11 ноября 2011

ОК, тогда другой альтернативой является создание / получение / покупка службы C ++, которая регистрирует содержимое PreShutdown и останавливает / закрывает ваши службы .Net в требуемом порядке (и ожидает их фактического выхода).

Он может иметь свой собственный список / график порядка выключения или построить его, используя существующие зависимости запуска Windows (игнорируя службы, которыми он не должен управлять).

1 голос
/ 30 мая 2014

Вот решение на основе отражения: http://www.sivachandran.in/2012/03/handling-pre-shutdown-notification-in-c.html

0 голосов
/ 09 апреля 2013

В этой статье рассматриваются некоторые базовые компоненты ServiceModel, чтобы зарегистрировать его для PreShutDown ... - http://www.sivachandran.in/2012/03/handling-pre-shutdown-notification-in-c.html

Однако он ссылается на закрытую переменную, и поэтому любой человек, которого я видел, реализует это, выдает исключение (какэта статья демонстрирует), если измененный член "acceptCommands" будет изменен в более поздних версиях .Net Framework.

Мне больше интересно узнать, вводил ли кто-нибудь вручную значение своих процессов в HKLM \ SYSTEM \Запись реестра CurrentControlSet \ Control \ PreShutDownOrder.Кто-нибудь пробовал это?

0 голосов
/ 11 ноября 2011

В качестве альтернативы используйте более разумную операционную систему, в которой гораздо проще настроить систему, чтобы обычное отключение не приводило к потере данных.

Серьезно, сервисные зависимости уже существуют, поэтому Windows должна просто использовать их, если это обычное отключение, а не отключение «OMG UPS low battery». И в этом отношении предлог для того, чтобы не делать надлежащее отключение из-за таких вещей, как «разряженная батарея ИБП», является глупым, когда для Windows так легко и обычно применять более 30 обновлений Windows при выключении ...

В любом случае, вот еще плохие новости: http://connect.microsoft.com/VisualStudio/feedback/details/641737/add-windows-service-preshutdown

Что касается предложений, чтобы написать материал в другом месте: 1) Я подумал, что одной из причин использования MSMQ является более надежный обмен сообщениями, чем просто запись чего-либо в файл. 2) AFAIK, вы также не можете записывать в БД, так как без этих зависимостей Windows может отключить БД перед вашим обслуживанием. Черт возьми, не учитывая зависимости, даже на 100% нет уверенности, что в этот момент вы можете записать в нужную файловую систему

0 голосов
/ 16 сентября 2011

Если вы напишите сообщение в базу данных / файл, когда служба закроется и чем когда снова включите компьютер, проверьте таблицу / файл и отправьте сообщение MSMQ

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...