Eliminar archivos confidenciales y sus confirmaciones del historial de Git

Resuelto Stefan asked hace 15 años • 12 respuestas

Me gustaría poner un proyecto Git en GitHub pero contiene ciertos archivos con datos confidenciales (nombres de usuario y contraseñas, como /config/deploy.rb para capistrano).

Sé que puedo agregar estos nombres de archivos a .gitignore , pero esto no eliminaría su historial dentro de Git.

Tampoco quiero empezar de nuevo eliminando el directorio /.git.

¿ Existe alguna manera de eliminar todos los rastros de un archivo en particular en su historial de Git?

Stefan avatar May 16 '09 21:05 Stefan
Aceptado

A todos los efectos prácticos, lo primero que debería preocuparle es ¡ CAMBIAR SUS CONTRASEÑAS! Su pregunta no deja claro si su repositorio git es completamente local o si todavía tiene un repositorio remoto en otro lugar; si es remoto y no está protegido de otros, tiene un problema. Si alguien ha clonado ese repositorio antes de que arregles esto, tendrá una copia de tus contraseñas en su máquina local, y no hay manera de que puedas obligarlos a actualizar a tu versión "reparada" si ya no está en el historial. Lo único seguro que puedes hacer es cambiar tu contraseña por otra en todos los lugares donde la hayas usado.


Una vez aclarado esto, aquí se explica cómo solucionarlo. GitHub respondió exactamente esa pregunta como una pregunta frecuente :

Nota para usuarios de Windows : utilice comillas dobles (") en lugar de simples en este comando

git filter-branch --index-filter \
'git update-index --remove PATH-TO-YOUR-FILE-WITH-SENSITIVE-DATA' <introduction-revision-sha1>..HEAD
git push --force --verbose --dry-run
git push --force

Actualización 2019:

Este es el código actual de las preguntas frecuentes:

  git filter-branch --force --index-filter \
  "git rm --cached --ignore-unmatch PATH-TO-YOUR-FILE-WITH-SENSITIVE-DATA" \
  --prune-empty --tag-name-filter cat -- --all
  git push --force --verbose --dry-run
  git push --force

Tenga en cuenta que una vez que haya enviado este código a un repositorio remoto como GitHub y otros hayan clonado ese repositorio remoto, ahora se encontrará en una situación en la que estará reescribiendo el historial. Cuando otros intenten desplegar sus últimos cambios después de esto, recibirán un mensaje indicando que los cambios no se pueden aplicar porque no es un avance rápido.

Para solucionar este problema, tendrán que eliminar su repositorio existente y volver a clonarlo, o seguir las instrucciones en "RECUPERACIÓN DE LA REBASE ARRIBA" en la página de manual de git-rebase .

Consejo : ejecutargit rebase --interactive


En el futuro, si accidentalmente realiza algunos cambios con información confidencial pero lo nota antes de enviarlos a un repositorio remoto, existen algunas soluciones más sencillas. Si su última confirmación es la que agrega la información confidencial, simplemente puede eliminar la información confidencial y luego ejecutar:

git commit -a --amend

Esto modificará la confirmación anterior con cualquier cambio nuevo que haya realizado, incluidas las eliminaciones completas de archivos realizadas con un archivo git rm. Si los cambios se remontan más atrás en el historial pero aún no se envían a un repositorio remoto, puede realizar una rebase interactiva:

git rebase -i origin/master

Eso abre un editor con las confirmaciones que ha realizado desde su último ancestro común con el repositorio remoto. Cambie "seleccionar" por "editar" en cualquier línea que represente una confirmación con información confidencial, guarde y salga. Git recorrerá los cambios y lo dejará en un lugar donde podrá:

$EDITOR file-to-fix
git commit -a --amend
git rebase --continue

Para cada cambio con información sensible. Con el tiempo, volverás a tu rama y podrás impulsar los nuevos cambios de forma segura.

natacado avatar May 16 '2009 16:05 natacado

Cambiar sus contraseñas es una buena idea, pero para el proceso de eliminar contraseñas del historial de su repositorio, recomiendo BFG Repo-Cleaner , una alternativa más rápida y sencilla que la git-filter-branchdiseñada explícitamente para eliminar datos privados de los repositorios de Git.

Cree un private.txtarchivo que enumere las contraseñas, etc., que desea eliminar (una entrada por línea) y luego ejecute este comando:

$ java -jar bfg.jar  --replace-text private.txt  my-repo.git

Se escanearán todos los archivos por debajo de un tamaño umbral (1 MB de forma predeterminada) en el historial de su repositorio y cualquier cadena coincidente (que no esté en su última confirmación) se reemplazará con la cadena "***REMOVED***". Luego puedes usar git gcpara limpiar los datos muertos:

$ git gc --prune=now --aggressive

El BFG suele ser entre 10 y 50 veces más rápido que ejecutarlo git-filter-branchy las opciones se simplifican y adaptan a estos dos casos de uso comunes:

  • Eliminación de archivos grandes y locos
  • Eliminación de contraseñas, credenciales y otros datos privados

Divulgación completa: soy el autor de BFG Repo-Cleaner.

Roberto Tyley avatar Feb 01 '2013 22:02 Roberto Tyley