BranchLab ← Volver al inicio
TEORÍA AVANZADA · TRABAJO EN EQUIPO

Git como sistema
de colaboración.

Aprende qué operaciones existen, cuándo se utilizan y en qué orden aparecen durante el desarrollo de un proyecto real con varios programadores.

ObjetivoPasar de memorizar comandos a comprender el flujo completo del trabajo compartido.
01 · MAPA MENTAL

Organiza los comandos por intención

Antes de escribir un comando, pregúntate qué operación necesitas realizar.

01

Obtener el proyecto

Crea tu copia local con archivos, ramas e historial.

git clone URL
02

Traer referencias remotas

Consulta el estado del servidor sin fusionar cambios todavía.

git fetch --prune
03

Leer el historial

Comprende qué cambió, quién lo hizo y dónde estás.

git log --oneline --graphgit show HASH
04

Revisar diferencias

Inspecciona cambios locales antes de preparar un commit.

git diffgit diff --staged
05

Trabajar en paralelo

Crea una rama por tarea para aislar modificaciones.

git switch -c feature/perfil
06

Guardar cambios

Prepara una unidad lógica y crea un commit descriptivo.

git add archivogit commit -m "mensaje"
07

Fusionar ramas

Integra trabajo revisado y resuelve conflictos si aparecen.

git merge nombre-ramagit merge --abort
08

Deshacer con trazabilidad

Revierte un cambio compartido sin reescribir el historial.

git revert HASH
02 · SECUENCIA DE TRABAJO

El orden dentro de un proyecto real

Este ciclo se repite para cada tarea que entra al equipo.

01
UNA SOLA VEZ

Clona el repositorio compartido

La persona se incorpora al proyecto y obtiene una copia local completa. origin queda configurado como remoto principal.

$ git clone https://github.com/equipo/plataforma.git
$ cd plataforma
$ git remote -v
02
ANTES DE EMPEZAR

Actualiza la visión del remoto

Antes de crear una tarea, consulta lo que publicó el resto del equipo. fetch descarga referencias y pull integra los cambios de la rama actual.

$ git switch main
$ git fetch --prune
$ git pull --ff-only
03
UNA RAMA POR TAREA

Aísla tu modificación

Crea una rama descriptiva desde una base actualizada. Así varias personas pueden avanzar sin alterar main.

$ git switch -c feature/perfil-usuario
04
MIENTRAS PROGRAMAS

Revisa y guarda unidades pequeñas

Inspecciona diferencias, prepara solo los archivos relacionados y crea commits que narren el avance.

$ git status
$ git diff
$ git add src/perfil.js
$ git commit -m "Añade formulario de perfil"
05
ANTES DE PUBLICAR

Sincroniza tu rama con el equipo

Trae las referencias recientes. Según la convención del equipo, fusiona main o reaplica tus commits con rebase.

$ git fetch origin
$ git merge origin/main
# o, si el equipo lo acordó:
$ git rebase origin/main
06
COMPARTIR Y REVISAR

Publica una rama y abre un pull request

El equipo revisa la propuesta antes de integrarla. Las correcciones solicitadas se añaden como commits nuevos.

$ git push -u origin feature/perfil-usuario
07
INTEGRAR

Fusiona la tarea aprobada

El pull request aprobado se fusiona en main. Si aparece un conflicto, conserva el contenido correcto, prepara el archivo y confirma la resolución.

$ git merge feature/perfil-usuario
# si existe un conflicto:
$ git add archivo-resuelto
$ git commit
08
PRODUCCIÓN

Corrige sin borrar la historia

Si un cambio publicado causa un problema, crea un commit inverso. Así el equipo mantiene una auditoría clara.

$ git log --oneline
$ git revert HASH
$ git push origin main
03 · MODELO DE EQUIPO

Cómo conviven varias personas

Cada desarrollador mantiene su copia local y sus ramas. El repositorio remoto funciona como punto de encuentro y main representa la versión integrada.

origin / mainRepositorio compartido
LMfeature/perfilARfix/loginJSfeature/pagos
04 · TALLER GUIADO

Dos casos de producción, paso a paso

Sigue la secuencia como si trabajaras en la terminal de un equipo real.

EJEMPLO 01 · PÁGINA 1 DE 2

Publica una funcionalidad nueva

Te incorporas al equipo de una tienda en línea. Tu tarea es añadir una página de favoritos sin alterar el trabajo del resto del equipo.

CASO HABITUAL
CONTEXTO

Trabajas en el equipo web de una tienda en línea. El repositorio central vive en GitHub y la rama main siempre debe conservar una versión desplegable. Ana acaba de publicar ajustes del catálogo mientras tú recibes una tarea nueva: añadir la página de favoritos y el botón que permite guardar productos.

No debes editar directamente main. Crearás una rama aislada, revisarás cada diferencia antes de confirmarla, integrarás los cambios recientes del equipo y publicarás tu propuesta para revisión mediante pull request.

  • Objetivo: entregar una funcionalidad completa sin interferir con otras tareas.
  • Restricción: cada commit debe contener una unidad lógica fácil de revisar.
  • Resultado esperado: una rama remota lista para revisión y pruebas automáticas.
01

Clona el repositorio

Como trabajas desde un equipo nuevo, necesitas una copia local completa. git clone descarga los archivos, el historial de commits y las referencias de ramas. Además, configura automáticamente origin como alias del repositorio compartido. Después entras en la carpeta y verificas que las direcciones de lectura y publicación sean correctas.

$ git clone https://github.com/equipo/tienda-web.git
Cloning into 'tienda-web'...
$ cd tienda-web
$ git remote -v
origin  https://github.com/equipo/tienda-web.git (fetch)
origin  https://github.com/equipo/tienda-web.git (push)
02

Comprueba la rama y actualiza referencias

Antes de modificar archivos, confirma que estás en main y que no existen cambios locales accidentales. git fetch --prune actualiza tu visión del servidor y elimina referencias obsoletas sin tocar tu directorio de trabajo. Después, git pull --ff-only adelanta tu rama local únicamente si puede hacerlo sin crear una fusión inesperada.

$ git status
On branch main
nothing to commit, working tree clean
$ git fetch --prune
From github.com:equipo/tienda-web
   a02d91f..be8923d  main -> origin/main
$ git pull --ff-only
Updating a02d91f..be8923d
Fast-forward
03

Crea una rama por tarea

Crea una rama desde el main actualizado. El prefijo feature/ comunica que estás desarrollando una capacidad nueva y el nombre favoritos identifica la tarea. Desde este momento puedes crear commits sin alterar la versión estable que usa el resto del equipo.

$ git switch -c feature/favoritos
Switched to a new branch 'feature/favoritos'
04

Revisa tus cambios antes del commit

Después de programar, no confirmes cambios a ciegas. git status --short ofrece un inventario compacto: M indica un archivo modificado y ?? uno nuevo sin seguimiento. git diff muestra las líneas exactas que todavía no preparaste. Esta revisión evita incluir archivos temporales, trazas de depuración o credenciales por error.

$ git status --short
 M src/pages/Favoritos.js
?? src/components/BotonFavorito.js
$ git diff
+ export function BotonFavorito({ productoId }) {
+   return <button>Guardar favorito</button>
+ }
05

Prepara una unidad lógica y confirma

Selecciona únicamente los archivos de la funcionalidad con git add. El área de preparación funciona como una cesta: decide qué formará parte del próximo commit. Revisa esa cesta con git diff --staged y crea un mensaje que explique la intención del cambio, no solo los archivos modificados.

$ git add src/pages/Favoritos.js src/components/BotonFavorito.js
$ git diff --staged
# muestra exactamente lo que formará parte del commit
$ git commit -m "Añade gestión básica de favoritos"
[feature/favoritos 3f821a7] Añade gestión básica de favoritos
 2 files changed, 48 insertions(+)
06

Sincroniza antes de publicar

Mientras desarrollabas, otras personas pudieron integrar cambios. Descarga las referencias recientes con git fetch origin e integra origin/main dentro de tu rama. Resolver incompatibilidades aquí reduce sorpresas durante la revisión y comprueba que tu trabajo convive con la versión más reciente del equipo.

$ git fetch origin
$ git merge origin/main
Merge made by the 'ort' strategy.
$ git log --oneline --graph --decorate -5
07

Publica la rama y abre el pull request

Envía la rama al remoto para que el equipo pueda verla. La opción -u establece la relación de seguimiento entre la rama local y la remota; en futuras actualizaciones bastará con ejecutar git push. El pull request será el espacio de revisión, conversación y validación automática antes de integrar en main.

$ git push -u origin feature/favoritos
branch 'feature/favoritos' set up to track
'origin/feature/favoritos'.
EJEMPLO 02 · PÁGINA 2 DE 2

Resuelve un conflicto y revierte un incidente

Dos personas modificaron el mismo componente. Después de integrar la solución, una regresión llega a producción y debes revertirla de forma trazable.

CASO DE INCIDENTE
CONTEXTO

Trabajas en feature/login-social para añadir acceso con un proveedor externo. Al mismo tiempo, Julia corrigió el comportamiento responsive del encabezado y su pull request ya llegó a main. Ambas tareas modifican src/components/Header.js, por lo que Git no puede decidir automáticamente qué versión conservar.

Después de resolver el conflicto y publicar la integración, las métricas de producción muestran que el login falla en móviles. Debes estabilizar el sistema sin borrar la historia compartida y conservar una vía de recuperación por si necesitas inspeccionar el estado anterior.

  • Objetivo: integrar trabajo paralelo y responder a una regresión de producción.
  • Restricción: no reescribir el historial que otras personas ya descargaron.
  • Resultado esperado: revertir el incidente con trazabilidad y conservar opciones de recuperación.
01

Guarda temporalmente una edición incompleta

Tu ajuste responsive todavía no forma una unidad lista para commit, pero necesitas actualizar main. git stash push guarda temporalmente los cambios del directorio de trabajo y deja la rama limpia. El mensaje descriptivo permite reconocer el trabajo guardado si acumulas varios stashes.

$ git status --short
 M src/components/Header.js
$ git stash push -m "WIP ajuste responsive del header"
Saved working directory and index state
$ git switch main
02

Actualiza main y recupera tu trabajo

Ya con el directorio limpio, actualiza main mediante un avance lineal. Regresa a tu rama y usa git stash pop: aplica el cambio guardado y elimina esa entrada del stash si la aplicación funciona. Comprueba el resultado antes de continuar.

$ git pull --ff-only
$ git switch feature/login-social
$ git stash pop
On branch feature/login-social
Changes not staged for commit:
  modified: src/components/Header.js
03

Integra main y detecta el conflicto

Fusiona la rama principal actualizada dentro de tu rama de funcionalidad. Git combina automáticamente los archivos compatibles, pero se detiene en Header.js porque ambas líneas de desarrollo editaron la misma zona. git status identifica los archivos que requieren una decisión humana.

$ git merge main
Auto-merging src/components/Header.js
CONFLICT (content): Merge conflict in src/components/Header.js
Automatic merge failed; fix conflicts and then commit the result.
$ git status
both modified: src/components/Header.js
04

Resuelve y valida el merge

Abre el archivo y busca las marcas de conflicto. HEAD representa tu rama actual; la sección inferior proviene de main. Conserva una versión que combine el login social con el diseño compacto, elimina las marcas y ejecuta las pruebas. Solo después prepara el archivo y confirma la resolución.

<<<<<<< HEAD
<Header socialLogin />
=======
<Header compact />
>>>>>>> main
$ npm test
$ git add src/components/Header.js
$ git commit -m "Resuelve conflicto del encabezado"
05

Publica la solución revisada

Publica la rama con el merge resuelto. El pull request permite revisar tanto la funcionalidad como la decisión tomada durante el conflicto. Cuando las pruebas y la revisión terminan, la propuesta se integra en main y el despliegue automatizado la lleva a producción.

$ git push -u origin feature/login-social
# pull request revisado y fusionado en main
06

Revierte una regresión publicada

Tras desplegar, el monitoreo detecta errores de autenticación en móviles. Primero actualiza main y localiza el merge problemático en el historial. git revert crea un commit nuevo que invierte el cambio publicado: la historia permanece intacta y el equipo puede auditar qué ocurrió y por qué se deshizo.

$ git switch main
$ git pull --ff-only
$ git log --oneline -5
98fd421 Merge pull request #184 from feature/login-social
751e20a Resuelve conflicto del encabezado
$ git revert 98fd421
[main 61fa011] Revert "Merge pull request #184..."
$ git push origin main
07

Recupera un commit perdido con reflog

Imagina que necesitas inspeccionar la resolución anterior o que una rama local fue eliminada por accidente. git reflog registra movimientos recientes de HEAD en tu equipo, incluso cuando un commit ya no aparece en el historial visible. Crea una rama de recuperación desde el hash elegido para investigar sin alterar main.

$ git reflog
61fa011 HEAD@{0}: revert: Revert "Merge pull request #184"
98fd421 HEAD@{1}: pull --ff-only: Fast-forward
751e20a HEAD@{2}: commit: Resuelve conflicto del encabezado
$ git switch -c recovery/header 751e20a
EJEMPLO 03 · CONFLICTO DE DEPENDENCIAS

Resuelve cambios simultáneos en package-lock.json

Dos ramas instalaron librerías diferentes. El archivo generado entra en conflicto y editarlo manualmente puede dejar una instalación aparentemente válida pero inconsistente.

DEPENDENCIAS
CONTEXTO

Tu rama feature/reportes añadió chart.js para visualizar ventas. Mientras trabajabas, main incorporó date-fns para procesar fechas. Ambas instalaciones modificaron package.json y package-lock.json.

El lockfile describe el árbol exacto de dependencias. Resolver sus cientos de líneas a mano puede conservar hashes o versiones incompatibles sin que el error sea evidente durante la revisión.

  • Objetivo: integrar ambas librerías y regenerar un lockfile coherente.
  • Restricción: no editar manualmente bloques internos de package-lock.json.
  • Resultado esperado: instalación reproducible y pruebas aprobadas.
01

Actualiza referencias e integra main

Descarga el estado reciente del servidor e integra origin/main en tu rama. Hacerlo antes de publicar permite resolver el conflicto localmente y probar la combinación real que llegará a revisión.

$ git switch feature/reportes
$ git fetch origin
$ git merge origin/main
CONFLICT (content): Merge conflict in package.json
CONFLICT (content): Merge conflict in package-lock.json
02

Revisa el alcance del conflicto

git status enumera los archivos no fusionados. git diff --name-only --diff-filter=U reduce la salida exclusivamente a rutas con conflicto para evitar olvidar alguna.

$ git status
$ git diff --name-only --diff-filter=U
package-lock.json
package.json
03

Resuelve el manifiesto, no el lockfile a mano

Edita package.json y conserva ambas dependencias. Después acepta temporalmente una versión del lockfile y regénéralo con el gestor de paquetes. npm install --package-lock-only reconstruye el árbol a partir del manifiesto resuelto.

# package.json conserva chart.js y date-fns
$ git checkout --ours package-lock.json
$ npm install --package-lock-only
$ npm ci
$ npm test
04

Confirma la resolución completa

Prepara ambos archivos y verifica que Git ya no reporte rutas sin fusionar. El commit explica que resolviste el conflicto de dependencias.

$ git add package.json package-lock.json
$ git status
$ git commit -m "Integra dependencias de reportes y fechas"
!

No uses estas salidas rápidas

Evita git add . antes de revisar el lockfile: podrías confirmar marcas de conflicto o archivos generados no deseados. Evita editar manualmente cada bloque de package-lock.json y no ejecutes git reset --hard: perderías trabajo local sin resolver la causa.

EJEMPLO 04 · RENOMBRADO FRENTE A EDICIÓN

Conserva cambios cuando un archivo cambia de ubicación

Una rama reorganizó carpetas mientras otra corrigió lógica dentro del archivo original. Git necesita ayuda para determinar dónde debe vivir la versión final.

REFACTORIZACIÓN
CONTEXTO

Tu rama fix/calculo-impuestos corrigió una fórmula en src/utils/precios.js. Paralelamente, main reorganizó utilidades y trasladó ese archivo a src/domain/precios.js.

Si eliges una versión completa sin inspeccionar el cambio, puedes recuperar la fórmula antigua o perder el nuevo diseño de carpetas. La solución correcta conserva la ubicación nueva y reaplica la corrección funcional.

  • Objetivo: conservar el renombrado y la corrección de impuestos.
  • Restricción: no restaurar la ruta antigua después de la refactorización.
  • Resultado esperado: un solo archivo en src/domain con la fórmula corregida.
01

Integra y observa el tipo de conflicto

Después de traer referencias recientes, fusiona origin/main. Git informa un conflicto de modificación frente a renombrado: tu rama modificó la ruta antigua y main movió el archivo.

$ git fetch origin
$ git merge origin/main
CONFLICT (modify/delete): src/utils/precios.js deleted in origin/main
and modified in HEAD.
02

Inspecciona ambos lados antes de decidir

git status muestra la situación general. git show permite leer cada versión sin modificar archivos: HEAD contiene tu corrección y origin/main la estructura nueva.

$ git status
$ git show HEAD:src/utils/precios.js
$ git show origin/main:src/domain/precios.js
03

Aplica la corrección en la ubicación nueva

Edita src/domain/precios.js e incorpora únicamente la fórmula corregida. Después elimina la ruta antigua con git rm. Este comando registra explícitamente que el archivo anterior ya no debe existir.

# edita src/domain/precios.js y aplica la fórmula correcta
$ git rm src/utils/precios.js
$ git add src/domain/precios.js
$ npm test
04

Verifica nombres y confirma

git diff --staged --name-status muestra el resultado preparado. Debes ver la eliminación de la ruta antigua y la modificación de la nueva antes de crear el commit.

$ git diff --staged --name-status
M  src/domain/precios.js
D  src/utils/precios.js
$ git commit -m "Conserva corrección fiscal tras reorganizar precios"
!

No elijas una versión completa sin inspección

Evita git checkout --ours . o git checkout --theirs . sobre todo el repositorio: una de esas órdenes puede descartar silenciosamente la refactorización o tu corrección. Evita recrear la ruta antigua; generaría dos fuentes de verdad difíciles de mantener.

EJEMPLO 05 · HOTFIX CON TRABAJO ABIERTO

Publica una corrección urgente sin mezclar una funcionalidad incompleta

Producción falla mientras tienes cambios locales a medio terminar. Debes aislar la corrección, publicarla con rapidez y volver a tu tarea sin contaminar ninguna rama.

HOTFIX
CONTEXTO

Estás desarrollando feature/nuevo-checkout con varios archivos modificados. El monitoreo reporta que los cupones aplican el descuento dos veces en producción. La corrección debe salir desde la versión desplegada, no desde tu funcionalidad incompleta.

Mezclar ambos trabajos aumentaría el alcance del despliegue urgente y podría introducir fallos no relacionados. La estrategia correcta guarda el trabajo temporalmente, crea una rama de hotfix desde origin/main y publica un cambio mínimo.

  • Objetivo: corregir producción con el menor cambio posible.
  • Restricción: no incluir archivos del checkout nuevo en el hotfix.
  • Resultado esperado: pull request pequeño, reversible y fácil de auditar.
01

Protege el trabajo incompleto

Comprueba qué cambió y guarda archivos rastreados y nuevos con git stash push -u. La opción -u incluye archivos todavía no seguidos por Git, algo frecuente durante una funcionalidad en desarrollo.

$ git status --short
$ git stash push -u -m "WIP nuevo checkout antes de hotfix"
$ git status
nothing to commit, working tree clean
02

Crea el hotfix desde la versión publicada

Actualiza referencias remotas y crea una rama directamente desde origin/main. Así la corrección parte de la misma base que producción y no arrastra commits de tu funcionalidad.

$ git fetch origin
$ git switch -c hotfix/cupon-duplicado origin/main
Switched to a new branch 'hotfix/cupon-duplicado'
03

Confirma un cambio mínimo y verificable

Modifica solo la lógica del cupón, ejecuta pruebas específicas y revisa la diferencia. Preparar la ruta explícita evita incluir archivos accidentales.

$ npm test -- cupones
$ git diff
$ git add src/domain/cupones.js
$ git commit -m "Evita aplicar dos veces el descuento del cupón"
$ git show --stat --oneline HEAD
04

Publica, revisa y vuelve a tu tarea

Envía la rama para revisión urgente. Después de integrar y desplegar el hotfix, vuelve a la rama original y recupera tu trabajo temporal. git stash pop aplica los cambios y elimina el stash solo si puede hacerlo correctamente.

$ git push -u origin hotfix/cupon-duplicado
# pull request aprobado, fusionado y desplegado
$ git switch feature/nuevo-checkout
$ git stash list
$ git stash pop
!

No corrijas producción desde tu rama incompleta

Evita confirmar el hotfix dentro de feature/nuevo-checkout y evita git push --force sobre main. Tampoco uses git reset --hard para limpiar rápidamente tu directorio: destruiría el trabajo local que intentas proteger.

EJEMPLO 06 · RAMA PROTEGIDA Y TRAZABILIDAD

Entrega una corrección cumpliendo la política de ramas

La empresa ficticia NovaCode exige que todo cambio esté asociado a un ticket, pase por revisión y llegue a main exclusivamente mediante pull request.

POLÍTICA NC-01
REGLAS DE LA EMPRESA
  • main y release/* están protegidas: nadie publica directamente.
  • La rama debe incluir el ticket: fix/NC-1842-validacion-email.
  • El mensaje del commit debe comenzar con el identificador del ticket.
  • Se requieren dos revisiones antes de integrar.
CONTEXTO

Soporte reporta que el registro permite correos sin dominio. Debes corregir la validación sin saltarte el proceso de auditoría. Aunque el cambio es pequeño, publicarlo directamente en main rompería la trazabilidad exigida por la empresa.

  • Objetivo: entregar una corrección mínima asociada a NC-1842.
  • Resultado esperado: pull request revisable con historial verificable.
01

Parte de main actualizado

Descarga referencias y adelanta tu copia local sin generar merges accidentales. La política exige comenzar desde la última versión aprobada.

$ git switch main
$ git fetch --prune origin
$ git pull --ff-only
02

Crea una rama trazable

El nombre incorpora tipo, ticket y propósito. Así herramientas de CI y auditoría pueden relacionar automáticamente código, tarea y revisión.

$ git switch -c fix/NC-1842-validacion-email
03

Prueba, revisa y confirma con el formato obligatorio

Ejecuta las pruebas de la validación, inspecciona la diferencia y crea un commit con el ticket al inicio.

$ npm test -- registro
$ git diff
$ git add src/domain/validarEmail.js
$ git commit -m "NC-1842 Corrige validación de dominio en email"
$ git push -u origin fix/NC-1842-validacion-email
!

Prohibido publicar directamente

No uses git push origin main ni git push --force. El pull request, las dos aprobaciones y el CI no son burocracia decorativa: permiten detectar regresiones y demostrar quién autorizó el cambio.

EJEMPLO 07 · COMMITS FIRMADOS

Integra una dependencia con autoría verificable

NovaCode desarrolla software para clientes regulados. Cada commit que llega a una rama de entrega debe estar firmado criptográficamente.

POLÍTICA NC-02
REGLAS DE LA EMPRESA
  • Los commits deben aparecer como verificados en el servidor.
  • Las dependencias nuevas requieren revisión de seguridad.
  • El lockfile debe regenerarse con el gestor de paquetes y confirmarse junto al manifiesto.
  • No se admiten secretos ni tokens dentro del repositorio.
CONTEXTO

Necesitas incorporar una librería para exportar reportes CSV. La dependencia debe quedar reproducible, pasar el escaneo de vulnerabilidades y llevar una firma verificable antes de solicitar revisión.

  • Objetivo: añadir una dependencia aprobada con commit firmado.
  • Resultado esperado: manifiesto, lockfile y evidencia de auditoría sin vulnerabilidades críticas.
01

Verifica tu identidad y firma configurada

Antes de trabajar, consulta la identidad local y la clave de firma. La opción commit.gpgsign true evita olvidar la firma en commits posteriores.

$ git config user.email
$ git config user.signingkey
$ git config commit.gpgsign true
02

Instala y audita la dependencia

Usa el gestor de paquetes para actualizar manifiesto y lockfile. Después ejecuta el escaneo y las pruebas antes de preparar cambios.

$ npm install csv-stringify
$ npm audit --audit-level=high
$ npm test
$ git diff -- package.json package-lock.json
03

Confirma con firma y compruébala

-S firma explícitamente el commit. git log --show-signature permite verificar localmente que la firma acompaña al cambio.

$ git add package.json package-lock.json
$ git commit -S -m "NC-1910 Añade exportación segura de reportes CSV"
$ git log --show-signature -1
$ git push -u origin feature/NC-1910-exportar-csv
!

No confirmes archivos sensibles

No uses git add . sin inspeccionar git status. Podrías incluir un archivo .env, un token o una configuración local. Tampoco desactives la firma para resolver deprisa un error de configuración.

EJEMPLO 08 · CONFLICTO EN MIGRACIONES

Resuelve dos migraciones de base de datos con orden seguro

Dos ramas crearon migraciones con el mismo número secuencial. Elegir una y borrar la otra rompería el despliegue de una funcionalidad.

POLÍTICA NC-03
REGLAS DE LA EMPRESA
  • Las migraciones ya desplegadas nunca se editan ni eliminan.
  • Cada migración debe conservar una operación de reversión.
  • El orden final debe validarse sobre una base de datos temporal limpia.
  • Todo conflicto de esquema requiere revisión del responsable de datos.
CONTEXTO

Tu rama añade 042_add_invoice_status.sql; otra tarea ya fusionada añadió 042_add_customer_segment.sql. Ambas son válidas, pero el sistema de migraciones requiere identificadores únicos y ordenados.

  • Objetivo: conservar ambas migraciones sin alterar la ya integrada.
  • Resultado esperado: renombrar tu migración como 043 y validar subida y reversión.
01

Integra main y localiza el conflicto

Trae el estado aprobado y fusiona. Después lista las migraciones para comprender el orden real antes de renombrar archivos.

$ git fetch origin
$ git merge origin/main
$ ls db/migrations
042_add_customer_segment.sql
042_add_invoice_status.sql
02

Renombra únicamente tu migración

git mv registra el traslado de forma explícita y conserva la trazabilidad. No modifiques la migración de clientes porque ya forma parte de main.

$ git mv db/migrations/042_add_invoice_status.sql db/migrations/043_add_invoice_status.sql
03

Valida el ciclo completo

Aplica las migraciones sobre una base temporal, ejecuta pruebas y comprueba la reversión. Una migración que solo funciona hacia adelante deja al equipo sin recuperación durante un despliegue fallido.

$ npm run db:test:create
$ npm run db:migrate
$ npm test -- database
$ npm run db:rollback
$ git add db/migrations
$ git commit -m "NC-1974 Reordena migración de estado de factura"
!

No alteres migraciones ya compartidas

No edites ni borres 042_add_customer_segment.sql. Tampoco uses git checkout --ours .: descartaría silenciosamente la migración integrada y el problema reaparecería al desplegar.

EJEMPLO 09 · RELEASE ESTABLE

Aplica un hotfix a dos líneas de versión con cherry-pick

Una corrección crítica debe llegar a producción y también permanecer en la siguiente versión sin mezclar funcionalidades todavía no aprobadas.

POLÍTICA NC-04
REGLAS DE LA EMPRESA
  • release/2.4 solo acepta correcciones aprobadas.
  • Las funcionalidades futuras permanecen en main.
  • Cada hotfix debe ser un commit pequeño, probado y fácilmente reversible.
  • La propagación entre ramas se realiza mediante cherry-pick del commit aprobado.
CONTEXTO

La versión 2.4 desplegada calcula mal un impuesto regional. main ya contiene funcionalidades para 2.5 que no pueden llegar a producción. Debes corregir release/2.4 y propagar exactamente el mismo commit a main.

  • Objetivo: publicar una corrección aislada en ambas líneas de versión.
  • Resultado esperado: un único cambio funcional trazable en release y main.
01

Crea el hotfix desde la release desplegada

Partir de origin/release/2.4 garantiza que no incluirás trabajo futuro. El nombre de rama comunica versión, ticket y propósito.

$ git fetch origin
$ git switch -c hotfix/NC-2041-impuesto origin/release/2.4
02

Confirma una corrección mínima

Ejecuta pruebas específicas y prepara solo el archivo fiscal. Guarda el hash porque será la unidad exacta que propagarás.

$ npm test -- impuestos
$ git add src/domain/impuestos.js
$ git commit -m "NC-2041 Corrige impuesto regional en release 2.4"
$ git log --oneline -1
c712ab9 NC-2041 Corrige impuesto regional en release 2.4
$ git push -u origin hotfix/NC-2041-impuesto
03

Propaga el commit aprobado a main

Tras fusionar el pull request de release, crea una rama desde origin/main y aplica solo el hash aprobado con git cherry-pick. Si aparece conflicto, resuélvelo y continúa con git cherry-pick --continue.

$ git switch -c backport/NC-2041-main origin/main
$ git cherry-pick c712ab9
$ npm test -- impuestos
$ git push -u origin backport/NC-2041-main
!

No fusiones main dentro de la release

No uses git merge main sobre release/2.4: arrastraría funcionalidades de 2.5 aún no aprobadas. No copies archivos manualmente; perderías la relación trazable con el commit corregido.

EJEMPLO 10 · RESOLUCIÓN DOCUMENTADA

Resuelve un conflicto de reglas de negocio con evidencia

Dos equipos modificaron la autorización de descuentos. La empresa exige documentar la decisión funcional y conservar evidencia de pruebas.

POLÍTICA NC-05
REGLAS DE LA EMPRESA
  • Los conflictos en reglas de negocio requieren aprobación del responsable funcional.
  • La resolución debe incluir pruebas automatizadas para ambos comportamientos.
  • El commit debe describir la decisión tomada, no solo indicar que existió un conflicto.
  • Está prohibido resolver en masa con --ours o --theirs.
CONTEXTO

El equipo comercial permitió descuentos de hasta 20% para clientes premium. En paralelo, el equipo antifraude añadió una revisión manual para cualquier descuento superior a 15%. Ambas reglas son válidas y deben convivir.

  • Objetivo: combinar límite comercial y control antifraude.
  • Resultado esperado: descuento premium permitido, con revisión manual cuando supera 15%.
01

Fusiona y limita la inspección a archivos conflictivos

Integra origin/main y lista solo las rutas no resueltas. Esto evita distraerte con cambios compatibles que Git ya fusionó correctamente.

$ git fetch origin
$ git merge origin/main
$ git diff --name-only --diff-filter=U
src/domain/descuentos.js
test/descuentos.test.js
02

Compara las intenciones de ambos lados

Lee las dos variantes sin sobrescribir archivos. :2: representa tu lado del merge y :3: el lado entrante. Esta comparación ayuda a diseñar una tercera solución que preserve ambas reglas.

$ git show :2:src/domain/descuentos.js
$ git show :3:src/domain/descuentos.js
03

Implementa la decisión aprobada y prueba bordes

Tras confirmar la regla con el responsable funcional, edita la solución combinada y prueba valores alrededor de los límites: 15%, 16% y 20%.

# edita descuentos.js y descuentos.test.js
$ npm test -- descuentos
✓ premium permite descuento de 15%
✓ premium requiere revisión manual con 16%
✓ premium permite hasta 20%
$ git add src/domain/descuentos.js test/descuentos.test.js
04

Documenta la razón del merge

Confirma con un mensaje que explique la política resultante. El historial debe permitir entender la decisión meses después sin reconstruir toda la conversación.

$ git commit -m "NC-2118 Combina límite premium con revisión antifraude"
$ git push -u origin feature/NC-2118-descuentos
!

No uses resolución masiva para reglas de negocio

No ejecutes git checkout --ours . ni git checkout --theirs .. Ambas alternativas eliminan una regla válida sin producir un error técnico inmediato: el fallo sería funcional, silencioso y difícil de detectar sin pruebas de borde.

EJEMPLO 11 · SECRETO EXPUESTO

Responde a una credencial publicada por accidente

Un token de acceso llegó al repositorio remoto. Eliminar el archivo en un commit nuevo no basta: la credencial permanece visible en el historial.

INCIDENTE SEV-1
REGLAS APLICABLES · NC-SEC-01
  • Revocar primero, investigar después: una credencial expuesta se considera comprometida.
  • Notificar al equipo de seguridad y registrar el incidente.
  • No reescribir historia compartida sin coordinación explícita.
  • Todo reemplazo debe quedar fuera del repositorio y gestionarse mediante variables seguras.
CONTEXTO CRÍTICO

Durante una revisión detectas que config/payment.env contiene un token del proveedor de pagos. El archivo fue incluido en un commit de la rama remota feature/checkout. Aunque todavía no llegó a main, cualquier persona con acceso al repositorio puede leerlo.

  • Impacto: riesgo de operaciones no autorizadas contra el proveedor de pagos.
  • Prioridad: revocar el token inmediatamente y bloquear nuevas publicaciones.
  • Resultado esperado: credencial rotada, archivo ignorado e historial limpiado mediante procedimiento coordinado.
01

Detén el uso de la credencial

La primera acción ocurre fuera de Git: revoca el token desde el gestor seguro del proveedor y genera uno nuevo. Git no puede invalidar una credencial filtrada. Registra el incidente según el procedimiento interno.

02

Retira el archivo y evita reincidencias

Elimina el archivo del índice con git rm --cached, pero conserva tu copia local. Añádelo a .gitignore y sustituye el valor por una referencia documentada a la variable segura.

$ git switch feature/checkout
$ git rm --cached config/payment.env
$ echo "config/payment.env" >> .gitignore
$ git add .gitignore config/payment.env.example
$ git commit -m "NC-SEC-331 Retira credencial y documenta variable segura"
03

Inspecciona el alcance antes de limpiar historia

Busca el archivo y posibles variantes dentro del historial. La limpieza histórica debe realizarse con el equipo avisado porque cambia hashes y obliga a recrear ramas afectadas.

$ git log --all -- config/payment.env
$ git grep -n "PAYMENT_TOKEN" $(git rev-list --all)
# seguridad coordina la limpieza con git filter-repo
04

Valida el repositorio corregido

Tras el procedimiento coordinado, confirma que el archivo no aparece en el historial remoto y que el escáner de secretos aprueba la rama antes de reabrir publicaciones.

$ git fetch --all --prune
$ git log --all -- config/payment.env
$ npm run security:secrets
✓ No exposed credentials found
!

No hagas una limpieza improvisada

No basta con ejecutar git rm y continuar: el token seguiría en commits anteriores. Tampoco uses git push --force --all sin coordinación; podrías destruir trabajo remoto y dejar clones inconsistentes. Nunca pegues el token nuevo en otro archivo versionado.

EJEMPLO 12 · DESPLIEGUE DEFECTUOSO

Revierte una release sin perder el análisis posterior

Una versión desplegada incrementa los errores HTTP 500. La prioridad es restaurar el servicio conservando evidencia suficiente para investigar.

INCIDENTE SEV-1
REGLAS APLICABLES · NC-OPS-02
  • Estabilizar producción antes de desarrollar una corrección compleja.
  • Revertir mediante commit trazable y pull request de emergencia.
  • Conservar el commit defectuoso para análisis post-incidente.
  • No modificar directamente la rama protegida.
CONTEXTO CRÍTICO

El despliegue de release/3.8.0 termina correctamente, pero la tasa de error sube del 0.2% al 18%. El historial muestra que el pull request #742 modificó el adaptador de pagos. No hay tiempo para diseñar una solución nueva durante la degradación.

  • Impacto: clientes sin completar compras.
  • Prioridad: recuperar estabilidad con el cambio mínimo reversible.
  • Resultado esperado: revertir el merge defectuoso mediante revisión urgente.
01

Actualiza y localiza el merge exacto

Trabaja desde una copia limpia y actualizada. git log --first-parent simplifica el historial de main mostrando integraciones principales.

$ git switch main
$ git pull --ff-only
$ git log --first-parent --oneline -10
4e91bc2 Merge pull request #742 from feature/payment-adapter
02

Crea una rama de reversión

Aunque el incidente sea urgente, la rama protegida conserva el mismo proceso. git revert -m 1 revierte un merge manteniendo como base el primer padre, que corresponde a main antes de integrar el PR.

$ git switch -c revert/NC-INC-508-payment-adapter
$ git revert -m 1 4e91bc2
[revert/NC-INC-508-payment-adapter 91ad801] Revert "Merge pull request #742..."
03

Ejecuta validación focalizada y publica

Comprueba el flujo crítico de pagos y publica la rama para un pull request de emergencia. El equipo puede revisar exactamente qué se revierte.

$ npm test -- payments
$ git show --stat HEAD
$ git push -u origin revert/NC-INC-508-payment-adapter
04

Conserva evidencia para el análisis

Después de estabilizar producción, crea una rama desde el commit defectuoso para investigar sin reintroducirlo en main.

$ git switch -c investigation/NC-INC-508 4e91bc2
$ git show --name-status 4e91bc2
!

No borres el commit defectuoso

No uses git reset --hard HEAD~1 ni force push sobre main. Borrarías evidencia, romperías clones del equipo y dificultarías saber qué versión estuvo desplegada. Tampoco intentes una refactorización extensa mientras producción sigue degradada.

EJEMPLO 13 · REBASE INTERRUMPIDO

Recupera commits locales sin sobrescribir la rama compartida

Un rebase mal resuelto parece haber eliminado dos días de trabajo. La recuperación debe preservar la rama remota y crear una copia verificable antes de continuar.

INCIDENTE SEV-2
REGLAS APLICABLES · NC-GIT-07
  • Rebase solo sobre ramas personales, nunca sobre ramas compartidas.
  • Antes de una recuperación, crear una referencia de respaldo.
  • No publicar con force push hasta revisar el historial resultante.
  • Preferir --force-with-lease cuando la reescritura autorizada sea imprescindible.
CONTEXTO CRÍTICO

En feature/NC-2250-panel ejecutaste un rebase para incorporar origin/main. Durante la resolución elegiste una versión incorrecta y luego abortaste tarde. Dos commits ya no aparecen en git log, pero todavía pueden estar registrados en el reflog local.

  • Impacto: pérdida aparente de trabajo y riesgo de sobrescribir la rama remota.
  • Prioridad: crear una referencia segura antes de intentar nuevas operaciones.
  • Resultado esperado: recuperar commits en una rama nueva y comparar historias.
01

Detén las operaciones destructivas

No ejecutes nuevos reset, rebase o limpieza. Consulta el estado para saber si Git todavía considera activo el rebase. Si continúa activo, cancélalo de forma explícita.

$ git status
rebase in progress
$ git rebase --abort
02

Busca el punto anterior en reflog

git reflog registra movimientos locales de HEAD. Identifica la referencia anterior al inicio del rebase y crea inmediatamente una rama de respaldo.

$ git reflog --date=local
81bd9a2 HEAD@{4}: rebase (start): checkout origin/main
cc72e18 HEAD@{5}: commit: NC-2250 Añade filtros del panel
$ git switch -c recovery/NC-2250-panel cc72e18
03

Compara la recuperación con el remoto

Inspecciona qué commits existen únicamente en la rama recuperada. git log remoto..local lista el trabajo pendiente sin modificar referencias.

$ git fetch origin
$ git log --oneline origin/feature/NC-2250-panel..recovery/NC-2250-panel
cc72e18 NC-2250 Añade filtros del panel
bd418a0 NC-2250 Conecta consulta del panel
04

Publica una rama nueva para revisión

Publicar la recuperación con otro nombre evita sobrescribir la referencia remota existente. El equipo compara ambas ramas antes de decidir si reemplaza la anterior.

$ npm test
$ git push -u origin recovery/NC-2250-panel
!

No fuerces la publicación durante el diagnóstico

No uses git push --force: podrías borrar commits remotos creados por otra persona. Si después de una revisión se autoriza reemplazar una rama personal, usa git push --force-with-lease, que falla si el remoto avanzó inesperadamente.

EJEMPLO 14 · INFRAESTRUCTURA COMO CÓDIGO

Resuelve un conflicto de configuración sin duplicar recursos

Dos ramas editaron la infraestructura del mismo servicio. Una fusión textual incorrecta podría crear dos bases de datos o eliminar reglas de red en producción.

INCIDENTE SEV-1
REGLAS APLICABLES · NC-IAC-04
  • Todo cambio de infraestructura requiere plan de ejecución revisado.
  • Está prohibido aplicar cambios desde una máquina local.
  • Los conflictos se resuelven semánticamente, no solo eliminando marcas.
  • La publicación ocurre mediante CI con aprobación del equipo de plataforma.
CONTEXTO CRÍTICO

Tu rama incrementa la capacidad de la base de datos en infra/prod/database.tf. En paralelo, main añadió cifrado administrado al mismo recurso. Git detecta conflicto en el bloque Terraform. Ambas modificaciones deben conservarse.

  • Impacto: una configuración errónea puede recrear recursos con pérdida de servicio.
  • Prioridad: producir un plan revisable sin aplicar cambios localmente.
  • Resultado esperado: un único recurso con capacidad nueva y cifrado activo.
01

Fusiona main y limita el análisis

Actualiza referencias, integra y lista archivos conflictivos. Evita editar otros módulos hasta resolver el recurso afectado.

$ git fetch origin
$ git merge origin/main
$ git diff --name-only --diff-filter=U
infra/prod/database.tf
02

Compara ambos bloques completos

Lee las variantes del índice de merge. Necesitas comprender la intención de cada equipo: capacidad por rendimiento y cifrado por cumplimiento.

$ git show :2:infra/prod/database.tf
$ git show :3:infra/prod/database.tf
03

Valida formato y genera un plan

Después de combinar ambos atributos, prepara el archivo y ejecuta validaciones estáticas. terraform plan muestra el efecto esperado sin aplicarlo.

# conserva allocated_storage y storage_encrypted
$ terraform fmt -check infra/prod
$ terraform validate
$ terraform plan -out plan.tfplan
Plan: 0 to add, 1 to change, 0 to destroy.
$ git add infra/prod/database.tf
$ git commit -m "NC-2298 Combina capacidad y cifrado de base de datos"
04

Publica para ejecución controlada

El pull request adjunta el plan. Plataforma revisa que no haya destrucciones y CI aplica el cambio tras aprobación.

$ git push -u origin feature/NC-2298-database-capacity
!

No ejecutes apply local ni aceptes un lado completo

No uses terraform apply desde tu equipo y no resuelvas con git checkout --ours o --theirs. Podrías perder cifrado, ignorar capacidad o recrear infraestructura sin revisión.

EJEMPLO 15 · PARCHE COORDINADO

Integra una corrección crítica sin omitir la auditoría

Dos equipos preparan soluciones parciales para una vulnerabilidad. Debes construir un parche único, firmado y verificable sin mezclar trabajo experimental.

INCIDENTE SEV-1
REGLAS APLICABLES · NC-SEC-09
  • Todo parche crítico debe partir de la release desplegada.
  • Solo se integran commits identificados y revisados mediante cherry-pick.
  • El commit final debe estar firmado y asociado al incidente.
  • La publicación requiere escaneo de seguridad y aprobación de dos equipos.
CONTEXTO CRÍTICO

Una vulnerabilidad permite evadir validaciones en la API. Backend preparó el commit 7bd31c2 con la validación y QA preparó a81e930 con pruebas de regresión. Ambos commits viven en ramas separadas junto a otros experimentos que no deben llegar a producción.

  • Impacto: solicitudes maliciosas pueden superar controles de entrada.
  • Prioridad: ensamblar únicamente los dos commits aprobados sobre la release activa.
  • Resultado esperado: parche pequeño, firmado, probado y auditable.
01

Parte de la release desplegada

Actualiza referencias y crea una rama de parche desde la versión exacta en producción. No partas de main, que puede incluir cambios futuros.

$ git fetch --prune origin
$ git switch -c security/NC-INC-612-input-validation origin/release/3.8
02

Aplica solo los commits aprobados

git cherry-pick incorpora commits concretos sin fusionar todas las ramas de origen. Aplica primero la corrección y después sus pruebas para que el historial sea legible.

$ git cherry-pick 7bd31c2
$ git cherry-pick a81e930
$ git log --oneline -3
03

Valida y firma el parche integrador

Ejecuta pruebas y escaneo de seguridad. Si la empresa exige un commit integrador firmado, crea uno vacío que documente la aprobación del paquete exacto.

$ npm test -- security
$ npm run security:scan
$ git commit --allow-empty -S -m "NC-INC-612 Certifica parche de validación de entradas"
$ git log --show-signature -1
04

Publica para revisión coordinada

La rama se publica y los equipos de backend y seguridad revisan hashes, firma y resultados automatizados antes de desplegar.

$ git push -u origin security/NC-INC-612-input-validation
!

No fusiones ramas experimentales completas

No uses git merge feature/backend-next ni copies archivos manualmente. El merge arrastraría commits no auditados; la copia perdería autoría y trazabilidad. Evita también saltarte pruebas porque el parche parezca pequeño.

EJEMPLO 16 · DEPENDENCIA COMPROMETIDA

Retira una librería vulnerable sin bloquear a 100 desarrolladores

El equipo de seguridad confirma que una dependencia transitiva ejecuta código malicioso durante la instalación. La corrección debe propagarse con rapidez sin introducir versiones inconsistentes entre servicios.

EMPRESA · SEV-1
REGLAS CORPORATIVAS · NC-SUPPLY-12
  • Los cambios de dependencias críticas requieren ticket de incidente, revisión de seguridad y lockfile reproducible.
  • La rama de remediación parte de la release desplegada y recibe únicamente cambios mínimos.
  • CI debe ejecutar instalación limpia, pruebas, SBOM y escaneo de vulnerabilidades.
  • Los equipos consumidores actualizan mediante pull request automatizado; no copian lockfiles entre repositorios.
CONTEXTO COMPLETO

NovaCode mantiene 18 servicios y 100 desarrolladores. El escáner central detecta que analytics-helper@4.2.1, dependencia transitiva de dashboard-sdk, fue comprometida. El paquete aparece en seis aplicaciones. La versión desplegada funciona, pero cualquier instalación nueva puede ejecutar código no confiable en equipos de desarrollo o runners de CI.

Seguridad bloquea temporalmente merges no esenciales. Plataforma publica una versión corregida de dashboard-sdk que fija la dependencia transitiva segura. Tu responsabilidad es remediar el portal administrativo sin arrastrar funcionalidades futuras.

  • Impacto: riesgo sobre estaciones de trabajo, CI y artefactos generados.
  • Prioridad: actualizar la dependencia con instalación reproducible y evidencia auditable.
  • Resultado esperado: parche mínimo sobre release, SBOM limpio y propagación controlada.
ALTERNATIVAS EVALUADAS
A · Borrar package-lock.json y reinstalar

Rápido, pero puede actualizar cientos de paquetes no relacionados. Aumenta el cambio y dificulta atribuir una regresión.

B · Editar manualmente la versión transitiva

No es fiable: el gestor de paquetes puede ignorar una edición inconsistente o regenerarla de forma distinta en CI.

01

Crea una rama desde la release afectada

git fetch --prune origin descarga referencias remotas y elimina referencias obsoletas sin tocar archivos locales. git switch -c crea una rama aislada desde la release desplegada; así no incluyes trabajo futuro de main.

$ git fetch --prune origin
$ git switch -c security/NC-INC-701-dashboard-sdk origin/release/4.6
02

Actualiza con el gestor y revisa el alcance

npm install dashboard-sdk@5.1.3 --save-exact fija la versión aprobada y regenera el árbol de dependencias. git diff --stat resume qué archivos cambiaron; el diff acotado permite confirmar que solo se modificaron manifiesto y lockfile.

$ npm install dashboard-sdk@5.1.3 --save-exact
$ git diff --stat
$ git diff -- package.json package-lock.json
03

Verifica una instalación limpia

npm ci instala exactamente lo descrito por el lockfile y falla si manifiesto y lockfile divergen. El escaneo, el SBOM y las pruebas aportan evidencia para seguridad y auditoría.

$ npm ci
$ npm audit --audit-level=high
$ npm run security:sbom
$ npm test
✓ 318 tests passed
✓ No high vulnerabilities found
04

Confirma y publica el parche mínimo

git add prepara solo los dos archivos esperados. git diff --staged revisa la versión exacta que entrará al commit. La firma -S demuestra autoría y el ticket conecta el cambio con el incidente.

$ git add package.json package-lock.json
$ git diff --staged
$ git commit -S -m "NC-INC-701 Actualiza dashboard-sdk comprometido"
$ git push -u origin security/NC-INC-701-dashboard-sdk
!

Evita cambios amplios durante la remediación

No borres el lockfile, no ejecutes actualizaciones masivas y no copies un lockfile desde otro servicio. Esas acciones introducen diferencias difíciles de atribuir. No omitas npm ci: una instalación local exitosa no garantiza que CI reproduzca el mismo árbol.

EJEMPLO 17 · RELEASE DIVERGENTE

Corrige producción cuando main contiene trabajo no desplegable

Una regresión afecta autenticación en la release activa mientras decenas de commits para la próxima versión ya viven en main. La solución debe corregir ambas líneas sin mezclar calendarios de entrega.

EMPRESA · SEV-1
REGLAS CORPORATIVAS · NC-REL-08
  • Las correcciones urgentes parten de la rama de release desplegada.
  • Solo el commit aprobado se propaga a otras líneas de desarrollo.
  • Las ramas protegidas se actualizan mediante pull request y validación automática.
  • Los conflictos de backport requieren pruebas específicas y aprobación del propietario del módulo.
CONTEXTO COMPLETO

NovaCode opera una plataforma B2B. Producción ejecuta release/7.2, pero main ya contiene 46 commits de la futura versión 7.3, incluyendo una refactorización parcial del módulo de autenticación. Un error en el refresco de sesión desconecta usuarios cada 20 minutos.

El cambio correcto ocupa pocas líneas, pero fusionar main dentro de la release incorporaría trabajo no probado. Tras arreglar producción, la misma intención debe adaptarse a la estructura nueva de main.

  • Impacto: interrupciones recurrentes para clientes empresariales.
  • Prioridad: parche mínimo sobre 7.2 y propagación controlada a 7.3.
  • Resultado esperado: dos pull requests trazables con pruebas propias.
ALTERNATIVAS EVALUADAS
A · Fusionar main dentro de release/7.2

Incorrecto: desplazaría 46 commits no aprobados hacia producción y ampliaría drásticamente el riesgo.

B · Copiar el archivo corregido a ambas ramas

Peligroso: la estructura difiere entre versiones y la copia manual pierde la relación entre commits.

01

Crea la rama desde la versión desplegada

git fetch origin actualiza referencias. La nueva rama parte explícitamente de origin/release/7.2, no de tu rama actual ni de main.

$ git fetch origin
$ git switch -c hotfix/NC-INC-733-session-refresh origin/release/7.2
02

Confirma el arreglo pequeño y probado

Las pruebas acotadas validan el flujo afectado. git diff --check detecta errores de espacios y marcas accidentales. git show --stat HEAD confirma que el commit no creció más de lo esperado.

$ npm test -- session-refresh
$ git diff --check
$ git add src/auth/session.js test/session.test.js
$ git commit -m "NC-INC-733 Corrige renovación de sesión en release 7.2"
$ git show --stat HEAD
$ git push -u origin hotfix/NC-INC-733-session-refresh
03

Propaga el hash aprobado a main

Tras integrar el hotfix, toma su hash. git cherry-pick intenta reaplicar únicamente ese commit sobre una rama nacida desde origin/main. Como autenticación cambió en 7.3, Git señala el conflicto en lugar de ocultarlo.

$ git switch -c backport/NC-INC-733-main origin/main
$ git cherry-pick f28a319
CONFLICT (content): Merge conflict in src/auth/sessionManager.js
04

Adapta la intención a la estructura nueva

Resuelve el conflicto conservando la corrección dentro del nuevo sessionManager. Después prepara el archivo y continúa la operación suspendida. --continue finaliza el cherry-pick sin crear un commit adicional desconectado.

# adapta la corrección en src/auth/sessionManager.js
$ git add src/auth/sessionManager.js test/sessionManager.test.js
$ git cherry-pick --continue
$ npm test -- session
$ git push -u origin backport/NC-INC-733-main
!

No mezcles líneas de entrega

No uses git merge main sobre la release y no resuelvas el cherry-pick con --ours sin inspección. La aplicación puede compilar mientras la sesión sigue fallando en un borde. No publiques directamente en ninguna rama protegida.

EJEMPLO 18 · ELIMINACIÓN DE INFRAESTRUCTURA

Evita una destrucción masiva detectada durante revisión

Un pull request aparentemente rutinario muestra que Terraform eliminará recursos compartidos. Debes detener la entrega, identificar la causa y producir una corrección verificable.

EMPRESA · SEV-1 PREVENTIVO
REGLAS CORPORATIVAS · NC-IAC-11
  • Ningún plan con destrucciones se aplica sin aprobación explícita de plataforma.
  • El estado remoto de Terraform nunca se modifica manualmente durante diagnóstico.
  • Las correcciones parten de una rama nueva y conservan el pull request original como evidencia.
  • CI, no una estación local, ejecuta apply tras aprobación.
CONTEXTO COMPLETO

Un equipo prepara feature/NC-2402-network-segmentation. El plan automático del pull request informa 12 to destroy, incluyendo una base de datos compartida y reglas de red usadas por tres servicios. La causa probable es un conflicto resuelto incorrectamente en infra/prod/shared.tf: alguien aceptó un lado completo y eliminó bloques aún necesarios.

El error todavía no llegó a producción gracias a la política de revisión. Debes preservar evidencia, restaurar la intención correcta desde el historial y generar un plan sin destrucciones.

  • Impacto potencial: caída simultánea de servicios y pérdida de disponibilidad.
  • Prioridad: impedir apply, localizar la regresión y validar un plan seguro.
  • Resultado esperado: corrección revisable con cero destrucciones no autorizadas.
ALTERNATIVAS EVALUADAS
A · Ejecutar terraform apply y corregir después

Inaceptable: convertiría una detección preventiva en un incidente real.

B · Editar manualmente el estado remoto

Muy riesgoso: puede desacoplar la realidad de la configuración y ocultar recursos huérfanos.

01

Conserva evidencia y crea una rama correctiva

No modifiques el pull request original. Actualiza referencias y crea una rama desde la rama problemática para mantener el estado detectado como punto de comparación.

$ git fetch origin
$ git switch -c fix/NC-2402-restore-shared-resources origin/feature/NC-2402-network-segmentation
02

Identifica cuándo desaparecieron los bloques

git log --follow -- muestra el historial del archivo incluso si fue renombrado. git blame atribuye líneas actuales y git show HASH:path permite leer una versión anterior sin sobrescribir el directorio.

$ git log --follow --oneline -- infra/prod/shared.tf
$ git blame infra/prod/shared.tf
$ git show 891bc20:infra/prod/shared.tf
03

Restaura selectivamente la configuración necesaria

Edita el archivo actual e incorpora únicamente los bloques compartidos omitidos. Después valida formato y sintaxis. terraform plan -detailed-exitcode distingue entre error, ausencia de cambios y plan con cambios.

# restaura los bloques compartidos dentro del archivo actual
$ terraform fmt -check infra/prod
$ terraform validate
$ terraform plan -detailed-exitcode -out safe.tfplan
Plan: 3 to add, 4 to change, 0 to destroy.
04

Confirma la corrección y solicita revisión de plataforma

Prepara exclusivamente la configuración restaurada. El commit explica la causa para que auditoría pueda relacionar la prevención con el conflicto anterior.

$ git add infra/prod/shared.tf
$ git diff --staged
$ git commit -S -m "NC-2402 Restaura recursos compartidos omitidos en merge"
$ git push -u origin fix/NC-2402-restore-shared-resources
!

No manipules estado ni apliques desde local

No uses terraform state rm, terraform import ni terraform apply durante el diagnóstico salvo procedimiento específico de plataforma. Esas órdenes alteran estado o infraestructura y pueden ocultar la causa original. Evita también restaurar el archivo completo con git checkout HASH -- archivo: borraría cambios válidos posteriores.

CASO MAESTRO · PROYECTO MULTINACIONAL

De repositorio vacío a producción global

Construye y publica una plataforma de pedidos para una multinacional siguiendo un flujo completo: arquitectura, ramas, desarrollo paralelo, pruebas, seguridad, release, despliegue y respuesta postproducción.

GUÍA SENIOR
EMPRESA HIPOTÉTICA · GLOBALCOMMERCE
  • 120 desarrolladores distribuidos entre Quito, Madrid, Toronto y Singapur.
  • main siempre debe ser desplegable y está protegida por pull requests.
  • Todo commit usa ticket, revisión automática, pruebas y escaneo de seguridad.
  • Producción se publica desde release/* con aprobación de plataforma y negocio.
  • Los incidentes se resuelven con cambios trazables; nunca se reescribe historial compartido.
OBJETIVO DEL PROYECTO

GlobalCommerce necesita order-hub, una API para recibir pedidos, calcular impuestos regionales y publicar eventos de facturación. El sistema debe operar en varios países, tolerar despliegues progresivos y permitir que equipos independientes trabajen sin bloquearse.

La guía recorre las fases reales del proyecto. En cada una aparece un conflicto habitual. La meta no es memorizar comandos: es entender qué estado del repositorio necesitas, qué riesgo estás controlando y qué evidencia dejarás para el siguiente equipo.

  • Resultado funcional: servicio desplegado con pruebas, auditoría y rollback.
  • Resultado técnico: historial legible, ramas efímeras y releases trazables.
  • Criterio senior: preferir operaciones pequeñas, verificables y reversibles.
FASE 01

Inicialización y estándares del repositorio

El equipo de plataforma crea la base común antes de que lleguen contribuciones.

Situación: el repositorio nace vacío. Si cada equipo inventa estructura, formato y exclusiones, las primeras revisiones se llenarán de ruido. La prioridad es establecer una línea base mínima y auditable.

$ mkdir order-hub && cd order-hub
$ git init -b main
$ printf "node_modules/\n.env\ncoverage/\n" > .gitignore
$ git add README.md .gitignore package.json
$ git commit -S -m "GC-001 Inicializa servicio order-hub"
$ git remote add origin git@github.com:globalcommerce/order-hub.git
$ git push -u origin main

git init -b main crea el repositorio con nombre de rama explícito.

git add selecciona archivos concretos para evitar incluir secretos o artefactos.

-S firma el commit inicial y -u enlaza la rama local con el remoto.

Conflicto típico:

Un desarrollador propone confirmar un archivo .env.example con credenciales “temporales”. Se acepta documentar nombres de variables, pero nunca valores reales.

Evita:git add .durante la inicialización sin revisar git status --short.
Verificacionesgit statusgit log --show-signature -1git remote -v
FASE 02

Desarrollo paralelo de la primera entrega

Tres equipos implementan pedidos, impuestos y facturación sin editar main directamente.

Situación: Madrid desarrolla feature/GC-110-create-order, Quito trabaja en feature/GC-112-regional-tax y Toronto publica feature/GC-114-billing-event. Cada tarea parte del mismo main actualizado.

$ git clone git@github.com:globalcommerce/order-hub.git
$ cd order-hub
$ git fetch --prune origin
$ git switch -c feature/GC-110-create-order origin/main
# desarrolla una unidad pequeña
$ git status --short
$ git diff
$ git add src/orders/createOrder.js test/createOrder.test.js
$ git commit -S -m "GC-110 Añade creación básica de pedidos"

clone descarga archivos, historial y remoto.

fetch --prune actualiza referencias sin mezclar cambios.

switch -c ... origin/main crea una rama aislada desde la base remota aprobada.

diff permite revisar líneas antes de preparar el commit.

Conflicto típico:

Dos equipos quieren modificar src/config/routes.js. En vez de reservar el archivo durante días, cada equipo mantiene commits pequeños y sincroniza con frecuencia para resolver diferencias pronto.

Evita:git pullsin saber en qué rama estás. Prefiere fetch y una integración explícita.
Verificacionesnpm test -- createOrdergit diff --checkgit log --oneline --decorate -3
FASE 03

Integración temprana y conflicto de contrato

Impuestos necesita una propiedad que el equipo de pedidos nombró de otra forma.

Conflicto presentado: pedidos publica countryCode, mientras impuestos implementó country. Git puede fusionar los archivos porque no editan las mismas líneas, pero la aplicación falla en ejecución. Es un conflicto semántico, más difícil de detectar que un conflicto textual.

A · Resolver solo si Git muestra conflicto

Insuficiente: Git no entiende contratos de negocio.

B · Renombrar en producción al detectar el fallo

Tardío y riesgoso.

$ git fetch origin
$ git merge origin/main
$ npm run test:integration -- order-tax
FAIL expected tax calculation for countryCode=EC
# adapta impuestos para consumir countryCode
$ git add src/tax/calculateTax.js test/integration/orderTax.test.js
$ git commit -S -m "GC-112 Unifica contrato regional de pedidos e impuestos"

merge origin/main incorpora la versión aprobada en tu rama antes de publicar.

La prueba de integración verifica la interacción entre módulos, no solo funciones aisladas.

Criterio senior:

Los conflictos semánticos no aparecen como marcas <<<. Define pruebas de contrato y ejecútalas en CI. Una fusión técnicamente limpia no garantiza software correcto.

Evita:git pushantes de probar la integración con la base reciente.
Verificacionesnpm run test:integrationnpm run lintnpm run typecheck
FASE 04

Pull request, revisión y rendimiento

El código funciona, pero una consulta nueva degrada el tiempo de respuesta.

Conflicto presentado: durante la revisión, CI detecta que el endpoint de pedidos sube de 120 ms a 1.8 s porque consulta impuestos fila por fila. El cambio es correcto funcionalmente, pero no cumple el presupuesto de rendimiento de 300 ms.

$ git push -u origin feature/GC-110-create-order
# abre PR hacia main; CI ejecuta validaciones
$ npm run test:performance -- create-order
FAIL p95=1800ms budget=300ms
# optimiza consulta y añade prueba de regresión
$ git add src/orders/createOrder.js test/performance/createOrder.perf.js
$ git commit -S -m "GC-110 Reduce consultas repetidas al crear pedidos"
$ git push

push -u publica la rama y establece seguimiento.

El segundo push actualiza el mismo pull request con la optimización.

Soluciones evaluadas:

Subir el timeout oculta el problema. Añadir caché global introduce invalidación compleja. La solución elegida agrupa consultas dentro de la operación y deja una prueba de presupuesto.

Evita:git commit --amenddespués de compartir la rama si el equipo ya revisa hashes concretos; añade un commit claro.
Puertas de calidadnpm testnpm run test:integrationnpm run test:performancenpm run security:scan
FASE 05

Preparación de release y conflicto de migraciones

Dos funcionalidades agregan migraciones con el mismo número secuencial.

Conflicto presentado: al crear release/1.0.0, aparecen dos archivos 014_*.sql. Ambos son necesarios. Las migraciones compartidas son inmutables porque editar una ya ejecutada deja entornos divergentes.

$ git switch -c release/1.0.0 origin/main
$ ls db/migrations
014_add_tax_region.sql
014_add_invoice_event.sql
$ git mv db/migrations/014_add_invoice_event.sql db/migrations/015_add_invoice_event.sql
$ npm run db:test:create
$ npm run db:migrate
$ npm run db:rollback
$ git add db/migrations
$ git commit -S -m "GC-160 Ordena migraciones para release 1.0.0"

git mv registra el renombrado de manera explícita.

Las pruebas de migración y rollback garantizan que despliegue y recuperación funcionan en una base limpia.

Solución seleccionada:

Renombrar la migración aún no desplegada. Editar la primera o unir ambas operaciones crearía diferencias entre entornos y haría más difícil revertir una sola funcionalidad.

Evita:git checkout --ours .porque descartaría silenciosamente una migración válida.
Verificaciones de releasenpm cinpm run db:migratenpm testnpm run security:sbom
FASE 06

Publicación gradual y trazabilidad

La release aprobada se etiqueta y despliega primero a una fracción del tráfico.

Situación: CI aprobó pruebas unitarias, integración, rendimiento, migraciones y seguridad. Plataforma crea una etiqueta firmada para identificar exactamente el artefacto desplegado.

$ git switch release/1.0.0
$ git pull --ff-only
$ git tag -s v1.0.0 -m "GlobalCommerce order-hub v1.0.0"
$ git push origin v1.0.0
$ git show --show-signature v1.0.0

tag -s crea una etiqueta firmada e inmutable para relacionar commit, artefacto y despliegue.

show --show-signature verifica localmente la firma antes de promocionar el artefacto.

Estrategia de rendimiento:

Despliega primero al 5% del tráfico, observa latencia p95, errores y saturación de base de datos. Promueve gradualmente solo si las métricas permanecen dentro del presupuesto.

Evita:git tag -fsobre una versión publicada: cambiaría qué código representa una etiqueta ya auditada.
Observabilidaderrores HTTPlatencia p95CPU y memoriacolas de eventos
FASE 07

Incidente postproducción y rollback auditable

El canary revela duplicación de eventos de facturación bajo concurrencia.

Conflicto presentado: al 5% de tráfico, algunos reintentos publican dos eventos. La aplicación supera pruebas funcionales normales, pero falla bajo concurrencia. Debes detener la promoción y restaurar estabilidad antes de diseñar una corrección definitiva.

A · Corregir directamente sobre producción

No auditable y demasiado riesgoso.

B · Continuar despliegue y observar

Amplía el impacto económico.

$ git switch -c revert/GC-INC-021-billing origin/release/1.0.0
$ git log --first-parent --oneline -5
$ git revert HASH_DEL_MERGE
$ npm test -- billing
$ git push -u origin revert/GC-INC-021-billing

log --first-parent simplifica la búsqueda del cambio integrado.

revert crea un commit inverso auditable sin borrar la historia desplegada.

Aprendizaje senior:

La rapidez no consiste en omitir controles. Consiste en elegir una operación pequeña y reversible. Después del rollback, crea una rama de investigación y añade una prueba concurrente que reproduzca el fallo.

Evita:git reset --hardy force push sobre ramas compartidas: eliminarían evidencia y romperían clones del equipo.
Salida del incidenteservicio establetimeline documentadaprueba de regresiónpostmortem sin culpa
EVALUACIÓN SENIOR · 10+ AÑOS DE EXPERIENCIA

Diseña una solución global de idempotencia para pedidos

Proyecto de contratación para una empresa transnacional de ingeniería de software. La evaluación mide criterio técnico, claridad, seguridad, rendimiento y capacidad de entregar una solución auditable.

TAKE-HOME + DEFENSA
EMPRESA HIPOTÉTICA · ORBITAL SOFTWARE
  • Plataforma de comercio utilizada en 32 países y operada por más de 100 desarrolladores.
  • Los cambios críticos deben ser pequeños, observables, reversibles y compatibles con despliegues graduales.
  • El candidato dispone de 6 horas para análisis y prototipo; después realiza una defensa técnica de 45 minutos.
  • No se evalúa cantidad de código: se evalúa calidad de decisiones, pruebas, comunicación y gestión de riesgos.
CONTEXTO DEL PROBLEMA

El servicio order-api recibe solicitudes desde aplicaciones móviles, web y socios externos. Algunos clientes reintentan una petición cuando la red es lenta. El balanceador también puede reenviar solicitudes después de un timeout. En ocasiones, dos instancias procesan el mismo pedido casi al mismo tiempo.

El síntoma visible es grave: algunos clientes reciben dos pedidos y dos cargos para una sola compra. Existe un intento de protección en memoria mediante un Set, pero cada instancia mantiene su propia copia, se pierde al reiniciar y no coordina concurrencia distribuida.

El equipo solicita una solución incremental. No puedes rediseñar todos los servicios ni depender de una migración riesgosa durante el primer despliegue. Debes explicar cómo detectar duplicados, cómo responder a reintentos, qué almacenar, qué probar y cómo desplegar sin interrumpir operaciones.

  • Objetivo funcional: procesar una intención de compra una sola vez aunque la solicitud se repita.
  • Restricción de compatibilidad: clientes antiguos todavía no envían clave de idempotencia.
  • Restricción operativa: múltiples instancias atienden tráfico concurrente.
  • Restricción de seguridad: no registrar datos sensibles de pago.
  • SLO: p95 menor a 300 ms y error rate inferior a 0.5%.
01

Cómo comenzaría un senior

Primero reduce incertidumbre. No escribas código hasta entender el contrato, el fallo y el camino de despliegue.

Preguntas iniciales

  • ¿Dónde se genera el identificador del pedido y quién controla su unicidad?
  • ¿La operación de cobro ocurre dentro del servicio o mediante un proveedor externo?
  • ¿Qué almacenamiento compartido existe y qué garantías de unicidad ofrece?
  • ¿Qué respuesta espera el cliente cuando repite exactamente la misma solicitud?
  • ¿Qué ocurre si usa la misma clave con un cuerpo diferente?
  • ¿Durante cuánto tiempo debe conservarse una respuesta idempotente?

Metodología propuesta

  1. Reproducir el problema con una prueba concurrente.
  2. Definir invariantes de negocio antes de implementar.
  3. Diseñar el cambio mínimo que cierre la carrera distribuida.
  4. Añadir migración reversible, métricas y feature flag.
  5. Validar funcionalidad, concurrencia, seguridad y rendimiento.
  6. Publicar mediante canary y observar antes de ampliar tráfico.
Invariante principal

Para una clave de idempotencia dada, existe como máximo un pedido confirmado. Repetir la misma solicitud devuelve el mismo resultado. Reutilizar la clave con otro payload devuelve error.

02

Alternativas y decisión arquitectónica

Una respuesta senior compara opciones y declara por qué descarta soluciones seductoras pero incompletas.

A · Set en memoria por instancia

Muy rápido, pero incorrecto en un entorno distribuido. No sobrevive reinicios y dos nodos pueden aceptar la misma clave.

B · Consultar antes de insertar

Insuficiente: dos peticiones pueden leer “no existe” simultáneamente y crear duplicados. Es una carrera clásica check-then-act.

C · Caché distribuida sin persistencia

Puede ayudar como optimización, pero no debe ser la única barrera para una operación financiera.

La solución usa una tabla idempotency_records con clave única, hash del payload, estado y respuesta serializada. La restricción de unicidad es la garantía primaria. Una caché podría añadirse después para rendimiento, nunca como fuente de verdad.

03

Diseño de datos y migración reversible

La base de datos expresa la invariante para que todas las instancias compartan la misma garantía.

-- db/migrations/021_create_idempotency_records.sql
CREATE TABLE idempotency_records (
  idempotency_key VARCHAR(128) PRIMARY KEY,
  request_hash VARCHAR(64) NOT NULL,
  status VARCHAR(24) NOT NULL,
  response_json JSONB,
  created_at TIMESTAMP NOT NULL DEFAULT NOW(),
  expires_at TIMESTAMP NOT NULL
);

CREATE INDEX idx_idempotency_expiry
  ON idempotency_records (expires_at);

Decisiones: la clave primaria impide duplicados atómicamente. request_hash detecta reutilización incorrecta. status representa operaciones en curso o completadas. expires_at permite limpieza controlada. El índice evita escaneos completos durante esa limpieza.

Rollback

La primera fase añade una tabla sin alterar rutas existentes. Si el canary falla, desactiva el feature flag antes de retirar la tabla. Nunca elimines estructuras mientras instancias antiguas o nuevas puedan seguir usándolas.

04

Implementación de referencia

El código separa validación, almacenamiento y lógica de negocio para mantener pruebas rápidas y razonamiento claro.

// src/orders/createOrder.js
export async function createOrder({ key, payload, repository, payments }) {
  if (!key) return createLegacyOrder({ payload, repository, payments });

  const requestHash = hashPayload(payload);
  const existing = await repository.findIdempotencyRecord(key);

  if (existing) {
    if (existing.requestHash !== requestHash) {
      throw new IdempotencyConflictError("Key reused with different payload");
    }
    if (existing.status === "completed") return existing.response;
    throw new OrderInProgressError("Order is already being processed");
  }

  const claimed = await repository.tryClaimKey({ key, requestHash });
  if (!claimed) return createOrder({ key, payload, repository, payments });

  const response = await payments.chargeAndCreateOrder(payload);
  await repository.completeKey({ key, response });
  return response;
}

Lectura técnica: los clientes antiguos siguen el camino legado durante una transición controlada. Los nuevos envían una clave. La consulta temprana optimiza reintentos conocidos, pero tryClaimKey con restricción única sigue siendo la defensa real contra carreras. Si otra instancia reclama primero, la operación reevalúa el estado.

// src/orders/idempotencyRepository.js
export async function tryClaimKey(db, { key, requestHash }) {
  const result = await db.query(`
    INSERT INTO idempotency_records
      (idempotency_key, request_hash, status, expires_at)
    VALUES ($1, $2, 'processing', NOW() + INTERVAL '24 hours')
    ON CONFLICT (idempotency_key) DO NOTHING
    RETURNING idempotency_key
  `, [key, requestHash]);
  return result.rowCount === 1;
}

Decisión de rendimiento: el índice primario convierte la reclamación en una operación acotada. No mantengas una transacción abierta mientras llamas a un proveedor externo: bloquearía conexiones y elevaría latencia bajo carga.

05

Estrategia de pruebas

La prueba importante no es solo el camino feliz: debes demostrar comportamiento bajo concurrencia y fallos parciales.

Unitarias

Misma clave y payload devuelve misma respuesta. Misma clave y payload distinto produce conflicto. Cliente antiguo conserva comportamiento.

Integración

Dos peticiones simultáneas compiten contra una base real. Solo una crea pedido y cargo.

Rendimiento

Prueba carga normal y ráfagas de reintentos. Mide p95, conexiones y contención del índice.

Seguridad

Confirma que logs no contienen payload completo, tokens ni datos de pago.

Resiliencia

Simula caída tras reclamar clave y define recuperación de registros atascados.

Migración

Aplica y revierte esquema en base temporal. Comprueba compatibilidad entre versiones.

// test/integration/createOrder.concurrent.test.js
it("creates one charge for concurrent retries", async () => {
  const requests = Array.from({ length: 20 }, () =>
    api.createOrder({ key: "checkout-901", payload })
  );

  const responses = await Promise.allSettled(requests);

  expect(await db.countOrdersFor("checkout-901")).toBe(1);
  expect(payments.charge).toHaveBeenCalledTimes(1);
  expect(responses.some(isSuccessful)).toBe(true);
});
Comandos de validaciónnpm testnpm run test:integrationnpm run test:loadnpm run security:scannpm run db:migrate:test
06

Flujo Git y entrega incremental

La forma de publicar es parte de la solución técnica, no una tarea posterior.

$ git fetch --prune origin
$ git switch -c feature/OS-4821-order-idempotency origin/main
# añade migración, repositorio, servicio y pruebas
$ git status --short
$ git diff --check
$ git add db/migrations/021_create_idempotency_records.sql
$ git commit -S -m "OS-4821 Añade almacenamiento idempotente"
$ git add src/orders test
$ git commit -S -m "OS-4821 Protege creación de pedidos concurrentes"
$ git push -u origin feature/OS-4821-order-idempotency

Dos commits separan esquema y comportamiento. Facilitan revisión, reversión y diagnóstico.

diff --check detecta problemas básicos antes de consumir tiempo de CI.

La firma -S cumple trazabilidad.

El pull request incluye plan de despliegue y rollback.

Despliegue seguro

Primero despliega la tabla. Después activa la lógica detrás de un feature flag para 1% del tráfico, luego 10%, 50% y 100%. Observa duplicados, latencia, errores y registros atascados entre cada paso.

07

Qué evitar y cómo defender la solución

La madurez aparece tanto en los límites declarados como en el código entregado.

git add .

Puede incluir secretos, logs o cambios no relacionados. Usa rutas explícitas después de revisar estado.

git push --force

Reescribe historia compartida y rompe trazabilidad. Usa pull request y commits nuevos.

git reset --hard

Puede destruir evidencia o trabajo local durante diagnóstico. Crea ramas de respaldo.

SELECT antes de INSERT sin unique

No resuelve concurrencia distribuida. Dos instancias pueden leer el mismo estado.

Lock de transacción durante pago

Agota conexiones y degrada p95. Reclama clave brevemente y procesa fuera del lock.

Activación al 100%

Amplía impacto antes de observar métricas reales. Usa feature flag y canary.

Estructura de la defensa ante el panel

  1. Explica el fallo con una línea temporal de dos solicitudes concurrentes.
  2. Declara la invariante y por qué la memoria local no la garantiza.
  3. Compara alternativas y justifica la restricción única transaccional.
  4. Recorre migración, código y prueba concurrente.
  5. Presenta métricas, feature flag, canary y rollback.
  6. Declara límites: expiración, recuperación de registros atascados y evolución de clientes antiguos.
Qué espera escuchar un panel senior

No solo “funciona en mi máquina”. Espera una solución razonada, medible, operable y reversible. También espera que distingas la garantía de corrección de las optimizaciones posteriores.

05 · REFERENCIA

Decisiones rápidas

Quiero ver cambios locales

git diff

Quiero actualizar referencias

git fetch --prune

Quiero revisar un commit

git show HASH

Quiero integrar otra rama

git merge rama

Quiero cancelar un merge

git merge --abort

Quiero deshacer algo publicado

git revert HASH