निम्नलिखित इतिहास की कल्पना करें:
c---e---g--- feature
/ \
-a---b---d---f---h--- master
मैं कैसे पा सकता हूं जब "सी" को मास्टर में विलय कर दिया गया है (यानी, मर्ज कमिट "एच" खोजें)?
निम्नलिखित इतिहास की कल्पना करें:
c---e---g--- feature
/ \
-a---b---d---f---h--- master
मैं कैसे पा सकता हूं जब "सी" को मास्टर में विलय कर दिया गया है (यानी, मर्ज कमिट "एच" खोजें)?
जवाबों:
आपका उदाहरण दिखाता है कि शाखा featureअभी भी उपलब्ध है।
उस मामले hमें अंतिम परिणाम है:
git log master ^feature --ancestry-path
शाखा तो featureअब उपलब्ध नहीं है, तो आप के बीच इतिहास लाइन में मर्ज करता दिखा सकते हैं cऔर master:
git log <SHA-1_for_c>..master --ancestry-path --merges
हालांकि यह भी सभी का आपस में विलय के बाद हुआ दिखाई देगा h, और के बीच eऔर gपर feature।
निम्नलिखित आदेशों के परिणाम की तुलना:
git rev-list <SHA-1_for_c>..master --ancestry-path
git rev-list <SHA-1_for_c>..master --first-parent
आपको hअंतिम पंक्ति के रूप में SHA-1 देगा ।
यदि आपके पास यह उपलब्ध है, तो आप comm -1 -2इन परिणामों पर उपयोग कर सकते हैं । यदि आप msysgit पर हैं, तो आप तुलना करने के लिए निम्न पर्ल कोड का उपयोग कर सकते हैं:
perl -ne 'print if ($seen{$_} .= @ARGV) =~ /10$/' file1 file2
(से पर्ल कोड http://www.cyberciti.biz/faq/command-to-display-lines-common-in-files/ है, जो "comp.unix.shell समाचार समूह में किसी को" से ले लिया)।
यदि आप इसे एक-लाइनर बनाना चाहते हैं, तो प्रक्रिया प्रतिस्थापन देखें ।
masterमें विलय हो गया feature, तो तुरंत featureमें विलय कर दिया गया है masterतेजी से आगे (की नोक के रूप में featureकी जगह master)। क्या वह --first-parentगलत माता-पिता को वापस करने का कारण होगा ?
comm -1 -2लेकिन यह काम नहीं किया। commकेवल हल की गई लाइनों पर काम करता है। (पर्ल वन-लाइनर काम करता है, हालांकि मैं इसे नहीं पढ़ सका।)
git find-merge h master(कुछ भी नहीं है लेकिन एच वापस लौटना चाहिए), git find-merge d master(रिटर्न एफ लेकिन डी वापस लौटना चाहिए), git find-merge c feature(रिटर्न ई लेकिन जी लौटना चाहिए)।
इसे अपने में जोड़ें ~/.gitconfig:
[alias]
find-merge = "!sh -c 'commit=$0 && branch=${1:-HEAD} && (git rev-list $commit..$branch --ancestry-path | cat -n; git rev-list $commit..$branch --first-parent | cat -n) | sort -k2 -s | uniq -f1 -d | sort -n | tail -1 | cut -f2'"
show-merge = "!sh -c 'merge=$(git find-merge $0 $1) && [ -n \"$merge\" ] && git show $merge'"
तो आप इस तरह उपनाम का उपयोग कर सकते हैं:
# current branch
git find-merge <SHA-1>
# specify master
git find-merge <SHA-1> master
मर्ज कमिट के संदेश और अन्य विवरण देखने के लिए, का उपयोग करें git show-merge उसी तर्कों के साथ ।
( गौथियर के जवाब पर आधारित । रोसेन माटेव और धन्यवाद के साथ एक समस्या को ठीक करने के लिए javabrettsort ।)
sort -k2 | uniq -f1 -d | sort -n | tail -1 | cut -f2सामान्य रूप से अंतिम पंक्ति को सही ढंग से नहीं ढूंढ रहा है। यहाँ एक उदाहरण है जहाँ यह विफल रहता है।
16db9fef5c581ab0c56137d04ef08ef1bf82b0b7जब मैं इसे आपके पेस्ट पर चलाता हूं, तो यह पता चलता है कि क्या यह अपेक्षित नहीं है? आप किस ओएस पर हैं?
29c40c3a3b33196d4e79793bd8e503a03753bad1
गिट-गेट-मर्ज का पता लगाएगा और उस मर्ज कमिट को दिखाएगा, जिसकी आप तलाश कर रहे हैं:
pip install git-get-merge
git get-merge <SHA-1>
कमांड दिए गए कमिट के बच्चों का अनुसरण तब तक करता है जब तक कि दूसरी ब्रांच में विलय (संभवतः मास्टर) नहीं मिल जाता।
गौथियर के पद को संक्षेप में प्रस्तुत करना है:
perl -ne 'print if ($seen{$_} .= @ARGV) =~ /10$/' <(git rev-list --ancestry-path <SHA-1_for_c>..master) <(git rev-list --first-parent <SHA-1_for_c>..master) | tail -n 1
EDIT: क्योंकि यह प्रक्रिया प्रतिस्थापन " <()" का उपयोग करता है , यह POSIX संगत नहीं है, और यह आपके शेल के साथ काम नहीं कर सकता है। यह साथ bashया zshयद्यपि काम करता है ।
<()POSIX संगत नहीं है। आपको उपयोग करने की आवश्यकता है bash, zshया शेल सपोर्टिंग प्रोसेस प्रतिस्थापन है । मैंने उसी के अनुसार अपना उत्तर संपादित किया।
मुझे ऐसा करने की ज़रूरत थी, और किसी तरह पाया गया git-when-merged(जो वास्तव में इस एसओ प्रश्न का संदर्भ देता है, लेकिन माइकल हाग्गर्टी ने कभी भी अपनी बहुत अच्छी पायथन स्क्रिप्ट का संदर्भ नहीं जोड़ा)। तो अब मेरे पास है।
Gauthier के महान उत्तर पर बिल्डिंग, हमें commसूचियों की तुलना करने के लिए उपयोग करने की आवश्यकता नहीं है । चूंकि हम अंतिम परिणाम की तलाश कर रहे हैं, --ancestry-pathजिसमें --first-parentहम भी हैं , हम बस पूर्व के आउटपुट में बाद के लिए जीआरपी कर सकते हैं:
git rev-list <SHA>..master --ancestry-path | grep -f <(git rev-list <SHA>..master --first-parent) | tail -1
या कुछ दुखी और पुन: प्रयोज्य के लिए, यहाँ एक समारोह पॉप में है .bashrc:
function git-find-merge() {
git rev-list $1..master --ancestry-path | grep -f <(git rev-list $1..master --first-parent) | tail -1
}
commइनपुट्स सॉर्ट नहीं किए जाने पर काम नहीं किया।
रूबी भीड़ के लिए, वहाँ git-whence है । बहुत आसान।
$ gem install git-whence
$ git whence 1234567
234557 Merge pull request #203 from branch/pathway
मैं बैश स्क्रिप्ट का उपयोग करता हूं, जिसे मैं पथ पर रखता हूं ~/bin/git-find-merge। यह कोने के मामलों को संभालने के लिए कुछ ट्वीक्स के साथ गौथियर के जवाब और बैडस्ट्रेक के उत्तर पर आधारित है । commजब इनपुट सॉर्ट नहीं किए जाते हैं तो फेंकता है। grep -fअच्छी तरह से काम।
कोने के मामले:
~/bin/git-find-merge स्क्रिप्ट:
#!/bin/bash
commit=$1
if [ -z $commit ]; then
echo 1>&2 "fatal: commit is required"
exit 1
fi
commit=$(git rev-parse $commit)
branch=${2-@}
# if branch points to commit (both are same), then return commit
if [ $commit == $(git rev-parse $branch) ]; then
git log -1 $commit
exit
fi
# if commit is a merge commit on first-parent path of branch,
# then return commit
# if commit is a NON-merge commit on first-parent path of branch,
# then return branch as it's either a ff merge or commit is only on branch
# and there is not a good way to figure out the right commit
if [[ $(git log --first-parent --pretty='%P' $commit..$branch | \
cut -d' ' -f1 | \
grep $commit | wc -l) -eq 1 ]]; then
if [ $(git show -s --format="%P" $commit | wc -w) -gt 1 ]; then
# if commit is a merge commit
git log -1 $commit
else
# if commit is a NON-merge commit
echo 1>&2 ""
echo 1>&2 "error: returning the branch commit (ff merge or commit only on branch)"
echo 1>&2 ""
git log -1 $branch
fi
exit
fi
# 1st common commit from bottom of first-parent and ancestry-path
merge=$(grep -f \
<(git rev-list --first-parent $commit..$branch) \
<(git rev-list --ancestry-path $commit..$branch) \
| tail -1)
if [ ! -z $merge ]; then
git log -1 $merge
exit
fi
# merge commit not found
echo 1>&2 "fatal: no merge commit found"
exit 1
जो मुझे यह करने देता है:
(master)
$ git find-merge <commit> # to find when commit merged to current branch
$ git find-merge <branch> # to find when branch merged to current branch
$ git find-merge <commit> pu # to find when commit merged to pu branch
यह लिपि मेरे गितुब पर भी उपलब्ध है ।
@ रॉबिन्सन के विचार का मेरा माणिक संस्करण, दो बार तेजी से काम करता है (जो बहुत पुरानी प्रतिबद्धताओं की खोज करते समय महत्वपूर्ण है)।
find-commit.rb
commit = ARGV[0]
master = ARGV[1] || 'origin/master'
unless commit
puts "Usage: find-commit.rb commit [master-branch]"
puts "Will show commit that merged <commit> into <master-branch>"
exit 1
end
parents = `git rev-list #{commit}..#{master} --reverse --first-parent --merges`.split("\n")
ancestry = `git rev-list #{commit}..#{master} --reverse --ancestry-path --merges`.split("\n")
merge = (parents & ancestry)[0]
if merge
system "git show #{merge}"
else
puts "#{master} doesn't include #{commit}"
exit 2
end
आप इसे इस तरह से उपयोग कर सकते हैं:
ruby find-commit.rb SHA master
आप कुछ इस तरह की कोशिश कर सकते हैं। यह विचार सभी मर्ज कमिट के माध्यम से पुनरावृति करना है और देखें कि क्या कमिट "सी" उनमें से किसी एक से उपलब्ध है:
$ git log --merges --format='%h' master | while read mergecommit; do
if git log --format='%h' $mergecommit|grep -q $c; then
echo $mergecommit;
break
fi
done
git rev-list <SHA-1_for_c>..master --ancestry-path --merges
मुझे यह कई बार करना पड़ा (इस प्रश्न का उत्तर देने वाले सभी के लिए धन्यवाद!), और एक पटकथा लिखना (Gauthier’s method का उपयोग करके) जिसे मैं अपने छोटे से संग्रह में उपयोगिताओं में जोड़ सकता था। आप इसे यहाँ पा सकते हैं: https://github.com/mwoehlke/git-utils/blob/master/bin/git-merge-point ।