using Sozsoft.MailQueue.Domain.Entities; using Sozsoft.MailQueue.Domain.MailGeneration; using Sozsoft.MailQueue.Domain.Shared; using Sozsoft.Sender.Mail; using Volo.Abp.BackgroundWorkers; using Volo.Abp.Domain.Repositories; using Volo.Abp.Timing; using Volo.Abp.Uow; namespace Sozsoft.MailQueue.Domain; public class MailQueueWorker : BackgroundWorkerBase { public Guid TemplateId { get; set; } public string TemplateName { get; set; } public MailQueueWorkerOptions Options { get; set; } protected ISozsoftEmailSender ErpEmailSender { get; } protected IRepository Repository { get; } public IClock Clock { get; } public ILogManager LogManager { get; } public ITableGenerator TableGenerator { get; } public IMailBodyGenerator MailBodyGenerator { get; } public IAttachmentGenerator AttachmentGenerator { get; } public MailQueueWorker( ISozsoftEmailSender erpEmailSender, IRepository repository, IClock clock, ILogManager logManager, ITableGenerator tableGenerator, IMailBodyGenerator mailBodyGenerator, IAttachmentGenerator attachmentGenerator) { ErpEmailSender = erpEmailSender; Repository = repository; Clock = clock; LogManager = logManager; TableGenerator = tableGenerator; MailBodyGenerator = mailBodyGenerator; AttachmentGenerator = attachmentGenerator; } /// /// Şablonun (TemplateId) gönderilmemiş kuyruk kayıtlarını işler: her kayıt için tablo, gövde ve /// ekler üretilir, mail gönderilir, sonuç kayda yazılır. Akış: tablo → gövde → ekler → gönderim. /// public override async Task StartAsync(CancellationToken cancellationToken = default) { var uowManager = LazyServiceProvider.LazyGetRequiredService(); using var uow = uowManager.Begin(); var jobId = $"{TemplateId}-{Clock.Now:yyyy-MM-dd-HH-mm-ss}"; var queues = await Repository.GetListAsync(a => a.TemplateId == TemplateId && !a.SendStatus, cancellationToken: cancellationToken); foreach (var queue in queues) { // Her kayıt kendi UoW'sinde: bir kaydın hatası diğerlerinin gönderimini ve kaydını düşürmez. using var uow2 = uowManager.Begin(requiresNew: true, isTransactional: false); try { await ProcessQueueAsync(queue, jobId, cancellationToken); await uow2.CompleteAsync(cancellationToken); } catch (Exception ex) { LogManager.LogError($"Hata. Kuyruk Id: {queue.Id}. {ex}", "HATA", "KUYRUK", queue.Id, jobId); } } await uow.CompleteAsync(cancellationToken); } private async Task ProcessQueueAsync(BackgroundWorker_MailQueue queue, string jobId, CancellationToken cancellationToken) { var tables = await TableGenerator.GenerateAsync(queue.TableName, queue.TableParameter, queue.Id); var mailBody = await MailBodyGenerator.GenerateAsync( TemplateName, queue.MailParameter, queue.Id, tables, jobId); // Ekler tablo şablonlarından (IN olmayanlar: PDF, XLS, TXT) üretilir. var attachments = await AttachmentGenerator.GenerateAsync(tables.Values.ToList(), queue.Id, jobId); // IN olmayan bir tablo belirtilmiş ama hiçbiri üretilememişse hata vardır, gönderilmez. if (tables.Values.Any(a => a.DosyaTipi != "IN") && attachments.IsNullOrEmpty()) { LogManager.LogWarning("Table attachments could not be generated", "ATTACHMENT", "KUYRUK", queue.Id, jobId); return; } var senderKeyValue = queue.From.Split(":"); var sender = new KeyValuePair( senderKeyValue.ElementAtOrDefault(0), senderKeyValue.ElementAtOrDefault(1)); var result = await ErpEmailSender.SendEmailAsync( queue.To.Split(";").Select(a => a.Trim()).ToArray(), sender, null, mailBody, Options.MailSubject, attachments, true); if (result.Success) { queue.AwsMessageId = result.MessageId; } else { LogManager.LogWarning($"Mail could not be sent. Message: {result.ErrorMessage}", "MAILSEND", "KUYRUK", queue.Id, jobId); queue.AwsMessageId = result.ErrorMessage; } queue.SendStatus = result.Success; queue.SendTime = Clock.Now; await Repository.UpdateAsync(queue, cancellationToken: cancellationToken); } }