2011-08-05 15 views
5

Estoy construyendo un historial de proyectos retrospectivo a partir de instantáneas zip. Ya he creado una larga secuencia de confirmaciones a partir de instantáneas que estaban a mano. Ahora agregué al final algunas instantáneas más 'encontradas' que deberían estar en varios lugares 'en el medio' de la secuencia de confirmación.git: cómo volver a ordenar (severamente) una secuencia de confirmación

Estoy tratando de usar el git rebase -i <startCommit> para reordenar las instantáneas de git. Simplemente cambio el orden de la lista de selección. Esto debería ser simplemente un caso de volver a escribir los objetos de confirmación, pero manteniendo los árboles subyacentes iguales (porque las instantáneas no han cambiado).

Parece que rebase, en este caso, todavía está tratando de crear parches y tener muchos conflictos, en lugar de hacer la simple reorganización. ¿Hay un comando más apropiado para este caso particular? No tengo fusiones, y solo una rama. El repositorio completo sigue siendo muy local y privado.

+1

'git rebase' asume que los commit son realmente identificados por sus cambios, no solo por el árbol. Lo que estás tratando de hacer es bastante inusual, así que creo que la parte de porcelana de git no será de mucha ayuda para ti y tendrás que usar tuberías. – svick

+0

Me pregunto si usar [este controlador de combinación personalizado] (http://stackoverflow.com/questions/928646/how-do-i-tell-git-to-always-select-my-local-version-for- conflicted-merges-on-a-sp/930495 # 930495) o similar funcionaría. –

+0

@Karl: echaré un buen vistazo a ese método para, al menos, entender qué está haciendo. La mirada rápida sugiere que podría adelantarse al método de Adymitruk si simplifica mis confusiones de Linux de Windows <-> ;-) –

Respuesta

3

no te molestes con rebase. Haz una nueva rama. Si X es SHA1 o treeish de comprometerse a utilizar, entonces:

git checkout X -- . 
git add -A 
git commit -C X 

Repita para todas las confirmaciones en el orden cronológico que desea.

Un ejemplo en el que invertir el orden de los 5 últimos se compromete:

git checkout -b temp old_branch~5 
git checkout old_branch -- . 
git add -A 
git commit -C old_branch 
git checkout old_branch~1 -- . 
git add -A 
git commit -C old_branch~1 
git checkout old_branch~2 -- . 
git add -A 
git commit -C old_branch~2 
git checkout old_branch~3 -- . 
git add -A 
git commit -C old_branch~3 
git checkout old_branch~4 -- . 
git add -A 
git commit -C old_branch~4 

git push . HEAD:old_branch -f 
git checkout old_branch 
git branch -d temp 

git log -5 # to see the new history 

esperanza esto ayuda.

+0

Creo que podría estar de acuerdo con este, pero con el giro de usar la base de datos inicial para obtener la lista de commit sha1s, principalmente porque los coloca a todos en el archivo de selección. Luego ejecútalo como un script. ¡Es incómodo aprender algunos de los métodos de edición y script de Linux después de 30 años en otros sistemas operativos! –

+0

¿Deberían los comandos 'git add -A' tener un' .' de rastreo para seleccionar todos los archivos, o es una parte implícita de '-A'? (Siempre lo he visto/usado) –

+0

También estoy recibiendo un problema con la falla de la secuencia para eliminar directorios y archivos caídos entre los registros. El nombre del directorio de nivel superior cambia entre cada instantánea, que normalmente se muestra como un conjunto de renombrados, ¡pero aquí simplemente estoy obteniendo un conjunto de aditivos! ¿Alguna sugerencia? –

0

No puedo ayudar a que la rebase sea más fácil, pero puedo explicar por qué no es una "simple reorganización". Como ejemplo, tome un archivo que tenga una línea de texto adjunta por revisión. En la primera confirmación, que parece:

Commit 1 

En el segundo compromiso, ya que originalmente los pone fuera de servicio, que parece:

Commit 1 
Commit 2 
Commit 3 

en la tercera confirmación, que era su segunda instantánea, que parece:

Commit 1 
Commit 2 

Git está tratando con parches, por lo que git, el seri es de confirmaciones se parece a:

  • añadir un archivo con una línea que dice "Commit 1"
  • Añadir líneas que dicen "Commit 2" y "Commit 3" después de la línea que dice "Commit 1"
  • eliminar la línea que dice "Commit 3" después de la línea que dice "Commit 2"

Cuando se reordena, que parece:

  • Añadir un archivo con una línea T hat dice "Commit 1"
  • Elimine la línea que dice "Commit 3" después de la línea que dice "Commit 2"
  • Agregue líneas que digan "Commit 2" y "Commit 3" después de la línea que dice "Commit 1 "

Llega al segundo paso, no ve líneas con" Commit 2 "para hacer coincidir, no sabe qué hacer, por lo que requiere una fusión manual.

Resuelve manualmente la fusión, luego en el siguiente paso, git ve 2 líneas donde esperaba una, y nuevamente requiere una fusión manual.

+0

Por eso creo que 'git rebase' no es la herramienta adecuada para este trabajo. No estoy seguro de qué es exactamente. – svick

+0

Esto sería muy tedioso. No desea aplicar un parche, sino simplemente unir las instantáneas presentes en cada confirmación. –

0

Si su historia es así:

a->b->c->d->e->f 

donde se supone que e y f para ser colocado en algún lugar entre a y d

Todavía se puede hacer lo rebase -i, pero puso edit en el comprometerse antes de donde quieres que se inserte la instantánea. Cuando git haga una pausa para esa edición, coloque la instantánea en su directorio de trabajo y agréguela/confírmela. Continúa la rebase hasta el siguiente punto, enjuaga, repite.

En caso de que sea necesario decirlo, también querrá quitar los commit inicialmente fuera de lugar, e y f, que se ocupan de las instantáneas perdidas.

+0

Eso probablemente todavía cause muchos conflictos. Y tratará de aplicar los cambios, por lo que el resultado puede no ser exactamente el mismo árbol que antes. – svick

Cuestiones relacionadas