TGViewer
C# Geeks (.NET) C# Geeks (.NET) @csharpgeeks · 550 subscribers
Post #441 165
🚀 نحوهٔ انتشار (Publish) Domain Eventها با EF Core

یک راه‌حل زیبا برای انتشار Domain Eventها استفاده از EF Core است.
از آنجا که EF Core مانند یک Unit of Work عمل می‌کند،
می‌توانید از آن برای جمع‌آوری تمام Domain Eventهای موجود در تراکنش فعلی و انتشار آن‌ها استفاده کنید.

من دوست ندارم این فرآیند را پیچیده کنم،
بنابراین به سادگی متد SaveChangesAsync را override می‌کنم تا بعد از ذخیره شدن تغییرات در پایگاه داده، Domain Eventها منتشر شوند.
البته می‌توانید از interceptor نیز استفاده کنید.
public class ApplicationDbContext : DbContext
{
public override async Task<int> SaveChangesAsync(
CancellationToken cancellationToken = default)
{
// چه زمانی باید Domain Eventها را منتشر کنید؟
//
// 1. قبل از فراخوانی SaveChangesAsync
// - Domain Eventها بخشی از همان تراکنش هستند
// - تضمین immediate consistency
// 2. بعد از فراخوانی SaveChangesAsync
// - Domain Eventها در تراکنش جداگانه اجرا می‌شوند
// - eventual consistency
// - احتمال خطا در Handlerها

var result = await base.SaveChangesAsync(cancellationToken);

await PublishDomainEventsAsync();

return result;
}
}

مهم‌ترین تصمیمی که در این مرحله باید بگیرید این است که چه زمانی Domain Eventها منتشر شوند.

من شخصاً ترجیح می‌دهم بعد از فراخوانی SaveChangesAsync آن‌ها را منتشر کنم،
یعنی پس از آن‌که تغییرات در پایگاه داده ذخیره شدند.

این کار البته معایب و مزایایی دارد 👇

✅ Eventual consistency:
چون پیام‌ها پس از پایان تراکنش اصلی پردازش می‌شوند.

⚠️ ریسک ناسازگاری داده‌ها (Database inconsistency): چون ممکن است اجرای Domain Eventها با خطا مواجه شود.
با eventual consistency می‌توانم کنار بیایم،
اما ریسک inconsistency در پایگاه داده موضوع مهمی است.
برای حل این مشکل می‌توان از الگوی Outbox استفاده کرد 💡

در این الگو، تغییرات در پایگاه داده به‌صورت اتمیک (Atomic) به همراه Domain Eventها (به عنوان پیام‌های Outbox) ذخیره می‌شوند.
سپس Domain Eventها به صورت ناهمزمان (asynchronously) توسط یک background job پردازش می‌شوند.

اگر می‌خواهید بدانید داخل متد PublishDomainEventsAsync چه اتفاقی می‌افتد 👇
private async Task PublishDomainEventsAsync()
{
var domainEvents = ChangeTracker
.Entries<Entity>()
.Select(entry => entry.Entity)
.SelectMany(entity =>
{
var domainEvents = entity.GetDomainEvents();

entity.ClearDomainEvents();

return domainEvents;
})
.ToList();

foreach (var domainEvent in domainEvents)
{
await _publisher.Publish(domainEvent);
}
}

🧩 نحوهٔ Handle کردن Domain Eventها

با تمام زیرساختی که تا اینجا ایجاد کردیم،
اکنون آماده‌ایم که Handler مربوط به Domain Eventها را پیاده‌سازی کنیم.
خوشبختانه این مرحله ساده‌ترین بخش کار است ✨

کافی است کلاسی بسازید که <INotificationHandler<Tرا پیاده‌سازی کند
و نوع Domain Event خود را به عنوان پارامتر generic مشخص نمایید.

در مثال زیر، یک Handler برای CourseCompletedDomainEvent داریم
که پس از وقوع Domain Event، یک CourseCompletedIntegrationEvent منتشر می‌کند
تا سایر سیستم‌ها را مطلع سازد 👇
public class CourseCompletedDomainEventHandler
: INotificationHandler<CourseCompletedDomainEvent>
{
private readonly IBus _bus;

public CourseCompletedDomainEventHandler(IBus bus)
{
_bus = bus;
}

public async Task Handle(
CourseCompletedDomainEvent domainEvent,
CancellationToken cancellationToken)
{
await _bus.Publish(
new CourseCompletedIntegrationEvent(domainEvent.CourseId),
cancellationToken);
}
}
More from @csharpgeeks
  1. Sep 22, 2026یه مدتی قراره از دنیای NET. فاصله بگیرم، چون وقتشه برم سربازی. راستش نمیدونم این مدت رو چج…
  2. Sep 20, 2026🔥 حالا مشکل اصلی: Alert Storm فرض کن Database از دسترس خارج شده. ۱۰۰ Pod داری. هر Pod می‌…
  3. Sep 20, 2026🚨 طراحی سیستم Monitoring و Alerting در یک سیستم بزرگ فرض کن ساعت ۳ صبح است. سیستم شما با…
  4. Sep 19, 2026#Engineering_Leadership تصمیم نگرفتن هم یک تصمیم است یه چیز عجیب توی تیم‌های مهندسی: گاهی…
  5. Sep 19, 2026☑ چک‌لیست آماده‌سازی تیم، فرایندها و زیرساخت برای توسعه با AI توجه: هیچ چک‌لیستی جهان‌شمول…
  6. Sep 19, 2026📌پایان یک انتظار طولانی: اعتبارسنجی ناهمگام (Async Validation) در NET 11.
Threads Profile ViewerView any public Threads profile without an account.Open ThreadLook →Writing with AI? Make it sound human.Metric37 rewrites AI drafts so they read naturally. Free AI detector, 1,500 words free.Try Metric37 →