क्या Git प्रोजेक्ट की सभी शाखाओं में 'grep खोज' करना संभव है?


138

क्या यह git grepएक गिट नियंत्रण वाली परियोजना की सभी शाखाओं के अंदर चलना संभव है ? या चलाने के लिए एक और आदेश है?



जवाबों:


189

सवाल " कैसे grep (खोज) git इतिहास में कोड प्रतिबद्ध है? "

 git grep <regexp> $(git rev-list --all)

वह सभी आवागमन के माध्यम से खोज करता है, जिसमें सभी शाखाएं शामिल होनी चाहिए।

एक और रूप होगा:

git rev-list --all | (
    while read revision; do
        git grep -F 'yourWord' $revision
    done
)

आप इस लेख में और भी उदाहरण पा सकते हैं :

मैंने ऊपर एक परियोजना पर बड़ी कोशिश की कि तर्क आकार के बारे में शिकायत की, इसलिए यदि आप इस समस्या में भाग लेते हैं, तो कुछ ऐसा करें:

git rev-list --all | (while read rev; do git grep -e <regexp> $rev; done)

(इस उत्तर के अंतिम भाग में एक विकल्प देखें, नीचे)

यदि आप उन्हें चाहते हैं, तो उन सेटिंग्स को न भूलें:

# Allow Extended Regular Expressions
git config --global grep.extendRegexp true
# Always Include Line Numbers
git config --global grep.lineNumber true

यह उपनाम भी मदद कर सकता है:

git config --global alias.g "grep --break --heading --line-number"

नोट: chernjie ने सुझाव दिया कि git rev-list --allयह एक ओवरकिल है।

एक अधिक परिष्कृत कमांड हो सकती है:

git branch -a | tr -d \* | xargs git grep <regexp>

जो आपको केवल शाखाओं को खोजने की अनुमति देगा (दूरस्थ शाखाओं सहित)

आप इसके लिए एक बैश / zsh उपनाम भी बना सकते हैं:

alias grep_all="git branch -a | tr -d \* | xargs git grep"
grep_all <regexp>

अगस्त 2016 को अपडेट करें: RM टिप्पणियों में अनुशंसा करता है

संस्करण की fatal: bad flag '->' used after filenameकोशिश करते समय मुझे एक " " मिला git branch। त्रुटि HEADअलियासिंग संकेतन के साथ जुड़ी हुई थी ।

मैंने इसे sed '/->/d'पाइप में, trऔर xargsकमांड के बीच में जोड़कर हल किया ।

 git branch -a | tr -d \* | sed '/->/d' | xargs git grep <regexp>

अर्थात्:

alias grep_all="git branch -a | tr -d \* | sed '/->/d' | xargs git grep"
grep_all <regexp>

git branchTr या sed के आउटपुट को पाइप करना अच्छा विचार नहीं है ; git branchएक चीनी मिट्टी के बरतन आदेश मानव उपभोग के लिए है। पसंदीदा विकल्पों के लिए stackoverflow.com/a/3847586/2562319 देखें ।
जेबलर

@jbyler अच्छा बिंदु। विडंबना यह है कि मैंने इस उत्तर से बहुत पहले पोर्सिलेन पर उत्तर पोस्ट किया: stackoverflow.com/a/6978402/6309 । और मैं इसका उपयोग stackoverflow.com/a/19206916/6309 में उदाहरण के लिए करता हूँ ।
VonC

हाँ, अच्छा है। अन्य उत्तरों को देखते हुए, मुझे लगता है कि @errordeveloper द्वारा उत्तर सबसे साफ है: stackoverflow.com/a/21284342/2562319 : "git grep <regexp> $ (git for-each-ref -format = '% (refname) /
रेफ्स

1
क्या खोज का मिलान करने वाली शाखा का नाम दिखाने का कोई तरीका है?
franksands

63

git log सभी शाखाओं में पाठ की खोज करने का एक अधिक प्रभावी तरीका हो सकता है, खासकर अगर कई मैच हैं, और आप अधिक हाल ही में (प्रासंगिक) परिवर्तन देखना चाहते हैं।

git log -p --all -S 'search string'
git log -p --all -G 'match regular expression'

ये लॉग कमांड सूची बताती है कि दिए गए खोज स्ट्रिंग / regex को जोड़ दें या हटा दें, (आमतौर पर) पहले हाल ही में। -pविकल्प प्रासंगिक diff, जहां पैटर्न जोड़ा गया है या हटा दिया दिखाया जा सकता है, तो आप इसे संदर्भ में देख सकते हैं का कारण बनता है।

एक प्रासंगिक कमिट मिला है जो आपके द्वारा खोजे जा रहे पाठ को जोड़ता है (उदाहरण। 8beeff00d), उन ब्रांचों को खोजें, जिनमें कमिट हैं:

git branch -a --contains 8beeff00d

22

मुझे यह सबसे उपयोगी लगा:

git grep -i foo `git for-each-ref --format='%(refname)' refs/`

आपको अंतिम तर्क को इस आधार पर समायोजित करना होगा कि क्या आप केवल दूरस्थ बनाम स्थानीय शाखाओं को देखना चाहते हैं, अर्थात:

  • git grep -i foo $(git for-each-ref --format='%(refname)' refs/remotes)
  • git grep -i foo $(git for-each-ref --format='%(refname)' refs/heads)

मेरे द्वारा बनाया गया उपनाम इस प्रकार है:

grep-refs = !sh -c 'git grep "$0" "$@" "$(git for-each-ref --format=\"%(refname)\"" refs/)'

1
दिलचस्प उर्फ। +1। मेरे उत्तर की तुलना में अधिक सटीक।
VonC

वाक्यांश खोज के लिए काम करने के लिए अपना उपनाम कैसे बनाएं? जब मैं एक पैरामीटर के रूप में "फू बार" पास करता हूं, तो मुझे मिलता है: घातक: अस्पष्ट तर्क 'बार': अज्ञात संशोधन या काम करने वाले पेड़ में नहीं। संशोधन से '-' पथ को अलग करने के लिए उपयोग करें
jutky

अंतरिक्ष से बचने की कोशिश करें: "फू \ बार"
गैरी गोमेज़

यह स्पष्ट रूप से स्वीकृत उत्तर होगा;) मैंने इसे अपनी परियोजना की नवीनतम शाखाओं में खोज करने के लिए विस्तारित किया है (500 से अधिक प्राप्त करें, मत पूछो, और प्रत्येक grep 4sec के बारे में लेता है इसलिए मुझे नहीं चाहिए और न ही आवश्यकता है) से अधिक खोज करने के लिए, कहते हैं, उनमें से 100 नवीनतम)। इसके लिए मैंने अपडेट किया git for-each-refहै --sort=-committerdate --count=100! मूल विचार के लिए धन्यवाद!
Vser

6

इसे दो सामान्य तरीकों से करना संभव है: बैश या गिट अलायस

यहाँ तीन आदेश दिए गए हैं:

  1. git grep-branch - सभी शाखाओं में खोजें स्थानीय और दूरस्थ
  2. git grep-branch-local - स्थानीय शाखाओं में ही खोजें
  3. git grep-branch-remote - दूरस्थ शाखाएँ ही

उपयोग के रूप में ही है git grep

git grep-branch "find my text"
git grep-branch --some-grep-options "find my text"

जीआरई उपनाम: जीआईटी अलायस

फ़ाइल ~ / .gitconfig

कमांड को ~/.gitconfigफाइल करने के लिए मैन्युअल रूप से जोड़ा जाना चाहिए , क्योंकि git config --global aliasआपके द्वारा जोड़े गए जटिल कोड का मूल्यांकन करें और इसे गड़बड़ करें।


[alias]
    grep-branch        = "!f(){ git branch -a | sed -e 's/[ \\*]*//' | grep -v -e '\\->' | xargs git grep $@; };f "
    grep-branch-remote = "!f(){ git branch -a | sed -e 's/[ \\*]*//' | grep -v -e '\\->' | grep '^remotes' | xargs git grep $@; };f"
    grep-branch-local  = "!f(){ git branch -a | sed -e 's/[ \\*]*//' | grep -v -e '\\->' -e '^remotes' | xargs git grep $@;  };f "

नोट: जब आप उपनाम जोड़ते हैं और वे चलाने में विफल रहते हैं - बैश कमांड की तुलना में बैकस्लैश की जांच \कर सकते हैं, तो उन्हें अतिरिक्त भागने की आवश्यकता हो सकती है ।\\

  • git branch -a - सभी शाखाओं को प्रदर्शित करें;
  • sed -e 's/[ \\*]*//'- ट्रिम स्पेस (से branch -a) और * (सक्रिय शाखा का नाम इसके पास है);
  • grep -v -e '\\->'- जैसे जटिल नामों को अनदेखा करें remotes/origin/HEAD -> origin/master;
  • grep '^remotes' - सभी दूरस्थ शाखाएं प्राप्त करें;
  • grep -v -e '^remotes'- दूरस्थ शाखाओं को छोड़कर शाखाएं प्राप्त करें ;

उदाहरण git grep-branch-local -n getTastyCookies

-n मिलान संख्याओं के लिए पंक्ति संख्या उपसर्ग करें।

[user@pc project]$ git grep-branch-local -n getTastyCookies

dev:53:modules/factory/getters.php:function getTastyCookies($user);
master:50:modules/factory/getters.php:function getTastyCookies($user)

वर्तमान संरचना है:

: - विभाजक

  1. डाली: dev
  2. रेखा संख्या: 53
  3. फ़ाइल पथ: modules/factory/getters.php
  4. मिलान लाइन: function getTastyCookies($user)

GREP का उपयोग कर: BASH

जैसा कि आपको पता होना चाहिए: बैश कमांड को .shस्क्रिप्ट में संग्रहीत किया जाना चाहिए या शेल में चलाया जाना चाहिए ।

केवल स्थानीय शाखाएँ

git branch -a | sed -e 's/[ \*]*//' | grep -v -e '\->' -e '^remotes' | xargs git grep "TEXT"

केवल दूरस्थ शाखाएँ

git branch -a | sed -e 's/[ \*]*//' | grep -v -e '\->' | grep '^remotes' | xargs git grep "TEXT"

स्थानीय और दूरस्थ शाखाएँ

git branch -a | sed -e 's/[ \*]*//' | grep -v -e '\->' | xargs git grep "TEXT"

अच्छा लगता है, लेकिन मुझे यह त्रुटि मिली git grep-branch "find my text":fatal: ambiguous argument 'client': both revision and filename
nealmcb

हमेशा उपयोग क्यों करें -a, जो सभी शाखाओं को दर्शाता है? मैं सुझाव देता हूं कि git branchआदेशों के विकल्प का उपयोग करके अलग-अलग शिलालेखों को अलग किया जाए। जब स्थानीय शाखाओं को देखते हैं, तो केवल एक ही होता है *, इसलिए इसे सेड के लिए भागने की कोई आवश्यकता नहीं है। इसलिए: git branch | sed -e 's/*/ /' | xargs git grep "TEXT"केवल स्थानीय शाखाओं के git branch -r | grep -v -- "->" | xargs git grep "TEXT"लिए , केवल दूरस्थ शाखाओं के git branch -a | grep -v -- "->" | xargs git grep "TEXT"लिए और सभी शाखाओं के लिए
जालानब

4

यहां बताया गया है कि मैं यह कैसे करता हूं:

git for-each-ref --format='%(*refname)' | xargs git grep SEARCHTERM

2
एकमात्र समाधान जिसने मेरे लिए विंडोज पर काम किया (गिट बश में)
इवान

4

यदि आप किसी भी SHA-1 हैश मूल्य को कमिट करते git grepहैं, तो आपके पास काम की प्रति के बजाय उनमें यह खोज है।

सभी शाखाओं की खोज करने के लिए, आप सभी पेड़ों को प्राप्त कर सकते हैं git rev-list --all। यह सब साथ रखो

git grep "regexp" $(git rev-list --all)

... और धैर्य रखें

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.