मुझे लगता है कि आपका मूल मुद्दा यह है कि आप गलत समझ रहे हैं और / या गलतफहमी है कि यह क्या करता है और यह क्यों करता है।
जब आप कुछ अन्य रिपॉजिटरी को क्लोन करते हैं, तो git "वहाँ पर" जो कुछ भी है, उसकी एक प्रति बनाता है। यह "उनके" शाखा लेबल को भी लेता है, जैसे कि master, और उस लेबल की एक प्रतिलिपि बनाता है जिसका "पूरा नाम" आपके गिट ट्री में है (सामान्य रूप से) remotes/origin/master(लेकिन आपके मामले में remotes/upstream/master)। अधिकांश समय आपको remotes/भाग को छोड़ना पड़ता है, इसलिए आप उस मूल प्रति का उल्लेख कर सकते हैं upstream/master।
यदि आप अब कुछ फ़ाइल (ओं) में कुछ परिवर्तन (परिवर्तन) करते हैं, तो आप उन परिवर्तनों के साथ एक ही हैं। इस बीच अन्य लोग अन्य क्लोन बनाने और उन क्लोन को बदलने के लिए मूल रिपॉजिटरी (जिससे आपने अपना क्लोन बनाया था) का उपयोग कर सकते हैं। वे केवल अपने परिवर्तनों के साथ हैं, निश्चित रूप से। अंततः, हालांकि, किसी में वे परिवर्तन हो सकते हैं जो वे मूल स्वामी ("पुश" या पैच या जो भी हों) के माध्यम से वापस भेजते हैं।
इसके बाद git pullकमांड केवल शॉर्टहैंड git fetchहै git merge। यह महत्वपूर्ण है क्योंकि इसका मतलब है कि आपको यह समझने की आवश्यकता है कि वास्तव में वे दो ऑपरेशन क्या करते हैं।
git fetchआदेश भी आप से क्लोन (या अन्य प्रकार से लाने के लिए एक जगह के रूप में स्थापित किया है) और "नया सामान किसी और जोड़ा या बदल या निकाल" खोजने के लिए वापस जाने के लिए कहते हैं। उन परिवर्तनों को कॉपी किया जाता है और आपकी कॉपी पर लागू होता है जो आपको उनसे पहले मिला था । वे केवल अपने काम पर ही लागू नहीं होते हैं।
git mergeआदेश अधिक जटिल और जगह है जहाँ आप धराशायी हो जा रहे हैं है। यह जो कुछ करता है, उसकी थोड़ी सी तुलना की जाती है, "आप अपनी कॉपी में क्या बदल गए हैं" की तुलना "किसी और से प्राप्त किए गए परिवर्तनों से करें और इस तरह आपकी कॉपी-ऑफ़-द-किसी-किसी के काम में जुड़ जाए"। यदि आपके परिवर्तन और उनके परिवर्तन संघर्ष के लिए प्रतीत नहीं होते हैं, तो mergeऑपरेशन उन्हें एक साथ जोड़ देता है और आपको एक "मर्ज कमिट" देता है जो आपके विकास और उनके विकास को एक साथ जोड़ता है (हालांकि एक बहुत ही सामान्य "आसान" मामला है जिसमें आपके पास कोई नहीं है परिवर्तन और आपको एक "फास्ट फॉरवर्ड") मिलता है।
अब आप जिस स्थिति का सामना कर रहे हैं, वह वह है जिसमें आपने बदलाव किए हैं और उन्हें नौ बार प्रतिबद्ध किया है, वास्तव में, इसलिए "आगे 9" - और उन्होंने कोई बदलाव नहीं किया है। इसलिए, fetchकर्तव्यनिष्ठता से कुछ भी नहीं मिलता है, और फिर mergeउनके अभावों को बदल देता है और कुछ भी नहीं करता है।
आप जो चाहते हैं, वह है, या कोड के उनके "संस्करण" को "रीसेट" करना भी है।
यदि आप इसे देखना चाहते हैं, तो आप बस उस संस्करण को देख सकते हैं:
git checkout upstream/master
यह बताता है कि आप वर्तमान निर्देशिका को उस शाखा में ले जाना चाहते हैं जिसका पूरा नाम वास्तव में है remotes/upstream/master। पिछली बार जब आप भागे थे git fetchऔर आपको उनका नवीनतम कोड मिला था, तो आप उनका कोड देखेंगे ।
यदि आप अपने सभी परिवर्तनों को छोड़ना चाहते हैं , तो आपको जो करने की आवश्यकता है, वह है बदलाव का विचार, जिसमें आपके लेबल को संशोधन masterकरना चाहिए, नाम होना चाहिए। वर्तमान में यह आपकी सबसे हाल की प्रतिबद्ध का नाम देता है। यदि आप उस शाखा पर वापस आते हैं:
git checkout master
तब git resetकमांड आपको "लेबल को स्थानांतरित करने" की अनुमति देगा, जैसा कि यह था। एकमात्र बची हुई समस्या (यह मानकर कि आप जो कुछ भी करना चाहते हैं उसे छोड़ देने के लिए वास्तव में तैयार हैं) यह पा रहा है कि लेबल को कहां इंगित करना चाहिए।
git logआपको संख्यात्मक नाम खोजने देगा 7cfcb29- जैसे कि वे चीजें जो स्थायी (कभी नहीं बदल रही) नाम हैं, और उन्हें नाम देने के लिए अन्य तरीकों की एक हास्यास्पद संख्या है, लेकिन इस मामले में आप केवल नाम चाहते हैं upstream/master।
लेबल को स्थानांतरित करने के लिए, अपने स्वयं के परिवर्तनों को मिटा देना (जो भी आपने किया है वह वास्तव में काफी समय के लिए पुनर्प्राप्त करने योग्य है, लेकिन यह बहुत कठिन है इसके बाद बहुत सुनिश्चित हो):
git reset --hard upstream/master
--hardका सफाया करने के लिए आप क्या कर दिया गया है, वर्तमान शाखा लेबल ले जाते हैं, और उसके बाद की जाँच दी प्रतिबद्ध git बताता है।
यह वास्तव में सुपर-आम नहीं है git reset --hardऔर काम का एक गुच्छा मिटा देना चाहता है । एक सुरक्षित तरीका (अगर आप कुछ तय कर लेते हैं, तो उस काम को ठीक करना बहुत आसान हो जाता है) अपनी मौजूदा शाखा का नाम बदलना है:
git branch -m master bunchofhacks
और फिर एक नई लोकल ब्रांच बनाइए जिसका नाम masterहै "ट्रैक्स" (मुझे वास्तव में यह शब्द पसंद नहीं है क्योंकि मुझे लगता है कि यह लोगों को भ्रमित करता है लेकिन यह गित शब्द है :-)) मूल (या अपस्ट्रीम) मास्टर:
git branch -t master upstream/master
जिसके बाद आप खुद को उसके साथ पा सकते हैं:
git checkout master
अंतिम तीन कमांड क्या करते हैं (मौजूदा दो लेबल बनाने के लिए शॉर्टकट है) मौजूदा लेबल पर चिपकाए गए नाम को बदलना है, फिर एक नया लेबल बनाना है, फिर उस पर स्विच करें:
कुछ भी करने से पहले:
C0 - "remotes/upstream/master"
\
\- C1 --- C2 --- C3 --- C4 --- C5 --- C6 --- C7 --- C8 --- C9 "master"
के बाद git branch -m:
C0 - "remotes/upstream/master"
\
\- C1 --- C2 --- C3 --- C4 --- C5 --- C6 --- C7 --- C8 --- C9 "bunchofhacks"
के बाद git branch -t master upstream/master:
C0 - "remotes/upstream/master", "master"
\
\- C1 --- C2 --- C3 --- C4 --- C5 --- C6 --- C7 --- C8 --- C9 "bunchofhacks"
यहाँ C0नवीनतम प्रतिबद्ध (एक पूर्ण स्रोत पेड़) है जो आपको तब मिला जब आपने पहली बार अपना काम किया था git clone। C9 के माध्यम से C1 आपके कमिट हैं।
ध्यान दें कि यदि आप git checkout bunchofhacksऔर फिर थे git reset --hard HEAD^^, तो यह अंतिम तस्वीर को बदल देगा:
C0 - "remotes/upstream/master", "master"
\
\- C1 --- C2 --- C3 --- C4 --- C5 --- C6 --- C7 - "bunchofhacks"
\
\- C8 --- C9
कारण यह है कि HEAD^^संशोधन को वर्तमान शाखा के प्रमुख से दो नाम दिए गए हैं (जो कि रीसेट से ठीक पहले होगा bunchofhacks), और reset --hardफिर लेबल को स्थानांतरित करता है। कमिट C8 और C9 अब ज्यादातर अदृश्य हैं (आप रिफ्लॉग जैसी चीजों का उपयोग कर सकते हैं और git fsckउन्हें ढूंढ सकते हैं लेकिन अब यह बहुत मामूली है)। आपके लेबल आपके कदम हैं जो आपको पसंद हैं। fetchआदेश जो कि के साथ शुरू की देखभाल करता है remotes/। यह "तुम्हारा" "उनके" के साथ मेल खाने के लिए पारंपरिक है (इसलिए यदि remotes/origin/mauveआपके पास आपका नाम mauveभी है), लेकिन आप "उनका" टाइप कर सकते हैं जब भी आप नाम चाहते हैं / देखते हैं कि आपको "उनसे मिला" है। (याद रखें कि "एक प्रतिबद्ध" एक संपूर्ण स्रोत वृक्ष है। आप git showउदाहरण के लिए , एक प्रतिबद्ध से एक विशिष्ट फ़ाइल निकाल सकते हैं ,