145M = .git / Objekte / Pack /
Ich habe ein Skript geschrieben, um die Größen der Unterschiede zwischen jedem Commit und dem Commit zu addieren, bevor es von der Spitze jedes Zweigs rückwärts geht. Ich erhalte 129 MB, ohne Komprimierung und ohne Berücksichtigung der gleichen Dateien in verschiedenen Filialen und des gemeinsamen Verlaufs zwischen den Filialen.
Git berücksichtigt all diese Dinge, so dass ich ein viel viel kleineres Repository erwarten würde. Warum ist .git so groß?
Ich habe getan:
git fsck --full
git gc --prune=today --aggressive
git repack
Um zu beantworten, wie viele Dateien / Commits ich habe, habe ich 19 Zweige mit jeweils etwa 40 Dateien. 287 Commits, gefunden mit:
git log --oneline --all|wc -l
Es sollte nicht 10 Megabyte dauern, um Informationen darüber zu speichern.
git repack -a -d
schrumpfte mein 956MB Repo auf 250MB . Großer Erfolg! Vielen Dank!Antworten:
Ich habe kürzlich das falsche Remote-Repository in das lokale (
git remote add ...
undgit remote update
) gezogen. Nach dem Löschen der unerwünschten Remote-Referenz, Zweige und Tags hatte ich immer noch 1,4 GB (!) Verschwendeten Speicherplatz in meinem Repository. Ich konnte dies nur durch Klonen loswerdengit clone file:///path/to/repository
. Beachten Sie, dassfile://
dies beim Klonen eines lokalen Repositorys einen großen Unterschied macht - nur die referenzierten Objekte werden kopiert, nicht die gesamte Verzeichnisstruktur.Bearbeiten: Hier ist Ians einziger Liner zum Neuerstellen aller Zweige im neuen Repo:
quelle
Einige Skripte, die ich benutze:
Git-Fatfiles
Wenn Sie mehr Zeilen wünschen, lesen Sie auch die Perl-Version in einer benachbarten Antwort: https://stackoverflow.com/a/45366030/266720
git-eradicate (für
video/parasite.avi
):Hinweis: Das zweite Skript dient zum vollständigen Entfernen von Informationen aus Git (einschließlich aller Informationen aus Reflogs). Mit Vorsicht verwenden.
quelle
git-fatfiles
) Skript ist entstanden, als ich die Frage im IRC (Freenode / # git) gestellt habe. Ich habe die beste Version in einer Datei gespeichert und sie dann als Antwort hier veröffentlicht. (Ich kann den ursprünglichen Autor jedoch nicht in IRC-Protokollen finden).git gc
git repack
Wenn Sie dies bereits tun, macht es keinen Sinn, manuell neu zu verpacken, es sei denn, Sie übergeben ihm einige spezielle Optionen.Der erste Schritt besteht darin, festzustellen, ob der größte Teil des Speicherplatzes (wie normalerweise der Fall ist) Ihre Objektdatenbank ist.
Dies sollte einen Bericht darüber geben, wie viele entpackte Objekte sich in Ihrem Repository befinden, wie viel Speicherplatz sie beanspruchen, wie viele Packdateien Sie haben und wie viel Speicherplatz sie belegen.
Idealerweise hätten Sie nach einem Umpacken keine entpackten Objekte und eine Packdatei, aber es ist völlig normal, dass einige Objekte, auf die die aktuellen Zweige nicht direkt verweisen, noch vorhanden und entpackt sind.
Wenn Sie eine einzelne große Packung haben und wissen möchten, was den Speicherplatz einnimmt, können Sie die Objekte, aus denen die Packung besteht, zusammen mit ihrer Speicherung auflisten.
Beachten Sie, dass
verify-pack
eine Indexdatei und nicht die Packdatei selbst verwendet wird. Dies gibt einen Bericht über jedes Objekt in der Packung, seine wahre Größe und seine Packungsgröße sowie Informationen darüber, ob es "deltifiziert" wurde und wenn ja, woher die Delta-Kette stammt.Um festzustellen, ob sich ungewöhnlich große Objekte in Ihrem Repository befinden, können Sie die Ausgabe numerisch in der dritten der vierten Spalte sortieren (z
| sort -k3n
. ) .Über diese Ausgabe können Sie den Inhalt eines Objekts mit dem
git show
Befehl anzeigen, obwohl nicht genau erkennbar ist, wo im Festschreibungsverlauf des Repositorys auf das Objekt verwiesen wird. Wenn Sie dies tun müssen, versuchen Sie etwas aus dieser Frage .quelle
Nur zu Ihrer Information, der Hauptgrund, warum Sie möglicherweise unerwünschte Objekte in der Nähe haben, ist, dass Git ein Reflog aufrechterhält.
Das Reflog dient dazu, Ihren Hintern zu retten, wenn Sie versehentlich Ihren Hauptzweig löschen oder Ihr Repository auf andere Weise katastrophal beschädigen.
Der einfachste Weg, dies zu beheben, besteht darin, Ihre Reflogs vor dem Komprimieren abzuschneiden (stellen Sie nur sicher, dass Sie niemals zu einem der Commits im Reflog zurückkehren möchten).
Dies unterscheidet sich davon,
git gc --prune=today
dass das gesamte Reflog sofort abläuft.quelle
Wenn Sie herausfinden möchten, welche Dateien Speicherplatz in Ihrem Git-Repository belegen, führen Sie aus
git verify-pack -v .git/objects/pack/*.idx | sort -k 3 -n | tail -5
Extrahieren Sie dann die Blob-Referenz, die am meisten Platz beansprucht (die letzte Zeile), und überprüfen Sie den Dateinamen, der so viel Platz beansprucht
git rev-list --objects --all | grep <reference>
Dies kann sogar eine Datei sein, mit der Sie entfernt haben
git rm
, aber git merkt sich das, weil es immer noch Verweise darauf gibt, wie Tags, Fernbedienungen und Reflog.Sobald Sie wissen, welche Datei Sie entfernen möchten, empfehle ich die Verwendung
git forget-blob
https://ownyourbits.com/2017/01/18/completely-remove-a-file-from-a-git-repository-with-git-forget-blob/
Es ist einfach zu bedienen, tun Sie es einfach
git forget-blob file-to-forget
Dadurch wird jeder Verweis aus git entfernt, der Blob aus jedem Commit im Verlauf entfernt und die Garbage Collection ausgeführt, um den Speicherplatz freizugeben.
quelle
Das Git-Fatfiles-Skript aus Vis Antwort ist sehr schön, wenn Sie die Größe all Ihrer Blobs sehen möchten, aber es ist so langsam, dass es unbrauchbar wird. Ich habe die 40-Zeilen-Ausgabegrenze entfernt und versucht, den gesamten RAM meines Computers zu verwenden, anstatt fertig zu werden. Also habe ich es umgeschrieben: Dies ist tausende Male schneller, hat Funktionen hinzugefügt (optional) und ein seltsamer Fehler wurde behoben - die alte Version würde ungenaue Zählungen ergeben, wenn Sie die Ausgabe summieren, um den gesamten von einer Datei verwendeten Speicherplatz zu sehen.
Nennen Sie diese git-fatfiles.pl und führen Sie sie aus. Verwenden Sie die
--sum
Option , um den von allen Revisionen einer Datei verwendeten Speicherplatz anzuzeigen. Verwenden Sie die--directories
Option , um dasselbe zu sehen, jedoch für Dateien in jedem Verzeichnis . Wenn Sie das Modul Number :: Bytes :: Human cpan installieren (führen Sie "cpan Number :: Bytes :: Human" aus), werden die Größen wie folgt formatiert: "21M /path/to/file.mp4".quelle
Sind Sie sicher, dass Sie nur die .pack-Dateien und nicht die .idx-Dateien zählen? Sie befinden sich im selben Verzeichnis wie die .pack-Dateien, haben jedoch keine Repository-Daten (wie die Erweiterung angibt, handelt es sich lediglich um Indizes für das entsprechende Pack. Wenn Sie den richtigen Befehl kennen, können Sie dies sogar tun Erstellen Sie sie einfach aus der Pack-Datei neu, und Git selbst erledigt dies beim Klonen, da nur eine Pack-Datei mit dem nativen Git-Protokoll übertragen wird.
Als repräsentatives Beispiel habe ich mir meinen lokalen Klon des Linux-2.6-Repositorys angesehen:
Was darauf hinweist, dass eine Expansion von rund 7% üblich sein sollte.
Es gibt auch die Dateien draußen
objects/
; in meiner persönlichen Erfahrung, von ihnenindex
undgitk.cache
ist in der Regel die größten (insgesamt 11M in meinem Klon der Linux-2.6 - Repository) sein.quelle
Andere in gespeicherte Git-Objekte
.git
sind Bäume, Commits und Tags. Commits und Tags sind klein, aber Bäume können groß werden, insbesondere wenn Sie eine sehr große Anzahl kleiner Dateien in Ihrem Repository haben. Wie viele Dateien und wie viele Commits haben Sie?quelle
Haben Sie versucht, Git Repack zu verwenden ?
quelle
Bevor Sie git filter-branch & git gc ausführen, sollten Sie die Tags überprüfen, die in Ihrem Repo vorhanden sind. Jedes echte System, das über ein automatisches Tagging für Dinge wie kontinuierliche Integration und Bereitstellung verfügt, führt dazu, dass unerwünschte Objekte immer noch durch diese Tags aktualisiert werden. Daher kann gc sie nicht entfernen, und Sie werden sich immer wieder fragen, warum das Repo immer noch so groß ist.
Der beste Weg, um alle unerwünschten Dinge loszuwerden, besteht darin, git-filter & git gc auszuführen und den Master dann auf ein neues Bare-Repo zu schieben. Das neue nackte Repo wird den aufgeräumten Baum haben.
quelle
Dies kann passieren, wenn Sie versehentlich einen großen Teil der Dateien hinzugefügt und diese bereitgestellt haben und nicht unbedingt festschreiben. Dies kann in einer
rails
App passieren, wenn Sie sie ausführen,bundle install --deployment
und dann werden versehentlichgit add .
alle untervendor/bundle
Ihnen hinzugefügten Dateien entfernt, aber sie sind bereits in den Git-Verlauf eingegangen. Sie müssen also die Antwortvideo/parasite-intro.avi
von Vi anwenden und ändern, bis Sievendor/bundle
den zweiten von ihm bereitgestellten Befehl ausführen.Sie können den Unterschied sehen, mit
git count-objects -v
dem in meinem Fall vor dem Anwenden des Skripts ein Größenpaket von 52 KB und nach dem Anwenden 3,8 KB vorhanden war.quelle
Es lohnt sich, die Datei stacktrace.log zu überprüfen. Grundsätzlich handelt es sich um ein Fehlerprotokoll zum Verfolgen von fehlgeschlagenen Commits. Ich habe kürzlich herausgefunden, dass mein stacktrace.log 65,5 GB und meine App 66,7 GB hat.
quelle