Tema 26: Agrupar commits con squash
Squash significa agrupar varios cambios en un solo commit. Git no incorpora un comando estándar git squash. Hay varios procedimientos y conviene distinguir si vas a reorganizar la rama de trabajo o solo a agrupar lo que incorporas a otra.
git rebase -i main, desde una rama con commits locales sobre main, abre una lista interactiva. Cada línea representa un commit, del más antiguo al más reciente. pick conserva un commit separado; squash —o s— combina ese commit con el anterior y permite reunir sus mensajes. El primero no puede agruparse con un anterior que no está en la lista.
El laboratorio ofrece un editor local de esa lista. Conserva el orden y los identificadores, deja pick en el primero y usa squash en los siguientes. Para mantener el ejercicio acotado, agrupa todos los commits seleccionados y combina sus mensajes automáticamente. Git real permite más operaciones y un editor posterior del mensaje; no las necesitamos aquí.
Como rebase reproduce el historial, la rama de trabajo termina apuntando a un commit nuevo y los identificadores originales dejan de formar parte de su recorrido. Hazlo con trabajo local no compartido, aplicando el criterio de los temas 22 y 23.
En cambio, git merge --squash feature/saludo, ejecutado desde main, prepara el resultado combinado en el índice sin crear el commit. Después usas git commit -m "feat: incorpora saludo". Ese commit tiene un padre; no es un commit de merge con dos padres. La rama feature/saludo conserva sus commits originales.
Ambos procedimientos pueden producir contenido equivalente, pero dejan referencias e historias distintas. Comprueba siempre diff --staged, log --graph --all y status para entender el resultado. El segundo procedimiento no sustituye una estrategia acordada para integrar repetidamente una rama larga.
Comandos para probar #
1git switch main 2git merge --squash feature/saludo 3git diff --staged 4git commit -m "feat: incorpora saludo" 5git log --oneline --graph --all
Error que conviene evitar #
Confundir merge --squash con un merge de dos padres o buscar un subcomando git squash inexistente.
Laboratorio local #
Prueba los comandos y observa qué cambia. Puedes reiniciar sin guardar una entrega. Los retos evaluables y el cuestionario están en las actividades de este tema.
Git / práctica local
Agrupa con rebase interactivo
Aplicar edición cambia el archivo; git add lo prepara.
Historial de commits
Las líneas conectan los commits con sus padres. Los commits que ya no tienen una referencia también permanecen visibles en este laboratorio.
- 0000004: Añade saludo; HEAD → feature/saludo
- 0000003: Añade pie;
- 0000002: Prepara documento; main
- 0000001: Commit inicial;
Comparar trabajo, índice y HEAD
Trabajo
Título inicial Centro Pie de feature Hola Git
Índice (staging)
Título inicial Centro Pie de feature Hola Git
HEAD
Título inicial Centro Pie de feature Hola Git
TERMINAL
Sesión local preparada. Escribe help para consultar los comandos de este tema.
Comandos disponibles y límites
git --version · git config --global <clave> [valor] git init · git status git add <archivo | .> · git commit -m "mensaje" · git log git log --oneline · git switch <rama> (antes: checkout) git restore [--staged] <archivo> · git commit --amend [-m "mensaje" | --no-edit] git switch --detach <commit> · HEAD · HEAD~1 git diff [--staged | <commit> <commit>] git remote [-v] · git remote add <nombre> <URL> · git remote get-url <nombre> · git remote set-url <nombre> <URL> git clone <URL> git push [-u] <remoto> <rama> ssh-keygen -t ed25519 · ssh -T git@github.com (ficticios) git branch [nombre] · git branch -m <nombre> · git branch -d <rama> · git switch -c <rama> git merge [--ff-only] <rama> git merge --no-ff <rama> · git log --graph --all --decorate git merge --abort · editar conflicto, git add y git commit -m "mensaje" git config --global alias.st status · git st git tag [nombre] · git tag -a <nombre> -m "mensaje" · git tag -n · git push origin <tag> git reset --soft|--mixed|--hard <commit> · git reflog git stash push [-u] [-m "mensaje"] · list · show · apply · pop · drop git rebase <rama> · git rebase --continue · git rebase --abort git grep [-n] <texto> [revisión] git rebase -i <base> (editar lista) · git merge --squash <rama> help · clear
Sesión en memoria: recargar descarta la práctica. Doscientas acciones como máximo. Dos archivos editables de hasta 250 líneas. Diez ramas como máximo. Diez entradas de stash como máximo. El modelo no ejecuta comandos reales ni realiza conexiones externas. diff muestra contenido anterior y posterior por archivo. grep busca texto literal. La lista interactiva conserva el orden y agrupa todos los commits seleccionados.
Resumen
- La ejecutas desde la rama cuyo trabajo quieres agrupar.
- La primera línea de este ejercicio debe usarla.
- También puede escribirse s.
- Confundir merge --squash con un merge de dos padres o buscar un subcomando git squash inexistente.