web-dev-qa-db-ja.com

Gitリポジトリで破損したオブジェクトを復元するにはどうすればよいですか(初心者向け)?

今日、リポジトリを開こうとしましたが、コミット履歴がありませんでした。私が試したすべて(git status、git log、git checkout ...)は、破損したオブジェクトに関するエラーをスローしました。

この問題をオンラインで調査し、Linus Torvaldsによる article を見つけましたが、壊れたリンクIDを見つけた時点で迷子になりました。エラーメッセージ。

その後、復旧に関する記事に戻りました 「ハードディスクの障害により破損したgitオブジェクト」 (原因のオブジェクトを邪魔にならないように移動した後)

$ cat packed-refs

その時点で私のコンピューターは言った:cat: packed-refs: No such file or directoryそのステップをスキップして、

$ git fsck --full

適切な出力を得ましたが、その後、犯人(または犯人と呼んでいたもの、エラーによってスローされたsha1 ID)をバックアップリポジトリからメインリポジトリにコピーし、欠落しているオブジェクトを私が知る限り、メインリポジトリへのバックアップリポジトリ。そして、私は何もしたくないtoo抜本的または私は後で強制を解除できない何かを強制するかもしれません。

だから私の質問は(ある)、バックアップを作成することになっていた(ooh、初心者アラート)、または.packファイルを解凍したときに起こったことでした?そして、私がコピーバックしている「犯人」は実際にはクリーンなファイル、つまり破損していないのですか?

(「git」と「fsck」の間にあるTorvaldsのファイル内の単純なダッシュに最初混乱したことを伝えるのは公平だと思います。だから私は[〜#〜] really [ 〜#〜]これで新しい。)

バグリスト

元のバグ:

$ git status
fatal: object 016660b7605cfc2da85f631bbe809f7cb7962608 is corrupted

破損したオブジェクトを移動した後のバグ:

$ git status
fatal: bad object HEAD
$ git fsck --full
error: HEAD: invalid sha1 pointer 016660b7605cfc2da85f631bbe809f7cb7962608
error: refs/heads/RPG does not point to a valid object!
dangling tree 2c1033501b82e301d47dbf53ba0a199003af25a8
dangling blob 531aca5783033131441ac7e132789cfcad82d06d
dangling blob 74a47ff40a8c5149a8701c2f4b29bba408fa36f5
dangling blob b8df4d9751c0518c3560e650b21a182ea6d7bd5e
dangling blob fc2d15aead4bd0c197604a9f9822d265bb986d8b

$ git ls-tree 2c1033501b82e301d47dbf53ba0a199003af25a8
040000 tree 4a8b0b3747450085b1cd920c22ec82c18d9311bd    folder1
040000 tree 33298295f646e8b378299191ce20b4594f5eb625    folder2
040000 tree dec82bad6283fc7fcc869c20fdea9f8588a2f1b2    folder3
040000 tree 4544967c6b04190f4c95b516ba8a86cab266a872    folder4

$ git ls-tree dec82bad6283fc7fcc869c20fdea9f8588a2f1b2
100644 blob 67bda6df733f6cd76fc0fc4c8a6132d8015591d8    fileA
100644 blob 4cb7272c9e268bfbd83a04e568d7edd87f78589c    fileB
100644 blob ce9e0f2cc4d3b656fa30340afbdfed47fe35f3ef    fileC

$ git ls-tree 4544967c6b04190f4c95b516ba8a86cab266a872
100644 blob d64fe3add8328d81b1f31c9dbd528956ab391fb6    fileD
100644 blob d1ebd7df7082abc5190d87caa821bf3edb7b68e8    fileE
100644 blob bb6cd264e47a3e5bc7beadf35ea13bac86024b02    ...
100644 blob 995d622b9012f4ef69921091d1e1a73f32aa94e6
100644 blob 9141dbd2b1c7931a6461195934b6599f5dfb485a 
100644 blob ab128da1d82907cd0568448dc089a7996d5f79d3
100644 blob 57b11a7eb408a79739d2bb60a0dc35c591340d18
100644 blob 118105291c1c6ca4a01744889ffafbb018bc7ed3
100644 blob 86b1dfda56d0603f16910228327751f869d16bdc
100644 blob 077fe0cddde0d0be9d0974f928f66815caca7b76
100644 blob c0b32fd0450f21994bdc53ea83d3cf0bccd74004
100644 blob 37b87a4d11453468c4ae04572db5d322cd2d1d80
100644 blob 79d39f8d4e57fa3a71664598a63b6dfd88149638
100644 blob ee07bbe3e8cb5d6bb79fb0cd52cfbc9bd830498d    files

$ git ls-tree 33298295f646e8b378299191ce20b4594f5eb625
100644 blob f9d6f45cd028aec97f761f00c5f4f2f6b50fb925    MoreFiles
100644 blob 0cb9eed1d0dd9214d54a03af1bda21f37b8c0d02
100644 blob 198e4f97ece735cce47b7e99b54f1b5fa99fabf5
100644 blob fc004212fa8e483e5a8ab35b508027c7a9a1cbfa
100644 blob 0c7d74c7a9a8337b4a9f20802b63d71d42287f89

$ git ls-tree 4a8b0b3747450085b1cd920c22ec82c18d9311bd
100644 blob 0320f5b23dd7cce677fac60b9ad03f418cff5c88    oneLASTfile

破損したオブジェクトを元に戻した後:

$ git log --raw --all
fatal: object 016660b7605cfc2da85f631bbe809f7cb7962608 is corrupted

$ cat packed-refs
cat: packed-refs: No such file or directory

$ git fsck --full
fatal: object 016660b7605cfc2da85f631bbe809f7cb7962608 is corrupted

ファイルを元に戻した後:

$ git fsck --full`  
error: HEAD: invalid sha1 pointer 016660b7605cfc2da85f631bbe809f7cb7962608
error: refs/heads/RPG does not point to a valid object!
dangling tree 2c1033501b82e301d47dbf53ba0a199003af25a8
dangling blob 531aca5783033131441ac7e132789cfcad82d06d
dangling blob 74a47ff40a8c5149a8701c2f4b29bba408fa36f5
dangling blob b8df4d9751c0518c3560e650b21a182ea6d7bd5e
dangling blob fc2d15aead4bd0c197604a9f9822d265bb986d8b

.packファイルを解凍した後:

$ git log
fatal: bad object HEAD

$ cat packed-refs
cat: packed-refs: No such file or directory

$ git fsck --full
error: HEAD: invalid sha1 pointer 016660b7605cfc2da85f631bbe809f7cb7962608
error: refs/heads/RPG does not point to a valid object!
dangling tree 2c1033501b82e301d47dbf53ba0a199003af25a8
dangling blob 531aca5783033131441ac7e132789cfcad82d06d
dangling blob 74a47ff40a8c5149a8701c2f4b29bba408fa36f5
dangling blob b8df4d9751c0518c3560e650b21a182ea6d7bd5e
dangling blob fc2d15aead4bd0c197604a9f9822d265bb986d8b
28
Humble Penguin

そして。 2番目のエラーメッセージから、移動した破損したオブジェクトはコミットであることがわかります。 (HEADはそれを指していました!)残念ながら、これは手動で修復するのが難しいことを意味します。 (「ハード」とは、コミットメッセージが何であったか、いつコミットしたかを正確に覚えていない限り、おそらく不可能であることを意味します。)新しいメッセージを書くだけです。

始める前に、.git/HEADの内容を見てください。ブランチ名の場合は、後で覚えておいてください。

まず、このコミットの親がどうあるべきかを把握する必要があります。 git reflogを使用してHEADのreflogを確認し、コミット016660bを作成する直前のHEADであった場所のSHA1を見つけることができます。次のようになります。

016660b HEAD@{n}: commit: <subject of commit>
1234abc HEAD@{n-1}: ...

HEADの前の位置のSHA1をコピーして、そのコミットをチェックアウトできます。

git checkout 1234abc

次に、破損したコミットが持っていたツリーを読むことができます:

git read-tree 2c1033501b82e301d47dbf53ba0a199003af25a8

そしてコミット!

git commit

さて、ここであなたのブランチに何が起きたのかという質問があります。 HEADがブランチ(マスター)を指しており、そのブランチが破損したコミットを指していた場合、間違いなく修正する必要があります。

git branch -d master       # remove the original master branch
git checkout -b master     # recreate it here

破損したコミットを含む他のブランチがある場合は、それらに対してもいくつかの復元を行う必要があります-それについて支援が必要かどうか教えてください。

18
Cascabel

FWIW、ここにあるのは、破損したgitリポジトリに関する他の質問に関する多くの絶望的に楽観的な答えよりも実用的な答えです-そのほとんどは、貧しいOPが「リモートOriginから再クローンできる」という根拠のない仮定をしています!うーん。 しかし。ちょっと待ってください。私がオリジンの場合

ホラー

単純なgit gc --aggressiveを実行しようとすると、ある時点で、私の-完全にローカルな-gitリポジトリが何らかの形で完全に使い果たされたことが明らかになり、数か月前に何もログに記録できなかったため、大半が失われましたgit fsck --full | grep -v danglingを求められたときはいつでも、悲鳴を上げました。 git fsckによっていくつかのオブジェクトが失われたと識別されました。

git-repair:2014年以降、恐ろしい肉体労働を最小限に抑える

パニックに陥り、「リモートOriginから再クローンしてください!」 -それは要点を言い聞かせて、私は持っていないので、私はオリジンです-見つけた git-repair 、簡単なSudo aptitude install git-repairを行い、すべての退屈なことをさせますおそらく私に数時間を要した自動化された修正(破損したレポのコピーで実行してください[duh]、without --force!)

git fsck --full | grep -v danglingによって報告される恐怖の量を減らすのに役立ちました。しかし、8月中旬以降はまだ到達できませんでした。

特に、これはすべて、取得できなかった1つのコミットに集中しているように見えました。どうすれば回復できますか?スタックオーバーフローの検索はあまり役に立ちませんでした!

バックアップがありますか?

11月末からバックアップを持っているに幸運だった場所です。バックアップを取りますか?私の場合、それはレポの手動のZipでした(私の毎日のバックアップルーチンは、実際にテストしたことのない恐ろしい増分tarのことです... a-cough)...しかし、それは十分でした。ライブレポを傷つけたin辱は何も受けていませんでした。

しかし、不足しているオブジェクトは、このバックアップの.git/objects/XY/RESTOFHASHBLAHBLAHBLAHに単に格納されているようには見えませんでした。これはおそらく、ファイルではなくコミットであったためです。知りません! gitは、理解する能力をはるかに超えて、私にとって魔法です。ただ修正が必要でした。それが私たち全員がここにいる理由ではありませんか?

バックアップからオブジェクトを回復します(これは正しいですか?)

今バックアップを手に入れて、私は陽気に愚かなアイデアを持っていて、「これが機能する方法はありません!」と言って、すぐに単純にcp -fr /path/to/repo_backup/.git/objects/* /path/to/repo_git-repaired/.git/objectsfile-merge the.git/objectsディレクトリをその破損した対応するディレクトリにマージします、-いくらか修復されたリポジトリ...すべての履歴を回復するために働きました-すぐに元の状態に戻りますinitial commit lol。修正の証明:git fsck --fullも幸せになりました(すべてのぶら下がりビットにもかかわらず)。

その後、ライブ/破損、一部修復されたバックアップを取り、リポジトリが必要になった場合に備えて、リポジトリを別のドライブに復元しました。

実行する前に、その方法論とコマンドを再確認するか、おそらく私が考えるのが面倒なはるかに良い方法を見つける必要があります。知りません。しかし、私にとっては、それは私のレポを保存しました。そして、私が言うことを再推測することについて...

無限の組み合わせの無限の免責事項

さて、明らかにこれにはすべて警告があります:you must_破損したレポジトリのコピーですべてを試し、すべてのドキュメントを読んで、私よりも少し注意することを検討してください(強制cpコマンド)間違いが発生した場合、絶対に責任を負わないか、責任を負いません* ...

*ただし、すべてがになった場合、多額の寄付が順番に行われる可能性があります。;)

誰かが私を必要とするなら、私はディスクドライブの一般的な方向に疑い深くみつけ、できれば復元するのに2桁の時間をかけないバックアップルーチンを考え出します。睡眠。

10
underscore_d

同じ問題がありました。ただし、サーバー上の.git/objectsフォルダーとサブフォルダーのアクセス許可を(再帰的に)変更することで、私の問題は解決しました。何かのようなもの:

chmod -R 770 .git/objects

それはあなたの問題ではないと思いますが、私の場合は解決しました。

6
Ruhan