Git: Як розчавити всі комірки на гілці


315

Я роблю нову гілку masterз:

git checkout -b testbranch

Я роблю в неї 20 комітів.

Тепер я хочу скинути ці 20 комітів. Я роблю це з:

git rebase -i HEAD~20

Що робити, якщо я не знаю, скільки комітетів? Чи є спосіб зробити щось на кшталт:

git rebase -i all on this branch

6
Ви можете зробити, git rebase -i 58333012713fc168bd70ad00d191b3bdc601fa2dщо зробить інтерактивну базу даних, де номер комітету є останньою коміткою, яка залишається незмінною
ден

@denns Використовуючи цей метод з останньою комісією у галузі, ви відмовляєтеся від фантастичної роботи. Дуже дякую!
Джошуа Пінтер

Відповіді:


393

Ще один спосіб зменшити всі ваші зобов’язання - це скинути індекс до головного:

 git checkout yourBranch
 git reset $(git merge-base master yourBranch)
 git add -A
 git commit -m "one commit on yourBranch"

Це не ідеально, оскільки це означає, що ви знаєте, з якої галузі "yourBranch" походить.
Примітка: виявити, що галузь походження не є простою / можливою за допомогою Git ( візуальний спосіб часто найпростіший , як це бачимо тут ).


EDIT: вам потрібно буде скористатися git push --force


Карлоча Хоа додає в коментарях :

Для скидання можна зробити

git reset $(git merge-base master $(git rev-parse --abbrev-ref HEAD)) 

[Що] автоматично використовує гілку, на якій ви зараз перебуваєте.
І якщо ви використовуєте це, ви також можете використовувати псевдонім, оскільки команда не покладається на ім'я гілки .


2
Краще оформити замовлення, щоб здійснити місце, де YourBranchзараз є. Це залишиться YourBranchнедоторканим, коли ви це зробитеreset
Євген Конков

1
@ Abdurrahim Або відкрийте git bash, і ви можете скопіювати та вставити команди команди!
VonC

3
Для скидання можна зробити git reset $(git merge-base master $(git rev-parse --abbrev-ref HEAD))автоматичне використання гілки, на якій ви зараз перебуваєте. І якщо ви використовуєте це, ви також можете використовувати псевдонім, оскільки команда не покладається на ім'я гілки.
Карлочча Хоа

1
@Druska Для спрощених випадків розгалуження, ні, це повинно працювати добре.
VonC

1
@Shimmy так, якщо ви змусили натиснути після скидання: git push --force(і попередити своїх колег, якщо у вас є кілька людей, які працюють на цій гілці)
VonC,

112

Оформіть відділення, для якого ви хочете зібрати всі зобов’язання за один комітет. Припустимо , його називають, feature_branch.

git checkout feature_branch

Крок 1:

Зробіть м'який перезавантаження origin/feature_branchвашої локальної masterфілії (залежно від ваших потреб, ви також можете скинути з походженням / головним). Це скине всі зайві зобов’язання у вашому feature_branch, але не змінюючи жодних змін вашого файлу локально.

git reset --soft master

Крок 2:

Додайте всі зміни у свій каталог git repo до нового комітету, який буде створено. І виконайте те ж саме з повідомленням.

git add -A && git commit -m "commit message goes here"


6
Це було найнадійнішим рішенням для мене - не викликати жодних помилок перезавантаження та конфліктів злиття.
ANTARA

1
Попередження: додавання git -Додати все, що є у локальній папці - до гілки.
Девід Н

люблю це рішення! це саме те, що я хотів!
jacoballenwood

1
Найкраще рішення для noob - не руйнівний і єдиний момент ой, можливо, перевірка занадто багато таких, як секрети додатків тощо, що не має значення, якщо у вас є належний файл
gitignore

@NSduToit Коротка відповідь: Ні, не потрібно. Зробивши вищезазначені кроки у моїй відповіді, ви закінчитеся одним фіксом із деякими змінами коду. Ви можете думати про це так само, як і про будь-який інший документ із деякими змінами коду. Ви можете натиснути це на вашу віддалену гілку без -fпрапора.
примхливий

110

Те, що ви робите, є досить схильним до помилок. Просто зробіть:

git rebase -i master

яка автоматично перезавантажує лише зобов'язання вашої філії на поточного останнього головного майстра.


5
дякую, я це зрозумів, але чому схильна моя системна помилка
user3803850

10
Можливо, тому, що легко зрозуміти число неправильно?
Даніель Скотт

13
Погодився, це найкраще рішення. але перейдіть за цим посиланням, оскільки це краще пояснює, що вам потрібно зробити.
Крісто

3
Замість того, щоб розкручувати коміти, ви можете об'єднати гілку до master та зробити git reset to origin / master для нестабільності всіх комітів. Це дозволить вам скористатись наявним нестандартним кодом зcommit -am "the whole thing!"
nurettin

2
@nurettin Я думаю, що reset origin/masterметод дійсно поганий, оскільки це точно так само, як робити зобов’язання безпосередньо на master - немає історії "об'єднання гілки", немає можливості запиту на тягу. Відповідь @WaZaA набагато більше відповідає нормальному робочому процесу Git, я думаю
Drenai

79

Ще один простий спосіб зробити це: перейти на гілку походження та зробити а merge --squash. Ця команда не виконує "розбитого" скоєння. коли ви це зробите, всі повідомлення про ваш пристрій будуть зібрані.

$ git checkout master
$ git merge --squash yourBranch
$ git commit # all commit messages of yourBranch in one, really useful
 > [status 5007e77] Squashed commit of the following: ...

1
Правда. Я згадав різницю між злиттям --squash і Rebase -i в stackoverflow.com/a/2427520/6309
VonC

1
Це працює, якщо ви не хочете сквош в батьківській гілці, просто створіть і перейдіть на нову гілку на основі батьківської гілки і зробіть сквош злиття в це.
Шарлотта

Привіт товариш, чудова порада!
Нестор

приємно! я створюю "temp" гілку від "master" спочатку для того, щоб розбити "yourBranch", а потім об'єднати "temp" у "master".
lazieburd

34

Якщо припустити, що ви відгалужуєтесь від головного, вам не потрібно yourBranchвесь час вступати в крок скидання:

git checkout yourBranch
git reset --soft HEAD~$(git rev-list --count HEAD ^master)
git add -A
git commit -m "one commit on yourBranch"

Пояснення :

  • git rev-list --count HEAD ^masterрахує комісії, коли ви створили свою галузь функції у майстра, f.ex. 20.
  • git reset --soft HEAD~20здійснить плавне скидання останніх 20 комісій. Це залишає ваші зміни у файлах, але видаляє коміти.

Використання :

У свій .bash_profile я додав псевдонім для gisquashцього за допомогою однієї команди:

# squash all commits into one
alias gisquash='git reset --soft HEAD~$(git rev-list --count HEAD ^master)'

Після перезавантаження та вчинення вам потрібно зробити git push --force.

Підказка :

Якщо ви використовуєте Gitlab> = 11.0, вам більше цього не потрібно робити, оскільки у нього є опція розсікання при об’єднанні гілок. Варіант сквашування Gitlab


15

На основі прочитання декількох запитань та відповідей Stackoverflow на сквош, я думаю, що це хороший вкладиш для скріпінгу всіх комісій на гілці:

git reset --soft $(git merge-base master YOUR_BRANCH) && git commit -am "YOUR COMMIT MESSAGE" && git rebase -i master

Це якщо припустити, що майстер є базовою галуззю.


1
Велике спасибі, компанія має чимало обмежень і не змогла перезавантажити звичайний спосіб з редактором, оскільки не була вголос зберегти. Також не вдалося використовувати функцію сквош і злиття в git, оскільки ця гілка переходить до Lead dev для злиття, і йому це не подобається. Цей 1 лайнер спрацював і врятував головний біль. Дивовижна робота.
L1ghtk3ira

10

Рішення для людей, які віддають перевагу натисканню:

  1. Встановіть sourcetree (безкоштовно)

  2. Перевірте, як виглядають ваші зобов’язання. Швидше за все, у вас є щось подібне до цього введіть тут опис зображення

  3. Клацніть правою кнопкою миші на батьківській фіксації. У нашому випадку це головна галузь.

введіть тут опис зображення

  1. Ви можете скосити фіксацію з попередньою, натиснувши кнопку. У нашому випадку ми повинні натиснути 2 рази. Ви також можете змінити повідомлення про фіксацію введіть тут опис зображення

  2. Результати є приголомшливими, і ми готові наполягати! введіть тут опис зображення

Бічна примітка: Якщо ви просували свої часткові зобов’язання на віддалене місце, вам доведеться використовувати силовий натиск після сквошу


Дякую за це!
Кришталь

0

Іншим рішенням буде збереження всіх журналів фіксування у файл

git log> branch.log

Тепер у branch.log будуть встановлені всі ідентифікатори фіксації з початку.

git reset --soft

всі коміти будуть зняті


0

Скидання Git, як згадувалося у багатьох відповідях раніше, - це найкращий і найпростіший спосіб досягти того, що ви хочете. Я використовую його в наступному робочому процесі:

(про галузь розвитку)

git fetch
git merge origin/master  #so development branch has all current changes from master
git reset origin/master  #will show all changes from development branch to master as unstaged
git gui # do a final review, stage all changes you really want
git commit # all changes in a single commit
git branch -f master #update local master branch
git push origin master #push it

0

Весь цей скит скидання, жорсткий, м'який, і все інше, що згадується тут, ймовірно, працює (це не було для мене), якщо ви робите кроки правильно і якийсь джин.
Якщо ви середній Джо Смо, спробуйте це:
Як використовувати git merge - сквош?


Врятувало моє життя і буде моїм піти на сквош, використовуючи це 4 рази, відколи я дізнався про це. Простий, чистий і в основному 1 команда.


Якщо коротко: якщо ви знаходитесь у відділенні, ви можете назвати його "my_new_feature", а ваш запит на витяг має 35 комітів (або скільки завгодно), і ви хочете, щоб це було 1.

А. Переконайтеся, що ваша філія актуальна, продовжуйте роботу розробляти, отримувати останню інформацію та об'єднувати та вирішувати будь-які конфлікти з "my_new_feature"
(цей крок дійсно слід зробити, як тільки можна весь час все-таки)

B. Отримати останню розробку та розгалужити нову гілку, називайте її "my_new_feature_squashed"

C. магія тут.
Ви хочете перенести свою роботу з "my_new_feature" на "my_new_feature_squashed"
Так що просто зробіть (поки на вашій новій гілці ми створили розробку):
git merge --squash my_new_feature

Усі ваші зміни тепер будуть у вашій новій гілці, не соромтесь перевірити її, тоді просто зробіть свою 1 єдину фіксацію, натисніть, новий піар цієї гілки - і чекайте повтору наступного дня.
Ви не любите кодування? :)


0

Ви можете використовувати інструмент, який я створив спеціально для цього завдання:

https://github.com/sheerun/git-squash

В основному вам потрібно зателефонувати, git squash masterі ви закінчили

Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.