<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0">
    <channel>
        <title>نوشته های Reza Salari</title>
        <link>https://virgool.io/feed/@rza.attacker</link>
        <description>یه برنامه نویس ساده - عاشق جستجو و یادگیری</description>
        <language>fa</language>
        <pubDate>2026-06-07 11:12:26</pubDate>
        <image>
            <url>https://files.virgool.io/upload/users/418164/avatar/w9qAKx.jpg?height=120&amp;width=120</url>
            <title>Reza Salari</title>
            <link>https://virgool.io/@rza.attacker</link>
        </image>

                    <item>
                <title>معماری Domain Event کامل + مثال - قسمت اول</title>
                <link>https://virgool.io/@rza.attacker/%D9%85%D8%B9%D9%85%D8%A7%D8%B1%DB%8C-domain-event-%DA%A9%D8%A7%D9%85%D9%84-%D9%85%D8%AB%D8%A7%D9%84-%D9%82%D8%B3%D9%85%D8%AA-%D8%A7%D9%88%D9%84-v063wowkgmwg</link>
                <description>سلام دوستان - تو این مقاله نسبتا طولانی قراره یکم راجع به معماری Domain Event صحبت کنیم اینکه چی هست - کجا به کارمون میاد - چه ارتباطی با DDD و Event Sourcing داره - چطور پیاده سازیش کنیم اصلا ! و چه چالش هایی رو واسمون حل میکنه                                                                            DDDچیست  ؟معماری Domain Driven Design یک معماری بسیار مستحکم و قدرمند نرم افزاری می باشد که برای پروژه هایی با پیچیدگی های فراوان طراحی شده است. در این معماری پایین ترین لایه دیتابیس یا داده نمی باشد. بلکه پایین ترین لایه منطق های اصلی پروژه می باشد.به عنوان مثال فرض کنید قرار است یک بازی شطرنج را پیاده سازی کنید. در این بازی هر مهره چندین حرکت می تواند انجام دهد و از قواعد خاصی نیز پیروی می شود. ترکیب حرکت مهره ها میلیون ها حرکت را به وجود می آورد. قطعا پیاده سازی میلیون ها حرکت تست کد غیر ممکن است. بنابراین در اینجا بایستی هر مهره را به عنوان یک Value Object تعریف کرد و رفتار آن را مشخص کرد.مثال دیگری که می توان برای استفاده از معماری DDD گفت پیاده سازی سیستم های پیش بینی آب و هوا می باشد. در این سیستم ها برای پیش بینی هوا هزاران عامل وجود دارد که هر عامل میتواند بر عامل یا عوامل دیگر تاثیر گذار باشد. بنابراین برای پیاده سازی چنین سیستم هایی معمولا از معماری DDD استفاده می شود. 1مشکل:  بزارید اول مشکل رو بگم و بعد بریم سراغ مابقی ماجرا :فرض کنید شما یک سامانه فروشگاه آنلاین دارید که از میکروسرویس های مختلفی تشکیل شدهیکی از این میکروسرویس ها مسئول مدیریت سفارشات هست و یکی دیگه مسئول مدیریت انبار-حالا فرض میگیریم کاربر سفارش جدیدی ثبت میشه تو حالت عادی وضعیت سفارش باید به ثبت شده تغییر پیدا کنه اطلاعات خریدار و روش پرداخت بررسی یا اضافه کنیم موجودی کالای سفارش داده شده  از میکروسرویس انبار بگیریم و کم کنیمفاکتور سفارش صادر و به خریدار ارسال کنیمحال فرض کنیم تمامی موارد بالا با استفاده از درخواست های همزمان (synchorouns )بخواد انجام بشه - تو این حالت باید با استفاده از Api  های Restfull یا GRPC درخواست مستقیم به سایر میکروسرویس ها بزنیم و منتظر پاسخشون بمونیم این کار یکسری مشکل داره coupling بالا :میکروسرویس سفارشات باید دقیقا بدونه با چه API های دیگه ای ارتباط برقرار کنه و میکروسرویس چه پارامتر هایی ارسال و چه پاسخ هایی دریافت کند  این باعث محدود شدن مواردی مثل flexibilty - scabilty - maintaibilty میشه خطای بالا :میکروسرویس سفارشات وابسته به درست کار کردن مابقی میکروسرویس هاست و اگر یک میکروسرویس خطا داشته باشد یا قطع شود عملیات سفارش ناتموم و معلوم نیست چه اتفاقاتی دقیقا رخ داده این اتفاق باعث inconsistency و دشواری rollback در صورت خطای سامانه میشود عملکرد پایین: میکروسرویس سفارشات باید منتظر پاسخ سایر میکروسرویس ها باشه تا عملیات تکمیل بشه این کار باعث کندشدن پاسخگویی به درخواست های کاربر و ضعف تجربه کاربری هست                               حالا فرض میگیریم این کار رو با رویداددامنه انجام میدیم....1- میکروسرویس سفارشات پس از ثبت سفارش یک رویداد دامنه تولید(OrderStartedDomainEvent) و منتشر میکند2- میکروسرویس خریداران با استفاده از یک Domain Event Handler ( تو فصل طراحی توضیح میدم) عضو میشوند و پس از دریافت خودکار این رویداد چک میکنند عملیات ثبت سفارش موفق بوده یا خیر 3- میکروسرویس انبار هم با استفاده از یک Domain Event Handler به اسم updateStockWhenOrderStartedDomain() به این ایونت هندلر عضو میشوند و پس از دریافت آن خودکار موجودی کالا را کاهش میدن4- همینطور میکروسرویس فاکتور و همین اتفاقات - دریافت رویداد - ایجاد فاکتور و ارسال ... مزایا : عملکرد بالا : میکروسرویس سفارشات نیازی ندارد که منتظر پاسخ سایر میکروسرویس ها باشد تا عملیات را تکمیل کند هر میکروسرویس بصورت غیرهمزمان  (asynchoronus ) و مستقل Domain Event های خود را پردازش میکند - این باعث افزایش سرعت پاسخگویی به درخواست های کاربران و بهبود تجربه کاربری میشودخطای پایین : میکروسرویس سفارشات وابسته به درست کار کردن میکروسرویس های دیگر نیست اگر یک میکروسرویس قطع یا خطا داشته باشد عملیات سفارش قطع نمیشود و تاثیری ندارد روی آن - این باعث کاهش ناسازگاری (inconsistency ) و اسانتر شدن عملیات رول بک میشودخب  Domain Event (رویداد دامنه )چیست ؟طبق تعریف مایکروسافت رویداد چیزی هست که تو گذشته اتفاق افتاده و رویداد دامنه اتفاقی هست که تو یک دامنه افتاده و میخوایم سایر بخش های در حال پردازش همون دامنه بهش اطلاع بدیم ! دامنه : &quot;حوزه دانش یا فعالیت&quot;. با کمی عمیق شدن، دامنه در حوزه مهندسی نرم افزار معمولاً به موضوع و هدفی که برنامه ی نرم افزاری در آن اعمال می شود، اشاره داردطبق تعریف مارتین فولر بزرگ !  Captures the memory of something interesting which affects the domainما هرچیزی که فکر میکنیم با دامنه سروکار داره رو باید ثبت کنیم (مثال معروف GIGO)- ماهیت یک رویداد دامنه هم همین هست  که از آن برای ثبت مواردی استفاده می‌کنیم که  باعث تغییر در وضعیت برنامه‌ای که در حال توسعه آن هستیم بشود.رویداد های دامنه رو نباید با integration Event ها اشتباه گرفت - integration Event  ها زمانی استفاده میشوند که شما نیاز دارید یک رویداد رو بصورت غیرهمزمان و خارج از پردازش فعلیتون منتشر کنیدبرای مثال بین چندتا microservice , Bounded Context یا حتی برنامه های مختلفویژگی های Domain Event :آنها Immutable و یا غیر قابل تغییر هستند. دلیل این موضوع هم منطقی است چرا که اتفاقی که افتاده است را نمیتوان تغییر داد.دارای یک Time Stamp هستند که مشخص کننده زمان رخ دادن Domain Event مورد نظر است.میتوانند دارای یک ID منحصر به فرد باشند که با استفاده از آن بتوانیم یک Event را از یک Event دیگر تمیز بدهیم. این موضع بستگی به نوع Domain Event و همچنین نحوه توزیع شدن Event ها دارد.توسط Aggregate Root ها و یا Domain Service ها منتشر و یا Publish میشوند. در رابطه با این موضوع بعدا بیشتر صحبت میکنیم. مزایا : بنظرم بزرگترین وبهترین مزایایی که داره قابل گسترش بدون سیستم هست شما میتونید n تا Business Logic مختلف رو با فقط با اضافه کردن Domain Event Listener بیشتر بدون تغییر در داخل کد های از قبل موجود انجام بدیم - گسترش کد بدون تغییر کد های قبل یکی از اصول Solid بود( Open Close Principle) شاید با خودتون بگید خب چه کاریه اصلا ! همون اول هرچی ایونت و بیزینسی که مدیر دامنه بهمون میگه رو داخل کد تزریق میکنیم اما ممکنه  اصل Yagni که مخفف You aren&#x27;t gonna need it را زیر پا بگذارید. روش بهتر اینه است که برنامه باز باشه تا بتونیم به راحتی در صورت لزوم Domain Event های جدید را اضافه و سپس انتشار بدیمبخش های مختلف سیستم رو میتونیم جدا کنیم وابستگی و اتصالات مستقیم رو کاهش بدیم و سیستم قابل توسعه تری داشته باشیم قوانین تجاری دامنه رو جدا از خود دامنه و بدون اسیب زدن بهش میتونیم تغییر بدیمبه زبون ساده تر فرض کنید یک سایت فروشگاهی داریم و هرکدوم از فعالیت هایی که مستقل از هم هستند رو میتونیم دامنه در نظر بگیریم - دامنه کاربران - دامنه سفارشات - دامنه خرید - دامنه ارسال و .. شکل بالا بهتون نشون میده که چطوری میشه consistency رو بین چند مجموعه تو یک دامنه بدست آورد هرزمان که سفارش جدید کاربر ثبت بشه مجموعه  Order Aggregate یک رویداد OrderStarted رو منتشر میکنه و متناوبا میتونیم بقیه رویداد ها رو هم کنترل کنیم مثال اگر تعداد کالای درخواستی زیاد بود رویداد مجزا تولید کنیمچه زمانی استفاده کنیم ؟هر زمانی که سامانه ای که در حال پیاده سازیش هستید یک سامانه توزیع شده با coupling پایین هست که نیاز به ارتباط و تبادل داده بین بخش های مختلف رو داره سامانه نیاز به پردازش رویداد های غیرهمزمان با سرعت بالا رو داره سامانه با نیازبه بروزرسانی قوانین دامنه به صورت صریح و مبتنی بر زبان رایج کسب کار هستیمو نیاز داریم به اثرات جانبی تغییرات در دامنه اهمیت زیادی بدیم و واضح پیاده سازی کنیمگزارش کاملی از عملکرد سیستم بخوایمتو قسمت های بعدی میریم برای پیاده سازی یک نمونه نسبتا ساده - به همراه تست و نتیجه ! سعی کردم خلاصه و قابل فهم باشه - اگر مشکل یا ایرادی بود عذرخواهی میکنم ازتون و قسمت های بعدی اصلاح میشه - لطفا نظرتون رو حتما بگید خوشحال میشم منابع : https://medium.com/@mena.meseha/use-domain-events-in-microservices-fb99a16ed590  https://learn.microsoft.com/en-us/dotnet/architecture/microservices/microservice-ddd-cqrs-patterns/domain-events-design-implementation  https://www.martinfowler.com/eaaDev/DomainEvent.html </description>
                <category>Reza Salari</category>
                <author>Reza Salari</author>
                <pubDate>Fri, 26 May 2023 12:32:31 +0330</pubDate>
            </item>
                    <item>
                <title>EventEmitter همه چی راجع به</title>
                <link>https://virgool.io/Only-js/eventemitter-%D9%87%D9%85%D9%87-%DA%86%DB%8C-%D8%B1%D8%A7%D8%AC%D8%B9-%D8%A8%D9%87-xijqtjhx4tkc</link>
                <description>خود عکس کامل داره میگه چخبره:))سلام رفقا ، این اولین نوشته ام هست امیدوارم مفید باشه ، سوتی چیزی دیدین حتما بگید درستش کنماقا ما یه هفته ای بود درگیر یه اصطلاحی شده بودیم اونم EventEmitter ها ! خلاصه ازین بپرس ازون بپرس مگه این رو میشد بفهمی :/ خلاصه نشد اومدیمو تو مقالات مدیوم ( هَوو ویرگول:دی) فهمیدیم حالا میزارم که بچها خودمونم یاد بگیرن همونطور ک میدونید nodejs یه یجور Runtime Env هست که از معماری asynchronous استفاده میکنه خب حالا این ایونت ها کجا بدردمون میخوره ، فرض کنید شما یه کال بک دارید که هرموقع ک کال شده میخواید ازش یه استفاده ببرید واسه اینکه اینکارو انجام بدید باید اون تابع رو async کنید و کال بک رو await یا روش های دیگه ... اما یه موقع هایی هست شما بین کال کردن و کال بک گرفتن میخواید پروسستون سریعتر بشه یه مثال میزنم: فرض کنید  یه کاربرقراره تو سایتتون رجیستر کنه خب نحوه کار اینه فرم ارسال میشه ولیدیت میشه مجدد برمیگرده و ثبت نام ولی شما میخواید تو این بین هرکاربر رو مشخصاتش رو مثلا از استک بگیرید واسه این کار باید کلاینت رو منتظر نگه داشت؟؟ نه طبیعتا ! خب کاری  ک اینجا میکنیم اینه ک یه رویداد (event) تعریف میکنیم که هربار تابع ما کال بک برگشت داد ، این ایونت اجرا بشه و رویدادمون رو اجرا کنه ، مثال دوم : فرض کنید قراره یه سیستم مدیریت بلیط برای کنسرت ( ترجیحا شایع) بسازید خب بریم بسازیم :)const EventEmitter = require(&amp;quotevents&amp;quot);

class TicketManager extends EventEmitter {
    constructor(supply) {
        super();
        this.supply = supply;
    }

    buy(email, price) {
        this.supply--;
        this.emit(&amp;quotbuy&amp;quot, email, price, Date.now());
    }
}
module.exprots = TicketManager

خب اومدیم خط اول ماژول رو فراخوانی کردیم تو خط دوم یک کلاس ساختیم که از ماژول ما ارث بری کنه متدهاشو ... سازنده ساختیم بابت ورودی های کلاسمون ،کاربرد سوپر هم برای اینه ک به ارث ببر متد های EventEmitter رو داخل کلاس خودمون یه متد buy گزاشتیم که ایمیل خریدارو مبلغی که پرداخت کردند برای بلیط رو بفرستیم واسشون بعدش عرضه کردن بلیط رو یکی کاهش میدیم :/ بعدشم صادرش کردیم  خب تو فایل بعدیمون require میکنیم و ازش یک نمونه میسازیم و به تعداد بلیط هایی ک داریم بهش مقدار میدیمconst TicketManager = require(&amp;quot./ticketManager&amp;quot);

const ticketManager = new TicketManager(10);

ticketManager.on(&amp;quotbuy&amp;quot, () =&gt; {
    console.log(&amp;quotSomeone bought a ticket!&amp;quot);
});حالا وقتشه رویدادمون ران بشهticketManager.buy(&quot;test@email.com&quot;, 20);خب خروجی جالب شد Someone bought a ticket!به همین راحتی هربار که buy رو مقداریم یعنی اینکه یه نفر بلیط مارو خریده و ارزش بلیط هارو کم میکنیم یسری متد داخل کدامون بود ک همشو توضیح میدیم emitter.addListener(event, listener)         برای رویدادی که مشخص کردیم یک شنونده اضافه می کندemitter.on(event, listener)   این متد هم دقیقا کاربرد بالا رو دارد وهمچینن چک نمی کند که ایا شنونده هست یا نهemitter.on(event, listener)                                     یک شنونده را یک بار برای این رویداد اجرا می کندخیلی زیاد هستن نمیشه همشونو گفت خودتون برید R&amp;D  ، امیدوارم حداقل باعث بشه اینا یه سطح اشنایی داشته باشید سوتی بود بگید ناراحت نمیشم : )))  منابع :  https://www.tutorialsteacher.com/nodejs/nodejs-eventemitter  https://nodejs.org/api/events.html#events_events</description>
                <category>Reza Salari</category>
                <author>Reza Salari</author>
                <pubDate>Sat, 28 Nov 2020 10:56:42 +0330</pubDate>
            </item>
            </channel>
</rss>