Vous devriez pouvoir récupérer tous les fichiers que vous avez ajoutés à l'index (par exemple, comme dans votre situation, avec git add .
) bien que cela puisse représenter un peu de travail. Afin d'ajouter un fichier à l'index, git l'ajoute à la base de données des objets, ce qui signifie qu'il peut être récupéré tant que le garbage collection n'a pas encore eu lieu. Il y a un exemple de comment faire cela donné dans La réponse de Jakub Narebski ici :
Cependant, j'ai essayé cela sur un référentiel de test, et il y a eu quelques problèmes --cached
devrait être --cache
et j'ai constaté qu'il ne créait pas réellement le fichier .git/lost-found
répertoire. Cependant, les étapes suivantes ont fonctionné pour moi :
git fsck --cache --unreachable $(git for-each-ref --format="%(objectname)")
Cela devrait donner tous les objets de la base de données des objets qui ne sont pas accessibles par une référence, dans l'index, ou via le reflog. La sortie ressemblera à quelque chose comme ceci :
unreachable blob 907b308167f0880fb2a5c0e1614bb0c7620f9dc3
unreachable blob 72663d3adcf67548b9e0f0b2eeef62bce3d53e03
... et pour chacun de ces blobs, vous pouvez faire :
git show 907b308
Pour sortir le contenu du fichier.
Trop de production ?
Mise à jour en réponse à sehe Le commentaire de l'auteur ci-dessous :
Si vous trouvez que vous avez beaucoup de commits et d'arbres listés dans la sortie de cette commande, vous pouvez vouloir supprimer de la sortie tous les objets qui sont référencés à partir de commits non référencés. (Typiquement, vous pouvez revenir à ces commits via le reflog de toute façon - nous sommes juste intéressés par les objets qui ont été ajoutés à l'index mais ne peuvent jamais être trouvés via un commit).
Tout d'abord, enregistrez la sortie de la commande, avec :
git fsck --cache --unreachable $(git for-each-ref --format="%(objectname)") > all
Maintenant les noms d'objets de ces commits inaccessibles peuvent être trouvés avec :
egrep commit all | cut -d ' ' -f 3
Ainsi, vous pouvez trouver seulement les arbres et les objets qui ont été ajoutés à l'index, mais pas engagés à un moment donné, avec :
git fsck --cache --unreachable $(git for-each-ref --format="%(objectname)") \
$(egrep commit all | cut -d ' ' -f 3)
Cela réduit énormément le nombre d'objets à prendre en compte.
Mise à jour : Philip Oakley ci-dessous suggère une autre façon de réduire le nombre d'objets à prendre en compte, qui consiste à ne considérer que les fichiers les plus récemment modifiés dans la rubrique .git/objects
. Vous pouvez les trouver avec :
find .git/objects/ -type f -printf '%TY-%Tm-%Td %TT %p\n' | sort
(J'ai trouvé que find
invocation ici .) La fin de cette liste pourrait ressembler à ceci :
2011-08-22 11:43:43.0234896770 .git/objects/b2/1700b09c0bc0fc848f67dd751a9e4ea5b4133b
2011-09-13 07:36:37.5868133260 .git/objects/de/629830603289ef159268f443da79968360913a
Dans ce cas, vous pouvez voir ces objets avec :
git show b21700b09c0bc0fc848f67dd751a9e4ea5b4133b
git show de629830603289ef159268f443da79968360913a
(Notez que vous devez retirer le /
à la fin du chemin pour obtenir le nom de l'objet).
0 votes
@MarkLongair génial mec ! Tu viens de récupérer mon travail ! J'ai écrit un script Python pour créer des fichiers de toutes les sorties ! Je vais ajouter le script comme réponse
6 votes
Pas "stupidement"... mais "naïvement"... parce que je viens de faire la même chose !
0 votes
Cela pourrait encore être stupidement ;-)
0 votes
Voici un grand article sur la façon d'inverser certaines de ces choses. Ça va demander un peu de travail manuel.
1 votes
@MarkLongair ``` find .git/objects/ -type f -printf '%TY-%Tm-%Td %TT %p \n ' | sort `` a fonctionné pour moi. Des dates apparaissent aussi, commencez à vérifier les blobs depuis la fin.
0 votes
Comment récupérer du texte après
git show 907b308...
? Cela me donne un diff, pas le fichier.