GIT-RERERE(1) راهنمای گیت GIT-RERERE(1)

git-rerere - استفاده مجدد از راه‌حل‌های ثبت‌شده برای تضادهای ادغام

git rerere [clear | forget <pathspec>... | diff | status | remaining | gc]

در یک گردش کاری که از شاخه‌های موضوعی با طول عمر نسبتاً طولانی استفاده می‌کند، توسعه‌دهنده گاهی نیاز دارد تا زمان نهایی شدن شاخه‌های موضوعی (چه ادغام در شاخه «انتشار» یا ارسال و پذیرفته شدن در بالادست)، تضادهای مشابه را بارها و بارها حل کند.

این دستور در این فرآیند با ثبت نتایج ادغام خودکار دارای تضاد و نتایج متناظر حل دستی در ادغام دستی اولیه، و اعمال راه‌حل‌های دستی از قبل ثبت‌شده بر روی نتایج متناظر ادغام خودکار، به توسعه‌دهنده کمک می‌کند.


نکته

برای فعال‌سازی این دستور، باید متغیر پیکربندی rerere.enabled را تنظیم کنید.

به‌طور معمول، git rerere بدون آرگومان یا دخالت کاربر اجرا می‌شود. با این حال، دارای چندین دستور فرعی است که به کاربران امکان تعامل با وضعیت کاری آن را می‌دهد.

clear

در صورتی که قرار است حل یک ادغام لغو شود، فراداده‌های مورد استفاده rerere را بازنشانی می‌کند. فراخوانی git am [--skip|--abort] یا git rebase [--skip|--abort] به‌طور خودکار این دستور را فراخوانی می‌کند.

forget <pathspec>

راه‌حل‌های تضادی را که rerere برای تضادهای فعلی در مسیرهای منطبق با <pathspec> ثبت کرده است، بازنشانی می‌کند.

diff

تفاوت‌ها را برای وضعیت فعلی حل تضاد نمایش می‌دهد. این دستور برای پیگیری تغییراتی که هنگام حل تضادها توسط کاربر ایجاد شده مفید است. آرگومان‌های اضافی مستقیماً به دستور diff سیستم که در PATH نصب شده ارسال می‌شوند.

status

مسیرهای دارای تضادی را که rerere راه‌حل ادغام آن‌ها را ثبت خواهد کرد، چاپ می‌کند.

remaining

مسیرهای دارای تضادی را که توسط rerere به‌طور خودکار حل نشده‌اند، چاپ می‌کند. این شامل مسیرهایی است که راه‌حل آن‌ها توسط rerere قابل ردیابی نیست، مانند زیرماژول‌های دارای تضاد.

gc

سوابق ادغام‌های دارای تضادی را که مدت‌ها پیش رخ داده‌اند، هرس می‌کند. به‌طور پیش‌فرض، تضادهای حل‌نشده با عمر بیش از ۱۵ روز و تضادهای حل‌شده با عمر بیش از ۶۰ روز هرس می‌شوند. این مقادیر پیش‌فرض به ترتیب از طریق متغیرهای پیکربندی gc.rerereUnresolved و gc.rerereResolved کنترل می‌شوند.

هنگامی که شاخه موضوعی (topic) شما ناحیه‌ای هم‌پوشان با تغییراتی که شاخه master (یا بالادست) از زمان انشعاب شاخه موضوعی روی آن اعمال کرده را دستکاری می‌کند، ممکن است بخواهید پیش از آماده شدن شاخه موضوعی برای ارسال به بالادست، آن را با آخرین نسخه شاخه master آزمایش کنید:

          o---*---o topic
         /
o---o---o---*---o---o master

برای چنین آزمایشی، باید به نحوی شاخه‌های master و topic را ادغام کنید. یک راه برای انجام این کار، دریافت (pull) شاخه master در شاخه موضوعی است:

    $ git switch topic
    $ git merge master
          o---*---o---+ topic
         /           /
o---o---o---*---o---o master

کامیت‌های علامت‌گذاری‌شده با * همان ناحیه از همان فایل را تغییر می‌دهند؛ شما باید هنگام ایجاد کامیت علامت‌گذاری‌شده با + تضادها را حل کنید. سپس می‌توانید نتیجه را آزمایش کنید تا مطمئن شوید کارهای در دست اقدام شما با آنچه در آخرین نسخه master وجود دارد همچنان به درستی کار می‌کند.

پس از این ادغام آزمایشی، دو راه برای ادامه کار روی شاخه موضوعی وجود دارد. ساده‌ترین راه این است که کارهای بعدی را روی همان کامیت ادغام آزمایشی + بنا کنید، و هنگامی که کار شما در شاخه موضوعی در نهایت آماده شد، شاخه موضوعی را به master بیاورید (pull کنید)، یا از بالادست بخواهید که تغییرات را از شما دریافت کند. با این حال، تا آن زمان ممکن است master یا بالادست پس از ادغام آزمایشی + جلوتر رفته باشند، که در این صورت نمودار نهایی کامیت‌ها شبیه به این خواهد بود:

    $ git switch topic
    $ git merge master
    $ ... work on both topic and master branches
    $ git switch master
    $ git merge topic
          o---*---o---+---o---o topic
         /           /         \
o---o---o---*---o---o---o---o---+ master

اما هنگامی که شاخه موضوعی شما طولانی‌مدت باشد، در نهایت تعداد زیادی از این کامیت‌های «Merge from master» در آن وجود خواهد داشت که تاریخچه توسعه را به شکلی غیرضروری شلوغ و نامرتب می‌کند. خوانندگان فهرست پستی کرنل لینوکس ممکن است به یاد داشته باشند که لینوس زمانی که یکی از نگه‌دارندگان زیرسیستم درخواست دریافت از شاخه‌ای پر از «ادغام‌های بیهوده» کرده بود، از چنین ادغام‌های آزمایشی بسیار مکرری گلایه کرد.

به عنوان یک راهکار جایگزین، برای تمیز نگه داشتن شاخه موضوعی از ادغام‌های آزمایشی، می‌توانید ادغام آزمایشی را دور بیندازید و ساخت کارهای بعدی را روی نوک شاخه قبل از ادغام آزمایشی ادامه دهید:

    $ git switch topic
    $ git merge master
    $ git reset --hard HEAD^ ;# rewind the test merge
    $ ... work on both topic and master branches
    $ git switch master
    $ git merge topic
          o---*---o-------o---o topic
         /                     \
o---o---o---*---o---o---o---o---+ master

این کار باعث می‌شود در نهایت هنگامی که شاخه موضوعی شما آماده شد و با شاخه master ادغام گردید، تنها یک کامیت ادغام باقی بماند. این ادغام مستلزم آن است که تضادی را که توسط کامیت‌های علامت‌گذاری‌شده با * ایجاد شده است، حل کنید. با این حال، این تضاد اغلب همان تضادی است که قبلاً هنگام ایجاد ادغام آزمایشی که آن را دور انداختید، حل کرده بودید. دستور git rerere به شما کمک می‌کند تا این ادغام نهایی دارای تضاد را با استفاده از اطلاعات حل دستی قبلی خود حل کنید.

اجرای دستور git rerere بلافاصله پس از یک ادغام خودکار دارای تضاد، فایل‌های درخت کاری دچار تضاد را همراه با نشانگرهای معمول تضاد یعنی <<<<<<<، ======= و >>>>>>> در آن‌ها ثبت می‌کند. بعداً، پس از اتمام حل تضادها، اجرای مجدد git rerere وضعیت حل‌شده این فایل‌ها را ثبت خواهد کرد. فرض کنید هنگام ایجاد ادغام آزمایشی master در شاخه موضوعی این کار را انجام داده‌اید.

دفعه بعد، پس از مشاهده همان ادغام خودکار دارای تضاد، اجرای git rerere یک ادغام سه‌طرفه (three-way merge) بین ادغام خودکار متضاد قبلی، راه‌حل دستی قبلی، و ادغام خودکار متضاد فعلی انجام خواهد داد. اگر این ادغام سه‌طرفه بدون مشکل حل شود، نتیجه در فایل درخت کاری شما نوشته می‌شود و بنابراین نیازی به حل دستی آن نخواهید داشت. توجه داشته باشید که git rerere فایل نمایه (index) را تغییر نمی‌دهد، بنابراین همچنان لازم است پس از اطمینان، بررسی‌های نهایی سلامت را با git diff (یا git diff -c) انجام دهید و در صورت رضایت، از git add استفاده کنید.

به عنوان یک اقدام تسهیل‌کننده، git merge هنگام خروج پس از شکست در ادغام خودکار، به‌طور خودکار git rerere را فراخوانی می‌کند؛ سپس git rerere اگر تضاد جدید باشد حل دستی را ثبت می‌کند، و اگر جدید نباشد از حل دستی قبلی مجدداً استفاده می‌نماید. همچنین git commit هنگام ثبت نتیجه یک ادغام، git rerere را فراخوانی می‌کند. معنای این امر آن است که نیازی نیست کار خاصی انجام دهید (به‌جز فعال‌سازی متغیر پیکربندی rerere.enabled).

در مثال ما، وقتی ادغام آزمایشی را انجام می‌دهید، راه‌حل دستی ثبت می‌شود و تا زمانی که راه‌حل ثبت‌شده همچنان قابل اعمال باشد، بعداً هنگام انجام ادغام واقعی با شاخه‌های به‌روزشده master و topic، دوباره مورد استفاده قرار خواهد گرفت.

اطلاعاتی که git rerere ثبت می‌کند هنگام اجرای git rebase نیز استفاده می‌شود. پس از دور انداختن ادغام آزمایشی و ادامه توسعه روی شاخه موضوعی:

          o---*---o-------o---o topic
         /
o---o---o---*---o---o---o---o   master
    $ git rebase master topic
                              o---*---o-------o---o topic
                             /
o---o---o---*---o---o---o---o   master

می‌توانید دستور git rebase master topic را اجرا کنید تا قبل از آماده شدن شاخه موضوعی برای ارسال به بالادست، خود را به‌روز کنید. این کار منجر به عقب‌گرد به یک ادغام سه‌طرفه می‌شود و به همان شیوه ادغام آزمایشی که قبلاً حل کردید دچار تضاد خواهد شد. در این حالت git rerere توسط git rebase اجرا می‌شود تا به شما در حل این تضاد کمک کند.

[نکته] git rerere برای تشخیص تضاد به نشانگرهای تضاد در فایل متکی است. اگر فایل از قبل دارای خطوطی باشد که شبیه به خطوط نشانگرهای تضاد هستند، ممکن است git rerere در ثبت راه‌حل تضاد ناموفق باشد. برای دور زدن این مشکل، می‌توان از تنظیم conflict-marker-size در gitattributes(5) استفاده کرد.

gitattributes(5), git-merge(1), git-rebase(1)

بخشی از مجموعه git(1)

2026-06-29 Git 2.55.0