Skąd mam wiedzieć, czy gałąź została już scalona w master?

1139

Mam repozytorium git z wieloma gałęziami.

Skąd mam wiedzieć, które gałęzie są już połączone w gałąź główną?

hektorsq
źródło

Odpowiedzi:

1792

git branch --merged masterwyświetla gałęzie scalone w master

git branch --mergedwyświetla gałęzie połączone w HEAD (tj. wierzchołek bieżącego oddziału)

git branch --no-merged wyświetla gałęzie, które nie zostały scalone

Domyślnie dotyczy to tylko lokalnych oddziałów. -aFlag pokaże zarówno lokalnych i zdalnych oddziałów, a -rpokazy flag tylko zdalnych oddziałów.

hektorsq
źródło
2
Na marginesie, kiedy próbowałem sprawdzić, czy zdalna gałąź została scalona, ​​najpierw skonfigurowałem lokalną gałąź śledzenia, zidentyfikowałem status za pomocą, git branch --mergeda następnie usunąłem lokalną i zdalną gałąź.
Kenneth Kalmer
83
Najwyraźniej git branch -a --merged/no-mergeddziała również bez tworzenia lokalnego oddziału śledzenia.
fresskoma
70
Lub po prostu git branch -r --merged/--no-mergedznaleźć tylko zdalne oddziały.
Asfand Qazi
5
W jakikolwiek sposób usunąć nie scalone gałęzie, które zostały scalone po zmianie bazy?
Ashfame
9
Zauważ, że --merged/--no-mergedpobiera opcjonalny argument zatwierdzenia po nim. Przynajmniej w mojej wersji git (1.9.1) dodanie flagi -alub -rpo nim powoduje błąd krytyczny. Dodaj -alub -r wcześniej --(no-)merged .
Jonathan Gawrych
113

Za pomocą tego git merge-basepolecenia można znaleźć najnowsze wspólne zatwierdzanie między dwoma gałęziami. Jeśli to zatwierdzenie jest takie samo jak szef gałęzi, gałąź została całkowicie scalona.

Zauważ, że git branch -drobi to już teraz, ponieważ odmówi usunięcia gałęzi, która nie została jeszcze całkowicie scalona.

Greg Hewgill
źródło
3
@ Hari odpowiedź przechodzi w bardziej szczegółowo, w jaki sposób to wykorzystać.
Muhd
jak możemy to zrobić automatycznie / programowo?
Alexander Mills,
1
„nie zostało jeszcze całkowicie scalone” ... całkowicie połączone w jakiej gałęzi?
Alexander Mills,
@AlexanderMills: Do twojego obecnego oddziału.
Greg Hewgill
2
@AlexanderMills: git branch -dodmówi usunięcia gałęzi, która nie została scalona z bieżącą gałęzią. Nie usuwam bieżącej gałęzi.
Greg Hewgill
27

Istnieje również rozwiązanie interfejsu graficznego. Po prostu wpisz

gitk --all

W nowym oknie aplikacji zostanie wyświetlona graficzna reprezentacja całego repozytorium, przy czym bardzo łatwo jest stwierdzić, czy gałąź została już scalona, ​​czy nie

iberbeu
źródło
17
Co jest jasne, wymaga instalacji aplikacji, która nie jest częścią gitklienta. Na Ubuntu apt-get install gitk.
metame
Na macOS, jeśli masz zainstalowany Homebrew, byłoby brew install git-gui, aby dostać gitksię do wiersza poleceń.
program247365
24

Korzystam z następującej funkcji bash, takiej jak: git-is-merged develop feature/new-feature

git-is-merged () {
  merge_destination_branch=$1
  merge_source_branch=$2

  merge_base=$(git merge-base $merge_destination_branch $merge_source_branch)
  merge_source_current_commit=$(git rev-parse $merge_source_branch)
  if [[ $merge_base = $merge_source_current_commit ]]
  then
    echo $merge_source_branch is merged into $merge_destination_branch
    return 0
  else
    echo $merge_source_branch is not merged into $merge_destination_branch
    return 1
  fi
}
Carl G.
źródło
3
to faktycznie nie działa. Jeśli gałąź źródłowa została już scalona z gałęzią docelową, a następnie gałąź docelowa otrzymuje jeszcze kilka zatwierdzeń, to już nie działa, ale nie wiem dlaczego
Alexander Mills
1
patrz pytanie tutaj: stackoverflow.com/questions/51355331/…
Alexander Mills
18

Zastosowanie git merge-base <commit> <commit>.

To polecenie wyszukuje najlepszych wspólnych przodków między dwoma zatwierdzeniami. A jeśli wspólny przodek jest identyczny z ostatnim zatwierdzeniem „gałęzi”, to możemy spokojnie założyć, że „gałąź” została już scalona z masterem.

Oto kroki

  1. Znajdź hash ostatniego zatwierdzenia w gałęzi master
  2. Znajdź hash ostatniego zatwierdzenia w „oddziale”
  3. Uruchom polecenie git merge-base <commit-hash-step1> <commit-hash-step2>.
  4. Jeśli dane wyjściowe z kroku 3 są takie same jak dane wyjściowe z kroku 2, to „gałąź” została już scalona w master.

Więcej informacji na temat git merge-base https://git-scm.com/docs/git-merge-base .

Hari
źródło
2
Myślę, że powie ci to tylko wtedy, gdy wskazówki zostaną połączone. Na przykład nie powie ci to, czy masterzostał scalony branch, a następnie dodano 4 kolejne zmiany branch.
mkobit
Dlaczego nie, git log -1 $(git merge-base base-branch feature-branch)a jeśli zobaczysz feature-branchw wynikach, to wiesz, że są scalone?
Carl G.
12

Na temat czyszczenia zdalnych gałęzi

git branch -r | xargs -t -n 1 git branch -r --contains

Zawiera listę każdej zdalnej gałęzi, a po niej zdalne gałęzie, w których znajdują się ich najnowsze SHA.

Jest to przydatne do rozpoznania, które zdalne gałęzie zostały scalone, ale nie usunięte, a które nie zostały scalone, a zatem ulegają rozkładowi.

Jeśli używasz „tig” (jest jak gitk, ale oparty na terminalach), możesz

tig origin/feature/someones-decaying-feature

aby zobaczyć historię zatwierdzania oddziału bez konieczności pobierania kasy

xxjjnn
źródło
3
Dobra robota tego człowieka! Bardzo przydatne, gdy obejrzysz to, co faktycznie wyświetla! Aplikacja GitHub musi uwzględniać to w wizualnym wyświetlaniu gałęzi, a nie alfabetyczną listę bez hierarchii!
CMash,
12

Aby sprawdzić, które gałęzie są połączone w master, należy użyć następujących poleceń:

  • git branch <flag[-r/-a/none]> --merged master lista wszystkich gałęzi scalonych w master.
  • git branch <flag[-r/-a/none]> --merged master | wc -l policz liczbę wszystkich oddziałów scalonych w master.

Flagi są:

  • -aflag - (wszystkie) pokazujące oddziały zdalne i lokalne
  • -rflag - (zdalny) pokazuje tylko zdalne gałęzie
  • <emptyFlag>- pokazywanie tylko lokalnych oddziałów

na przykład: git branch -r --merged master pokaże wszystkie zdalne repozytoria połączone w master.

avivamg
źródło
5

Oto moje techniki, kiedy muszę dowiedzieć się, czy gałąź została scalona, ​​nawet jeśli można ją było zmienić, aby była aktualna z naszą główną gałęzią, co jest częstym scenariuszem dla gałęzi funkcji.

Żadne z tych podejść nie jest głupie, ale wielokrotnie uważałem je za przydatne.

1 Pokaż dziennik dla wszystkich oddziałów

Używając wizualnego narzędzia, takiego jak gitk lub TortoiseGit, lub po prostu git log z opcją --all, przejrzyj historię, aby zobaczyć wszystkie połączenia do głównej gałęzi. Powinieneś być w stanie stwierdzić, czy ta konkretna gałąź funkcji została scalona, ​​czy nie.

2 Zawsze usuwaj zdalną gałąź podczas łączenia w gałąź funkcji

Jeśli masz dobry nawyk usuwania zarówno gałęzi lokalnej, jak i zdalnej podczas scalania w gałęzi funkcji, możesz po prostu zaktualizować i przyciąć piloty na drugim komputerze, a gałęzie funkcji znikną.

Aby to zapamiętać, używam już rozszerzeń git flow (edycja AVH) do lokalnego tworzenia i scalania moich gałęzi funkcji, dlatego dodałem następujący haczyk git flow z pytaniem, czy chcę również automatycznie usunąć gałąź zdalną.

Przykład tworzenia / zakończenia gałęzi funkcji

554 Andreas:MyRepo(develop)$ git flow start tmp
Switched to a new branch 'feature/tmp'

Summary of actions:
- A new branch 'feature/tmp' was created, based on 'develop'
- You are now on branch 'feature/tmp'

Now, start committing on your feature. When done, use:

     git flow feature finish tmp

555 Andreas:MyRepo(feature/tmp)$ git flow finish
Switched to branch 'develop'
Your branch is up-to-date with 'if/develop'.
Already up-to-date.

[post-flow-feature-finish] Delete remote branch? (Y/n)
Deleting remote branch: origin/feature/tmp.

Deleted branch feature/tmp (was 02a3356).

Summary of actions:
- The feature branch 'feature/tmp' was merged into 'develop'
- Feature branch 'feature/tmp' has been locally deleted
- You are now on branch 'develop'

556 Andreas:ScDesktop (develop)$

.git / hooks / post-flow-feature-finish

NAME=$1
ORIGIN=$2
BRANCH=$3

# Delete remote branch
# Allows us to read user input below, assigns stdin to keyboard
exec < /dev/tty

while true; do
  read -p "[post-flow-feature-finish] Delete remote branch? (Y/n) " yn
  if [ "$yn" = "" ]; then
    yn='Y'    
  fi
  case $yn in
      [Yy] ) 
        echo -e "\e[31mDeleting remote branch: $2/$3.\e[0m" || exit "$?"
        git push $2 :$3; 
        break;;
      [Nn] ) 
        echo -e "\e[32mKeeping remote branch.\e[0m" || exit "$?"
        break;;
      * ) echo "Please answer y or n for yes or no.";;
  esac
done

# Stop reading user input (close STDIN)
exec <&-
exit 0

3 Wyszukaj według komunikatu zatwierdzenia

Jeśli nie zawsze usuwasz zdalną gałąź, nadal możesz wyszukać podobne zatwierdzenia, aby ustalić, czy gałąź została scalona, ​​czy nie. Pułapka polega na tym, że gałąź zdalna została przeniesiona do nierozpoznawalnego, takiego jak zgniecenie zatwierdzeń lub zmiana komunikatów zatwierdzania.

  • Pobierz i przycinaj wszystkie piloty
  • Znajdź wiadomość o ostatnim zatwierdzeniu w gałęzi funkcji
  • Sprawdź, czy zatwierdzenie z tym samym komunikatem można znaleźć w gałęzi master

Przykładowe polecenia w gałęzi master:

gru                   
gls origin/feature/foo
glf "my message"

W moim bashu .profile config

alias gru='git remote update -p'
alias glf=findCommitByMessage

findCommitByMessage() {
    git log -i --grep="$1"
}
angularsen
źródło
@anjdeas - krok 1 - skąd wiesz, które gałęzie zostały połączone w główne. Patrzyłem na dzienniki i narzędzia GUI - i nie mogę znaleźć nigdzie, gdzie to wyraźnie pokazuje ???
The Huff,
@TheHuff Spróbuj tego:git log --all --color --graph --decorate --topo-order --date=relative --abbrev-commit --pretty=format:"%C(green)%h %C(red bold)[%<(14)%ad] %Creset%s%Cred%d%C(blue) [%an]"
angularsen
@TheHuff W TortoiseGit, jeśli jesteś w głównej gałęzi, powinien pokazywać wszystkie połączenia w main.
angularsen
Dzięki - ale skąd mam wiedzieć, co to jest scalenie? Zakładam, że wszystkie są zobowiązaniami - prawda?
The Huff
@TheHuff: Powinieneś zobaczyć wizualnie, że dwa strumienie / ścieżki zatwierdzeń łączą się w jeden zatwierdzony „downstream” (wyżej w widoku dziennika). To zatwierdzenie jest zatwierdzeniem przez scalenie. Ponadto, git logmożesz dodać, --mergesaby pokazać tylko zatwierdzenia scalania. stackoverflow.com/a/25986615/134761
angularsen
4

Oto mały linijka, która poinformuje cię, czy twoja gałąź zawiera lub nie zawiera danych ze zdalnego źródła / gałęzi master:

$ git fetch && git branch -r --merged | grep -q origin/master && echo Incorporates origin/master || echo Out of date from origin/master

Natknąłem się na to pytanie podczas pracy nad gałęzią funkcji i często chciałem się upewnić, że najnowsze prace zostały włączone do mojej osobnej gałęzi.

Aby uogólnić ten test, dodałem następujący alias do mojego ~ / .gitconfig:

[alias]
   current = !git branch -r --merged | grep -q $1 && echo Incorporates $1 || echo Out of date from $1 && :

Następnie mogę zadzwonić:

$ git current origin/master

sprawdzić, czy jestem obecny.

radke
źródło