private async Task DeliverMessageAsync(Message message) { var accountRepository = _container.GetInstance <IAccountRepository>(); var messageRepository = _container.GetInstance <IMessageRepository>(); var folderRepository = _container.GetInstance <IFolderRepository>(); var dnsClient = _container.GetInstance <IDnsClient>(); message.NumberOfDeliveryAttempts++; bool isLastAttempt = message.NumberOfDeliveryAttempts >= 3; var deliveryResults = new List <DeliveryResult>(); try { var remainingRecipients = new List <Recipient>(message.Recipients); var localDelivery = new LocalDelivery(accountRepository, messageRepository, folderRepository, _log); deliveryResults.AddRange(await localDelivery.DeliverAsync(message, remainingRecipients.Where(recipient => recipient.AccountId != 0).ToList())); var externalDelivery = new ExternalDelivery(messageRepository, dnsClient, _log); deliveryResults.AddRange(await externalDelivery.DeliverAsync(message, remainingRecipients.Where(recipient => recipient.AccountId == 0).ToList())); var failedRecipients = deliveryResults.Where(result => result.ReplyCodeSeverity == ReplyCodeSeverity.PermanentNegative || (isLastAttempt && result.ReplyCodeSeverity == ReplyCodeSeverity.TransientNegative)); await SubmitBounceMessageAsync(message, failedRecipients); var deliveryCompleted = deliveryResults.Any(result => result.ReplyCodeSeverity == ReplyCodeSeverity.TransientNegative); if (isLastAttempt || !deliveryCompleted) { await messageRepository.DeleteAsync(message); } } catch (Exception ex) { var logEvent = new LogEvent() { EventType = LogEventType.Application, LogLevel = LogLevel.Error, Protocol = "SMTPD", }; if (isLastAttempt) { logEvent.Message = "Failed delivering message due to an error. Giving up."; } else { logEvent.Message = "Failed delivering message due to an error. Will retry later."; } _log.LogException(logEvent, ex); if (isLastAttempt) { await messageRepository.DeleteAsync(message); } else { await messageRepository.UpdateAsync(message); } } }
private async Task DeliverMessageAsync(Message message) { var accountRepository = _container.GetInstance<IAccountRepository>(); var messageRepository = _container.GetInstance<IMessageRepository>(); var folderRepository = _container.GetInstance<IFolderRepository>(); var dnsClient = _container.GetInstance<IDnsClient>(); message.NumberOfDeliveryAttempts++; bool isLastAttempt = message.NumberOfDeliveryAttempts >= 3; var deliveryResults = new List<DeliveryResult>(); try { var remainingRecipients = new List<Recipient>(message.Recipients); var localDelivery = new LocalDelivery(accountRepository, messageRepository, folderRepository, _log); deliveryResults.AddRange(await localDelivery.DeliverAsync(message, remainingRecipients.Where(recipient => recipient.AccountId != 0).ToList())); var externalDelivery = new ExternalDelivery(messageRepository, dnsClient, _log); deliveryResults.AddRange(await externalDelivery.DeliverAsync(message, remainingRecipients.Where(recipient => recipient.AccountId == 0).ToList())); var failedRecipients = deliveryResults.Where(result => result.ReplyCodeSeverity == ReplyCodeSeverity.PermanentNegative || (isLastAttempt && result.ReplyCodeSeverity == ReplyCodeSeverity.TransientNegative)); await SubmitBounceMessageAsync(message, failedRecipients); var deliveryCompleted = deliveryResults.Any(result => result.ReplyCodeSeverity == ReplyCodeSeverity.TransientNegative); if (isLastAttempt || !deliveryCompleted) { await messageRepository.DeleteAsync(message); } } catch (Exception ex) { var logEvent = new LogEvent() { EventType = LogEventType.Application, LogLevel = LogLevel.Error, Protocol = "SMTPD", }; if (isLastAttempt) logEvent.Message = "Failed delivering message due to an error. Giving up."; else logEvent.Message = "Failed delivering message due to an error. Will retry later."; _log.LogException(logEvent, ex); if (isLastAttempt) { await messageRepository.DeleteAsync(message); } else { await messageRepository.UpdateAsync(message); } } }