Jeśli uruchomię git branch -d XYZ
, czy istnieje sposób na odzyskanie oddziału? Czy istnieje sposób na powrót, jakbym nie uruchomił polecenia usuwania gałęzi?
Jeśli uruchomię git branch -d XYZ
, czy istnieje sposób na odzyskanie oddziału? Czy istnieje sposób na powrót, jakbym nie uruchomił polecenia usuwania gałęzi?
Odpowiedzi:
Tak, powinieneś być w stanie zrobić git reflog
i znaleźć SHA1 dla zatwierdzenia na końcu usuniętej gałęzi, a potem po prostu git checkout [sha]
. A kiedy znajdziesz się w tym zatwierdzeniu, możesz po prostu git checkout -b [branchname]
odtworzyć gałąź.
Podziękowania dla @Cascabel za tę wersję skróconą / jednowarstwową.
Możesz to zrobić w jednym kroku:
git checkout -b <branch> <sha>
git checkout -b <branch> <sha>
.
<sha>
. Np. Jak wspomniano powyżej -git checkout -b <branch> <sha>
CMD+K
)
git reflog --no-abbrev
aby zobaczyć pełne, <sha>
które są domyślnie skracane.
git checkout remotes/origin/deleted_branch
.
W większości przypadków nieosiągalne zatwierdzenia znajdują się w rejestrze. Więc pierwszą rzeczą jest, aby spróbować spojrzeć na reflog używając polecenia git reflog
(które wyświetlają reflog dla HEAD
).
Być może czymś łatwiejszym, jeśli zatwierdzenie było częścią jeszcze istniejącej gałęzi, jest użycie polecenia git reflog name-of-my-branch
. Działa również z pilotem, na przykład, jeśli wymusiłeś push (dodatkowa rada: zawsze wolisz, git push --force-with-lease
aby lepiej zapobiegać błędom i jest łatwiejsza do odzyskania).
Jeśli twoje zatwierdzenia nie znajdują się w twoim logu (być może dlatego, że zostały usunięte przez narzędzie innej firmy, które nie zapisują w logu), udało mi się odzyskać gałąź, resetując moją gałąź do sha zatwierdzenia znalezionego za pomocą takiego polecenia (to tworzy plik ze wszystkimi wiszącymi zatwierdzeniami):
git fsck --full --no-reflogs --unreachable --lost-found | grep commit | cut -d\ -f3 | xargs -n 1 git log -n 1 --pretty=oneline > .git/lost-found.txt
Jeśli powinieneś użyć go więcej niż jeden raz (lub chcesz go gdzieś zapisać), możesz również utworzyć alias za pomocą tego polecenia ...
git config --global alias.rescue '!git fsck --full --no-reflogs --unreachable --lost-found | grep commit | cut -d\ -f3 | xargs -n 1 git log -n 1 --pretty=oneline > .git/lost-found.txt'
i używaj go z git rescue
Aby zbadać znalezione zatwierdzenia, możesz wyświetlić każde zatwierdzenie za pomocą niektórych poleceń, aby je przejrzeć.
Aby wyświetlić metadane zatwierdzenia (autor, data utworzenia i komunikat zatwierdzenia):
git cat-file -p 48540dfa438ad8e442b18e57a5a255c0ecad0560
Aby zobaczyć także różnice:
git log -p 48540dfa438ad8e442b18e57a5a255c0ecad0560
Po znalezieniu zatwierdzenia utwórz gałąź tego zatwierdzenia za pomocą:
git branch commit_rescued 48540dfa438ad8e442b18e57a5a255c0ecad0560
Dla tych, które są w systemie Windows i lubią GUI, możesz łatwo odzyskać zatwierdzenia (a także niezaangażowane pliki etapowe) za pomocą GitExtensions , używając funkcji Repository
=> Git maintenance
=>Recover lost objects...
Usunięto podobne polecenie, aby łatwo odzyskać pliki przemieszczane: https://stackoverflow.com/a/58853981/717372
Jeśli chcesz użyć GUI, możesz wykonać całą operację za pomocą gitk.
gitk --reflog
Umożliwi to przeglądanie historii zatwierdzeń oddziału, tak jakby oddział nie został usunięty. Teraz wystarczy kliknąć prawym przyciskiem myszy najnowsze zatwierdzenie w gałęzi i wybrać opcję menu Create new branch
.
Najlepiej ocenione rozwiązanie ma więcej niż wymagane:
git checkout <sha>
git checkout -b <branch>
lub
git checkout -b <branch> <sha>
przenieś Cię do nowego oddziału wraz ze wszystkimi ostatnimi zmianami, które mogłeś zapomnieć. To może nie być twoja intencja, szczególnie w „trybie paniki” po utracie gałęzi.
Bardziej przejrzystym (i prostszym) rozwiązaniem wydaje się być jedno-liniowy (po znalezieniu <sha>
z git reflog
):
git branch <branch> <sha>
Teraz nie ma to wpływu ani na twoją obecną gałąź, ani na nieprzewidziane zmiany. Zamiast tego zostanie utworzony tylko nowy oddział aż do <sha>
.
Jeśli nie jest to wskazówka, nadal będzie działać, a otrzymasz krótszą gałąź, a następnie możesz ponowić próbę z nową <sha>
i nową nazwą gałęzi, dopóki nie uzyskasz poprawności.
Wreszcie możesz zmienić nazwę pomyślnie przywróconej gałęzi na jej nazwę lub cokolwiek innego:
git branch -m <restored branch> <final branch>
Nie trzeba dodawać, że kluczem do sukcesu było znalezienie odpowiedniego zatwierdzenia <sha>
, więc mądrze nazwij swoje zobowiązania :)
Dodanie do odpowiedzi tfe : istnieje również skrypt git-resurrect.sh w contrib/
obszarze źródeł Git (w repozytorium git.git), który może ci pomóc.
git-resurrect <name>
próbuje znaleźć ślady zwanego wierzchołkiem gałęzi<name>
i próbuje go wskrzesić. Obecnie reflog jest przeszukiwany pod kątem komunikatów kasowych, a-r
także korespondencji seryjnej. Za pomocą-m
i-t
, historia wszystkich referencji jest skanowana w celuMerge <name> into other
/Merge <other> into <name>
(odpowiednio) zatwierdzania tematów, co jest raczej powolne, ale pozwala wskrzesić gałęzie tematyczne innych osób.
Użyłem następujących poleceń, aby znaleźć i odzyskać usuniętą gałąź. Pierwsze kroki pochodzą z opisu gcb.
$ git fsck --full --no-reflogs --unreachable --lost-found > lost
$ cat lost | cut -d\ -f3 > commits
$ cat commits | xargs -n 1 git log -n 1 --pretty=oneline
Teraz poszukaj identyfikatora git commit (GIT-SHA) na podstawie komentarzy zatwierdzenia i użyj go w poniższym poleceniu. Zapoznaj się z nowym oddziałem o nazwie NEW-BRANCH z wcześniej znalezionym GIT-SHA:
$ git checkout -b NEW-BRANCH GIT-SHA
Jeśli nie masz dziennika, np. ponieważ pracujesz w czystym repozytorium, w którym nie włączono ponownego rejestrowania, a zatwierdzenie, które chcesz odzyskać, zostało niedawno utworzone, inną opcją jest znalezienie ostatnio utworzonych obiektów zatwierdzenia i przejrzenie ich.
Z poziomu .git/objects
katalogu uruchom:
find . -ctime -12h -type f | sed 's/[./]//g' | git cat-file --batch-check | grep commit
Znajduje wszystkie obiekty (zatwierdzenia, pliki, tagi itp.) Utworzone w ciągu ostatnich 12 godzin i filtruje je, aby wyświetlać tylko zatwierdzenia. Sprawdzenie ich jest wtedy szybkim procesem.
Najpierw jednak spróbuję skryptu git-ressurect.sh wspomnianego w odpowiedzi Jakuba .
man find
: „-ctime n - Status pliku został ostatnio zmieniony n * 24 godziny temu.” Dlatego też powinniśmy zmienić 12 na 0,5, aby uzyskać oczekiwane zachowanie z ostatnich 12 godzin.
Dla użytkowników GitHub bez zainstalowanego Git:
Jeśli chcesz przywrócić go ze strony GitHub , możesz użyć jego interfejsu API, aby uzyskać listę zdarzeń związanych z repo:
Pierwszy
znajdź te SHA (zatwierdzaj skróty):
curl -i https://api.github.com/repos/PublicUser/PublicRepo/events
... lub w przypadku prywatnych repozytoriów:
curl -su YourUserName https://api.github.com/repos/YourUserName/YourProject/events
(zostanie wyświetlony monit o podanie hasła GitHub)
Kolejny
• Idź do oddziałów i usuń ten.
• Na tej samej stronie, bez ponownego ładowania , otwórz DevTools, panel Sieć. Teraz przygotuj ...
• Kliknij przywróć. Zauważysz nową „linię”. Kliknij go prawym przyciskiem myszy i wybierz „Kopiuj jako cURL” i zapisz ten tekst w edytorze.
• Dołącz do końca kopiowanego wiersza kodu, to jedno: -H "Cookie="
.
Powinieneś teraz uzyskać coś takiego:
curl 'https://github.com/UserName/ProjectName/branches?branch=BranchSHA&name=BranchName' -H 'Cookie:' -H 'Origin: https://github.com' -H 'Accept-Encoding: gzip, deflate, br' -H 'Accept-Language: en-US' -H 'User-Agent: User-Agent' -H 'Content-Type: application/x-www-form-urlencoded; charset=UTF-8' -H 'Accept: */*' -H 'Referer: https://github.com/UserName/ProjectName/branches' -H 'X-Requested-With: XMLHttpRequest' -H 'Connection: keep-alive' --data 'utf8=%E2%9C%93&authenticity_token=token' --compressed
Ostatni krok
PS
Zdaję sobie sprawę, że to nie może być „najprostsze rozwiązanie” lub „właściwe” rozwiązanie, ale jest oferowane w przypadku, gdy ktoś uzna to za przydatne.
git reflog
i dlatego było przydatne na przykład, gdy usunięto zdalną gałąź i utracono dostęp do komputera, z którego zostało zrobione, więc nic użytecznego nie można uzyskać reflog
. Uwaga przy użyciu uwierzytelniania OAuth lub dwuskładnikowego na Githubcurl
polecenie staje się w postaci: curl -u username:token https://api.github.com/user
lubcurl -H "Authorization: token TOKEN" https://api.github.com/repos/USER_OR_ORG_NAME/REPO_NAME/events
Z mojego zrozumienia, czy gałąź, która ma zostać usunięta, może być osiągnięta przez inną gałąź, możesz ją bezpiecznie usunąć za pomocą
git branch -d [branch]
a twoja praca nie jest stracona. Pamiętaj, że gałąź nie jest migawką, ale wskaźnikiem do jednego. Więc kiedy usuwasz gałąź, usuwasz wskaźnik.
Nie stracisz nawet pracy, jeśli usuniesz gałąź, do której nie może dotrzeć żaden inny. Oczywiście nie będzie to tak łatwe, jak sprawdzenie skrótu, ale nadal możesz to zrobić. Dlatego Git nie może usunąć gałęzi, do której nie można uzyskać dostępu za pomocą -d
. Zamiast tego musisz użyć
git branch -D [branch]
To część obowiązkowego filmu Scotta Chakona na temat Gita. Sprawdź minutę 58:00, kiedy mówi o oddziałach i jak je usunąć.
reflog
to po prostu przesada.
Wykonaj to wszystko lokalnie i upewnij się, że Twoje repo jest w pożądanym stanie, zanim przejdziesz do Bitbucket Cloud. Dobrym pomysłem może być również sklonowanie bieżącego repozytorium i przetestowanie tych rozwiązań w pierwszej kolejności.
Deleted branch <your-branch> (was <sha>)
2. Aby przywrócić gałąź, użyj:
git checkout -b <branch> <sha>
Jeśli nie znasz „sha” z czubka głowy, możesz:
git reflog
git checkout -b <branch> <sha>
Jeśli twoich zatwierdzeń nie ma w twoim logu:
git fsck --full --no-reflogs --unreachable --lost-found | grep commit | cut -d\ -f3 | xargs -n 1 git log -n 1 --pretty=oneline > .git/lost-found.txt
2. Następnie możesz wyświetlić każde zatwierdzenie, używając jednego z tych:
git log -p <commit>
git cat-file -p <commit>
Odwróciłem gałąź od pilota, aby spróbować wyczyścić kilka niepotrzebnych zmian i zamierzałem wybrać właściwe, które chciałem. Oczywiście, że źle napisałem SHA ...
Oto jak je znalazłem (głównie łatwiejszy interfejs / interakcja na podstawie odpowiedzi tutaj):
Najpierw wygeneruj listę luźnych zatwierdzeń w swoim dzienniku. Zrób to jak najszybciej i przestań działać, ponieważ mogą zostać zrzucone przez moduł wyrzucający śmieci.
git fsck --full --no-reflogs --unreachable --lost-found > lost
Spowoduje to utworzenie lost
pliku ze wszystkimi zatwierdzeniami, które będziesz musiał obejrzeć. Aby uprościć nasze życie, odetnijmy od niego tylko SHA:
cat lost | cut -d\ -f3 > commits
Teraz masz commits
plik ze wszystkimi zobowiązaniami, które musisz sprawdzić.
Zakładając, że używasz Bash, ostatni krok:
for c in `cat commits`; do git show $c; read; done
Spowoduje to wyświetlenie różnic i zatwierdzenie informacji dla każdego z nich. I czekaj, aż naciśniesz Enter. Teraz zapisz wszystkie te, które chcesz, a następnie wybierz je. Po zakończeniu, po prostu Ctrl-C to.
DUŻE TAK
jeśli używasz GIT, wykonaj te proste kroki https://confluence.atlassian.com/bbkb/how-to-restore-a-deleted-branch-765757540.html
jeśli używasz smartgit i już wypychasz tę gałąź do źródła, znajdź tę gałąź i kliknij prawym przyciskiem myszy, a następnie do kasy
Najpierw przejdź do git i przenieś do swojego projektu w następujący sposób:
cd android studio project
cd Myproject
then type :
git reflog
Wszyscy macie listę zmian, a numer referencyjny weź numer referencyjny, a następnie kasy
z Android Studio lub z Git Betcha. innym rozwiązaniem weź numer referencyjny i przejdź do Android Studio, kliknij gałęzie git w dół, a następnie kliknij tag kasy lub rewizję obok numeru referencyjnego, a następnie lol masz gałęzie.
Dodając do odpowiedzi tfe, możesz odzyskać dzięki wspomnianemu procesowi, chyba że jego zatwierdzenia nie są usuwane. Git gałąź jest po prostu wskaźnikiem do konkretnego zatwierdzenia w drzewie zatwierdzeń. Ale jeśli usuniesz wskaźnik, a zatwierdzenia w tej gałęzi nie zostaną scalone z innymi istniejącymi gałęziami, git traktuje go jako wiszące zatwierdzenia i usuwa je podczas wyrzucania elementów bezużytecznych, które może okresowo uruchamiać się automatycznie.
Jeśli twoja gałąź nie została scalona z istniejącą gałęzią, a jeśli została wyrzucona śmieci, stracisz wszystkie zatwierdzenia aż do momentu, w którym gałąź została rozwidlona z istniejącej gałęzi.
Powiązany problem: Przyszedłem na tę stronę po wyszukiwaniu hasła „jak się dowiedzieć, jakie skasowane gałęzie”.
Usuwając wiele starych gałęzi, czułem, że omyłkowo usunąłem jedną z nowszych gałęzi, ale nie znałem nazwy, aby ją odzyskać.
Aby wiedzieć, które gałęzie zostały ostatnio usunięte, wykonaj następujące czynności:
Jeśli przejdziesz do adresu URL Git, który będzie wyglądał mniej więcej tak:
https://your-website-name/orgs/your-org-name/dashboard
Następnie możesz zobaczyć kanał, z którego usunięto, przez kogo, w niedawnej przeszłości.
Zrobiłem to na komputerze, który usunąłem gałąź:
git reflog
odpowiedź:
74b2383 (develope) HEAD@{1}: checkout: moving from master to develope
40ef328 (HEAD -> master, origin/master, origin/HEAD) HEAD@{2}: checkout: moving from develope to master
74b2383 (develope) HEAD@{3}: checkout: moving from master to develope
40ef328 (HEAD -> master, origin/master, origin/HEAD) HEAD@{4}: reset: moving to HEAD
40ef328 (HEAD -> master, origin/master, origin/HEAD) HEAD@{5}: clone: from http://LOCALGITSERVER/myBigProject/Android.git
i pobieram gałąź za pomocą tego polecenia:
git checkout -b newBranchName 74b2383
Samo użycie git reflog
nie zwróciło sha
mi. Tylko commit id
(który ma 8 znaków, a sha jest znacznie dłuższy)
Więc użyłem
git reflog --no-abbrev
A następnie wykonaj to samo, co wspomniano powyżej:
git checkout -b <branch> <sha>
Zauważ, że usunięcie gałęzi git usuwa tylko kopię lokalną, a nie kopię na serwerze. Najpierw w panelu Git (ikona git na lewym pasku narzędzi) przejrzyj gałęzie i sprawdź, czy gałąź wciąż tam jest pod „origin / two_branch_name”. Jeśli tak, po prostu wybierz to i powinieneś odzyskać swój kod (sugeruj, aby natychmiast skopiować / wkleić / zapisać go lokalnie w innym miejscu).
Jeśli nie widziałeś „origin / your_branch_name”, zainstaluj rozszerzenie GitLens. Pozwala to wizualnie przeszukiwać repozytoria serwerów i zlokalizować zsynchronizowaną kopię z serwerem. Jeśli masz wiele repozytoriów, pamiętaj, że może być konieczne otwarcie co najmniej jednego pliku z żądanego repozytorium, aby repozytorium pojawiło się w GitLens. Następnie:
Otwórz panel GitLens
Rozwiń repozytorium
Powinieneś zobaczyć listę kategorii: Oddziały / Współautorzy / Piloty / Skrytki / itp
YourLostTreasure powinien znaleźć się w „Oddziałach” lub ewentualnie w „Pilocie -> Początki”. Mamy nadzieję, że zobaczysz gałąź o pożądanej nazwie - jeśli ją rozwiniesz, powinieneś zobaczyć pliki, które zmieniłeś w tej gałęzi. Kliknij dwukrotnie nazwy plików, aby je otworzyć, i natychmiast wykonaj kopię zapasową tego kodu.
Jeśli nie widzisz od razu swojej zagubionej gałęzi, rozejrzyj się, a jeśli znajdziesz coś obiecującego, natychmiast otwórz ją i pobierz kod. Musiałem trochę się rozejrzeć, aż znalazłem TheGoldenBranch, a nawet wtedy w kodzie brakowało ostatniego jednego lub dwóch zapisów (być może dlatego, że nie udało mi się zsynchronizować z serwerem przed próbą scalenia oddziału, ale przypadkowo kliknięcia- Usuń oddział). Moje poszukiwania zostały niepotrzebnie wydłużone, ponieważ kiedy pierwszy raz znalazłem gałąź, nie byłem do końca pewien, czy nazwa jest poprawna, więc szukałem dalej i zajęło mi to trochę czasu, aby znaleźć tę pierwszą gałąź. (Tak więc Carpe Carpum, a następnie szukaj dalej.)