¿Cómo aplicar un parche de Git a un archivo con un nombre y una ruta diferentes?


Tengo dos repositorios. En uno, hago cambios en file ./hello.test. Confirmo los cambios y creo un parche a partir de ese commit con git format-patch -1 HEAD. Ahora, tengo un segundo repositorio que contiene un archivo que tiene el mismo contenido que hello.test pero se coloca en un directorio diferente bajo un nombre diferente: ./blue/red/hi.test. ¿Cómo puedo aplicar el parche antes mencionado al archivo hi.test? Intenté git am --directory='blue/red' < patch_file pero eso, por supuesto, se queja de que los archivos no tienen el mismo nombre (¿lo que pensé que a Git no le importaba?). Sé que probablemente podría editar la diferencia para aplicarla a ese archivo específico, pero estoy buscando una solución de comandos.

Author: mart1n, 2013-05-13

5 answers

Puede crear el parche usando git diff y luego aplicarlo usando el patch utilidad, que le permite especificar el archivo al que desea aplicar la diferencia.

Por ejemplo:

cd first-repo
git diff HEAD^ -- hello.test > ~/patch_file

cd ../second-repo
patch -p1 blue/red/hi.test ~/patch_file
 63
Author: georgebrock,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2013-05-13 16:38:33

Existe una solución sencilla que no implica edición manual de parches ni script externo.

En el primer repositorio (esto también puede exportar un rango de commit, use -1 si desea seleccionar solo un commit):

git format-patch --relative <committish> --stdout > ~/patch

En el segundo repositorio :

git am --directory blue/red/ ~/patch

En lugar de usar --relative en git format-patch, otra solución es usar la opción -p<n> en git am para eliminar los directorios n de la ruta de acceso de los parches, como se menciona en una respuesta a una pregunta.

También es posible ejecutar git format-patch --relative <committish> sin el --stdout, y generará un conjunto de archivos .patch. Estos archivos pueden ser alimentados directamente a git am con git am --directory blue/red/ path/to/*.patch.

 29
Author: magiraud,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-05-23 12:02:34

Respondiendo a mi propia pregunta con un script que hace precisamente esto: https://github.com/mprpic/apply-patch-to-file

En lugar de modificar el archivo de parche manualmente, solicita al usuario el archivo de destino, modifica el parche y lo aplica al repositorio en el que se encuentra actualmente.

 8
Author: mart1n,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2013-05-17 11:52:07

Basándose en la respuesta de @ georgebrock, he aquí una solución que usé:

Primero, cree los archivos de parche como de costumbre (por ejemplo. git format-patch commitA..commitB).

Luego asegúrese de que su repositorio de destino esté limpio (no debe haber archivos cambiados o sin seguimiento) y aplique los parches de esta manera:

cd second-repo
git am ~/00*.patch

Por cada archivo de parche obtendrá un error como "error: XYZ no existe en el índice". Ahora puede aplicar este archivo de parche manualmente:

patch --directory blue/red < ~/0001-*.patch
git add -a
git am --continue

Usted tiene que hacer estos tres pasos para cada parche file.

Esto preservará el mensaje de confirmación original, etc. sin requerir ningún comando especial git format-patch o editar los archivos de parche.

 1
Author: oliver,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2018-10-02 11:52:01

Entiendo que los dos archivos son exactamente iguales en su situación, por lo que es probable que el parche tenga éxito.

Sin embargo, en caso de que desee aplicar un parche a un archivo similar, pero no exactamente el mismo, o si desea hacer un parche interactivo, utilizará la combinación de tres vías.

Digamos que modificó el archivo A, denotemos A~1 como la versión anterior, y desea aplicar la diferencia entre A~1 a A al Archivo B.

Abra una herramienta de combinación de tres vías, para instancia Más allá de comparar, la ruta del panel izquierdo es A, el panel central es el ancestro común por lo que la ruta es A~1, la ruta del panel derecho es B. Luego, el panel inferior muestra el resultado de aplicar la diferencia entre A~1 a A al Archivo B.

La siguiente figura ilustra la idea.

introduzca la descripción de la imagen aquí

 0
Author: Gqqnbig,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2018-03-12 22:02:25