Git: पुनर्प्राप्त हटाए गए (दूरस्थ) शाखा


94

मुझे दो गिट शाखाओं को पुनर्प्राप्त करने की आवश्यकता है जिन्हें मैंने किसी तरह एक धक्का के दौरान हटा दिया था।

इन दोनों शाखाओं को एक अलग प्रणाली पर बनाया गया था और फिर मेरे "साझा" (जीथूब) भंडार पर धकेल दिया गया।

मेरे सिस्टम पर, मैंने (स्पष्ट रूप से) एक ब्रांच के दौरान शाखाओं को पुनः प्राप्त किया:

~/myfolder> git fetch
remote: Counting objects: 105, done.
remote: Compressing objects: 100% (58/58), done.
remote: Total 62 (delta 29), reused 0 (delta 0)
Unpacking objects: 100% (62/62), done.
From github.com:mygiturl
 * [new branch]      contact_page -> origin/contact_page
   731d1bb..e8b68cc  homepage   -> origin/homepage
 * [new branch]      new_pictures -> origin/new_pictures

ठीक इसके बाद मैंने अपने स्थानीय परिवर्तनों को केंद्रीय रेपो तक भेजने के लिए एक धक्का दिया। किसी कारण से, ये शाखाएँ मेरे स्थानीय सिस्टम और केंद्रीय रेपो दोनों से हटा दी गईं:

~/myfolder> git push
Counting objects: 71, done.
Delta compression using up to 2 threads.
Compressing objects: 100% (43/43), done.
Writing objects: 100% (49/49), 4.99 KiB, done.
Total 49 (delta 33), reused 0 (delta 0)
To git@github.com:mygiturl.git
 - [deleted]         contact_page
 + e8b68cc...731d1bb homepage -> homepage (forced update)
   bb7e9f2..e0d061c  master -> master
 - [deleted]         new_pictures
   e38ac2e..bb7e9f2  origin/HEAD -> origin/HEAD
   731d1bb..e8b68cc  origin/homepage -> origin/homepage
   e38ac2e..bb7e9f2  origin/master -> origin/master
 * [new branch]      origin/contact_page -> origin/contact_page
 * [new branch]      origin/new_pictures -> origin/new_pictures

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

"पूर्ववत करें" जानकारी के सभी जो मैंने गुगले किए हैं उन्हें खोए हुए कमानों को पुनर्प्राप्त करने के साथ है। मुझे नहीं लगता कि यह यहाँ लागू होता है, क्योंकि मैंने इन शाखाओं के लिए यूआईडी नहीं किया है।

मैं जानना चाहता हूं कि मैं ये कैसे वापस पा सकता हूं। मैं यह भी जानना चाहता हूं कि पहली बार में उन्हें कैसे हटा दिया गया और भविष्य में मैं इससे कैसे बच सकता हूं।

संपादित करें: अनुरोध के अनुसार, यहां मेरा रेपो कॉन्फ़िगरेशन है

user.name=Craig Walker
user.email=github@softcraft.ca
alias.unadd=reset HEAD
core.repositoryformatversion=0
core.filemode=true
core.bare=false
core.logallrefupdates=true
core.ignorecase=true
remote.origin.fetch=+refs/heads/*:refs/remotes/origin/*
remote.origin.url=git@github.com:MyGitURL.git
remote.origin.mirror=true
branch.master.remote=origin
branch.master.merge=refs/heads/master
alias.undo=reset --hard
alias.test=push -f ci HEAD:master
alias.st=status
alias.ci=commit
alias.br=branch
alias.co=checkout
alias.ch=checkout
alias.df=diff
alias.lg=log -p
alias.who=shortlog -s --
remote.ci.url=ContinuousIntegrationGitURL
remote.ci.fetch=+refs/heads/*:refs/remotes/ci/*
branch.photo.remote=origin
branch.photo.merge=refs/heads/photos
remote.foo.url=FooGitURL
remote.foo.fetch=+refs/heads/*:refs/remotes/cynthia/*
branch.homepage.remote=origin
branch.homepage.merge=refs/heads/homepage

ऐसा लगता है कि आपके पास एक 'असामान्य' या बेमेल भ्रूण और धक्का विन्यास है। git config -lस्थानीय भंडार के लिए क्या दिखाता है?
सीबी बेली

काफी संभवतः; मैंने इसे पोस्ट किया है।
क्रेग वॉकर

2
आपका remote.origin.fetchrefspec उपयोग के लिए उपयुक्त नहीं है remote.origin.mirror = true। क्या आप दर्पण का उपयोग करना चाहते हैं या आप एक सामान्य रिमोट के रूप में गिटहब रेपो का उपयोग करना चाहते हैं? मेरे जवाब में आपके पास जरुरी तरीके हैं।
क्रिस जॉन्सन

मैं अनुमान लगा रहा हूं कि 2 के भंडार के साथ, मिररिंग अब एक विकल्प नहीं है (यह संभवतः पहली जगह में हटाने का कारण बना)।
क्रेग वॉकर

जवाबों:


102

मैं कोई विशेषज्ञ नहीं हूं। लेकिन आप प्रयास कर सकते हैं

git fsck --full --no-reflogs | grep commit

हटाए गए शाखा के हेड को खोजने और उन्हें वापस पाने के लिए।


मैंने पहले fsck की कोशिश की; क्या आप जानते हैं कि कैसे पता लगाएं कि कौन सा कमिट सही है? मुझे कोशिश करने के लिए 20 मिला है।
क्रेग वॉकर

1
इसने ऐसा किया; एक बार जब मेरे पास कमिटमेंट मैसेज थे, git branch <uid>उन्हें वापस मिल गया। धन्यवाद!
क्रेग वॉकर

सुन कर अच्छा लगा। अपने remotes.origin.mirrorऔर remotes.origin.fetchसेटिंग्स के बीच संघर्ष को भी हल करना सुनिश्चित करें , अन्यथा आप समस्या में फिर से दौड़ने के लिए बाध्य हैं (या अनजाने में क्लोबर अन्य रिपोज से धक्का दिया गया)।
क्रिस जॉन्सन

@ क्रेग: मददगार होने की खुशी :)
iamamac

3
मैंने आज एक रिलीज़ उम्मीदवार शाखा खो दी। कमिट आईडी नहीं जानता था। इसका उपयोग करके इसे पुनः प्राप्त करें:git fsck --full --no-reflogs | cut -d' ' -f3 | xargs -P8 git log --oneline | grep 'Release 2.60.0.157'
स्पेज़िफैंटा

23

सिर्फ दो आज्ञाएँ मेरी जान बचाती हैं

1. यह पिछले सभी प्रमुखों को सूचीबद्ध करेगा

git reflog

2. यह आपके द्वारा हटाई गई प्रतिबद्धता के लिए HEAD को वापस कर देगा।

git reset --hard <your deleted commit>
ex. git reset --hard b4b2c02

1
मैंने कभी भी स्थानीय स्तर पर शाखा में जाँच नहीं की है इसलिए मेरा HEAD कभी नहीं हुआ है, इसलिए मैं कमिट आईडी नहीं ढूँढ सकता git reflog। क्या यहां कुछ और है जिसके लिए मैं कोशिश कर सकता हूं?
zyy

1
@Zyy के रूप में भी। इस कमेटी को रिमोट में टीम के अन्य सदस्य द्वारा डिलीट कर दिया गया है, इसलिए मुझे इसे अपनी लोकल मशीन में वापस लेना है (मैंने कभी ऐसा नहीं किया था) और इसे पीछे धकेल दिया ...
OmGanesh

11

आपकी हटाई गई शाखाएं खो नहीं जाती हैं, वे मूल / contact_page और उत्पत्ति / new_pictures "दूरस्थ ट्रैकिंग शाखाओं" में आपके द्वारा दिखाए गए भ्रूण द्वारा कॉपी किए गए थे (वे आपके द्वारा दिखाए गए धक्का द्वारा वापस भी धकेल दिए गए थे, लेकिन वे रेफरी / रिमोट / में धकेल दिए गए थे) मूल / रेफरी / सिर के बजाय /)। जांचें git log origin/contact_pageऔर git log origin/new_picturesदेखें कि आपकी स्थानीय प्रतियां "अप टू डेट" हैं, जो भी आपको लगता है कि होना चाहिए। यदि भ्रूण और धक्का के बीच उन शाखाओं (किसी अन्य रेपो से) पर कोई नया संचार किया गया था, तो आपने उन लोगों को "खो दिया" हो सकता है (लेकिन शायद आप उन्हें अन्य रेपो में पा सकते हैं जो कि हाल ही में उन शाखाओं को धक्का दिया है) ।

लाँच / धक्का संघर्ष

ऐसा लगता है कि आप एक सामान्य, 'रिमोट मोड' (रिमोट रेफ / हेड / / में स्थानीय रूप से रीफ़्स / रेमोड्स / ओरिजिन /) में संग्रहित कर रहे हैं, लेकिन 'मिरर मोड' (लोकल रीफ़्स) में पुश किया जा रहा है या रिमोट रीफ़ / । अपने .it / config की जाँच करें remote.origin.fetchऔर remote.origin.pushसेटिंग्स और सामंजस्य स्थापित करें ।

एक बैकअप बनाएं

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

विकल्प A: एक दर्पण के रूप में पुन: कॉन्फ़िगर करें

यदि आप अपने दूरस्थ रेपो का उपयोग अपने स्थानीय व्यक्ति के दर्पण के रूप में करना चाहते हैं, तो यह करें:

git branch contact_page origin/contact_page &&
git branch new_pictures origin/new_pictures &&
git config remote.origin.fetch '+refs/*:refs/*' &&
git config --unset remote.origin.push &&
git config remote.origin.mirror true

आप अंततः अपने सभी रीफ़्स / रिमूव्स / ओरिजिन / रेफ्स को डिलीट करना चाहते हैं, क्योंकि वे उपयोगी नहीं हैं यदि आप मिरर मोड में काम कर रहे हैं (आपकी सामान्य शाखाएँ सामान्य रिमोट ट्रैकिंग शाखाओं की जगह लेती हैं)।

विकल्प बी: एक सामान्य रिमोट के रूप में पुन: कॉन्फ़िगर करें

लेकिन जब से ऐसा लगता है कि आप इस रिमोट रेपो का उपयोग कई "काम" रिपोज के साथ कर रहे हैं, आप शायद मिरर मोड का उपयोग नहीं करना चाहते हैं। आप यह कोशिश कर सकते हैं:

git config push.default tracking &&
git config --unset remote.origin.push
git config --unset remote.origin.mirror

फिर, आप अंततः अपने दूरस्थ रेपो में बोगस रीफ्स / रीमोट्स / ओरिजिन रिफ्स को हटाना चाहेंगे git push origin :refs/remotes/origin/contact_page :refs/remotes/origin/new_pictures …

टेस्ट पुश

git push --dry-runयह देखने की कोशिश करें git pushकि रिमोट रेपो पर कोई बदलाव किए बिना यह क्या करेगा। यदि आपको यह पसंद नहीं है कि यह क्या करने जा रहा है, तो अपने बैकअप (टार / जिप) से उबरें और दूसरे विकल्प का प्रयास करें।


1
मुझे नहीं लगता कि रिमोट ट्रैकिंग शाखाएं रखी गई थीं, अगर उन्हें बिल्कुल कॉपी किया गया था। 'git branch -a' उन्हें नहीं दिखाती है, और मैं .git dir में उन नामों के साथ कोई भी फाइल नहीं खोज सकता। अंत में, "git log" आपके द्वारा अनुशंसित वापसी की आज्ञा देता है "घातक: अस्पष्ट तर्क 'मूल / contact_page': अज्ञात संशोधन या कार्यशील पेड़ में नहीं पथ": - \ धन्यवाद यद्यपि।
क्रेग वॉकर

1
खैर, वे शाखाएँ वहाँ थीं, आपका पुश लॉग इसे दिखाता है। जब .gitडीआईआर में रेफरी की तलाश हो, तो .git/packed_refsइसके अलावा जांच करना सुनिश्चित करें .git/refs/git show-refआपके सभी स्थानीय रेफरी को बाहर निकाल देगा (पैक या 'ढीला')। आप अभी भी रेपो में रेफ को ढूंढने में सक्षम होना चाहिए जो मूल रूप से आपके गीथहब रेपो (एक अलग मशीन पर?) को किसी और के रेपो में धकेल देता है। उस समय तक, जब तक आपने कोई gc या prune नहीं किया है, तब तक आप git fsckआउटपुट को झूलने वाले कमिट्स की जांच करने और उन्हें रीटेट करने में सक्षम होना चाहिए git branch contact_page-recovered <SHA-1-of-dangling-commit>:।
क्रिस जॉन्सन

pack_refs के पास यह नहीं था। कमिट्स निश्चित रूप से लटक रहे थे; पता नहीं कैसे हुआ। यद्यपि कि आपकी इस सहायता के लिए धन्यवाद!
क्रेग वॉकर

8

यदि हाल ही में डिलीट पर्याप्त है (ओह-नो-मोमेंट की तरह) तो आपको अभी भी एक संदेश देना चाहिए:

Deleted branch <branch name> (was abcdefghi).

आप अभी भी चला सकते हैं:

git checkout abcdefghi

git checkout -b <some new branch name or the old one>


8
  1. Coimmit id पता करें

    git reflog

  2. स्थानीय शाखा को पुनर्प्राप्त करें जिसे आपने गलती से हटा दिया है

    git branch need-recover-branch-name commitId

  3. यदि आपने रिमोट ब्रांच को पहले भी डिलीट कर दिया है तो फिर से रिकवरी-रिकवरी-ब्रांच-नेम पुश करें

    git push origin need-recover-branch-name


2
इसने मेरे लिए काम किया। मैं स्वीकृत उत्तर को पसंद करता हूं क्योंकि यह बहुत कम कदम था। मैं git reflogअनुमान लगाने के बजाय और से अपने प्रतिबद्ध संदेश को देखने में सक्षम था git show
TheUtherSide

3

डेटा अभी भी जीथब में मौजूद है, आप पुराने डेटा से एक नई शाखा बना सकते हैं:

git checkout origin/BranchName #get a readonly pointer to the old branch
git checkout –b BranchName #create a new branch from the old
git push origin BranchName #publish the new branch

1

मुझे लगता है कि आपके पास 'लाने' और 'पुश' के लिए एक बेमेल कॉन्फिग है, इसलिए इसने डिफॉल्ट ब्रांच / पुश को ट्रिप ट्रिप ठीक से न करने के लिए प्रेरित किया है। सौभाग्य से आपने उन शाखाओं को प्राप्त कर लिया है जिन्हें आपने बाद में हटा दिया है ताकि आप उन्हें स्पष्ट धक्का देकर फिर से बना सकें।

git push origin origin/contact_page:contact_page origin/new_pictures:new_pictures

@ क्रिस जॉनसन को मेरी टिप्पणी के साथ, ऐसा प्रतीत होता है कि शाखाएं अब (कभी नहीं?) स्थानीय रूप से मौजूद हैं। जब मुझे git push origin origin/contact_page:contact_pageयह मिलता है: error: src refspec origin/contact_page does not match any
क्रेग वॉकर

ठीक है, मुझे लगता है कि मैं देख रहा हूं कि क्या हुआ है, (हालांकि पूर्ण त्रुटि सहायक होगी)। पुश ने हटाए गए शाखा को अपडेट किया है और स्थानीय रूप से रेफरी को हटा दिया है और साथ ही यह एक ट्रैकिंग रेफरी है। क्या git rev-parse refs/remotes/origin/origin/contact_pageकहता है? फर्जी 'दर्पण' विन्यास के कारण, स्थानीय शाखा में अब मेरी शाखा को संदर्भित किया गया है।
सीबी बेली

हाय चार्ल्स; जब से मैंने यह लिखा है कि मैंने अपने कॉन्फिग को मूंज (और निश्चित) कर लिया है इसलिए मुझे (मीनिंगफुल) रि-पार्स आउटपुट नहीं मिल रहा है। हालांकि, मुझे नहीं लगता कि रीमोट में एक डबल-नेस्टेड "मूल" निर्देशिका थी।
क्रेग वाकर

0

यदि आपका संगठन JIRA या किसी अन्य समान प्रणाली का उपयोग करता है, जिसे git में बांधा गया है, तो आप टिकट पर सूचीबद्ध कमिट स्वयं पा सकते हैं और कोड परिवर्तन के लिंक पर क्लिक कर सकते हैं। गितुब ने शाखा को हटा दिया, लेकिन अभी भी चेरी-पिकिंग के लिए कमिट उपलब्ध है।


-1

यह बहुत सतर्क होने के रूप में प्रतीत हो सकता है, लेकिन मैं अक्सर स्रोत नियंत्रण परिवर्तन करने से पहले जो कुछ भी मैं काम कर रहा हूं उसकी एक प्रति ज़िप करता हूं। Gitlab प्रोजेक्ट में, जिस पर मैं काम कर रहा हूं, मैंने हाल ही में एक दूरस्थ शाखा को गलती से हटा दिया था जिसे मैं मर्ज अनुरोध के विलय के बाद रखना चाहता था। यह मुझे पता है कि प्रतिबद्ध इतिहास के साथ इसे वापस लाने के लिए क्या करना था। मर्ज अनुरोध अभी भी गिटलैब द्वारा ट्रैक किया गया था, इसलिए यह अभी भी शाखा के दाईं ओर नीले 'मर्ज किए गए' लेबल को दिखाता है। मैंने अभी भी अपने स्थानीय फ़ोल्डर को खराब होने की स्थिति में ज़िप किया है।

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