コミットIDが与えられた場合、現在のブランチにコミットが含まれているかどうかを判断するにはどうすればよいですか?


156

私がやろうとしているのはバージョンチェックです。私はコードが最小バージョンの上にとどまることを確実にしたいです。したがって、現在のブランチに指定されたコミットが含まれているかどうかを知る方法が必要です。



10
指定されたコミットを含むすべてのブランチを見つける方法については、提案された複製を参照してください。現在のブランチにcommit Cが含まれているかどうかを確認するには、「plumbing」コマンドを使用しgit merge-base --is-ancestorます。Cがの祖先である場合、現在のブランチにはCが含まれるため、次のようになりますHEADif git merge-base --is-ancestor $hash HEAD; then echo I contain commit $hash; else echo I do not contain commit $hash; fi
。– torek

1
こんにちは。正解として選択できるように、これを回答として送信してください=)
Ben

1
@Ben-コミュニティのwikiの回答として追加しました。
Zitrax 2018

1
@Remover:シェルスクリプトでは、ゼロはtrue、非ゼロはfalseです。Cの規則の逆です。/bin/trueは、exit 0および/bin/falseとして元々実装されていましたexit 1。(その後、最新の砲弾が組み込まれています。)
torek

回答:


220

この結果を達成する方法はいくつかあります。最初の素朴なオプションは、を使用git logして特定のコミットを使用して検索するgrepことですが、常に正確であるとは限りません

git log | grep <commit_id>

あなたはgit branch与えられたCOMMIT_ID使用を含むすべてのブランチを見つけるために直接使用する方が良いです

git branch --contains $COMMIT_ID

次のステップは、git 1.8.1使用してから実行できる現在のブランチを見つけることです

git symbolic-ref --short HEAD

と一緒に組み合わせる

git branch $(git symbolic-ref --short HEAD) --contains $COMMIT_ID

しかし、上記のコマンドはtrueまたはfalseを返さず、コミットが現在のブランチにある場合は終了コード0を返し、そうでない場合は終了コード1を返す短いバージョンがあります。

git merge-base --is-ancestor $COMMIT_ID HEAD

終了コードはいいですが、文字列が必要な場合truefalse回答として、もう少し追加してifからbash と組み合わせる必要があります

if [ 0 -eq $(git merge-base --is-ancestor $COMMIT_ID HEAD) ]; then echo "true"; else echo "false"; fi

9
それは正しくありません。別のブランチからのポートの結果としてコミットメッセージで言及されているなど、他の理由でコミットSHAについて言及しているgrep場合、誤検知になる可能性がありgit logます。
Adam Spiers 2017

1
修正されました(または別のオプションが追加されました)。
JiriS 2017

3
組み込みのgitツールセットを使用する質問のコメントを参照してください。 stackoverflow.com/questions/43535132/...
ベン

2
私は最初のオプションが好きですが、アダムの異議を排除するには、オプション--format=format:%Hをに追加しますgit log
PJSCopeland

71

特定のコミットを含むブランチのリストを取得します。

# get all the branches where the commit exists
$ git branch --contains <commit-id>

ブランチに特定のコミットがあるかどうかを確認します。

# output the branch-name if the commit exists in that branch
$ git branch --contains <commit-id> | grep <branch-name>

完全一致のブランチ(たとえば、feature)を検索します。

$ git branch --contains <commit-id> | grep -E '(^|\s)feature$'

例えば、あなたが3つの支部が呼び出されている場合はfeaturefeature1feature2その後、

$ git branch --contains <commit-id> | grep 'feature'

# output
feature
feature1
feature2

$ git branch --contains <commit-id> | grep -E '(^|\s)feature$'

# output
feature     

localおよびremoteブランチの両方(を使用-a)またはremoteブランチのみ(を使用)で検索することもでき-rます。

# search in both 'local' & 'remote' branches  
$ git branch -a --contains <commit-id> | grep -E '(^|\s)feature$'

# search in 'remote' branches  
$ git branch -r --contains <commit-id> | grep -E '(^|\s)feature$'

1
grep名前も含まれてコミット含む他の枝がある場合は、ここでまた偽陽性につながる可能性が<branch-name>列として。
Adam Spiers 2017

1
はい、@ AdamSpiers、ブランチ名と完全に一致するように回答を更新しましたgrep -E '(^|\s)branchname$'
Khan

1
関連する質問に関するこのコメントによれば、-r(「リモート」)または-a(「すべて」)オプションを追加しgit branchて、ローカルレポク​​ローンで複製されない可能性のあるブランチを探すと便利です。
sxc731

これは私にはうまくいきませんでした、私は必要でした git branch --all --contains <commit-id>
Arthur Tacca

7

@torekが回答として抽出したコメント:

指定されたコミットを含むすべてのブランチを見つける方法については、提案された複製を参照してください。

現在のブランチにcommit Cが含まれているかどうかを確認するには、「plumbing」コマンドを使用しgit merge-base --is-ancestorます。CがHEADの祖先である場合、現在のブランチにはCが含まれます。

if git merge-base --is-ancestor $hash HEAD; then
    echo I contain commit $hash
else
    echo I do not contain commit $hash
fi

(補足:シェルスクリプトでは、ゼロ以外で終了するコマンドは「false」ですが、ゼロで終了するコマンドは「true」です。)


4

commitを含むローカルブランチを一覧表示するには:

git branch --contains <commit-id>

そして、コミットのみを含む、リモートのみを含むすべてのブランチをリストするには:

git branch -a --contains <commit-id>

同様に、コミットが特定のブランチにあるかどうかを確認するには:

git log <branch> | grep <commit_id>

ブランチがローカルに存在しない場合は、ブランチ名の前に origin/


の発言に投票しました-a。そのアドバイスをありがとう!
ThorkilVærge

3

うん別の選択肢:

git rev-list <branch name> | grep `git rev-parse <commit>`

それはのようなローカルにキャッシュされたリモートブランチでの作業も出来これは私にとって最高の作品remotes/origin/master、その上に、git branch --contains機能しません。

これは「現在のブランチ」に関するOPの質問以上のものをカバーしていますが、私はこの質問の「任意のブランチ」バージョンを尋ねるのは馬鹿げていると思うので、とにかくここに投稿することにします。


1
git branch --contains <commit-id> --points-at <target branch name>

コミットIDがそのブランチに存在する場合、ターゲットブランチ名を返します。そうでない場合、コマンドは失敗します。


いいえ...error: malformed object name 'branch-name'
bbodenmiller

1
2つのケースでこのエラーが発生する可能性があります。1.指定された<ブランチ名>に指定された<コミットID>が含まれていない場合2.チェックアウト<ブランチ名>が指定された<ブランチ名>ではありません
DreamUth

0

この質問にはすばらしいスクリプトの回答があるため、お気に入りを追加します。

これ$nは、$brブランチにそれぞれが含まれている最後のコミットについて表示します:

br=mybranch
n=10
git log --oneline -n$n $br | awk '{print; system("git branch --contains "$1)}'

これは似ていますが、ブランチのリストに対して同じです:

br="mybranch yourbranch herbranch"
n=4
for br in $brs; do git log --oneline -n$n $br | awk '{print; system("git branch --contains "$1)}'; done
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.