¿Cuál es la forma más fácil de confirmar y enviar un solo archivo sin tocar otras modificaciones?

StackOverflow https://stackoverflow.com/questions/125272

Pregunta

Soy relativamente nuevo en Mercurial y mi equipo lo está probando ahora mismo como reemplazo de Subversion.

¿Cómo puedo enviar y enviar un solo archivo a otro repositorio y dejar otras modificaciones en mi directorio de trabajo sin confirmar (o al menos no enviar al otro repositorio)?

Esto nos sucede con las migraciones de bases de datos.Queremos enviar la migración al control de código fuente para que un DBA pueda verla y editarla mientras trabajamos en las modificaciones del código para acompañar la migración de la base de datos.Los cambios aún no están listos para implementarse, por lo que no queremos eliminarlos todos.

En subversión, simplemente haría:

svn add my_migration.sql  
# commit only the migration, but not the other files I'm working on
svn commit -m "migration notes" my_mygration.sql

y seguir trabajando localmente.

Esto no funciona con Mercurial, ya que cuando lo envío al otro repositorio, si hay cambios que no he eliminado, quiere que los elimine, los fusione y confirme esa combinación. el repositorio.Las confirmaciones después de una fusión no le permiten omitir archivos, por lo que le obligan a confirmar todo en su repositorio local.

Lo más fácil que puedo resolver es enviar el archivo a mi repositorio local, clonar mi repositorio local, recuperar cualquier cambio nuevo del repositorio real, fusionarlos y confirmar esa combinación, y luego eliminar mis cambios.

hg add my_migration.sql 
hg commit -m "migration notes" my_migration.sql 
cd ..
hg clone project project-clone
cd project-clone
hg fetch http://hg/project
hg push  http://hg/project

Esto funciona, pero parece que me falta algo más fácil, alguna forma de decirle a Mercurial que ignore los archivos que ya están en mi directorio de trabajo, simplemente combine y envíe los archivos.Sospecho que las colas mercuriales pueden hacer esto, pero todavía no asimilo completamente mq.

¿Fue útil?

Solución

Hay una característica de Mercurial que implementa comandos de archivar y desarchivar, que le brindan una forma interactiva de especificar cambios para almacenar hasta más adelante: Dejar de lado.

Entonces tú puedes hg shelve y hg unshelve para almacenar temporalmente los cambios.Le permite trabajar en el nivel de "parche" para seleccionar los elementos que desea guardar.No parecía archivar ningún archivo que se hubiera incluido para agregar, solo archivos que ya estaban en el repositorio con modificaciones.

Está incluido con Mercurial como una "extensión", lo que simplemente significa que debe habilitarlo en su archivo de configuración hg.


Notas para versiones realmente antiguas de Mercurial (antes de que se incluyera shelve, esto ya no es necesario):

No vi ninguna buena instrucción de instalación al buscar en Google, así que aquí está el material combinado que utilicé para que funcionara:

Consíguelo con:

hg clone http://freehg.org/u/tksoh/hgshelve/ hgshelve

El único archivo (actualmente) en el proyecto es el archivo hgshelve.py.

Modifique su ~/.hgrc para agregar la extensión shelve, apuntando a donde clonó el repositorio:

[extensions] 
hgshelve=/Users/ted/Documents/workspace/hgshelve/hgshelve.py

Otros consejos

Han pasado casi 2 años desde que planteé esta pregunta originalmente.Lo haría de manera diferente ahora (como mencioné en un comentario encima de la pregunta anterior).Lo que haría ahora sería enviar mis cambios a un archivo en mi repositorio local (puede usar la extensión de registro hg para enviar solo partes de un archivo):

hg commit -m "commit message" filename

Luego simplemente empuja hacia afuera.

hg push

Si hay un conflicto porque se han realizado otros cambios en el repositorio que necesito fusionar primero, actualizaría a la revisión principal (que se ve con "hg parent -r." si no sabes cuál es), confirma mis otros cambios allí, así que tengo 2 cabezas.Luego, vuelva a la confirmación de archivo único original y extraiga/fusione los cambios en esa versión.Luego, elimine los cambios con

hg push --rev .

Para eliminar solo el archivo único y la combinación de esa revisión.Luego puedes fusionar las dos cabezas que tienes localmente.

De esta manera se elimina el material mq y la posibilidad de que se rechacen fragmentos y el control de fuente mantiene todo rastreado.También puedes eliminar las revisiones si luego decides que no las quieres.

tl;dr:Mi explicación original parece complicada, pero espero que explique completamente cómo usar una cola de parches.Aquí está la versión corta:

$ hg qnew -m "migration notes" -f migration my_migration.sql
$ hg qnew -f working-code
# make some changes to your code
$ hg qrefresh # update the patch with the changes you just made
$ hg qfinish -a # turn all the applied patches into normal hg commits

Mercurial Queues hace que este tipo de cosas sea muy sencillo y hace posible una manipulación más compleja de los conjuntos de cambios.Vale la pena aprenderlo.

En esta situación, primero probablemente querrás guardar lo que hay en tu directorio actual antes de implementar los cambios:

# create a patch called migration containing your migration
$ hg qnew -m "migration notes" -f migration.patch my_migration.sql
$ hg qseries -v # the current state of the patch queue, A means applied
0 A migration.patch
$ hg qnew -f working-code.patch # put the rest of the code in a patch
$ hg qseries -v
0 A migration.patch
1 A working-code.patch

Ahora hagamos un trabajo adicional en el código de trabajo.voy a seguir haciendo qseries Solo para ser explícito, pero una vez que construyas un modelo mental de colas de parches, no tendrás que seguir mirando la lista.

$ hg qtop # show the patch we're currently editing
working-code.patch
$ ...hack, hack, hack...
$ hg diff # show the changes that have not been incorporated into the patch
blah, blah
$ hg qrefresh # update the patch with the changes you just made
$ hg qdiff # show the top patch's diff

Debido a que ahora todo su trabajo se guarda en la cola de parches, puede cancelar la aplicación de esos cambios y restaurarlos después de haber introducido los cambios remotos.Normalmente, para cancelar la aplicación de todos los parches, simplemente haga hg qpop -a.Sólo para mostrar el efecto en la cola de parches, los eliminaré uno a la vez.

$ hg qpop # unapply the top patch, U means unapplied
$ hg qseries -v
0 A migration.patch
1 U working-code.patch
$ hg qtop
migration.patch
$ hg qpop
$ hg qseries -v
0 U migration.patch
1 U working-code.patch

En este punto, es como si no hubiera cambios en su directorio.Hacer el hg fetch.Ahora puede volver a activar los cambios en la cola de parches y fusionarlos si hay algún conflicto.Esto es conceptualmente algo similar al rebase de git.

$ hg qpush # put the first patch back on
$ hg qseries -v
0 A migration.patch
1 U working-code.patch
$ hg qfinish -a # turn all the applied patches into normal hg commits
$ hg qseries -v
0 U working-code.patch
$ hg out
migration.patch commit info... blah, blah
$ hg push # push out your changes

En este punto, ha cancelado la migración manteniendo los demás cambios locales.Sus otros cambios están en un parche en la cola.Hago la mayor parte de mi desarrollo personal utilizando una cola de parches para ayudarme a estructurar mejor mis cambios.Si desea deshacerse de la cola de parches y volver a un estilo normal, tendrá que exportar sus cambios y volver a importarlos en mercurial "normal".

$ hg qpush
$ hg qseries -v
0 A working-code.patch
$ hg export qtip > temp.diff
$ rm -r .hg/patches # get rid of mq from the repository entirely
$ hg import --no-commit temp.diff # apply the changes to the working directory
$ rm temp.diff

Soy enormemente adicto a las colas de parches para el desarrollo y mq es una de las mejores implementaciones que existen.La capacidad de elaborar varios cambios simultáneamente realmente mejora el nivel de concentración y limpieza de sus compromisos.Lleva un tiempo acostumbrarse, pero combina increíblemente bien con un flujo de trabajo DVCS.

Otra opción si no desea depender de extensiones es mantener un clon de su repositorio ascendente localmente que solo use para este tipo de tareas de integración.

En su ejemplo, podría simplemente extraer/fusionar su cambio en el repositorio de integración/ascendente y enviarlo directamente al servidor remoto.

Lo que uso generalmente es enviar un solo archivo:

 hg commit -m "commit message" filename

En caso de que más adelante tenga un conflicto de fusión y todavía no esté listo para realizar mis cambios, siga estos pasos:

1) Cree un archivo de parche.

hg diff > changes.patch

2) Revierta todos los cambios pendientes no confirmados, solo después de verificar su archivo de parche.

hg revert --all

3) Extraer, actualizar y fusionar con la última revisión

hg pull -u
hg merge
hg commit -m "local merge"

4) Ahora simplemente vuelva a importar su parche y obtenga los cambios.

hg import --no-commit changes.patch

Recuerde utilizar el indicador -no-commit para evitar la confirmación automática de los cambios.

Como dijiste que es más fácil, a menudo uso hg commit -i (--interactive) incluso cuando se confirman archivos completos.Con --interactive puede simplemente seleccionar los archivos que desee en lugar de escribir sus rutas completas en la línea de comando.Como ventaja adicional, puedes incluso incluir/excluir selectivamente fragmentos dentro de los archivos.

Y luego solo hg push para impulsar ese compromiso recién creado.

pongo más detalles sobre el uso hg commit --interactive en esta respuesta: https://stackoverflow.com/a/47931672/255961

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top