我與傳統的Windows服務讀取專用MSMQ隊列中的消息的工作處理它們(做一些數據庫的工作,發送一些電子郵件),然後等待下一條消息(PeekCompleted)MSMQ,Windows服務和服務器重新啓動
服務有問題 - 無論何時Windows Update需要服務器重新啓動(幾乎總是如此),服務將以「已啓動」狀態恢復,但必須手動重新啓動或消息只是堆積在隊列中。
我的第一個想法是認爲OnStart處理程序中有某些東西在服務器恢復時沒有被擊中,我試圖理清日誌(另一個故事),但Windows服務和線程不是我正常的域名,所以我希望有人可以指向我在正確的方向......
下面是OnStart處理程序和消息處理函數,剝奪無關緊要的東西。
問題:在OnStart中,MessageRecieved函數附加到PeekCompleted事件。 我假設OnStart在服務器重新啓動時觸發,因此處理程序必須連接,但我不清楚(a)重新啓動期間已經在隊列中的消息或(b)在重新啓動期間到達的消息是否會實際觸發事件 ?
如果應該還有別的東西我應該找?
歡迎任何建議!前排隊的基礎設施已經啓動並全面運作
protected override void OnStart(string[] args)
{
try
{
_inProcess = false;
_queueMessage = null;
_stopping = false;
_queue = ReadyQueue(_queueName);
if (_queue == null)
{
throw new Exception(string.Format("'ReadyFormQueue({0})' returned null", _queueName));
}
_queue.PeekCompleted += new PeekCompletedEventHandler(MessageReceived);
_queue.Formatter = new BinaryMessageFormatter();
_queue.BeginPeek();
}
catch (Exception exception)
{
//do cleanup and other recovery stuff
}
}
private void MessageReceived(object sender, PeekCompletedEventArgs e)
{
_currentMessage = null;
_inProcess = false;
try
{
_queueMessage = _queue.EndPeek(e.AsyncResult);
_queueMessage.Formatter = new BinaryMessageFormatter();
_currentMessage = (MyMessageType)_queueMessage.Body;
_queue.ReceiveById(_queueMessage.Id);
_inProcess = true;
_helper = new MessageHelper();
_currentMessage = _helper.Process(_currentMessage); //sets global _inProcess flag
if (_inProcess)
{
Thread.Sleep((int)(_retryWaitTime * 0x3e8));
SendFormMessageToQueue(FailedQueueName, _currentMessage);
}
else
{
_queue.BeginPeek();
}
}
catch (Exception exception)
{
_inProcess = false;
//do other recovery stuff
if (_currentMessage != null)
{
ReadyFormQueue(_poisonQueueName);
SendFormMessageToQueue(_poisonQueueName, _currentMessage);
}
}
}
感謝看起來像問題!我已經將服務設置爲「自動延遲」(它本應該放在第一位),但要設置依賴項,我的理解是必須在服務安裝項目中進行配置 - 除非我丟失了某些內容 - 「依賴項」選項卡在SCM對話框中,如果安裝程序沒有設置依賴關係,則禁用,是的? – Serexx
是的,這可能是一個OnInstall進程 - 您可能無法通過SCM訪問它,但可能是荒謬的。 –