2012-10-12 80 views
10

Tengo un repositorio para almacenar algunos archivos binarios grandes (tifs, jpgs, pdfs) que crecen bastante. También hay una buena cantidad de archivos que se crean, eliminan y renombran, y no me importa el historial de compromisos individuales. Esta pregunta se simplifica un tanto porque estoy tratando con un repositorio que no tiene ramas ni etiquetas.Eliminar información de compromiso anterior de un repositorio git para ahorrar espacio

Tengo curiosidad por saber si hay una manera fácil de eliminar parte del historial del sistema para ahorrar espacio.

me encontré con un viejo hilo on the git mailing list pero en realidad no especifica cómo utilizar este (es decir, ¿cuál es la gota $):

git filter-branch --parent-filter "sed -e 's/-p $drop//'" \ 
     --tag-name-filter cat -- \ 
     --all ^$drop 
+0

curioso, de usted archivo de proyecto de 10 Gb, ¿cuánto espacio puede ahorrar? 2Mbs? ¿25mb o como 200Mgb? – Honey

+0

En mi caso, el 90% de los archivos en el repositorio seguían siendo necesarios, por lo que solo se guardó ~ 10% del espacio. – greggles

+0

¿Quieres decir que ahorraste 1Gb? O el 10% de los metadatos relacionados con git? ¿Cuál fue la cantidad? – Honey

Respuesta

8

creo, se puede reducir el tamaño de su historia tras esta respuesta:

How to delete a specific revision of a github gist?

decidir en qué momentos de la historia, que desea mantener.

pick <hash1> <commit message> 
pick <hash2> <commit message> 
pick <hash3> <commit message> <- keep 
pick <hash4> <commit message> 
pick <hash5> <commit message> 
pick <hash6> <commit message> <- keep 
pick <hash7> <commit message> 
pick <hash8> <commit message> 
pick <hash9> <commit message> 
pick <hash10> <commit message> <- keep 

Luego, deje el primero después de cada "mantener" como "recoger" y marque los otros como "squash".

pick <hash1> <commit message> 
squash <hash2> <commit message> 
squash <hash3> <commit message> <- keep 
pick <hash4> <commit message> 
squash <hash5> <commit message> 
squash <hash6> <commit message> <- keep 
pick <hash7> <commit message> 
squash <hash8> <commit message> 
squash <hash9> <commit message> 
squash <hash10> <commit message> <- keep 

Luego, ejecute la rebase guardando y saliendo del editor. En cada punto de "mantenimiento", el editor de mensajes aparecerá para un mensaje de compromiso combinado que va desde el anterior "recoger" hasta el "mantener" confirmar. A continuación, puede conservar el último mensaje o, de hecho, combinarlos para documentar el historial original sin mantener todos los estados intermedios.

Después de esa rebase, los datos del archivo intermedio seguirán estando en el repositorio pero ahora sin referencia. git gc ahora te deshacera de esos datos.

+0

Esto parece que podría ser útil si simplemente compruebo cada confirmación (o cada confirmación antes de la fecha X) pero eso parece tedioso. ¿Hay una manera más automatizada de hacerlo? – greggles

+0

Además, mi objetivo es ahorrar espacio en disco, así que me pregunto si tiene algunas estadísticas sobre cuánto espacio podría guardar en un repo grande (~ 10 GB de archivos relativamente grandes). Si elimino los metadatos pero no la información sobre los objetos eliminados, creo que esto no ayudará mucho. – greggles

+1

Al eliminar una confirmación, está eliminando los metadatos y las referencias a los datos del árbol. Si eso significa que se descarta la última referencia (ninguna otra confirmación hace referencia a los contenidos específicos), la carga útil real se elimina en el siguiente 'gc'. Por ejemplo, si está aplastando todas las confirmaciones desde la adición de un archivo dado hasta la confirmación en la que se elimina de nuevo, los datos del archivo se eliminarán en 'gc'. –

6

siempre se puede simplemente eliminar .git y hacer una nueva git --init con uno Compromiso inicial. Esto eliminará, por supuesto, todos los historial de confirmaciones.

+0

Sí, definitivamente considerando esto como una opción fácil pero drástica. Me gustaría archivar el .git repo y luego hacer esto. Estoy esperando algo un poco menos drástico :) – greggles

+0

'git init'. ¿Por qué '--init'? –

+1

básicamente: 'mover .git/somewhere/else; git init; git add.; git commit -m "confirmación inicial"; git add origin [repoUrl]; origen de git push --force' –

3

$ gota es una variable (que desea buscar)

Si desea limpiar los archivos innecesarios y optimizar el repositorio local debe comprobar el comando git gc

Y git prune es otra opción, porque elimina objetos a los que ya no apunta ningún objeto en ninguna rama alcanzable.

Espero que esto pueda ayudarlo.

+0

Esto no se aplica a ningún objeto que aún esté en el historial y a eso es a lo que creo que se refiere la pregunta. –

+0

Estos parecen útiles, pero todavía estoy confundido sobre cómo usar ese comando (por ejemplo, qué argumentos modificar para mantener más o menos historial). – greggles

+0

"git gc" llama "git prune". Ver https://git-scm.com/docs/git-prune#_notes – Hackless

1

Si quiere encontrar y eliminar archivos grandes de su historial de Git, Pro Git tiene una sección llamada Removing Objects, que lo guía a través de este proceso. Es un poco complicado, pero le permite eliminar los archivos de su historial que haya eliminado de todos modos, mientras mantiene intacto el resto de su historial.

0

Es un poco complicado olvidarse de un archivo.

git rm a partir de ahora solo eliminará el archivo en esta rama, pero permanece en el historial y git lo recordará.

La forma correcta de hacerlo es con git filter-branch, como han mencionado otros aquí. Reescribirá cada confirmación en el historial de la sucursal para eliminar ese archivo.

Pero, incluso después de hacer eso, git puede recordarlo porque puede haber referencias a él en reflog, controles remotos, etiquetas y demás.

me escribió una pequeña utilidad llamada git forget-blob

https://ownyourbits.com/2017/01/18/completely-remove-a-file-from-a-git-repository-with-git-forget-blob/

Es fácil, basta con hacer git forget-blob file1.txt.

Esto eliminará todas las referencias, haga git filter-branch, y finalmente ejecute el recolector de basura git git gc para eliminar por completo este archivo en su repositorio.

Cuestiones relacionadas