Volver a Últimas PublicacionesBlog

Liderando una Migracion Mayor de Framework Sin Detener el Desarrollo de Funcionalidades

Por Carlos Diaz · 5 de marzo de 2024 · 3 min de lectura

Corrimos una migracion mayor de framework a traves de una plataforma de produccion con trafico diario real durante casi un ano, sin un solo sprint en el que se detuviera el trabajo de funcionalidades. La leccion que mas se me quedo es que el cronograma de una migracion es una decision de roadmap de producto, y necesita el mismo rigor - hitos, visibilidad para los stakeholders, tradeoffs explicitos - que cualquier lanzamiento de funcionalidad.

El mecanismo que hizo esto posible fue una capa de compatibilidad que permitia que el codigo viejo y el nuevo coexistieran en la misma base de codigo y el mismo deploy, controlados por feature flags a nivel de modulo. Esto significo que cada release se mantuvo desplegable durante toda la migracion: nunca hubo una rama de varias semanas que tuviera que aterrizar de golpe, y nunca un momento en el que revertir significara perder semanas de trabajo. Cada sprint tenia una porcion visible tanto de trabajo de funcionalidades como de avance de migracion, lo que mantuvo la confianza de los stakeholders lo suficientemente alta para que la migracion nunca corriera riesgo de ser despriorizada a la mitad.

La estrategia de pruebas importo tanto como los cambios de codigo. Nos apoyamos en pruebas de contrato en los limites de servicio y pruebas de regresion visual en la capa de UI especificamente porque atrapan el modo de falla que una migracion tiene mas probabilidad de introducir: algo que sigue compilando y pasando pruebas unitarias, pero se comporta sutilmente distinto para un usuario. El QA manual solo nunca iba a atrapar eso a la escala de una migracion de toda la plataforma.

El lado humano de la migracion tomo al menos tanto esfuerzo deliberado como el lado tecnico. Escribimos guias de migracion especificas de nuestra base de codigo en lugar de documentacion generica del framework, emparejamos a ingenieros experimentados con los miembros del equipo que tocaban un modulo legado por primera vez, y agregamos reglas de lint que hacian estructuralmente dificil escribir codigo nuevo contra los patrones obsoletos, porque una regla de lint escala mas que pedirle a la gente que recuerde una convencion.

La pregunta que define cuando una migracion realmente termino no es 'cuantos archivos se han convertido', sino 'el equipo escribe codigo idiomatico en los patrones nuevos por defecto, sin pensarlo.' Medir archivos convertidos incentiva declarar victoria demasiado pronto y vivir con una base de codigo permanentemente medio migrada; medir los habitos del equipo no.

Puntos Clave

  • Trata una migracion grande como una decision de roadmap de producto con hitos y visibilidad para stakeholders.
  • Las capas de compatibilidad y los feature flags a nivel de modulo mantienen cada release desplegable durante la migracion.
  • Las pruebas de contrato y de regresion visual atrapan el cambio sutil de comportamiento que las migraciones suelen introducir.
  • Las guias de migracion, el pair programming y las reglas de lint hacen mas que una wiki que nadie lee.
  • Una migracion termina cuando el codigo nuevo es idiomatico por defecto, no cuando se convierte el ultimo archivo.