Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Recover unreferenced commits from remote git repository

Here's the situation : some commits have been done in a remote repository.

Unfortunately, someone did push -f such that no remote branch references these commits anymore.

To make matters worse, I don't have those commits in my local clone.

My goal is basically to recover those commits. These are some of the things I tried :

  • git checkout -b recovery <commit_id> : fatal: reference is not a tree
  • git push origin <commit_id>:recovery

    error: refs/heads/recovery does not point to a valid object! error: unable to push to unqualified destination: recovery The destination refspec neither matches an existing ref on the remote nor begins with refs/, and we are unable to guess a prefix based on the source ref.

The repository is on bitbucket, and the commit is accessible from the web interface, so it hasn't been garbage-collected.
like image 831
mickael9 Avatar asked Feb 23 '14 00:02

mickael9


People also ask

What is git fetch-- prune?

git fetch --prune is the best utility for cleaning outdated branches. It will connect to a shared remote repository remote and fetch all remote branch refs. It will then delete remote refs that are no longer in use on the remote repository.

What is refspec git?

A refspec maps a branch in the local repository to a branch in a remote repository. This makes it possible to manage remote branches using local Git commands and to configure some advanced git push and git fetch behavior.


1 Answers

The problem is that your local repository doesn't have that commit id.

git checkout -b recovery <commit_id>
git push origin <commit_id>:recovery

Both of these commands fail for that reason, I get the exact same messages with a GitHub repo if I use a commit id that doesn't exist locally.

I thought the answer will be simply fetching the lost commits locally, in one of these ways:

git fetch origin         #1
git fetch origin SHA1    #2
git fetch origin SHA1:refs/remotes/origin/recovery  #3

Unfortunately none of these work. It seems #2 used to work as of Git v1.4 according to this answer. As of now, it doesn't work anymore.

There is a help page for this on GitHub, but with no answer that you can use: it basically says that if you have the commit locally you can create a branch from it and push it. Yeah, but if you don't have the commit locally then what? It doesn't answer that.

I can think of two options:

  1. Find a teammate who has this commit. It's easy to check with git log SHA1. If anybody has it, they can create a branch from it with git branch recovery SHA1 and then push it.
  2. Contact bitbucket support. Since they have the commit, somewhere, they should be able to create a recovery branch for you.
like image 59
janos Avatar answered Sep 29 '22 04:09

janos