<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0">
    <channel>
        <title>نوشته های Ahmad Safari</title>
        <link>https://virgool.io/feed/@sargashte118</link>
        <description></description>
        <language>fa</language>
        <pubDate>2026-04-15 08:14:53</pubDate>
        <image>
            <url>https://files.virgool.io/upload/users/946977/avatar/RIf6QJ.jpg?height=120&amp;width=120</url>
            <title>Ahmad Safari</title>
            <link>https://virgool.io/@sargashte118</link>
        </image>

                    <item>
                <title>معروف ترین استراتژی‌های برنچینگ در Git</title>
                <link>https://virgool.io/@sargashte118/%D9%85%D8%B9%D8%B1%D9%88%D9%81-%D8%AA%D8%B1%DB%8C%D9%86-%D8%A7%D8%B3%D8%AA%D8%B1%D8%A7%D8%AA%DA%98%DB%8C-%D9%87%D8%A7%DB%8C-%D8%A8%D8%B1%D9%86%DA%86%DB%8C%D9%86%DA%AF-%D8%AF%D8%B1-git-k4dwrasm6ksi</link>
                <description>معروف ترین استراتژی‌های برنچینگ در Git اصول غیرقابل مذاکره در Trunk-Basedیک شاخه اصلی (main) منبع حقیقت است.تغییرات کوچک و پرتکرار به main می‌رسند.برنچ‌ها اگر وجود دارند خیلی کوتاه‌عمر هستند (ساعت‌ها تا حداکثر ۱–۲ روز).«کار ناتمام» را با Feature Flag / Toggle و Backward Compatibility هندل می‌کنیم، نه با برنچ طولانی.کیفیت با گیت‌های اتومات + کدریویو سبک حفظ می‌شود، نه با فازهای طولانی فریز.1) ساختار ریپو و برنچینگ استانداردشاخه‌هاmain (یا trunk): تنها شاخه دائمیshort-lived branches (اختیاری اما رایج): feature/&lt;ticket&gt; یا fix/&lt;ticket&gt; با عمر کوتاهrelease branch (فقط در صورت نیاز، موقتی): وقتی production از یک commit قدیمی‌تر است یا نیاز به patch سریع روی نسخه منتشرشده دارید.قانون طلایی برنچ‌هافیچر برنچ طولانی نداریم.اگر کاری بزرگ است: به چند PR کوچک + feature flag بشکن.2) از صفر تا صد جریان توسعه (Development Flow)مرحله 1: برنامه‌ریزی و شکستن کارچه چیزهایی اینجا هندل می‌شود؟شکستن فیچر بزرگ به “vertical slices” (قابل merge شدن)تعریف flagهاتعریف migration plan دیتابیس (اگر هست)تعریف معیار Done و تست‌هاخروجی استاندارد:هر slice یک Ticket + یک PR کوچکمرحله 2: پیاده‌سازی روی برنچ کوتاه‌عمر یا مستقیم روی mainاستاندارد رایج:تیم‌های کوچک: مستقیم روی main با commits کوچک + CIتیم‌های متوسط/بزرگ: برنچ کوتاه + PRفیچرهای نیمه‌کاره چطور merge می‌شن؟با Feature Flag:flag پیش‌فرض OFFمسیرهای جدید پشت flagUI/endpoint جدید hidden یا limitedمرحله 3: تست‌ها در چه مرحله‌ای و چگونه؟بهترین استاندارد در trunk-based اینه که «تست‌ها نزدیک به کد» و اتومات باشند:A) قبل از PR (لوکال)unit testslint/formattype check (اگر دارید)اجرای quick smokeB) در CI روی PRگیت‌های لازم (Minimum Standard):Build ✅Unit tests ✅Lint/Static analysis ✅Security basic: dependency scan / SAST سبک ✅حداقل یک لایه integration/contract سریع ✅Coverage gate (اختیاری ولی مفید) ✅C) بعد از merge روی mainتست‌های سنگین‌تر (integration گسترده‌تر)e2e/smoke روی محیط stagingperformance sanity (اگر مهمه)نکته: e2e را کم اما مؤثر نگه دارید (شکننده نشه).مرحله 4: کدریویو استاندارد در Trunk-Basedکدریویو هست، ولی سبک، سریع، با SLA.قواعد پیشنهادی:PR کوچک (ترجیحاً &lt; ۲۰۰–۴۰۰ خط تغییر)۱ Reviewer کافی (برای تغییرات معمول)۲ Reviewer برای تغییرات حساس (Security/Payments/Core)Reviewer روی این‌ها تمرکز کند:correctness &amp; edge casesbackward compatibilityتست کافیخوانایی/maintainabilitymigration safetyflag درستAnti-pattern:PR بزرگ و چندروزه → عملاً می‌شه mini-waterfall3) ادغام (Merge) و قوانین محافظت از mainBranch Protection استانداردmerge فقط با CI greenحداقل ۱ approvalno direct push (برای اکثر تیم‌ها)squash merge یا rebase merge (سلیقه‌ای، ولی تاریخچه تمیز مهمه)commit message با ticket/semantic (مفید برای versioning)4) CI/CD استاندارد: از merge تا releaseمرحله 1: بعد از mergebuild artifact (docker image / package)ثبت artifact با یک شناسه:git_shabuild numberdeploy خودکار به stagingمرحله 2: QA روی stagingاستاندارد:smoke + regression کوتاه (روی flows حیاتی)exploratory روی تغییرات جدیداگر feature پشت flag است:flag را در staging روشن می‌کنند یا برای user گروهی باز می‌کنندمرحله 3: Production releaseدو مدل استاندارد:مدل A) Continuous Deployment (پیشرفته)هر merge با گیت‌ها → مستقیم تا prod (با canary/flags)مدل B) Continuous Delivery (رایج‌تر)هر merge آماده انتشار استانتشار با “promote” کردن همان artifact انجام می‌شودمعمولاً روزانه/هفتگی “release train”5) Tag گذاری و Versioning استانداردتگ‌ها چرا؟برای اینکه بگیم کد دقیقا چه نسخه‌ای روی prod رفته.استاندارد معمول:روی همان commit که deploy می‌شود:vMAJOR.MINOR.PATCH (SemVer)یا release-2026.02.23-1 (Calendar Versioning)قانون مهم:تگ روی main است (یا روی release branch موقت)artifact باید قابل trace باشد: tag -&gt; commit -&gt; build -&gt; deployRelease Notesاتومات از commit messages/PR titlesیا از labels (feature/fix/breaking)6) Hotfix / Bugfix در trunk-basedاگر باگ در main هم هستPR کوتاه → merge main → deployاگر prod روی commit قدیمی استایجاد release/&lt;version&gt; موقت از همان tagpatch روی آنdeploy patchبعد همان patch را به main هم merge/cherry-pick می‌کنیم7) Multi-tenant و نسخه‌ها (Versioning در مولتی‌تننت)این بخش خیلی مهمه چون “نسخه برای همه” همیشه درست نیست.سناریوی استاندارد 1: یک کدbase، رفتار متفاوت per-tenantراه استاندارد: Feature Flags / Tenant Configflag می‌تواند:globalper-tenantدرصدی (rollout)گروهی (beta users)مزیت: یک نسخه کد، rollout کنترل‌شده نیاز: سیستم flag/config قوی + observabilityسناریوی استاندارد 2: tenantهای خاص روی نسخه قدیمی می‌ماننداین معمولاً ضد الگوی trunk-based است، اما اگر مجبورید:به جای نگه داشتن شاخه‌های طولانی، بهتر:یک “compat layer” و feature flags داشته باشید  - و نهایتاً tenantها را migrate کنیداگر واقعاً نسخه‌های جدا لازم است:release branches طولانی می‌شود (نزدیک به GitFlow) و هزینه نگهداشت بالا می‌رودجمع‌بندی استاندارد: در trunk-based، multi-version per tenant را با toggle/config حل می‌کنند، نه branch.8) Database Migrations و Backward Compatibilityاین جاییه که خیلی‌ها زمین می‌خورند.استاندارد مهاجرت امن (Expand/Contract)Expand: ستون/جدول جدید اضافه کن (بدون شکستن قدیمی)اپلیکیشن همزمان از هر دو پشتیبانی کندداده‌ها backfill شوند (job)وقتی مطمئن شدی همه جا migrated:Contract: حذف ساختار قدیمیقانون طلایی:هر deploy باید با نسخه قبلی هم‌زیست باشد (rolling deploy safe)9) Code Freeze در trunk-basedترانک‌بیسد ذاتاً ضد “فریز طولانی” است، ولی در عمل گاهی لازم می‌شود.جایگزین استاندارد فریزبه جای فریز: Release cut + flagsmain ادامه پیدا می‌کندبرای release فقط artifact مشخص promote می‌شوداگر مجبور به فریز هستید:فریز خیلی کوتاه (ساعت‌ها) برای release window -فقط برای تغییرات riskyبقیه merge می‌شوند ولی پشت flag OFF می‌مانندبهترین استاندارد:“Freeze code” را تبدیل کنید به “Freeze flags” (یعنی قابلیت‌ها خاموش تا زمان آماده شدن)10) مدیریت ریسک انتشار: Canary / Blue-Green / Rollbackاستانداردهای کنترل ریسکCanary: درصد کمی از ترافیک tenantها/کاربرهاBlue-Green: دو محیط prod و سوئیچRollback:rollback به نسخه قبل باید سریع باشداما ترجیح trunk-based: roll forward (fix سریع)برای DB: rollback سخت است، برای همین expand/contract حیاتی است11) Observability و SRE gatesچیزهایی که خیلی‌ها در فرآیند نمی‌گویند ولی باید باشد:logging ساختاریافته با correlation idmetrics (latency, error rate, saturation)tracing (اگر microservices)alerts روی SLOهاhealth checks (readiness/liveness)automated smoke در prod بعد از deploy12) امنیت و Compliance در خط CI/CDحداقل استاندارد:dependency scanning (CVEs)secret scanningSAST سبکبرای تغییرات حساس: threat modeling سبک + manual review13) استاندارد تعریف “Done”یک تغییر فقط وقتی Done است که:merge شدهتحت flag/باگیت‌ها امن استتست‌ها پاس استروی staging دیده شده (حداقل smoke)release note قابل تولید استobservability برایش وجود دارد (حداقل log/metric)14) چک‌لیست نهایی: چیزهایی که باید حتماً در نظر بگیریداگر بخوام “همه موارد مهم” را یکجا لیست کنم:حتماً داشته باشیدFeature Flags (global + per-tenant + gradual rollout)CI gates قبل از mergebranch protectionartifact immutability + promotetagging/release notesexpand/contract برای DBcanary/blue-green یا حداقل rollback planmonitoring + alertingتعریف SLA برای code reviewمحدودیت اندازه PR + policy برنچ کوتاهمعمولاً فراموش می‌شودقرارداد API/contract tests بین سرویس‌هامدیریت schema version و backward compatibilityمدیریت config per tenantتست داده‌های واقعی‌نما (seed/masking)چرخه خاموش کردن flagها (flag debt)runbook برای incident + hotfix مسیر سریعیک نمونه “فرآیند استاندارد” خیلی خلاصه (قابل اجرا)Ticket → PR کوچکلوکال: unit+lintPR: CI gates + 1 reviewmerge به mainCI: build artifact + deploy stagingQA: smoke/regression (flags)promote به prod (canary اگر شد)tag نسخه + release notesmonitor + rollback/roll-forward planپاکسازی: حذف flagهای قدیمی، contract migrations0) اصول GitFlowدو شاخه دائمی و اصلی داریم:main (یا master): فقط کدِ Production-ready / نسخه‌های منتشرشدهdevelop: خط اصلی توسعه (Integration branch)توسعه روزمره روی develop جمع می‌شود.انتشار به prod از طریق release/*هات‌فیکس روی prod از طریق hotfix/*فیچرها روی feature/* انجام می‌شوند.1) ساختار شاخه‌ها و نقش هرکدامشاخه‌های دائمیmain: هر commit (یا هر tag) نماینده یک ریلیز واقعی است.develop: جدیدترین وضعیت توسعه و ادغام فیچرها.شاخه‌های موقتfeature/&lt;name&gt;: برای پیاده‌سازی فیچرهاrelease/&lt;version&gt;: آماده‌سازی انتشار (freeze نسبی)hotfix/&lt;version&gt;: رفع مشکل فوری روی production2) جریان کامل توسعه (Development Flow)مرحله 1: شروع فیچرچه می‌شود؟از develop برنچ می‌زنید:feature/ABC-123-user-profileاینجا چه چیزهایی هندل می‌شود؟کارهای بزرگ معمولاً روی همین feature branch انجام می‌شوند (برخلاف trunk-based که خرد می‌کردیم)Feature flag هم می‌تواند باشد، ولی GitFlow بدون flag هم کار می‌کند چون فیچر جداست.مرحله 2: تست‌ها در طول توسعهA) لوکال (توسعه‌دهنده)unit / lint / type checkB) CI روی feature branch / PR به developاستاندارد خوب:buildunitlintsecurity scan پایهintegration/contract سبکدر GitFlow معمولاً CI روی PR به develop خیلی مهم است چون develop محل ادغام چند فیچر است و سریع خراب می‌شود.مرحله 3: کدریویو و Merge به developاستاندارد GitFlow:feature → PR به developcode review (۱ یا ۲ نفر)merge وقتی CI سبز استنکته کلیدی GitFlow:اختلاف و conflict زیادتر از trunk-based می‌شود چون feature branch ها ممکن است طولانی باشند.3) Release آماده‌سازی (Release Branch + Code Freeze)اینجا GitFlow خیلی «رسماً» وارد فاز انتشار می‌شود.مرحله 4: ایجاد Release Branchوقتی تصمیم گرفتید نسخه منتشر کنید:از develop برنچ می‌زنید:release/1.8.0از اینجا به بعد چه اتفاقی می‌افتد؟Feature Freeze: فیچر جدید به این release branch اضافه نمی‌شود.فقط این‌ها مجاز است:باگ‌فیکستغییرات نسخه‌دهیمستندات releaseآماده‌سازی پکیج/کانفیگتست QA اینجا کجاست؟استاندارد GitFlow:QA اصلی و سنگین معمولاً روی release branch انجام می‌شود:regression کامل‌ترe2e گستردهتست‌های عملکردی/سازگاریUAT4) Tag گذاری و نسخه‌دهیمرحله 5: وقتی release آماده شدrelease/1.8.0 به main merge می‌شودروی main tag می‌زنیم:v1.8.0سپس:همان release/1.8.0 به develop هم merge می‌شود (تا باگ‌فیکس‌های مرحله release دوباره به خط توسعه برگردد)✅ این نقطه، “لحظه رسمی انتشار” در GitFlow است5) Hotfix / Bugfix در GitFlowسناریو: باگ در Productionاز main برنچ می‌زنید:hotfix/1.8.1fix انجام می‌شود + تستmerge به maintag:v1.8.1merge به develop هم انجام می‌شود (خیلی مهم!)چرا merge به develop؟ برای اینکه fix فقط روی prod نماند و در توسعه آینده گم نشود.6) Multi-tenant و نسخه‌های مختلف در GitFlowGitFlow ذاتاً کمک می‌کند نسخه‌ها جدا نگه داشته شوند، ولی هزینه دارد.حالت رایج 1: همه tenantها یک نسخهساده: release branch → main → همه tenantهاحالت رایج 2: tenantهای مختلف روی نسخه‌های مختلفدر GitFlow این ساده‌تر از trunk-based است، چون:می‌توانید release branch های جدا برای نسخه‌های مختلف نگه داریدیا maintenance branch برای نسخه‌های قدیمی بسازید (مثلاً support/1.7)ولی هزینه‌ها:backport bugfix ها به چند شاخهانفجار تست و QAمدیریت همگرایی سخت‌تر7) Database migrations در GitFlowهمان قواعد فنی پابرجاست، ولی زمان‌بندی فرق دارد:تغییرات schema بزرگ معمولاً در feature branch شروع می‌شوداما “قفل” و هماهنگی دیتابیس اغلب در release branch چک می‌شودبهترین استاندارد همچنان:expand/contractbackward compatible migrationsGitFlow باعث می‌شود migrationها ممکن است دیرتر “در کنار هم” تست شوند (چون feature branch ها جدا هستند).8) Code Freeze در GitFlow استاندارد استبرخلاف trunk-based که سعی می‌کنیم حذفش کنیم، در GitFlow:فریز عملاً بخشی از فرایند است:وقتی release branch ساخته شد، فیچر جدید وارد آن نمی‌شودطول فریز بستگی به QA/UAT دارد (ممکن است چند روز تا چند هفته)9) Rollback و کنترل ریسک انتشاردر GitFlow معمولاً:ریلیزها کمتر و بزرگ‌ترند → ریسک هر ریلیز بالاتر استانداردهای مفید:deploy مرحله‌ای (staging → prod)canary/blue-green (اختیاری ولی خیلی توصیه می‌شود)rollback به tag قبلی در main10) Observability / امنیت در GitFlowهمان ابزارها باید باشد، اما گیت‌ها معمولاً در چند نقطه اعمال می‌شود:PR به developPR به release/*merge به main (آخرین گیت)11) خلاصه مرحله‌ای GitFlow (End-to-End)feature/* از developتوسعه + تست + CIPR → merge به developزمان ریلیز: release/* از developQA سنگین روی release/* + باگ‌فیکس فقط همینجاmerge release/* → main + tag نسخهmerge release/* → develophotfix: hotfix/* از main → merge به main + tag → merge به develop12) مواردی که باید در GitFlow حواستان باشد (نکات واقعیِ پروژه‌ای)چیزهایی که GitFlow را سخت می‌کند:feature branch های طولانی → conflict زیادادغام دیرهنگام → باگ‌ها دیر دیده می‌شوندQA bottleneck روی release branchbackport های متعدد (اگر چند نسخه/tenant دارید)drift بین develop و main اگر mergeها دقیق انجام نشودنکته مهم: GitHub Flow خیلی نزدیک به Trunk-Based است، با این تفاوت که «همه چیز از طریق PR به main» انجام می‌شود و معمولاً یک develop دائمی نداریم.0) اصول GitHub Flowیک شاخه اصلی: mainmain همیشه deployable است (قابل انتشار)هر کار (feature/bugfix/hotfix) روی یک branch کوتاه‌عمر انجام می‌شودmerge فقط از طریق Pull Request + گیت‌های CI + reviewبعد از merge: deploy (یا اتومات یا با دکمه Promote)1) ساختار شاخه‌هاشاخه دائمیmainشاخه‌های موقتfeature/&lt;ticket&gt;-&lt;slug&gt;fix/&lt;ticket&gt;-&lt;slug&gt;chore/&lt;slug&gt;(اختیاری) release/&lt;version&gt; فقط اگر واقعاً لازم شد (در GitHub Flow اصولاً کمتر استفاده می‌شود)قانون: برنچ‌ها کوتاه، PR کوچک، merge سریع.2) جریان کامل توسعه (End-to-End)مرحله 1: شروع کاراز main برنچ می‌زنید:feature/ABC-123-checkout-discountsتغییرات را کوچک نگه می‌دارید (slice)اینجا چی باید هندل بشه؟اگر فیچر بزرگ است: از همین اول Feature Flag تعریف کنیداگر DB دارد: plan برای migration امن (expand/contract)مرحله 2: توسعه و کار ناتمام (Feature Branch و Feature Flags)GitHub Flow استانداردش اینه:برنچ هست، ولی کوتاه‌عمرفیچرهای نیمه‌کاره با Feature Flag merge می‌شوند (flag OFF)بهترین تمرین‌ها برای Flagdefault OFFقابلیت rollout (درصدی/گروهی/per-tenant)لاگ و متریک برای مسیر flaggedبرنامه جمع کردن flag بعد از rollout (flag debt)مرحله 3: تست‌ها (کجا و چطور)A) لوکال (توسعه‌دهنده)lint/formatunitquick smokeB) CI روی PR (استاندارد Minimum)این‌ها باید “Required checks” باشند:Build ✅Unit tests ✅Lint / Static analysis ✅Dependency/secret scan ✅Integration/contract tests سبک ✅C) بعد از merge به maindeploy به staging (یا preview)smoke/e2e کوتاه روی محیط واقعی(اختیاری) تست‌های سنگین‌تر شبانه/دوره‌ای3) کدریویو استانداردGitHub Flow = PR-centricPR کوچک۱ reviewer کافی (۲ تا برای قسمت‌های حساس)Review روی:correctnessتست کافیbackward compatibilitymigration safetyflag درستsecurity impactSLA پیشنهادی (استاندارد تیم‌های چابک):PRهای کوچک: همان روز4) Merge و محافظت از mainBranch protection استانداردRequired status checks (CI باید سبز باشد)Required approvals (حداقل ۱)منع force-pushمنع merge بدون reviewsquash merge یا merge commit (هر کدام، ولی consistency مهم است)5) Deploy و محیط‌ها (Staging / Preview / Prod)مدل‌های رایج در GitHub Flowمدل 1) Preview Environments برای هر PR (استاندارد مدرن)با باز شدن PR:یک محیط موقت ساخته می‌شود (URL جدا)QA و PO همانجا تست می‌کنندبا merge: محیط حذف می‌شودمدل 2) Staging مشترکبعد از merge، main اتومات روی staging می‌رودQA روی staging تست می‌کند✅ اگر زیرساخت دارید، Preview per PR بهترین تجربه را می‌دهد.6) QA در GitHub Flow دقیقاً کجاست؟QA معمولاً اینجاهاست:روی PR Preview (بهترین حالت)یا بعد از merge روی stagingاستاندارد عملیQA دستی بیشتر روی:regression مسیرهای حیاتیexploratoryUXcross-device/browserاتوماسیون بیشتر روی:smokee2e کوتاهcontract/integration7) Release به ProductionGitHub Flow دو حالت استاندارد دارد:حالت A) Continuous Deploymentهر merge به main → اتومات تا prod (با canary و flags)حالت B) Continuous Delivery (رایج‌تر)main همیشه آماده انتشار استانتشار با “promote” یک artifact انجام می‌شود (مثلاً دکمه Release)نکته مهم: در هر دو، main deployable می‌ماند.8) Tag گذاری و نسخه‌دهیاستانداردهاTag روی همان commit که به production رفتvMAJOR.MINOR.PATCH (SemVer)یا release-YYYY.MM.DD.N (CalVer)Release notesاز PR title + labels (feature/fix/breaking)یا Conventional Commits برای اتومات‌سازی version bump9) Hotfix / Bugfix در GitHub Flowچون main منبع واحد است، مسیر سریع:برنچ از main: hotfix/... یا fix/...PR کوچک + CI + review سریعmerge به maindeploy سریع (در صورت نیاز bypass حداقلی با policy مشخص)tag patch نسخهاگر prod روی commit قدیمی باشد (کمتر رایج در GH Flow):موقت release/&lt;version&gt; از tag ساخته می‌شود، patch می‌خورد، deploy می‌شود، بعد patch به main هم برمی‌گردد.10) Multi-tenant و نسخه‌ها در GitHub Flowاستاندارد بهتر (پیشنهادی)یک کدbase + یک pipelineتفاوت‌ها با:feature flags per tenantconfig per tenantgradual rollout per tenantاگر tenantها نسخه‌های جدا لازم دارنداین برخلاف روح GH Flow است و هزینه را زیاد می‌کندراه بهتر: tenantها را با flag/config کنترل کنید نه با شاخه‌های طولانیاگر مجبور شدید: release branch های پشتیبانی (maintenance) ایجاد می‌شود، ولی این شما را به سمت GitFlow می‌برد.11) Database migrations (خیلی مهم)همان استاندارد امن:Expand → Backfill → Switch → Contractdeploy باید backward compatible باشداگر rolling deploy دارید، کد جدید و قدیم باید هم‌زیست باشند12) Code Freeze در GitHub Flowاصولاً فریز طولانی نداریم.جایگزین استانداردrelease cut = انتخاب یک commit/artifact برای prodبقیه کارها می‌توانند merge شوند ولی:پشت feature flag OFF بماننداگر مجبورید:فریز کوتاه در پنجره انتشار (ساعت‌ها)نه چند روز13) کنترل ریسک: Canary / Blue-Green / Rollbackاستانداردهای توصیه‌شده:canary (درصدی یا per-tenant)blue-greenrollback به tag قبلیولی برای DB: rollback سخت → پس expand/contract حیاتی است14) امنیت، Compliance، Observabilityامنیت (گیت‌ها)secret scanningdependency scanningSAST سبکpolicy برای تغییرات حساس (۲ reviewer)observabilitylogging ساختاریافتهmetrics + alertingtracing (اگر microservices)post-deploy smoke در prod15) “Definition of Done” در GitHub Flowیک تغییر Done است اگر:PR merge شده به mainCI سبزreview انجام شدهروی preview/staging تست شده (حداقل smoke)release notes قابل تولید استمانیتورینگ/لاگ قابل اتکا داردflag plan دارد (enable/cleanup)16) خلاصه خیلی کوتاه GitHub Flow (کل مسیر)branch از mainتغییر کوچک + تست لوکالPR → CI checks + reviewmerge به maindeploy به staging/preview + QArelease/prod deploy (اتومات یا promote)tag version + release notesmonitor + rollback/roll-forwardcleanup flags + debtGitLab Flow ترکیبی از:سادگی GitHub Flowساختار محیطی (environment-based)و کنترل انتشار شبیه GitFlow🔹 تفاوت اصلی با GitHub Flow: در GitLab Flow معمولاً علاوه بر main، شاخه‌های محیطی مثل:productionstagingpreprodهم داریم.🧱 1) ساختار شاخه‌ها در GitLab Flowحالت استاندارد (Environment-based)شاخه‌های دائمیmain → توسعه جاریstaging → نسخه آماده تست نهاییproduction → آنچه روی prod استشاخه‌های موقتfeature/&lt;ticket&gt;fix/&lt;ticket&gt;hotfix/&lt;ticket&gt;🔄 2) جریان کامل توسعه (End-to-End)مرحله 1️⃣: شروع فیچراز main:feature/ABC-123-payment-refactorاینجا چه چیزهایی هندل می‌شود؟Feature Flag اگر فیچر بزرگ استبرنامه migration دیتابیستست‌های مورد نیازمرحله 2️⃣: توسعه + تستتست‌های لوکالunitlinttype checkCI روی Merge Request (MR)گیت‌های استاندارد:Build ✅Unit tests ✅Static analysis ✅Security scan (SAST/Dependency) ✅Integration test سبک ✅MR باید سبز باشد تا merge شود.مرحله 3️⃣: Merge به mainوقتی MR approve شد:feature → main🔹 main باید همیشه stable و deployable باشد.🚀 3) حرکت بین محیط‌ها (جذاب‌ترین بخش GitLab Flow)بعد از merge به main:مسیر استاندارد:main → staging → productionمرحله 4️⃣: انتقال به stagingدو مدل رایج:مدل A) Merge-based promotionmerge main → stagingمدل B) Tag-based promotion (بهتر)یک commit از main انتخاب می‌شودهمان commit به staging deploy می‌شودQA اینجا تست می‌کند:regressionsmokeexploratoryperformance sanityمرحله 5️⃣: انتشار به productionوقتی staging تأیید شد:staging → productionیا promote همان artifact.سپس:Tag زده می‌شود: v1.4.2🧪 4) QA دقیقاً کجاست؟در GitLab Flow سه نقطه دارد:1️⃣ Preview Environment (برای هر MR) 2️⃣ روی staging 3️⃣ smoke بعد از production deployاستاندارد حرفه‌ای:Preview per MR (اگر زیرساخت دارید)QA سنگین‌تر روی stagingsmoke سریع روی prod🛠 5) Hotfix در GitLab Flowسناریو: باگ روی Productionاز production:hotfix/1.4.3-critical-fixجریان:hotfix → productionhotfix → mainhotfix → stagingسپس:Tag: v1.4.3این یکی از تفاوت‌های مهم با GitHub Flow است: چون شاخه production داریم، hotfix از آن زده می‌شود.🏷 6) Tag گذاری و نسخه‌دهیاستانداردها:SemVer: vMAJOR.MINOR.PATCHیا Calendar VersioningTag باید:روی commit production باشدartifact traceable باشدRelease Notes:از MRهایا Conventional Commits🧩 7) Multi-Tenant در GitLab Flowحالت استاندارد توصیه‌شده:یک کدbaseیک productionتفاوت tenantها با:feature flagsconfig per tenantgradual rolloutاگر tenant نسخه متفاوت بخواهد:می‌توانید شاخه‌های maintenance داشته باشید: production-tenant-Aproduction-tenant-Bاما: ⚠ پیچیدگی و هزینه شدیداً بالا می‌رود.بهترین استاندارد: کنترل با config/flag نه با branch.🗄 8) Database Migration استانداردهمان قاعده طلایی:Expand → Migrate → Contractچون در GitLab Flow:ممکن است main جلوتر از production باشدباید migrationها backward compatible باشند❄ 9) Code Freezeدر GitLab Flow ممکن است:هنگام آماده‌سازی staging → productionفریز کوتاه روی staging داشته باشیداما:main می‌تواند جلو برودفقط merge به staging متوقف می‌شوداین مدل فریز سالم‌تر از GitFlow است.🛡 10) امنیت و Complianceدر CI GitLab معمولاً این stageها داریم:buildtestsecuritypackagedeploySecurity Gates:SASTDependency scanSecret detectionContainer scan📊 11) Rollout و کنترل ریسکاستانداردهای توصیه‌شده:Canary deploymentBlue/GreenFeature flags rolloutAuto rollback بر اساس metrics🧠 12) Definition of Done در GitLab Flowیک تغییر Done است اگر:MR approve شدهCI سبزmerge به maindeploy به stagingQA تأییدdeploy به productiontag خوردهمانیتورینگ سالم است📌 خلاصه نهایی GitLab Flowfeature → main → staging → productionHotfix:production → hotfix → production                ↘ main                ↘ stagingدر این مدل، هر محیط (Environment) یک شاخه جدا دارد. مثلاً:main        → توسعهstaging     → تستproduction  → محیط واقعیو کد با merge از یک محیط به محیط بعدی «حرکت» می‌کند.🧱 1) ساختار شاخه‌هاشاخه‌های دائمی (بر اساس محیط‌ها)main یا devstagingproductionشاخه‌های موقتfeature/&lt;ticket&gt;fix/&lt;ticket&gt;hotfix/&lt;ticket&gt;🔄 2) جریان کامل توسعه (End-to-End)مرحله 1️⃣ شروع فیچراز main:feature/ABC-123-add-discountاینجا چه چیزهایی باید هندل شود؟اگر فیچر بزرگ است → Feature Flag تعریف شوداگر تغییر DB دارد → migration plan (expand/contract)تست‌ها مشخص شوندمرحله 2️⃣ توسعه + تستلوکالunitlinttype checkCI روی PR به mainگیت‌های استاندارد:BuildUnit testsStatic analysisSecurity scanIntegration tests سبکبعد از سبز شدن:feature → main🚀 3) حرکت بین محیط‌هامرحله 3️⃣ انتقال به stagingوقتی آماده تست شد:main → stagingیا با merge مستقیم یا با انتخاب commit خاصروی staging چه اتفاقی می‌افتد؟Deploy اتوماتQA:regressionexploratorysmokeperformance sanityمرحله 4️⃣ انتقال به productionبعد از تایید QA:staging → productionDeploy prodTag نسخه: v1.6.0🧪 4) QA دقیقاً کجاست؟QA در این مدل معمولاً:1️⃣ روی staging 2️⃣ smoke سریع بعد از prodاگر زیرساخت دارید:Preview environment برای هر feature branch هم می‌شود اضافه کرد🛠 5) Hotfix در Environment Branchingاگر باگ در production پیدا شد:از production:hotfix/critical-fixجریان:hotfix → productionhotfix → staginghotfix → mainچرا merge به همه؟ چون اگر فقط روی production بماند، drift ایجاد می‌شود.🏷 6) نسخه‌دهی و TagTag باید:روی production زده شودقابل trace به commit و artifact باشداستاندارد:vMAJOR.MINOR.PATCHRelease notes:از PRهایا Conventional Commits🧩 7) Multi-Tenant در Environment Branchingحالت استانداردیک production branchتفاوت tenantها با:config per tenantfeature flag per tenantrollout تدریجیحالت پیچیده‌تراگر tenant نسخه جدا بخواهد:ممکن است branch های production جدا بسازید production-tenant-Aproduction-tenant-Bاما: ⚠️ هزینه نگهداری بالا و merge پیچیده می‌شود.بهترین روش: کنترل با config نه branch.🗄 8) Database Migrationخیلی مهم چون چند branch دائمی داریم.قانون طلایی:migration باید backward compatible باشدچون main ممکن است جلوتر از production باشدروش استاندارد:Add columnDeployBackfillSwitch codeRemove old column❄ 9) Code Freezeدر این مدل معمولاً:هنگام آماده‌سازی staging → production فریز کوتاه روی stagingاما:main می‌تواند جلو برودفقط merge به staging موقتاً متوقف می‌شود🛡 10) امنیت و Quality Gatesدر CI:BuildTestSecurity scanContainer scanSecret detectionبرای merge به production:Manual approvalChange log بررسی شود📊 11) Rollout و کنترل ریسکتوصیه‌ها:Canary deployBlue/GreenFeature flagsAuto rollback بر اساس metrics🧠 12) Definition of Doneیک تغییر Done است اگر:merge به mainmerge به stagingQA تاییدmerge به productiontag زده شدهمانیتورینگ سالم⚠ مشکلات رایج Environment Branchingچیزهایی که باید حواستان باشد:1️⃣ Drift بین branchها 2️⃣ Merge conflict زیاد 3️⃣ تاخیر در انتقال تغییرات 4️⃣ Hotfix فراموش شود به main برگردد 5️⃣ Release بزرگ و ریسکی شود📌 خلاصه مسیر کاملfeature → main → staging → productionHotfix:production → hotfix → production                      ↘ staging                      ↘ mainغیر از مدل‌هایی که گفتیم (Trunk-Based, GitFlow, GitHub Flow, GitLab Flow, Environment Branching)، چند مدل معروف و کاربردی دیگه هم هست که در دنیای واقعی استفاده می‌شن.من همه مدل‌های شناخته‌شده و پرکاربرد رو دسته‌بندی می‌کنم 👇1️⃣ 🧱 Centralized Workflow (مدل ساده متمرکز)4ایده:فقط یک شاخه اصلی (main)همه مستقیم روی آن commit می‌زنندمناسب برای:تیم‌های خیلی کوچکپروژه‌های داخلی سادهmigration از SVNضعف:ریسک بالابدون isolationمناسب CI/CD حرفه‌ای نیست2️⃣ 🌲 Forking Workflow (مدل متن‌باز)4ایده:هر توسعه‌دهنده یک fork جدا داردتغییرات از طریق Pull Request به ریپوی اصلی می‌آیدمناسب برای:پروژه‌های Open Sourceسازمان‌های بزرگ با دسترسی محدودمزیت:ایزوله کاملامنیت بالا3️⃣ 🏷 Release Train Model4ایده:انتشار در زمان‌های ثابت (مثلاً هر دو هفته)هر چیزی که آماده باشد سوار قطار می‌شودمعمولاً همراه با:Trunk-Basedیا GitHub Flowمناسب برای:SaaS با ریلیز منظمتیم‌های بزرگ که cadence مشخص دارند4️⃣ 🧩 Monorepo + Trunk Strategy4ایده:همه سرویس‌ها در یک repoیک trunkتغییرات کوچک و سریعاستفاده توسط:GoogleMetaنیاز:CI بسیار قویتست‌های سریع5️⃣ 🔀 Scaled GitFlow (مدل سازمانی بزرگ)نسخه‌ای از GitFlow با:maintenance branchsupport branchlong term support (LTS)مناسب برای:نرم‌افزارهای on-premiseمحصولاتی با نسخه‌های همزمان فعال6️⃣ 🧠 Hybrid Flow (مدل ترکیبی)خیلی از سازمان‌ها یک مدل pure ندارند.مثال‌ها:Trunk-Based + Environment BranchGitHub Flow + Release TrainGitFlow ساده‌شده بدون developدر عمل، اکثر شرکت‌ها hybrid هستند.7️⃣ 🔐 Long-Term Support Branching (LTS Model)ایده:یک نسخه پایدار برای مشتریان سازمانینسخه جدید برای مشتریان عمومیمثلاً:mainlts/1.0lts/2.0نیازمند:backport مرتبتیم جدا برای پشتیبانی نسخه قدیمی8️⃣ 🚀 Progressive Delivery Modelاین بیشتر استراتژی انتشار است تا برنچینگ، ولی مهمه:Feature FlagsCanaryA/B TestingGradual Rolloutمعمولاً روی:Trunk-BasedGitHub Flowسوار می‌شود.9️⃣ 🧪 Experimental Branching Modelبرای R&amp;D:branchهای آزمایشی بلندمدتmerge فقط اگر موفق شدکمتر رایج در محصول production-critical.📊 خلاصه مدل‌های معروفمدلپیچیدگیمناسب برایCentralizedکمتیم کوچکGitHub FlowکمSaaS سریعTrunk-BasedکمCI/CD پیشرفتهGitFlowزیادریلیز دوره‌ایGitLab Flowمتوسطسازمان محیط‌محورEnvironment Branchingمتوسطچند محیط سازمانیForkingمتوسطOpen SourceRelease Trainکمریلیز منظمLTS BranchingزیادEnterpriseHybridمتغیرسازمان‌های واقعی</description>
                <category>Ahmad Safari</category>
                <author>Ahmad Safari</author>
                <pubDate>Mon, 23 Feb 2026 12:35:33 +0330</pubDate>
            </item>
                    <item>
                <title>تفاوت بین Synthetic Events و Native Events در React</title>
                <link>https://virgool.io/@sargashte118/%D8%AA%D9%81%D8%A7%D9%88%D8%AA-%D8%A8%DB%8C%D9%86-synthetic-events-%D9%88-native-events-%D8%AF%D8%B1-react-lujzfxtodbky</link>
                <description>برای توضیح دقیقتر و جامعتر تفاوت بین Synthetic Events و Native Events در React، بیایم این دو مفهوم رو با جزئیات، مثالهای عملی، و دلایل استفاده React از Synthetic Events بررسی کنیم. هدف اینه که کاملاً روشن بشه این دو نوع رویداد چطور کار میکنن، چرا React از Synthetic Events استفاده میکنه، و چه مزیتهایی دارن.Native Events چیست؟Native Events رویدادهای خالصی هستن که مستقیماً توسط مرورگر (Browser DOM) تولید و مدیریت میشن. این رویدادها بخشی از API استاندارد DOM هستن و بستگی به مرورگر دارن (مثل Chrome، Firefox، یا Safari). هر مرورگر ممکنه این رویدادها رو کمی متفاوت پیادهسازی کنه، که میتونه باعث مشکلات سازگاری (cross-browser inconsistencies) بشه.ویژگیهای Native Events:مستقیماً به DOM واقعی وصلن و با دستوراتی مثل addEventListener مدیریت میشن.رفتارشون بستگی به مرورگر داره، مثلاً نحوه مدیریت event.preventDefault یا ویژگیهای event ممکنه تو مرورگرهای مختلف فرق کنه.مثال: رویدادهایی مثل click, input, keydown که مستقیماً تو DOM فعال میشن.مثال Native Event (بدون React):javascriptconst button = document.getElementById(&#039;myButton&#039;);
button.addEventListener(&#039;click&#039;, (event) =&gt; {
  console.log(&#039;رویداد کلیک:&#039;, event);
  console.log(&#039;نوع رویداد:&#039;, event.type); // &#039;click&#039;
  console.log(&#039;هدف:&#039;, event.target); // &lt;button id=&quot;myButton&quot;&gt;
});توضیح:اینجا یه رویداد click مستقیماً به یه عنصر DOM وصل شده.شیء event که دریافت میشه، یه شیء Native Eventه که مرورگر تولید کرده.رفتار این رویداد ممکنه تو مرورگرهای مختلف (مثلاً Internet Explorer قدیمی) کمی متفاوت باشه.Synthetic Events چیست؟Synthetic Events یه لایه انتزاعی (abstraction) هستن که React روی Native Events ساخته. به جای اینکه مستقیماً با رویدادهای مرورگر کار کنی، React یه نسخه استانداردشده و یکپارچه از رویدادها رو ارائه میده که رفتارشون تو همه مرورگرها یکسانه. این رویدادها به صورت wrapper دور Native Events ساخته میشن.ویژگیهای Synthetic Events:React یه شیء SyntheticEvent تولید میکنه که شبیه Native Eventه، ولی رفتارش استاندارد و cross-browserه.به جای اتصال مستقیم رویدادها به عناصر DOM، React یه سیستم رویداد مرکزی (event delegation) تو ریشه اپلیکیشن (root element) پیادهسازی میکنه.ویژگیهای استاندارد DOM (مثل event.target, event.preventDefault, event.stopPropagation) رو پشتیبانی میکنه، ولی با یه API یکپارچه.مثال Synthetic Event (در React):javascriptfunction Button() {
  const handleClick = (event) =&gt; {
    console.log(&#039;رویداد کلیک:&#039;, event);
    console.log(&#039;نوع رویداد:&#039;, event.type); // &#039;click&#039;
    console.log(&#039;هدف:&#039;, event.target); // &lt;button&gt;
    event.preventDefault(); // کار میکنه، مثل Native Event
  };

  return &lt;button ={handleClick}&gt;کلیک کن&lt;/button&gt;;
}توضیح:اینجا  یه Synthetic Eventه که React مدیریتش میکنه.شیء event که به handleClick پاس داده میشه، یه نمونه از SyntheticEventه که React ساخته.این شیء ویژگیهای مشابه Native Event (مثل target, type, preventDefault) داره، ولی React تضمین میکنه که رفتارش تو همه مرورگرها یکسانه.چطور React Synthetic Events رو پشت صحنه مدیریت میکنه؟React یه سیستم رویداد مرکزی و بهینه برای مدیریت Synthetic Events پیادهسازی کرده:Event Delegation (نمایندگی رویدادها):به جای اینکه رویدادها رو مستقیماً به هر عنصر DOM وصل کنه (مثل element.addEventListener)، React همه رویدادها رو به یه ریشه مرکزی (معمولاً document یا container اصلی اپلیکیشن) وصل میکنه.وقتی یه رویداد (مثل کلیک) تو DOM رخ میده، React اون رو میگیره، یه SyntheticEvent میسازه، و بر اساس ساختار Virtual DOM تشخیص میده کدوم کامپوننت باید این رویداد رو دریافت کنه.Pooling (استخر رویدادها):برای بهینهسازی عملکرد، React از یه Event Pool استفاده میکنه. یعنی شیءهای SyntheticEvent بعد از استفاده بازیافت میشن و دوباره استفاده میشن.به همین دلیل، اگه بخوای یه SyntheticEvent رو بعد از اتمام تابع نگه داری (مثلاً تو یه setTimeout)، باید از event.persist() استفاده کنی، وگرنه ویژگیهای رویداد null میشن.مثال:javascriptfunction Button() {
  const handleClick = (event) =&gt; {
    event.persist(); // نگه داشتن رویداد
    setTimeout&#40;(&#41; =&gt; {
      console.log(event.type); // بدون persist، این خط خطا میده
    }, 1000);
  };

  return &lt;button ={handleClick}&gt;کلیک کن&lt;/button&gt;;
}Cross-Browser Consistency:React تفاوتهای بین مرورگرها (مثل نحوه مدیریت رویدادهای خاص تو Safari در مقابل Chrome) رو استاندارد میکنه. مثلاً:اطمینان میده event.preventDefault() تو همه مرورگرها به یه شکل کار میکنه.ویژگیهایی مثل event.target یا event.currentTarget همیشه رفتار قابلپیشبینی دارن.تفاوتهای کلیدی Synthetic Events و Native EventsویژگیSynthetic Events (React)Native Events (مرورگر)مدیریتتوسط React مدیریت میشهمستقیماً توسط مرورگر مدیریت میشهسازگاری مرورگرهاکاملاً cross-browser و یکپارچهممکنه تو مرورگرهای مختلف متفاوت باشهاتصال رویداداز طریق event delegation به ریشه اپلیکیشنمستقیماً به عناصر DOM با addEventListenerبهینهسازیاستفاده از event pooling و Virtual DOMبدون بهینهسازی داخلیدسترسی به شیء رویدادمحدود به scope تابع (نیاز به persist)همیشه در دسترسهمثالonClick={handleClick}element.addEventListener(&#039;click&#039;, ...)چرا React از Synthetic Events استفاده میکنه؟React به دلایل زیر از Synthetic Events به جای Native Events استفاده میکنه:Cross-Browser Consistency (سازگاری بین مرورگرها):مرورگرهای مختلف (مثل Chrome، Firefox، یا Edge) ممکنه رویدادها رو به شکلهای کمی متفاوت مدیریت کنن. Synthetic Events یه API یکپارچه ارائه میدن که تو همه مرورگرها رفتار یکسانی داره.بهینهسازی عملکرد:Event Delegation: به جای اضافه کردن listener به هر عنصر DOM، React یه listener مرکزی تو ریشه اپلیکیشن (root) داره. این کار تعداد listenerها رو کاهش میده و حافظه کمتری مصرف میکنه.Event Pooling: بازیافت رویدادها باعث میشه مصرف حافظه کمتر بشه، مخصوصاً تو اپهایی با تعداد زیادی رویداد.هماهنگی با Virtual DOM:Synthetic Events با سیستم Virtual DOM و Reconciliation در React هماهنگن. React میتونه رویدادها رو با تغییرات state و رندرینگ همگام کنه.مدیریت سادهتر برای توسعهدهنده:با Synthetic Events، نیازی نیست توسعهدهنده نگران تفاوتهای مرورگرها یا جزئیات اتصال رویدادها باشه. مثلاً  تو React همیشه کار میکنه، بدون نیاز به مدیریت click یا touch به صورت جداگانه.پشتیبانی از قابلیتهای پیشرفته:Synthetic Events به React اجازه میدن قابلیتهایی مثل Concurrent Rendering (تو React 18) رو پیادهسازی کنه، چون میتونه اولویت رویدادها رو مدیریت کنه.مثال عملی: مقایسه Synthetic و Native Eventsفرض کن میخوای یه دکمه بسازی که با کلیک روش، یه پیام لاگ کنه و رفتار پیشفرض (مثل ارسال فرم) رو متوقف کنه.با Synthetic Events (React):javascriptfunction FormButton() {
  const handleClick = (event) =&gt; {
    event.preventDefault(); // متوقف کردن رفتار پیشفرض
    console.log(&#039;کلیک شد:&#039;, event.target);
  };

  return (
    &lt;form&gt;
      &lt;button ={handleClick}&gt;کلیک کن&lt;/button&gt;
    &lt;/form&gt;
  );
}توضیح:onClick یه Synthetic Eventه که React مدیریتش میکنه.event.preventDefault() تضمین میشه که تو همه مرورگرها به درستی کار میکنه.React رویداد رو از ریشه اپلیکیشن میگیره و به کامپوننت مربوطه پاس میده.با Native Events (JavaScript خالص):javascriptconst form = document.querySelector(&#039;form&#039;);
const button = document.querySelector(&#039;button&#039;);

button.addEventListener(&#039;click&#039;, (event) =&gt; {
  event.preventDefault(); // متوقف کردن رفتار پیشفرض
  console.log(&#039;کلیک شد:&#039;, event.target);
});توضیح:اینجا باید خودت رویداد رو به عنصر DOM وصل کنی.اگه مرورگر خاصی (مثلاً یه نسخه قدیمی) preventDefault رو متفاوت پیادهسازی کرده باشه، ممکنه مشکل پیش بیاد.تفاوت در عمل:تو React، نیازی نیست نگران پیدا کردن عنصر یا مدیریت تفاوتهای مرورگر باشی. Synthetic Event همهچیز رو ساده و یکپارچه میکنه.تو Native Event، باید خودت همهچیز (از اتصال رویداد تا مدیریت سازگاری) رو مدیریت کنی.چه زمانی از Native Events در React استفاده کنیم؟هرچند React معمولاً با Synthetic Events کار میکنه، گاهی ممکنه نیاز به Native Events داشته باشی:وقتی با کتابخانههای خارجی کار میکنی که مستقیماً با DOM کار میکنن (مثل jQuery یا Chart.js).برای رویدادهایی که React پشتیبانی نمیکنه (مثل رویدادهای خاص مثل resize روی window).وقتی نیاز به دسترسی مستقیم به DOM داری (مثلاً با ref).مثال استفاده از Native Event در React:javascriptimport { useEffect, useRef } from &#039;react&#039;;

function WindowResize() {
  const handleResize = () =&gt; {
    console.log(&#039;اندازه پنجره تغییر کرد:&#039;, window.innerWidth);
  };

  useEffect(() =&gt; {
    window.addEventListener(&#039;resize&#039;, handleResize);
    return () =&gt; window.removeEventListener(&#039;resize&#039;, handleResize);
  }, []);

  return &lt;div&gt;تغییر اندازه پنجره رو چک کن&lt;/div&gt;;
}توضیح:اینجا چون resize یه رویداد windowه و React مستقیماً براش Synthetic Event نداره، از Native Event استفاده کردیم.با useEffect مطمئن میشیم که listener موقع پاکسازی کامپوننت حذف میشه.جمعبندیNative Events: رویدادهای خالص مرورگر که مستقیماً به DOM وصلن و ممکنه تو مرورگرهای مختلف رفتار متفاوتی داشته باشن.Synthetic Events: wrapperهای React که رویدادهای Native رو استاندارد میکنن، با Virtual DOM هماهنگن، و رفتار یکپارچهای تو همه مرورگرها دارن.چرا Synthetic Events؟سازگاری بین مرورگرها.بهینهسازی عملکرد با event delegation و pooling.هماهنگی با Virtual DOM و سیستم رندرینگ React.سادهسازی توسعه با API یکپارچه.پشت صحنه: React رویدادها رو از ریشه اپلیکیشن مدیریت میکنه، SyntheticEvent میسازه، و با Virtual DOM و Reconciliation تغییرات رو اعمال میکنه.</description>
                <category>Ahmad Safari</category>
                <author>Ahmad Safari</author>
                <pubDate>Tue, 21 Oct 2025 12:14:59 +0330</pubDate>
            </item>
                    <item>
                <title>ری اکت پشت صحنه چطور رویکرد Declarative رو هندل می‌کنه</title>
                <link>https://virgool.io/@sargashte118/%D8%B1%DB%8C-%D8%A7%DA%A9%D8%AA-%D9%BE%D8%B4%D8%AA-%D8%B5%D8%AD%D9%86%D9%87-%DA%86%D8%B7%D9%88%D8%B1-%D8%B1%D9%88%DB%8C%DA%A9%D8%B1%D8%AF-declarative-%D8%B1%D9%88-%D9%87%D9%86%D8%AF%D9%84-%D9%85%DB%8C-%DA%A9%D9%86%D9%87-pxrgfuuoia06</link>
                <description>برای اینکه بفهمیم React پشت صحنه چطور رویکرد Declarative رو هندل میکنه، باید به نحوه کار داخلی React و مکانیزمهایی که برای مدیریت رندرینگ و آپدیت DOM استفاده میکنه نگاه کنیم. تو این پاسخ، من این فرآیند رو به زبون ساده و با جزئیات توضیح میدم و قدم به قدم نشون میدم که React چطور از کد Declarative (توصیفی) شما به آپدیتهای بهینه DOM میرسه. همچنین یه مثال عملی میذارم تا موضوع روشنتر بشه.چطور React رویکرد Declarative رو مدیریت میکنه؟وقتی تو React یه UI رو به صورت Declarative مینویسی (مثلاً با JSX و state)، شما فقط توصیف میکنی که UI باید چه شکلی باشه، و React پشت صحنه مسئولیت تبدیل این توصیف به تغییرات واقعی تو DOM رو بر عهده میگیره. این فرآیند چند مرحله کلیدی داره:JSX به JavaScript ترجمه میشه:JSX (که شبیه HTMLه) در واقع یه syntax sugar برای فراخوانی تابع React.createElementه. وقتی کد JSX مینویسی، کامپایلر (مثل Babel) اون رو به یه ساختار داده JavaScript به اسم React Element تبدیل میکنه.React Element یه شیء سبک (lightweight)ه که توصیف میکنه یه کامپوننت یا عنصر DOM باید چه شکلی باشه (مثلاً نوع تگ، props، و فرزندانش).// JSX&lt;div className=&quot;container&quot;&gt;سلام دنیا&lt;/div&gt;// تبدیل به:React.createElement(&#039;div&#039;, { className: &#039;container&#039; }, &#039;سلام دنیا&#039;);این شیء یه tree از React Elementها میسازه که بهش میگیم Virtual DOM.Virtual DOM و رندرینگ اولیه:Virtual DOM یه نسخه سبک و در حافظه (in-memory) از DOM واقعیه که React ازش برای مدیریت UI استفاده میکنه.وقتی کامپوننت رندر میشه (مثلاً با render یا createRoot)، React یه tree از React Elementها (Virtual DOM) میسازه که توصیف کاملی از UI بر اساس state و props فعلیه.تو رندر اولیه، React این Virtual DOM رو به DOM واقعی (real DOM) تبدیل میکنه و عناصر رو تو صفحه نمایش میده.Reconciliation (همگامسازی):وقتی state یا props تغییر میکنه، React یه Virtual DOM جدید میسازه که UI رو با state/propهای جدید توصیف میکنه.حالا React این Virtual DOM جدید رو با Virtual DOM قبلی مقایسه میکنه (به این فرآیند میگن Diffing). این مقایسه خیلی بهینهست، چون React از یه الگوریتم خاص (heuristic-based diffing) استفاده میکنه که فقط بخشهای تغییرکرده رو شناسایی میکنه.بعد از پیدا کردن تغییرات، React فقط بخشهای لازم از DOM واقعی رو آپدیت میکنه (به این میگن Reconciliation).بهینهسازی با Diffing:الگوریتم Diffing در React خیلی سریع عمل میکنه، چون:فقط کامپوننتهایی که props یا stateشون تغییر کرده رو دوباره رندر میکنه.از کلیدهای منحصربهفرد (key) تو لیستها استفاده میکنه تا تغییرات رو دقیقتر تشخیص بده.به جای بازنویسی کل DOM، فقط عملیاتهای ضروری (مثل تغییر متن، اضافه/حذف عنصر، یا آپدیت ویژگیها) رو انجام میده.Batch Updates (بهروزرسانیهای دستهای):تو React 18، آپدیتهای state به صورت خودکار دستهبندی (batch) میشن. یعنی اگه چند setState پشت سر هم فراخوانی بشن، React همه تغییرات رو جمع میکنه و فقط یه بار رندر میکنه تا عملکرد بهینه بمونه.Concurrent Rendering (در React 18):با معرفی createRoot و قابلیتهای Concurrent Rendering، React میتونه رندرینگ رو به صورت قابل وقفه (interruptible) انجام بده. مثلاً اگه یه آپدیت سنگین در جریان باشه و کاربر یه تعامل فوری (مثل تایپ) انجام بده، React میتونه رندر سنگین رو متوقف کنه و به تعامل کاربر اولویت بده.فرآیند قدم به قدم پشت صحنهبیایم با یه مثال ساده فرآیند رو مرحله به مرحله بررسی کنیم:کد نمونه (Declarative):import { useState } from &#039;react&#039;;

function Counter() {

  const [count, setCount] = useState(0);

  return (

    &lt;div&gt;

      &lt;p&gt;شمارنده: {count}&lt;/p&gt;

      &lt;button ={() =&gt; setCount(count + 1)}&gt;اضافه کن&lt;/button&gt;

    &lt;/div&gt;



}چطور React این کد رو هندل میکنه؟تبدیل JSX به React Elementها:وقتی کامپوننت Counter رندر میشه، JSX به یه ساختار JavaScript تبدیل میشه:React.createElement(&#039;div&#039;, null,  React.createElement(&#039;p&#039;, null, شمارنده: ${count}),  React.createElement(&#039;button&#039;, { : () =&gt; setCount(count + 1) }, &#039;اضافه کن&#039;)این یه tree از React Elementها میسازه که Virtual DOM اولیه رو تشکیل میده.رندر اولیه:React این Virtual DOM رو به DOM واقعی تبدیل میکنه و عناصر &lt;div&gt;, &lt;p&gt;, و &lt;button&gt; رو تو صفحه قرار میده.

  &lt;p&gt;شمارنده: 0&lt;/p&gt;

  &lt;button&gt;اضافه کن&lt;/button&gt;

&lt;/div&gt;

تغییر State (کلیک روی دکمه): وقتی کاربر روی دکمه کلیک میکنه، setCount(count + 1) فراخوانی میشه و count به 1 تغییر میکنه.React دوباره کامپوننت رو رندر میکنه (به صورت داخلی) و یه Virtual DOM جدید میسازه:React.createElement(&#039;div&#039;, null,  React.createElement(&#039;p&#039;, null, شمارنده: 1),  React.createElement(&#039;button&#039;, { : () =&gt; setCount(count + 1) }, &#039;اضافه کن&#039;)Diffing و Reconciliation:React Virtual DOM جدید رو با قبلی مقایسه میکنه:میبینه که &lt;div&gt; و &lt;button&gt; هیچ تغییری نکردن (props و ساختار همونه).فقط متن داخل &lt;p&gt; از شمارنده: 0 به شمارنده: 1 تغییر کرده.React فقط متن داخل &lt;p&gt; رو تو DOM واقعی آپدیت میکنه (مثلاً با textContent) و بقیه DOM رو دست نمیزنه.نتیجه در DOM:DOM واقعی به این شکل آپدیت میشه:&lt;div&gt;

  &lt;p&gt;شمارنده: 1&lt;/p&gt;

  &lt;button&gt;اضافه کن&lt;/button&gt;

&lt;/div&gt;

جزئیات فنیتر پشت صحنهFiber Architecture:از React 16 به بعد، React از یه معماری داخلی به اسم Fiber استفاده میکنه. Fiber یه ساختار دادهست که به React اجازه میده رندرینگ رو به واحدهای کوچکتر (fiber nodes) تقسیم کنه.این معماری به React امکان میده:رندرینگ رو متوقف کنه یا ادامه بده (برای Concurrent Rendering).اولویتبندی کنه (مثلاً تعاملات کاربر اولویت بالاتری دارن).تغییرات رو به صورت incremental اعمال کنه.Scheduler:React از یه ماژول داخلی به اسم Scheduler (معرفیشده تو React 18) استفاده میکنه تا وظایف رندرینگ رو زمانبندی کنه.مثلاً اگه یه آپدیت سنگین (مثل رندر یه لیست بزرگ) در جریان باشه، Scheduler میتونه اون رو به تعویق بندازه تا یه آپدیت فوری (مثل پاسخ به کلیک کاربر) انجام بشه.Batching خودکار:تو React 18، آپدیتهای state که تو یه رویداد (مثل کلیک) رخ میدن، به صورت خودکار دستهبندی میشن. این یعنی React فقط یه بار رندر میکنه، حتی اگه چندین setState فراخوانی بشه.مدیریت رویدادها (Synthetic Events):React یه سیستم رویداد مصنوعی (Synthetic Event) داره که رویدادهای DOM (مثل ) رو مدیریت میکنه. این سیستم به React اجازه میده رویدادها رو بهینهتر پردازش کنه و با state هماهنگ باشه.مثال پیشرفتهتر: لیست فیلترشدهبرای نشون دادن اینکه React چطور Declarative رو تو سناریوهای پیچیدهتر مدیریت میکنه، بیایم یه مثال از یه لیست فیلترشده رو بررسی کنیم:import { useState } from &#039;react&#039;;

function FilterList() {

  const [filter, setFilter] = useState(&#039;&#039;);

  const items = [&#039;سیب&#039;, &#039;موز&#039;, &#039;پرتقال&#039;, &#039;انگور&#039;];

  const filteredItems = items.filter((item) =&gt; item.includes(filter));

  return (

    &lt;div&gt;

      &lt;input

        type=&quot;text&quot;

        value={filter}

        ={(e) =&gt; setFilter(e.target.value)}

        placeholder=&quot;فیلتر...&quot;

      /&gt;

      &lt;ul&gt;

        {filteredItems.map((item) =&gt; (

          &lt;li key={item}&gt;{item}&lt;/li&gt;

        ))}

      &lt;/ul&gt;

    &lt;/div&gt;

  );

}

پشت صحنه چه اتفاقی میافته؟رندر اولیه:JSX به یه Virtual DOM تبدیل میشه که شامل یه &lt;div&gt;, یه &lt;input&gt;, و یه &lt;ul&gt; با تمام آیتمهای itemsه.React این Virtual DOM رو به DOM واقعی تبدیل میکنه.تغییر State (تایپ تو اینپوت):وقتی کاربر تو اینپوت تایپ میکنه (مثلاً &quot;سیب&quot;)، setFilter فراخوانی میشه و filter به &quot;سیب&quot; آپدیت میشه.React یه Virtual DOM جدید میسازه که فقط شامل &lt;li&gt;هایی میشه که با &quot;سیب&quot; همخونی دارن (مثلاً فقط &lt;li&gt;سیب&lt;/li&gt;).Diffing:React Virtual DOM جدید رو با قبلی مقایسه میکنه:میبینه که &lt;input&gt; تغییر کرده (مقدارش از &quot;&quot; به &quot;سیب&quot;).میبینه که &lt;ul&gt; تغییر کرده، چون حالا فقط یه &lt;li&gt; داره (به جای 4 تا).React از keyها (مثل key={item}) استفاده میکنه تا بفهمه کدوم &lt;li&gt;ها حذف شدن و کدوما موندن.آپدیت DOM:React فقط این تغییرات رو اعمال میکنه:مقدار value اینپوت رو به &quot;سیب&quot; آپدیت میکنه.سه &lt;li&gt; (موز، پرتقال، انگور) رو از &lt;ul&gt; حذف میکنه.این کار خیلی بهینهست، چون React کل &lt;ul&gt; رو از نو نمیسازه، فقط آیتمهای غیرضروری رو حذف میکنه.Concurrent Rendering (در React 18):اگه لیست خیلی بزرگ باشه (مثلاً 10,000 آیتم)، React میتونه رندرینگ &lt;ul&gt; رو به تکههای کوچکتر تقسیم کنه و اگه کاربر همزمان تایپ کنه، رندرینگ رو متوقف کنه تا اینپوت پاسخگو بمونه.چرا این رویکرد Declarative بهینهست؟مدیریت خودکار DOM:شما نیازی نداری نگران جزئیات آپدیت DOM باشی (مثل پیدا کردن عنصر یا حذف دستی). React این کار رو بهینه انجام میده.عملکرد بالا:Virtual DOM و الگوریتم Diffing باعث میشن فقط تغییرات لازم اعمال بشن، نه کل DOM.خوانایی و نگهداری:چون شما فقط UI رو توصیف میکنی، کد تمیزتر و قابلفهمتره.پشتیبانی از قابلیتهای پیشرفته:معماری Fiber و Concurrent Rendering به React اجازه میدن رندرها رو به صورت هوشمند و غیرهمزمان مدیریت کنه، که برای اپهای پیچیده عالیه.جمعبندیReact رویکرد Declarative رو با این مکانیزمها مدیریت میکنه:JSX به React Elementها: کد توصیفی شما به یه ساختار داده سبک (Virtual DOM) تبدیل میشه.Virtual DOM و Diffing: React تغییرات رو با مقایسه Virtual DOM جدید و قدیم شناسایی میکنه.Reconciliation: فقط بخشهای لازم DOM واقعی آپدیت میشن.Fiber و Scheduler: رندرینگ بهینه و قابل وقفه میشه، مخصوصاً تو React 18.Batching و Synthetic Events: آپدیتها و رویدادها به صورت خودکار بهینهسازی میشن.</description>
                <category>Ahmad Safari</category>
                <author>Ahmad Safari</author>
                <pubDate>Tue, 21 Oct 2025 11:43:38 +0330</pubDate>
            </item>
                    <item>
                <title>درباره Telemetry بیشتر بدونیم !!</title>
                <link>https://virgool.io/@sargashte118/telemetry-ih63j1ae7sjy</link>
                <description>Telemetry به فرآیند جمع‌آوری و ارسال داده‌ها از یک نرم‌افزار یا سیستم به سرور برای تحلیل و پایش گفته می‌شود.هدف آن معمولاً این است که توسعه‌دهندگان بتوانند:نحوه استفاده کاربران از نرم‌افزار را بفهمندمشکلات و باگ‌ها را سریع‌تر شناسایی کنندویژگی‌ها و عملکرد سیستم را بهبود دهندمثلا توی فریم ورک next js اطلاعاتنسخه‌ی Next.js و Node.jsاسکریپت‌ها و کامپایلرهای استفاده‌شدهپیکربندی پروژه (مثلاً تنظیمات next.config.js)اطلاعات ناشناس درباره‌ی ساختار پروژههدف اصلی این است که تیم Next.js بفهمد کدام ویژگی‌ها بیشتر استفاده می‌شوند و چه بهبودهایی لازم است.چه چیزهایی ممکن است جمع‌آوری شود؟اطلاعات نرم‌افزار: نسخه فریم‌ورک، نسخه زبان برنامه‌نویسی، پلاگین‌ها و dependency‌هاتنظیمات و پیکربندی‌ها: فایل‌های کانفیگ و گزینه‌های فعال/غیرفعالرفتار کاربران: اقداماتی که در نرم‌افزار انجام می‌دهند (مثلاً کدام بخش‌ها بیشتر استفاده می‌شوند)آمار عملکردی: زمان پاسخ، مصرف منابع و crashها⚠️ توجه کنید که حتی وقتی داده‌ها به‌صورت ناشناس هستند، در محیط‌های سازمانی یا پروژه‌های حساس، ارسال آن‌ها می‌تواند ریسک امنیتی یا حریم خصوصی ایجاد کند.چرا در پروژه‌های Enterprise باید غیرفعال شود؟در محیط‌های سازمانی یا پروژه‌های حساس امنیتی:حتی داده‌های ناشناس می‌توانند اطلاعات پروژه و وابستگی‌ها را فاش کنند.احتمال نقض حریم خصوصی یا قوانین انطباق (compliance) وجود دارد.ارسال داده بدون اجازه می‌تواند ریسک امنیتی برای تیم یا مشتریان ایجاد کند.به همین دلیل، بهترین کار این است که telemetry را برای پروژه‌های سازمانی غیرفعال کنید.چگونه می‌توان آن را مدیریت یا غیرفعال کرد؟اکثر فریم‌ورک‌ها گزینه‌ای برای خاموش کردن telemetry دارند، معمولاً با دستور خط فرمان یا تنظیمات کانفیگ.این کار باعث می‌شود هیچ داده‌ای حتی به صورت ناشناس ارسال نشود و امنیت پروژه تضمین گردد.Telemetry در چه فریم‌ورک‌ها و زبان‌هایی وجود دارد؟تقریباً همه فریم‌ورک‌ها و زبان‌های مدرن سیستم‌های telemetry دارند، از جمله:چگونه Telemetry را در فریم ورک Nextjs غیرفعال کنیم؟برای خاموش کردن telemetry در Next.js دو روش ساده وجود دارد:روش خط فرمان:npx next telemetry disableروش تنظیم فایل next.config.js:const nextConfig = {
  telemetry: false,
};

module.exports = nextConfig;
روش تنظیم env. :NEXT_TELEMETRY_DISABLED=1پس از انجام این کار، Next.js دیگر هیچ داده‌ای از پروژه شما ارسال نخواهد کرد.💡 نکته: حتی ویژگی‌هایی که به نظر “بی‌ضرر” می‌آیند، مثل telemetry، در محیط‌های Enterprise باید بررسی و مدیریت شوند تا امنیت پروژه تضمین شود.</description>
                <category>Ahmad Safari</category>
                <author>Ahmad Safari</author>
                <pubDate>Sun, 05 Oct 2025 10:45:09 +0330</pubDate>
            </item>
                    <item>
                <title>🔍مسیر همزمان یا همون  Parallel Routing در Next.js چیست؟</title>
                <link>https://virgool.io/@sargashte118/parallel-routing-ig048qool20j</link>
                <description>Parallel Routing یکی از قابلیت‌های App Router در Next.js (از نسخه 13 به بعد) هست که اجازه میده چند مسیر (Route) رو به‌صورت همزمان و مستقل توی یک صفحه رندر کنیم.یعنی چی؟فرض کن توی یه صفحه اصلی، چند بخش مختلف داری (مثل Sidebar، Header، Main Content، Chatbox) که هر کدومشون مسیر (route) جدا دارن ولی میخوای بدون رفرش کل صفحه، هر بخش رو مستقل لود و کنترل کنی. Parallel Routing دقیقاً برای همین اومده! 🚀🔑 مفهوم اسلات (Slot) یا اسلات‌های موازیParallel routing از slot‌ها استفاده می‌کنه:یک اسلات مثل یه placeholder توی layout هست که هر مسیر رو می‌تونی داخلش قرار بدی.مثلاً:/app /@sidebar /@feed /@chatاینجا سه اسلات داریم: @sidebar، @feed، @chat که هرکدوم مسیر و کامپوننت خودش رو داره و می‌تونه موازی با بقیه رندر بشه.حالا به این شکل در لی اوت استفاده میکنیم:// app/layout.tsxexport default function RootLayout({children,sidebar,feed,chat,}: {children: React.ReactNode;sidebar: React.ReactNode;feed: React.ReactNode;chat: React.ReactNode;}) {return (&lt;html lang=&quot;en&quot;&gt;&lt;body&gt;&lt;div style={{ display: &quot;flex&quot;, height: &quot;100vh&quot; }}&gt;&lt;aside style={{ width: 200 }}&gt;{sidebar}&lt;/aside&gt;&lt;main style={{ flex: 1 }}&gt;{feed}&lt;/main&gt;&lt;section style={{ width: 300 }}&gt;{chat}&lt;/section&gt;&lt;/div&gt;&lt;/body&gt;&lt;/html&gt;);}📌 چه زمانی باید استفاده کنیم؟داشبوردهای پیچیده: هر بخش داشبورد از یک مسیر جدا بیاد ولی یکجا نشون داده بشه.اپلیکیشن ایمیل/چت: لیست گفتگوها، جزئیات گفتگو، نوار ابزار همزمان لود بشن.UI چندبخشی: مثلا صفحه پروفایل که Sidebar، Activity، Friends همزمان باشن.بهبود UX: وقتی نمی‌خوای با هر کلیک، کل صفحه لود بشه.❌ معایب Parallel Routing⚠️ پیچیدگی پیاده‌سازی: برای پروژه‌های ساده اضافیه.⚠️ ذهنیت جدید لازم داره: باید مفهوم slot و layout رو خوب بفهمی.⚠️ SEO سخت‌تر میشه: چون URLها پیچیده‌تر میشن.⚠️ کدبیس بزرگتر: ممکنه ساختار فولدر زیاد بشه.چه مواقعی باید سراغ Parallel Routing بریم؟این ویژگی برای سناریوهای پیچیده و دینامیک مناسب است. مواقع اصلی استفاده:داشبورد‌ها: جایی که چندین پنل مستقل مثل آمار، لیست کاربران و تنظیمات همزمان نمایش داده می‌شوند (مثل داشبورد GitHub یا Twitter).فیدها و شبکه‌های اجتماعی: نمایش همزمان پست‌ها، نوتیفیکیشن‌ها و پروفایل.رندر شرطی: بر اساس نقش کاربر (مثل ادمین vs. کاربر عادی) محتوای متفاوت نمایش دهید.مودال‌ها و تب‌ها: ترکیب با Intercepting Routes برای مودال‌های deep-linked یا تب‌های مستقل.اپ‌های بزرگ با navigation مستقل: جایی که هر بخش navigation خودش را دارد بدون تأثیر روی کل صفحه.اگر اپ شما ساده است (مثل یک بلاگ استاتیک)، از روتینگ معمولی استفاده کنید. اما اگر بخش‌های دینامیک زیادی دارید، این ویژگی ضروری می‌شود.مزایا (فواید) Parallel Routingبهبود عملکرد: بارگذاری موازی کاهش زمان TTFB (Time to First Byte) و بهبود سرعت کلی اپ را به همراه دارد.مدیریت بهتر حالت‌ها: هر اسلات loading، error و suspense خودش را دارد، پس اگر یک بخش خطا بدهد، کل صفحه کرش نمی‌کند.انعطاف‌پذیری بالا: امکان رندر شرطی، تب‌های مستقل و مودال‌ها بدون نیاز به لایبرری‌های خارجی.بهینه برای SEO و SSR: با Server-Side Rendering کار می‌کند و صفحات را بهینه نگه می‌دارد.کاهش کد تکراری: layoutها را reusable می‌کند و navigation را ساده‌تر مدیریت می‌کند.در نتیجه، UX را بسیار بهتر می‌کند، به ویژه در اپ‌های بزرگ.معایب Parallel Routingپیچیدگی بیشتر: یادگیری آن سخت‌تر است و ساختار فولدرها پیچیده‌تر می‌شود (مثل استفاده از @folder). برای تازه‌کاران می‌تواند گیج‌کننده باشد.باگ‌های احتمالی: برخی کاربران گزارش داده‌اند که در نسخه‌های اولیه buggy است، مثلاً در navigation یا state management.Overhead عملکردی در اپ‌های کوچک: اگر اپ ساده باشد، این ویژگی اضافه‌کاری است و ممکن است کد را پیچیده‌تر کند بدون فایده واقعی.مهاجرت سخت: اگر از Pages Router به App Router مهاجرت می‌کنید، پیاده‌سازی Parallel Routes نیاز به بازنویسی زیادی دارد.مدیریت state: در navigation سخت (hard navigation)، اسلات‌های unmatched به fallback می‌روند که ممکن است UX را مختل کند اگر درست مدیریت نشود.به طور کلی، اگر اپ پیچیده نباشد، ممکن است ارزش دردسرش را نداشته باشد.چرا از کامپوننت استفاده نکنیم؟ به خاطر اینکه میخوای ویژگی های یک صفحه رو در بخش های یک پیج داشته باشیم مثلا این ها :1️⃣ URL مستقل برای هر بخش (Route Independence)وقتی از @slot/page.tsx استفاده می‌کنی، هر بخش یک مسیر (Route) مستقل در Next.js داره.یعنی Next.js این بخش رو مثل یک صفحه کامل می‌بینه، می‌تونی برای هر بخش URL، Query Params یا Dynamic Route داشته باشی.این برای اشتراک‌گذاری لینک مستقیم به یک تب یا بخش خاص فوق‌العاده است.🔹 مثال:/dashboard?tab=chat → با Parallel Routing حتی بدون Refresh، Chat در Slot مربوطه لود میشه.اگر فقط یک کامپوننت ساده داشته باشی، باید خودت همه stateها و params رو مدیریت کنی.2️⃣ Data Fetching جدا برای هر Slot (SSR/SSG جداگانه)هر page.tsx در Parallel Routing می‌تونه داده خودش رو Fetch کنه، حتی به صورت Server-side.یعنی Sidebar از یک API، Feed از یک API دیگه و Chat از یک API دیگه میاد، بدون اینکه یکدیگر رو بلاک کنن.اگر اینا کامپوننت باشن، باید یک API Call سنگین در Parent Layout بزنی و همه داده‌ها رو بریزی پایین → کند و غیرماژولاره.3️⃣ Streaming جداگانه (React Server Components Streaming)Parallel Routing به Next.js اجازه میده هر Slot رو جدا Stream کنه.فرض کن Sidebar سریع لود میشه ولی Feed طول می‌کشه. با Parallel Routing:Sidebar فوری نمایش داده میشه.Feed بعداً اضافه میشه.اگر همه‌چیز داخل یک کامپوننت باشه، کل صفحه تا گرفتن همه داده‌ها متوقف میشه.4️⃣ Error Boundaries مستقلهر Slot می‌تونه فایل error.tsx خودش رو داشته باشه.اگر فقط یکی از Slotها خطا بده، بقیه صفحه سالم می‌مونه.در مقابل، اگر فقط کامپوننت باشه، یک خطا ممکنه کل صفحه رو بترکونه.5️⃣ Loading States مستقلمی‌تونی برای هر Slot یک loading.tsx بذاری.یعنی UI هر بخش در حال بارگذاری شخصی‌سازی میشه.اگر همه‌چیز یک کامپوننت باشه، باید دستی کلی state بنویسی.6️⃣ Prefetching و Caching جداگانهNext.js می‌تونه هر بخش (Slot) رو جدا Prefetch کنه و Cache کنه.یعنی وقتی کاربر بین بخش‌ها جابجا میشه، نیازی به رفرش کل صفحه نداره.در حالت کامپوننت، خودت باید caching رو دستی پیاده کنی.7️⃣ Optional Routes / Default UI برای هر بخشParallel Routing بهت اجازه میده:اگر یک بخش موجود نباشه، default.tsx نمایش داده بشه.یا با not-found.tsx برای همون بخش 404 بده.🔹 مثال:کاربر /chat/123 باز کرده ولی Chat ID 123 وجود نداره → فقط Chat Slot خطا میده، بقیه صفحه سالمه.8️⃣ Dynamic Parallel Routing (Slotهای داینامیک)می‌تونی اسلات‌های داینامیک بسازی و بر اساس Context، تصمیم بگیری چی نشون بدی.مثلاً:app/@tab/(settings)/page.tsxapp/@tab/(inbox)/page.tsx9️⃣ بهبود ساختار کد و ماژولار بودن (Separation of Concerns)هر بخش صفحه مثل یک Mini-Page عمل می‌کنه.این یعنی تیم‌های مختلف می‌تونن روی بخش‌های مختلف کار کنن بدون اینکه یکدیگر رو بلاک کنن.در پروژه‌های بزرگ (مثلاً داشبورد SaaS با ۱۰ها تب) این تفاوت فاحشه.10️⃣ SEO بهتر برای بخش‌های مستقلهر Slot page.tsx می‌تونه generateMetadata داشته باشه.یعنی Title و Meta Tag هر بخش مستقل مدیریت میشه.💡 به زبان ساده:Parallel Routing یعنی هر بخش UI تبدیل میشه به یک Route واقعی که Next.js مدیریت می‌کنه → این یعنی هوشمندی، سرعت، و انعطاف بالاتر.اگر فقط UI ثابت می‌خوای یا همه‌چیز خیلی ساده‌ست، نیازی به Parallel Routing نداری.رفرنس:https://nextjs.org/docs/app/api-reference/file-conventions/parallel-routes</description>
                <category>Ahmad Safari</category>
                <author>Ahmad Safari</author>
                <pubDate>Sat, 30 Aug 2025 12:15:46 +0330</pubDate>
            </item>
                    <item>
                <title>ایجاد Nx monorepo با ویژگی های TypeScript,storybook, Prettier, ESLint, Husky  به همراه پروژه های ری اکت و نکست جی اس</title>
                <link>https://virgool.io/@sargashte118/%D8%A7%DB%8C%D8%AC%D8%A7%D8%AF-nx-monorepo-%D8%A8%D8%A7-%D9%88%DB%8C%DA%98%DA%AF%DB%8C-%D9%87%D8%A7%DB%8C-typescriptstorybook-prettier-eslint-husky-%D8%A8%D9%87-%D9%87%D9%85%D8%B1%D8%A7%D9%87-%D9%BE%D8%B1%D9%88%DA%98%D9%87-%D9%87%D8%A7%DB%8C-%D8%B1%DB%8C-%D8%A7%DA%A9%D8%AA-%D9%88-%D9%86%DA%A9%D8%B3%D8%AA-%D8%AC%DB%8C-%D8%A7%D8%B3-spa90lksi631</link>
                <description>create app as user and admin with next-js and reactچزور کانفیک های تیم ورک را تنظم کنیم؟چطور ui-shared برای اشتراک در پروژه ها ایجاد کنیم؟در Nx چطور هوک بسازیم؟هاسکی را در Nx چطور کانفیگ کنیم ؟ چطور کتابخانه های مجزا روی پروزه ها نصب کنیم؟ و...1- ساخت Nx Monorepo:شما با دستور زیر به صورت عمومی میتوانید ان ایکس را ایجاد نمایید:npm install -g nx2- ساخت یک ورک اسپیس به همرا یک پروژه نکست:npx create-nx-workspace@latest --preset=next
# In add new next app by running the following command:
nx g @nx/next:app my-next-app✔ Where would you like to create your workspace? · my-workspace✔ Application name · nextjs-user✔ Would you like to use the App Router (recommended)? · No✔ Would you like to use the src/ directory? · Yes✔ Test runner to use for end to end (E2E) tests · cypress✔ Default stylesheet format · @emotion/styled✔ Do you want Nx Cloud to make your CI fast? · skipafter install next js ap3- اضافه کردن یک پروژه جدید:nx g @nx/react:app my-react-appReplace my-react-app with your application name.✔ Which stylesheet format would you like to use? · @emotion/styled✔ Would you like to add React Router to this application? (y/N) · true✔ Which E2E test runner would you like to use? · cypress✔ Which bundler do you want to use to build the application? · webpack✔ What should be the project name and where should it be generated? · react-admin @ apps/react-admin4- نصب متریال یو آی یا هر کتابخانه ی دیگر به صورت مجزا:به دایرکتوری پروژه خود میرویم:cd apps/my-react-app
npm install @mui/material @emotion/react @emotion/styledنصب tailwindcd apps/my-next-app
npm install tailwindcss postcss autoprefixer
npx tailwindcss init -pتنظیمات tailwind.config.js /** @type {import(&#039;tailwindcss&#039;).Config} */module.exports = {content: [&#039;./src/**/*.{js,jsx,ts,tsx}&#039;],darkMode: &#039;class&#039;,theme: {extend: {},},plugins: [require(&#039;autoprefixer&#039;)],};اضافه کردن کلاس ها به فایل global.css دستورا زیر رو به فایل اصلی استایل خود که درون پروژه ادد شده است اضافه کنید@tailwind base;@tailwind components;@tailwind utilities;5- ساخت یک کتابخانه به عنوان ورک اسپیس:مورادی که ممکنه به شما در این بخش کمک میکند:Share code between applicationsPublish a package to be used outside the monorepoBetter visualize the architecture using nx graphnx g @nx/next:lib my-next-lib
# for remove workspace
nx g @nrwl/workspace:remove --project=my-next-lib6- ایجاد ui-shared lib و shared-componentnx g @nrwl/react:lib ui-shared
nx g @nrwl/react:component ui-shared/src/my-shared-component --project=ui-shared --export
usage all react base project:
import { MySharedComponent } from &#039;@myorg/ui-shared&#039;;7- نصب storybook:nx add @nx/storybookبرای ست کردن تنظیمات هاسکی روی هر پروژه به صورت زیر انجام میشود:nx g @nx/storybook:configuration my-next-app --uiFramework=@storybook/nextjs
nx g @nx/storybook:configuration my-react-app --uiFramework=@storybook/react
nx g @nx/storybook:configuration my-next-lib --uiFramework=@storybook/react
nx g @nrwl/react:storybook-configuration ui-sharedنصب story book روی ui-sharednx g @nrwl/react:storybook-configuration ui-shared
run: nx run ui-shared:storybook✔ Do you want to set up Storybook interaction tests? (Y/n) · false✔ Automatically generate *.stories.ts files for components declared in this project? (Y/n) · true✔ Configure a static file server for the storybook instance? (Y/n) · trueراه اندازی StorybookServe :nx run project-name:storybookor:nx storybook my-next-appساخت نهایی StorybookBuild Storybook using this command:nx run my-next-app:build-storybookornx build-storybook my-next-appتست StorybookWith the Storybook server running, you can test Storybook (run all the interaction tests) using this command:nx run my-next-app:test-storybookornx test-storybook my-next-app8- نصب husky و lint-stagedWe install and init Husky with:npx husky-init &amp;&amp; npm installThis will also add a prepare script in the package.json:&amp;quotprepare&amp;quot: &amp;quothusky install&amp;quotSetting up lint-stagedWe first need to set up lint-staged:npm install --save-dev lint-stagedLet’s go ahead and use lint-staged to run lint and formatting before committing.Setting up the hookWe create a .lintstagedrc to run commands on staged files:{
&amp;quot*.ts&amp;quot: [&amp;quotnx affected:lint --fix --files&amp;quot],&amp;quot*&amp;quot: [&amp;quotnpx nx format:write --files&amp;quot],&amp;quot*.scss&amp;quot: [&amp;quotnpx stylelint --fix&amp;quot]
}We make a pre-commit hook that triggers stage-lint:npx husky add .husky/pre-commit &#039;npx lint-staged –relative&#039;This gives us:#!/usr/bin/env sh. &amp;quot$(dirname -- &amp;quot$0&amp;quot)/_/husky.sh&amp;quotnpx lint-staged --relativeWe use --relative so lint-staged will apply the paths of the staged files as relative paths which we need for nx format:write.So now we will have eslint, formatting and stylelint running when we commit.pre-pushRunning tests can be a rather lengthy job especially if you both are running unit and component tests (which is what I recommend). So we want to only run this before we push a branch so we still get fast feedback if a test is failing and can fix it with a git amend commit in case.npx husky add .husky/pre-push &#039;npx nx affected -t test &amp;&amp; npx nx affected -t component-test&#039;This will both run test and component-test for any affected project on pre-push.9- ایجاد Pages و ComponentsNx also provides commands to quickly generate new pages and components for your application.nx g @nx/next:page my-next-page --project=my-next-app
nx g @nx/next:component my-next-component --project=my-next-appAbove commands will add a new page my-next-page and a component my-next-component to my-next-app project respectively.Nx generates components with tests by default. For pages, you can pass the --withTests option to generate tests under the specs folder.10- ساخت HooksIf you want to add a new hook, run the followingnx g @nx/react:hook my-react-hook --project=my-react-appReplace my-react-lib with the name of your project.11- چگونگی استفاده پروژه ها Run as Deve Mode:nx dev my-next-appnx serve my-react-appTesting ProjectsYou can run unit tests with:nx test my-next-app
nx test my-next-libReplace my-next-app with the name or your project. This command works for both applications and libraries.You can also run E2E tests for applications:nx e2e my-next-app-e2eReplace my-next-app-e2e with the name or your project with -e2e appended.12-خروجی نهایی React ProjectsReact applications can be build with:nx build my-react-appAnd if you generated a library with --bundler specified, then you can build a library as well:nx build my-next-libThe output is in the dist folder. You can customize the output folder by setting outputPath in the project&#x27;s project.json file.The application in dist is deployable, and you can try it out locally with:npx http-server dist/apps/my-react-appThe library in dist is publishable to npm or a private registry.13-خروجی نهایی  Next-js ProjectsReact applications can be build with:nx build my-next-appTo serve a Next.js application for production:nx start my-next-appلینک پروژه در گیت هاب:nx repository</description>
                <category>Ahmad Safari</category>
                <author>Ahmad Safari</author>
                <pubDate>Mon, 11 Mar 2024 17:50:07 +0330</pubDate>
            </item>
                    <item>
                <title>Nx monorepo vs Turborepo مزایا و معایب هر کدام چیست</title>
                <link>https://virgool.io/@sargashte118/nx-monorepo-vs-turborepo-%D9%85%D8%B2%D8%A7%DB%8C%D8%A7-%D9%88-%D9%85%D8%B9%D8%A7%DB%8C%D8%A8-%D9%87%D8%B1-%DA%A9%D8%AF%D8%A7%D9%85-%DA%86%DB%8C%D8%B3%D8%AA-e4fb92rm38fh</link>
                <description>Nx monorepo vs Turborepoبه اشتراک گذاری کد ها : به اشتراک گذاری کد بین بخش‌های مختلف پروژه راحت تره. می‌تونید کتابخونه‌ها، اجزا و ابزارهای مشترکی داشته باشید که در چندین برنامه داخل مونوریپو قابل استفاده هستند.کامیت‌های اتمی: تغییرات در بخش‌های مختلف پروژه می‌توانند به صورت اتمی کامیت شوند.مدیریت وابستگی ساده: تمام وابستگی‌ها در یک مخزن واحد مدیریت می‌شوند که می تونه مدیریت و نسخه‌بندی وابستگی‌ها را ساده‌تر کنه.ابزارگرایی یکپارچه: ابزارهای استاندارد در تمام پروژه‌های مونوریپو، که می‌تواند مدیریت و به‌روزرسانی آن‌ها را آسان‌تر کند.ا pipeline CI/CD : یک pipeline CI/CD برای کل مونوریپو قابل تنظیم است که فرایند یکپارچه‌سازی و تحویل مداوم را ساده می‌کند.قدیمی و پر تجربه: اینکه توسعه دهنده هایی زیادی در حال استفاده هستند و مطالب و چالش های زیادی درباره NX مطرح و پاسخ داده شده.معایب Nx :پیچیدگی: مونوریپوها می‌توانند پیچیده شوند، به ویژه زمانی که پروژه رشد می‌کند. مدیریت وابستگی‌ها، پیکربندی ساخت و ساز و ساختار پروژه ممکن است چالش‌برانگیز بشه.عملکرد: مونوریپوهای بزرگ ممکن است از مشکلات عملکرد رنج ببرند، مانند زمان ساخت بلندتر و زمان گیت عملیات بلندتر. البته در نسخه های جدید با کش کردن های ریموت و ابری مقداری این موضوع رفع شدهمنحنی یادگیری: برای توسعه‌دهندگانی که تازه به مونوریپوها یا ابزارهای خاص Nx آشنا می‌شوند، ممکن است مشکلاتی وجود داشته باشه و کمی سخت.مزایا Turborepo :سادگی: هر پروژه مختلف مخزن خودش را دارد که می‌تواند ساختار پروژه و جریان کار توسعه را ساده کند، به ویژه برای تیم‌ها یا پروژه‌های کوچک‌تر.عملکرد: مخازن کوچکتر به طور معمول منجر به بهبود عملکرد می‌شوند، شامل زمان کلون، عملیات گیت و ساخت سریعتر.جداسازی پروژه‌ها: هر پروژه دارای مخزن مجزاست که از هم مستقل است. این امر به توسعه‌دهندگان اجازه می‌دهد به طور مستقل بر روی پروژه‌های خود کار کنند بدون تداخل با دیگر پروژه‌ها.تأثیر تغییرات در یک پروژه روی دیگران کمتر می‌شود. این می‌تواند مدیریت وابستگی‌ها و نسخه‌بندی را آسان‌تر کند.کاهش ارتباطات وابسته: افزایش تعداد مخازن موجب کاهش وابستگی‌های میان پروژه‌ها می‌شود، که این می‌تواند انعطاف‌پذیری بیشتری در توسعه و تست هر پروژه فراهم کند.استفاده از تکنولوژی‌های مناسب: هر پروژه می‌تواند از تکنولوژی‌های وابسته به خود استفاده کند، بدون نیاز به هماهنگی با سایر پروژه‌ها. این موجب انعطاف بیشتر در انتخاب فناوری‌های مناسب برای هر پروژه می‌شود.مدیریت و کنترل موثرتر: با داشتن مخازن جداگانه، مدیران می‌توانند به طور مستقیم کنترل کنند که کدام تیم‌ها یا توسعه‌دهندگان به کدام پروژه دسترسی دارند و می‌توانند این دسترسی‌ها را به طور دقیق مدیریت کنند.مدیریت ارتباط با ذینفعان: برای پروژه‌هایی که با ذینفعان خارجی دیگری همکاری می‌کنند، داشتن مخازن جداگانه می‌تواند مدیریت ارتباط با آن‌ها را ساده‌تر کند، زیرا هر ذینفع می‌تواند به طور مستقل به مخزن مربوط به پروژه مورد نظر دسترسی داشته باشد.معایب Turborepo:تکرار کد: بدون مدیریت دقیق، تکرار کد ممکن است در سراسر مخازن رخ دهد که منجر به هزینه نگهداری و سازگاری ممکن است شود.پیچیدگی ادغام: ادغام تغییرات بین چندین مخزن می‌تواند پیچیده باشد و نیاز به روش‌ها و ابزارهای خاصی برای مدیریت این ادغام دارد. این ممکن است زمان‌بر و چالش‌برانگیز باشد.مدیریت وابستگی‌ها: مدیریت وابستگی‌ها و نسخه‌بندی بین مخازن مختلف ممکن است دشوار باشد، زیرا نیاز به هماهنگی و هماهنگی میان وابستگی‌ها و نسخه‌ها دارید.سختی در پیدا کردن و استفاده از کد مشترک: در حالت چندین مخزن، پیدا کردن و استفاده از کد مشترک بین پروژه‌ها ممکن است مشکل باشد و نیاز به ایجاد و نگهداری مخازن جداگانه برای کدهای مشترک وجود دارد.افزایش هزینه نگهداری و مدیریت: داشتن چندین مخزن به معنای داشتن هزینه‌های بیشتر در مورد نگهداری، مدیریت و نگهداری است. هر مخزن نیازمند مدیریت جداگانه است و این می‌تواند به موجب افزایش هزینه‌ها و زمان مورد نیاز برای نگهداری بپردازد.استانداردسازی و ادغام کد: استانداردسازی کد و ادغام تغییرات بین مخازن مختلف ممکن است مشکلاتی ایجاد کند، زیرا هر مخزن ممکن است دارای استانداردها و رویه‌های خاص خود باشد که نیاز به هماهنگی دارد.کاهش انعطاف‌پذیری در مدیریت پروژه: با داشتن چندین مخزن، مدیریت و کنترل پروژه ممکن است مقرون به صرفه‌تر نباشد و باعث کاهش انعطاف‌پذیری در مواجهه با نیازهای تغییرات پروژه شود.به طور کلی، استفاده از چندین مخزن ممکن است برای پروژه‌های بزرگ یا پیچیده با مشکلات و چالش‌های خود همراه باشد که نیازمند مدیریت دقیق و ابزارهای مناسب برای مواجهه با آن‌ها است.</description>
                <category>Ahmad Safari</category>
                <author>Ahmad Safari</author>
                <pubDate>Mon, 11 Mar 2024 16:19:17 +0330</pubDate>
            </item>
            </channel>
</rss>