2011-02-28 4 views
105

कुछ स्क्रिप्ट्स हैं जो परिवर्तनों की जांच करते समय सही तरीके से काम नहीं करती हैं।यदि मेरे स्थानीय गिट भंडार में बदलाव आया है तो मैं बैश स्क्रिप्ट में कैसे जांच सकता हूं?

मैं इसे इस तरह की कोशिश की:

VN=$(git describe --abbrev=7 HEAD 2>/dev/null) 

git update-index -q --refresh 
CHANGED=$(git diff-index --name-only HEAD --) 
if [ ! -z $CHANGED ]; 
    then VN="$VN-mod" 
fi 

वहाँ बूलियन जांच किसी तरह का है तभी, जब परिवर्तन के बाद से पिछले प्रतिबद्ध किया गया है, या कैसे मैं वास्तव में परीक्षण कर सकते हैं, अगर वहाँ अपने स्थानीय भंडार के लिए नए परिवर्तन कर रहे हैं?

मैं यह सब एक संस्करण निर्माण स्क्रिप्ट के लिए कर रहा हूं (जिसे मैंने कहीं कहीं पाया)।

+2

'गिट स्थिति' के साथ क्या गलत है? – karlphillip

+2

@karlphipip: यह बहुत सारी प्रसंस्करण करता है जिसकी आपको वास्तव में आवश्यकता नहीं है। – Cascabel

उत्तर

128

तुम क्या कर रहे हैं काम लगभग जाएगा: आप खाली के लिए $CHANGED मामले में यह खाली है, और -z परीक्षण बोली चाहिए, जो कोई बदलाव नहीं होता है। क्या आप मतलब था:

if [ -n "$CHANGED" ]; then 
    VN="$VN-mod" 
fi 

एक उद्धरण Git के GIT-VERSION-GEN से:

git update-index -q --refresh 
test -z "$(git diff-index --name-only HEAD --)" || 
VN="$VN-dirty" 

ऐसा लगता है कि आपको लगता है कि कॉपी करने गए थे, लेकिन आप सिर्फ इतना है कि हवाले से की विस्तार भूल गया।

बेशक

, आप भी बस ऐसा कर सकता है:

if git diff-index --quiet HEAD --; then 
    # No changes 
else 
    # Changes 
fi 

या यदि आप केवल "कुछ बदल गया है" मामले के बारे में परवाह:

if ! git diff-index --quiet HEAD --; then 
    VN="$VN-mod" 
fi 

--quiet का प्रयोग लाभ यह है कि Git कर सकते है जैसे ही यह एक अलग अंतर का सामना कर रहा है, प्रसंस्करण बंद करो, इसलिए इसे आपके पूरे कार्य पेड़ की जांच नहीं करनी पड़ेगी।

+2

हाय, यह एक प्रश्न पर सबसे अच्छे उत्तरों में से एक था, आपने मुझे केवल वह सारी जानकारी दी जो मुझे चाहिए और दूसरों को भी मेरी ज़रूरत है :)। मुझे बस आखिरी की आवश्यकता होगी, "कुछ बदल गया है" :) और आप सही थे, मैंने इसकी प्रतिलिपि बनाई। – kmindi

+6

अद्भुत [बैश समापन स्क्रिप्ट] (http://git.kernel.org/?p=git/git.git;a=blob_plain;f=contrib/completion/git-completion.bash;hb=HEAD) ऐसा लगता है गंदे राज्य को निर्धारित करने के लिए 'गिट diff --no-ext-diff --quiet --exit-code' का उपयोग करें। – mjs

+2

@ एमजेएस: यह वास्तव में ऐसी चीजों को देखने के लिए एक शानदार जगह है! '--no-ext-diff' विकल्प सुरक्षा के लिए अच्छा है (यदि किसी ने बाहरी diff ड्राइवर को कॉन्फ़िगर किया है), हालांकि' --exit-code' आवश्यक नहीं होना चाहिए, क्योंकि यह '--quiet द्वारा निहित है '। – Cascabel

14

हालांकि जेफ्रोमी का जवाब अच्छा है, मैं इसे संदर्भ के लिए पोस्ट कर रहा हूं।

गिट स्रोत कोड से sh स्क्रिप्ट है जिसमें निम्न शामिल हैं।

require_clean_work_tree() { 
    git rev-parse --verify HEAD >/dev/null || exit 1 
    git update-index -q --ignore-submodules --refresh 
    err=0 

    if ! git diff-files --quiet --ignore-submodules 
    then 
     echo >&2 "Cannot $1: You have unstaged changes." 
     err=1 
    fi 

    if ! git diff-index --cached --quiet --ignore-submodules HEAD -- 
    then 
     if [ $err = 0 ] 
     then 
      echo >&2 "Cannot $1: Your index contains uncommitted changes." 
     else 
      echo >&2 "Additionally, your index contains uncommitted changes." 
     fi 
     err=1 
    fi 

    if [ $err = 1 ] 
    then 
     test -n "$2" && echo >&2 "$2" 
     exit 1 
    fi 
} 
6

मुझे एक ही समस्या थी, लेकिन मुझे अतिरिक्त फ़ाइलों को भी जांचना पड़ा।

cd /local/repo 
RUN=0 
git diff --no-ext-diff --quiet --exit-code || RUN=1 
if [ $RUN = 0 ]; then 
    RUN=`git ls-files --exclude-standard --others| wc -l` 
fi 

if [ $RUN = 0 ]; then 
    exit 0 
fi 
0

यहाँ कैसे मैं यह कर रहा है ...

CHANGES=`git status | grep "working directory clean"` 
if [ ! CHANGES -eq "" ] then 
    # do stuff here 
else 
    echo "You have uncommitted changes..." 
fi 
+3

मुझे गिट स्थिति का उपयोग करना पसंद है, लेकिन स्क्रिप्ट में - निर्यात करने के लिए बेहतर है और परिणामों को किसी भी बदलाव के लिए खाली स्ट्रिंग में तुलना करने के लिए बेहतर है, क्योंकि यह गारंटी है कि संस्करणों में एक असंगत तरीके से नहीं बदला जाए। –

152

git status का उपयोग करना::

cd /git/directory 
if [[ `git status --porcelain` ]]; then 
    # Changes 
else 
    # No changes 
fi 
+6

सबसे अच्छा जवाब, शेल और गिट आर्किटेक्ट्स के जवाबों को शर्मिंदा करने के लिए अधिक शर्मिंदा हैं। – jwg

+0

ठीक है, अन्य उत्तरों सही हैं, लेकिन यह वही है जो मैं ढूंढ रहा था। धन्यवाद! – SuperJames

+2

यह बहुत अच्छा है क्योंकि यह बदली हुई फ़ाइलों को ध्यान में रखता है और चीनी मिट्टी के बरतन का उपयोग भी करता है, यह विभिन्न गिट संस्करणों के साथ अधिक संगत होना चाहिए। – Jayd

0

यह अच्छी तरह से काम करता है तो मैं निम्नलिखित किया था। यह भी सूची जाएगा फ़ाइलें प्रभावित:

if git diff-index --name-status --exit-code HEAD; 
then 
    echo Git working copy is clean...; 
else 
    echo ; 
    echo ERROR: Git working copy is dirty!; 
    echo Commit your changes and try again.; 
fi; 
1

यहाँ, बैश स्क्रिप्ट कार्यों का एक अच्छा सेट है कि जाँच अगर वहाँ एक अंतर है उपयोगकर्ता के लिए यह प्रिंट और उपयोगकर्ता को संकेत देता है अगर वे तैनाती से पहले परिवर्तनों को प्रतिबद्ध करने के लिए चाहते हैं । यह एक हेरोकू और पायथन आवेदन के लिए बनाया गया है, लेकिन इसे किसी अन्य एप्लिकेशन के लिए थोड़ा बदलाव की जरूरत है।

commit(){ 
    echo "Please enter a commit message..." 
    read msg 
    git add . --all 
    git commit -am $msg 
} 

check_commit(){ 
    echo ========== CHECKING FOR CHANGES ======== 
    changes=$(git diff) 
    if [ -n "$changes" ]; then 
     echo "" 
     echo "*** CHANGES FOUND ***" 
     echo "$changes" 
     echo "" 
     echo "You have uncomitted changes." 
     echo "Would you like to commit them (y/n)?" 
     read n 
     case $n in 
      "y") commit;; 
      "n") echo "Changes will not be included...";; 
      *) echo "invalid option";; 
     esac 
    else 
     echo "... No changes found" 
    fi 
} 

deploy(){ 
    check_commit 
    echo ========== DEPLOYING TO HEROKU ======== 
    git push heroku master 
    heroku run python manage.py syncdb 
} 

आप पर gists से कॉपी कर सकते हैं: https://gist.github.com/sshadmand/f33afe7c9071bb725105

1

git status अपने दोस्त

git status के लिए Git निर्देशिका को बदलें काम करने के लिए है:

cd c:/path/to/.git 

एक चर के लिए सेट करें कार्य पेड़ सेट करें ताकि आपको 'यह ऑपरेशन किसी कार्य पेड़ में चलाना आवश्यक न हो' त्रुटि:

WORKTREE=c:/path/to/worktree 

कैद एक बैश चर में git status उत्पादन

उपयोग --porcelain जो एक मानक प्रारूप और parsable में होने की गारंटी देता है:

CHANGED=$(git --work-tree=${WORKTREE} status --porcelain) 

तो -n (शून्य नहीं), हम परिवर्तन है ।

if [ -n "${CHANGED}" ]; then 
    echo 'changed'; 

else 
    echo 'not changed'; 
fi 
+0

यह अनचाहे फ़ाइलों का पता लगाने का लाभ भी है। –

संबंधित मुद्दे