private string CreateUrl(SQSQueueSetting queueSetting, int receiveCount)
 {
     return(queueSetting.DelayType != SQSDelayType.FirstTimeOnly &&
            !string.IsNullOrEmpty(queueSetting.DeadLetterQueueUrl) &&
            queueSetting.MaxReceiveCount > 0 &&
            queueSetting.MaxReceiveCount <= receiveCount ? queueSetting.DeadLetterQueueUrl : queueSetting.QueueUrl);
 }
Пример #2
0
        private async Task <ReceiveMessageResponse> ReceiveMessageAsync(SQSQueueSetting setting)
        {
            var receiveMessageRequest = new ReceiveMessageRequest(setting.QueueUrl)
            {
                AttributeNames        = { SQSConstans.ApproximateReceiveCountKey },
                MessageAttributeNames = { SQSConstans.TypeFullNameKey, SQSConstans.ReceiveCountKey },
            };

            return(await this.SQSClient.ReceiveMessageAsync(receiveMessageRequest));
        }
Пример #3
0
        private async Task SubscribeAsync(SQSQueueSetting setting)
        {
            var queueInfo = await this.GetQueueInfoAsync(setting);

            while (!this.tokenSource.Token.IsCancellationRequested)
            {
                await(this.semaphoreSlim?.WaitAsync() ?? Task.Delay(0));
                if (setting.DelayType != SQSDelayType.FirstTimeOnly)
                {
                    await this.ProcessMessageWithDelayAsync(setting, queueInfo);
                }
                else
                {
                    await this.ProcessMessageAsync(setting, queueInfo);
                }
                this.semaphoreSlim?.Release();
            }
        }
Пример #4
0
        private async Task NoticeFailureAsync(SQSQueueSetting setting, Message message, int count = 0)
        {
            try
            {
                var changeRequest = new ChangeMessageVisibilityRequest(setting.QueueUrl, message.ReceiptHandle, 0);
                await this.SQSClient.ChangeMessageVisibilityAsync(changeRequest);

                this.logger.LogInformation($"Change visibility message (id:{message.MessageId})");
            }
            catch (Exception ex)
            {
                await this.NoticeFailureAsync(setting, message, count ++);

                if (count >= 10)
                {
                    this.logger.LogCritical(ex, $"Critical Error Can't change visibility message (id:{message.MessageId})");
                    throw;
                }
            }
        }
Пример #5
0
        private async Task DeleteMessageAsync(SQSQueueSetting setting, Message message, int count = 0)
        {
            try
            {
                var deleteMessageRequest = new DeleteMessageRequest(setting.QueueUrl, message.ReceiptHandle);
                await this.SQSClient.DeleteMessageAsync(deleteMessageRequest);

                this.logger.LogInformation($"Delete message (id:{message.MessageId})");
            }
            catch (Exception ex)
            {
                await this.DeleteMessageAsync(setting, message, count ++);

                if (count >= 10)
                {
                    this.logger.LogCritical(ex, $"Critical Error Can't delete message (id:{message.MessageId})");
                    throw;
                }
            }
        }
Пример #6
0
        private async Task ProcessMessageAsync(SQSQueueSetting setting, GetQueueAttributesResponse queueInfo)
        {
            var receiveMessageResponse = await this.ReceiveMessageAsync(setting);

            if ((receiveMessageResponse?.Messages?.Count ?? 0) == 0)
            {
                return;
            }
            var message = receiveMessageResponse.Messages.Single();

            try
            {
                using (var source = new CancellationTokenSource(queueInfo.VisibilityTimeout * 900))
                {
                    this.logger.LogInformation($"Receive {message.MessageId} at {DateTime.Now}");
                    var result = await this.ExecuteAsync(message, source);

                    if (result != 0)
                    {
                        this.logger.LogInformation($"Handling Error {message.MessageId} at {DateTime.Now}(code:{result})");
                        await this.NoticeFailureAsync(setting, message);

                        return;
                    }
                    await this.DeleteMessageAsync(setting, message);
                }
            }
            catch (Exception ex)
            {
                if (ex is OperationCanceledException)
                {
                    this.logger.LogError($"Time out {message.MessageId} at {DateTime.Now}");
                }
                else
                {
                    this.logger.LogError(ex, $"Error {message.MessageId} at {DateTime.Now}");
                }
                await this.NoticeFailureAsync(setting, message);
            }
        }
Пример #7
0
        private async Task ResendMessageAsync(SQSQueueSetting setting, Message message, int count = 0)
        {
            try
            {
                var type                = this.typeHelper.GetType(x => x.FullName == (message.MessageAttributes[SQSConstans.TypeFullNameKey].StringValue));
                var receiveCount        = int.Parse(message.MessageAttributes[SQSConstans.ReceiveCountKey].StringValue);
                var sendMessageRequest  = this.sendMessageRequestFactory.CreateSendMessage(message.Body, type, receiveCount + 1);
                var sendMessageResponse = await this.SQSClient.SendMessageAsync(sendMessageRequest);

                this.logger.LogInformation($"Resend message (id:{message.MessageId})");
            }
            catch (Exception ex)
            {
                await this.ResendMessageAsync(setting, message, count ++);

                if (count >= 10)
                {
                    this.logger.LogCritical(ex, $"Critical Error Can't resend message (id:{message.MessageId})");
                    throw;
                }
            }
            await this.DeleteMessageAsync(setting, message);
        }
Пример #8
0
 private async Task <GetQueueAttributesResponse> GetQueueInfoAsync(SQSQueueSetting setting)
 {
     return(await this.SQSClient.GetQueueAttributesAsync(setting.QueueUrl, new List <string> {
         SQSConstans.VisibilityTimeoutKey
     }, this.tokenSource.Token));
 }