Я нещодавно писав блоги на цю тему:
Як ми підтримуємо актуальність цієї гілки функцій? Злиття найновіших коммітів нагорі за течією легко, але ви хочете уникнути створення коміту злиття, оскільки це не буде оцінено при натисканні вгору за течією: ви тоді ефективно повторно фіксуєте зміни вгору за течією, і ці коміти вгору за течією отримають новий хеш ( коли вони отримують нового батька). Це особливо важливо, оскільки ці об’єднані коміти відображатимуться у вашому запиті на витягування GitHub, коли ви надсилаєте ці оновлення до вашої особистої гілки функцій GitHub (навіть якщо ви робите це після того, як ви видали запит на витягування).
Ось чому нам потрібно перебазувати замість об’єднання:
git co devel #devel is ansible's HEAD aka "master" branch
git pull --rebase upstream devel
git co user-non-unique
git rebase devel
Як параметр rebase, так і команда rebase для git дозволять зберегти дерево чистою та уникнути коммітування злиття. Але майте на увазі, що це ваші перші коміти (з якими ви видали свій перший запит на витягування), які перебазуються, і які тепер мають новий хеш коміту, який відрізняється від початкових хешів, які все ще є у вашій віддаленій гілці репо .
Тепер виштовхування цих оновлень до вашої особистої гілки функції GitHub тут не відбудеться, оскільки обидві гілки відрізняються: локальне дерево гілок та дерево віддалених гілок „не синхронізовані” через ці різні хеші комітів. Git скаже вам спочатку git pull --rebase
, а потім натисне знову, але це не буде простим натисканням вперед, оскільки ваша історія була переписана. Не роби цього!
Проблема в тому, що ви знову отримаєте свої перші змінені коміти, як вони були спочатку, і вони будуть об’єднані поверх вашої локальної гілки. Через несинхронізований стан ця тяга не застосовується чисто. Ви отримаєте побиту історію, де ваші коміти з’являються два рази. Коли ви натиснете все це на вашу гілку функцій GitHub, ці зміни відобразяться на початковому запиті на витяг, який стане дуже, дуже потворним.
AFAIK, насправді немає абсолютно чистого рішення для цього. Найкраще рішення, яке я знайшов, - примусово пересунути вашу локальну гілку до вашої гілки GitHub (насправді примушуючи нешвидке оновлення):
Відповідно до git-push (1):
Update the origin repository’s remote branch with local branch, allowing non-fast-forward updates. This can leave unreferenced commits dangling in the origin repository.
Тож не тягніть, просто силою натискайте так:
git push svg +user-non-unique
або:
git push svg user-non-unique --force
Це насправді явно перезапише вашу віддалену гілку з усім у вашій локальній гілці. Комісії, що знаходяться у віддаленому потоці (і спричинили збій), залишаться там, але будуть звисаючими комітами, які з часом будуть видалені git-gc (1). Нічого страшного.
Як я вже говорив, це AFAICS найчистіше рішення. Недоліком цього є те, що ваш PR буде оновлений тими найновішими комітами, які отримають пізніше, і можуть з’явитися не синхронізовано в історії коментарів PR. Не представляє великих проблем, але потенційно це може заплутати.