static void SendMessages(TopicClient topicClient, SubscriptionClient responseClient) { // Send request messages to queue: Console.WriteLine("Sending request messages to topic {0}", topicClient.Path); Console.WriteLine("Receiving response messages on subscription {0}", responseClient.Name); MessageSession session = responseClient.AcceptMessageSession(ClientId); for (int i = 0; i < SampleManager.NumMessages; ++i) { // send request message BrokeredMessage message = new BrokeredMessage { ReplyToSessionId = ClientId, MessageId = i.ToString(), CorrelationId = SampleManager.RequestSubName }; topicClient.Send(message); SampleManager.OutputMessageInfo("REQUEST: ", message); // start asynchronous receive operation session.BeginReceive(TimeSpan.FromSeconds(ResponseMessageTimeout), ProcessResponse, session); } Console.WriteLine(); }
private void OnMessageSession(IAsyncResult ar) { try { _logger.Write(LogLevel.Info, "Got message session " + _sessionId); _session = _readQueueClient.EndAcceptMessageSession(ar); _session.BeginReceive(OnMessage, null); } catch (Exception exception) { BusFailed(this, new ExceptionEventArgs(exception)); } }
private void OnMessageSession(IAsyncResult ar) { try { _session = _readQueueClient.EndAcceptMessageSession(ar); _logger.Write(LogLevel.Info, "Are not listening on session " + _sessionId); _session.BeginReceive(OnMessage, null); } catch (Exception exception) { _logger.Write(LogLevel.Error, "Failed to EndAcceptMessageSession " + _sessionId, exception); BusFailed(this, new ExceptionEventArgs(exception)); } }
private void ReceiveMessage() { try { if (_shutdown) { _shutdownEvent.Set(); return; } _session.BeginReceive(OnMessage, null); } catch (Exception exception) { BusFailed(this, new ExceptionEventArgs(exception)); } }
private void ReceiveMessage() { try { if (_shutdown) { _shutdownEvent.Set(); return; } _session.BeginReceive(OnMessage, null); } catch (Exception exception) { _logger.Write(LogLevel.Error, "Failed to receive message on session " + _sessionId, exception); BusFailed(this, new ExceptionEventArgs(exception)); } }
/// <summary> /// Receives the messages in an asynchronous loop and closes the session once there are no more messages. /// </summary> private void ReceiveMessagesAndCloseSession(MessageSession session, CancellationToken cancellationToken) { CountdownEvent unreleasedMessages = new CountdownEvent(1); Action <bool> closeSession = (bool success) => { Action doClose = () => { try { unreleasedMessages.Signal(); if (!unreleasedMessages.Wait(15000, cancellationToken)) { Trace.TraceWarning("Waited for pending unreleased messages before closing session in subscription {0} but they did not complete in time", this.subscription); } } catch (OperationCanceledException) { } finally { unreleasedMessages.Dispose(); } this.receiveRetryPolicy.ExecuteAction( cb => session.BeginClose(cb, null), session.EndClose, () => { this.instrumentation.SessionEnded(); if (success) { this.dynamicThrottling.NotifyWorkCompleted(); } else { this.dynamicThrottling.NotifyWorkCompletedWithError(); } }, ex => { this.instrumentation.SessionEnded(); Trace.TraceError("An unrecoverable error occurred while trying to close a session in subscription {1}:\r\n{0}", ex, this.subscription); this.dynamicThrottling.NotifyWorkCompletedWithError(); }); }; if (this.requiresSequentialProcessing) { doClose.Invoke(); } else { // Allow some time for releasing the messages before closing. Also, continue in a non I/O completion thread in order to block. TaskEx.Delay(200).ContinueWith(t => doClose()); } }; // Declare an action to receive the next message in the queue or closes the session if cancelled. Action receiveNext = null; // Declare an action acting as a callback whenever a non-transient exception occurs while receiving or processing messages. Action <Exception> recoverReceive = null; // Declare an action responsible for the core operations in the message receive loop. Action receiveMessage = (() => { // Use a retry policy to execute the Receive action in an asynchronous and reliable fashion. this.receiveRetryPolicy.ExecuteAction ( cb => { // Start receiving a new message asynchronously. // Does not wait for new messages to arrive in a session. If no further messages we will just close the session. session.BeginReceive(TimeSpan.Zero, cb, null); }, // Complete the asynchronous operation. This may throw an exception that will be handled internally by retry policy. session.EndReceive, msg => { // Process the message once it was successfully received // Check if we actually received any messages. if (msg != null) { var roundtripStopwatch = Stopwatch.StartNew(); long schedulingElapsedMilliseconds = 0; long processingElapsedMilliseconds = 0; unreleasedMessages.AddCount(); Task.Factory.StartNew(() => { var releaseAction = MessageReleaseAction.AbandonMessage; try { this.instrumentation.MessageReceived(); schedulingElapsedMilliseconds = roundtripStopwatch.ElapsedMilliseconds; // Make sure the process was told to stop receiving while it was waiting for a new message. if (!cancellationToken.IsCancellationRequested) { try { try { // Process the received message. releaseAction = this.InvokeMessageHandler(msg); processingElapsedMilliseconds = roundtripStopwatch.ElapsedMilliseconds - schedulingElapsedMilliseconds; this.instrumentation.MessageProcessed(releaseAction.Kind == MessageReleaseActionKind.Complete, processingElapsedMilliseconds); } catch { processingElapsedMilliseconds = roundtripStopwatch.ElapsedMilliseconds - schedulingElapsedMilliseconds; this.instrumentation.MessageProcessed(false, processingElapsedMilliseconds); throw; } } finally { if (roundtripStopwatch.Elapsed > TimeSpan.FromSeconds(45)) { this.dynamicThrottling.Penalize(); } } } } finally { // Ensure that any resources allocated by a BrokeredMessage instance are released. if (this.requiresSequentialProcessing) { this.ReleaseMessage(msg, releaseAction, () => { receiveNext(); }, () => { closeSession(false); }, unreleasedMessages, processingElapsedMilliseconds, schedulingElapsedMilliseconds, roundtripStopwatch); } else { // Receives next without waiting for the message to be released. this.ReleaseMessage(msg, releaseAction, () => { }, () => { this.dynamicThrottling.Penalize(); }, unreleasedMessages, processingElapsedMilliseconds, schedulingElapsedMilliseconds, roundtripStopwatch); receiveNext.Invoke(); } } }); } else { // no more messages in the session, close it and do not continue receiving closeSession(true); } }, ex => { // Invoke a custom action to indicate that we have encountered an exception and // need further decision as to whether to continue receiving messages. recoverReceive.Invoke(ex); }); }); // Initialize an action to receive the next message in the queue or closes the session if cancelled. receiveNext = () => { if (!cancellationToken.IsCancellationRequested) { // Continue receiving and processing new messages until told to stop. receiveMessage.Invoke(); } else { closeSession(true); } }; // Initialize a custom action acting as a callback whenever a non-transient exception occurs while receiving or processing messages. recoverReceive = ex => { // Just log an exception. Do not allow an unhandled exception to terminate the message receive loop abnormally. Trace.TraceError("An unrecoverable error occurred while trying to receive a new message from subscription {1}:\r\n{0}", ex, this.subscription); // Cannot continue to receive messages from this session. closeSession(false); }; // Start receiving messages asynchronously for the session. receiveNext.Invoke(); }
/// <summary> /// Receives the messages in an asynchronous loop and closes the session once there are no more messages. /// </summary> private void ReceiveMessagesAndCloseSession(MessageSession session, CancellationToken cancellationToken) { CountdownEvent unreleasedMessages = new CountdownEvent(1); Action<bool> closeSession = (bool success) => { Action doClose = () => { try { unreleasedMessages.Signal(); if (!unreleasedMessages.Wait(15000, cancellationToken)) { Trace.TraceWarning("Waited for pending unreleased messages before closing session in subscription {0} but they did not complete in time", this.subscription); } } catch (OperationCanceledException) { } finally { unreleasedMessages.Dispose(); } this.receiveRetryPolicy.ExecuteAction( cb => session.BeginClose(cb, null), session.EndClose, () => { this.instrumentation.SessionEnded(); if (success) { this.dynamicThrottling.NotifyWorkCompleted(); } else { this.dynamicThrottling.NotifyWorkCompletedWithError(); } }, ex => { this.instrumentation.SessionEnded(); Trace.TraceError("An unrecoverable error occurred while trying to close a session in subscription {1}:\r\n{0}", ex, this.subscription); this.dynamicThrottling.NotifyWorkCompletedWithError(); }); }; if (this.requiresSequentialProcessing) { doClose.Invoke(); } else { // Allow some time for releasing the messages before closing. Also, continue in a non I/O completion thread in order to block. TaskEx.Delay(200).ContinueWith(t => doClose()); } }; // Declare an action to receive the next message in the queue or closes the session if cancelled. Action receiveNext = null; // Declare an action acting as a callback whenever a non-transient exception occurs while receiving or processing messages. Action<Exception> recoverReceive = null; // Declare an action responsible for the core operations in the message receive loop. Action receiveMessage = (() => { // Use a retry policy to execute the Receive action in an asynchronous and reliable fashion. this.receiveRetryPolicy.ExecuteAction ( cb => { // Start receiving a new message asynchronously. // Does not wait for new messages to arrive in a session. If no further messages we will just close the session. session.BeginReceive(TimeSpan.Zero, cb, null); }, // Complete the asynchronous operation. This may throw an exception that will be handled internally by retry policy. session.EndReceive, msg => { // Process the message once it was successfully received // Check if we actually received any messages. if (msg != null) { var roundtripStopwatch = Stopwatch.StartNew(); long schedulingElapsedMilliseconds = 0; long processingElapsedMilliseconds = 0; unreleasedMessages.AddCount(); Task.Factory.StartNew(() => { var releaseAction = MessageReleaseAction.AbandonMessage; try { this.instrumentation.MessageReceived(); schedulingElapsedMilliseconds = roundtripStopwatch.ElapsedMilliseconds; // Make sure the process was told to stop receiving while it was waiting for a new message. if (!cancellationToken.IsCancellationRequested) { try { try { // Process the received message. releaseAction = this.InvokeMessageHandler(msg); processingElapsedMilliseconds = roundtripStopwatch.ElapsedMilliseconds - schedulingElapsedMilliseconds; this.instrumentation.MessageProcessed(releaseAction.Kind == MessageReleaseActionKind.Complete, processingElapsedMilliseconds); } catch { processingElapsedMilliseconds = roundtripStopwatch.ElapsedMilliseconds - schedulingElapsedMilliseconds; this.instrumentation.MessageProcessed(false, processingElapsedMilliseconds); throw; } } finally { if (roundtripStopwatch.Elapsed > TimeSpan.FromSeconds(45)) { this.dynamicThrottling.Penalize(); } } } } finally { // Ensure that any resources allocated by a BrokeredMessage instance are released. if (this.requiresSequentialProcessing) { this.ReleaseMessage(msg, releaseAction, () => { receiveNext(); }, () => { closeSession(false); }, unreleasedMessages, processingElapsedMilliseconds, schedulingElapsedMilliseconds, roundtripStopwatch); } else { // Receives next without waiting for the message to be released. this.ReleaseMessage(msg, releaseAction, () => { }, () => { this.dynamicThrottling.Penalize(); }, unreleasedMessages, processingElapsedMilliseconds, schedulingElapsedMilliseconds, roundtripStopwatch); receiveNext.Invoke(); } } }); } else { // no more messages in the session, close it and do not continue receiving closeSession(true); } }, ex => { // Invoke a custom action to indicate that we have encountered an exception and // need further decision as to whether to continue receiving messages. recoverReceive.Invoke(ex); }); }); // Initialize an action to receive the next message in the queue or closes the session if cancelled. receiveNext = () => { if (!cancellationToken.IsCancellationRequested) { // Continue receiving and processing new messages until told to stop. receiveMessage.Invoke(); } else { closeSession(true); } }; // Initialize a custom action acting as a callback whenever a non-transient exception occurs while receiving or processing messages. recoverReceive = ex => { // Just log an exception. Do not allow an unhandled exception to terminate the message receive loop abnormally. Trace.TraceError("An unrecoverable error occurred while trying to receive a new message from subscription {1}:\r\n{0}", ex, this.subscription); // Cannot continue to receive messages from this session. closeSession(false); }; // Start receiving messages asynchronously for the session. receiveNext.Invoke(); }