QA en ERP complejo: cómo reporté el 37% de los bugs de mi equipo en 4 años
En 4 años como QA en un ERP complejo, reporté el 37% de los bugs de mi equipo. No fue talento: fue sistema. Priorización por riesgo, edge cases y optimización.
De qué va este post
Este post no trata de “cómo encontré más bugs que otros”, sino de qué decisiones aumentaron mi impacto: elegir mejor qué testear, diseñar edge cases, mejorar funciones e infraestructura del framework y saber cuándo dejar la herramienta de lado para no frenar al equipo.
Si trabajás en QA, varias de estas decisiones se pueden replicar aunque no uses mi stack ni trabajes sobre un ERP.
Ideas clave
- elegí módulos de alto riesgo, no trabajo cómodo
- diseñé escenarios edge-case, no solo caminos felices
- optimicé infraestructura y funciones base del framework
- cuando la automatización frenaba, testee manual para destrabar el flujo
- acepté un % de cancelación razonable a cambio de más impacto neto
Resultados
- ~37% de los bugs del equipo reportados por mí en 4 años
- mejora del 33% en una función central del framework
- 3 a 4 bugs urgentes por día durante una etapa crítica
- +450 bugs reales encontrados, incluso aceptando un 21% de cancelación -> reducción de bugs comunes reportados por clientes
El contexto: un ERP donde los bugs cuestan plata real
El sistema que testeamos es un ERP completo: facturación, ventas, compras, stock, producción, contabilidad, fondos. Empresas reales lo usan para operar su negocio diario.
Un bug en el cálculo de IVA o en el circuito de facturación no es un inconveniente menor. Es un cliente que no puede facturar. Es plata mal calculada. Es un problema real de negocio.
Con eso claro, mi trabajo nunca fue "correr scripts". Era ser la última línea de defensa antes de que los errores llegaran al cliente.
El enfoque: pensar como cazador, no como ejecutor
Teníamos 7 suites con aproximadamente 50 proyectos de TestComplete. En un sprint típico, las suites tardaban unas 80 horas en ejecutarse en total.
Mientras otros se repartían los proyectos más pequeños, yo elegía consistentemente los módulos más grandes y complejos: ventas, compras, facturación. De las 80 horas de ejecución del sprint, yo tomaba proyectos equivalentes a ~30 horas. Mis 3–4 compañeros se repartían las 50 restantes.
¿Por qué? Tres razones.
1. Priorización por riesgo de negocio
Los módulos de facturación y ventas son donde el negocio es más frágil. Un bug ahí tiene impacto directo en el cliente final. Más complejidad = más superficie de ataque = más probabilidad de encontrar defectos críticos.
2. Diseño de casos con datos edge-case
No me limitaba a probar el "camino feliz". Elegía y diseñaba escenarios con datos que un usuario real podría usar pero que nadie prueba:
- Probar un circuito de venta para clientes consumidores finales, responsables inscriptos, exentos, alternar activación de parámetros y permisos que pueden involucrarse en operación
- Combinaciones inusuales de condiciones de venta, depósitos y transportes
- Artículos con características específicas (talles, series, fraccionado)
Esa intuición sobre qué datos "raros" podrían romper el sistema me permitió encontrar bugs que las pruebas estándar no detectaban.
3. Cobertura proactiva
Cuando me asignaban automatizar un circuito, no me limitaba a lo especificado. Los escenarios Gherkin que recibía definían los caminos principales, pero yo agregaba caminos de prueba adicionales que veía necesarios: variantes de datos, flujos alternativos, condiciones límite que el Gherkin original no contemplaba. Cada prueba extra era una oportunidad más de encontrar defectos.
Caso técnico: optimización de Fn_ValidarGrilla (–33% de tiempo de ejecución)
Un ejemplo concreto de cómo un cambio técnico puede impactar todo un framework.
El problema
Teníamos una función central llamada Fn_ValidarGrilla que validaba los datos de cualquier grilla del ERP (artículos, clientes, libro IVA, libro diario, stock histórico) contra un Excel con valores esperados.
Tenía dos problemas graves:
- Performance: Un proyecto que validaba muchas grillas tardaba aproximadamente 6 horas.
- Lógica incompleta: Si el ERP mostraba 5 registros y el Excel esperaba 7, la función encontraba los 5 en el Excel y daba OK. No validaba que la cantidad total coincidiera. Bugs pasaban como si no existieran.
El análisis
Revisé el código y encontré loops while que iteraban más veces de lo necesario, sin validación del último registro ni comparación de totales, y con operaciones redundantes dentro de los ciclos.
La solución
Optimicé los while para reducir iteraciones innecesarias, agregué validación de límites (el último registro del ERP debe coincidir con el último del Excel), verificación de cantidad total de registros, y documenté el código para mantenimiento futuro.
El resultado
El proyecto pasó de 6 horas a 4 horas. Mejora del 33%.
Pero lo importante es que esta función se usaba en decenas de proyectos. La optimización no mejoró solo uno — mejoró todo el framework. Y la validación de límites empezó a detectar bugs que antes pasaban desapercibidos.
Mejora de infraestructura: eliminar puntos de falla sistemáticos
Repositorio de validaciones
Los archivos Excel de validaciones (datos esperados, updates para la base de datos) se manejaban de forma manual. Cada QA modificaba sus Excels y los juntábamos en un RAR para copiarlos a las máquinas de ejecución.
El resultado era predecible: errores humanos constantes. Alguien olvidaba copiar un archivo, los tests fallaban, pero no por bugs reales sino por datos incorrectos. Tiempo perdido investigando falsos negativos.
Propuse crear un repositorio separado para los Excels de validación. Cada QA subía sus cambios, cada máquina de ejecución solo tenía que hacer fetch-pull. Sin copias manuales, sin errores de sincronización. Un punto de falla sistemático eliminado.
El problema del cambio de fecha a medianoche
Las corridas de TestExecute se lanzaban por lotes con archivos .bat. Si un proyecto empezaba a las 23:30 y terminaba a las 00:30 del día siguiente, cualquier comprobante creado antes de medianoche fallaba al consultarse después — porque las grillas del ERP filtran por la fecha "hoy", que ya había cambiado.
La solución: calcular los tiempos de ejecución al armar el .bat para que ningún proyecto cruzara la medianoche. El último proyecto debía terminar lo más cerca de las 00hs, y agregábamos un delay (timeout) para que los siguientes arrancaran después.
El problema de la resolución de pantalla
Las máquinas de ejecución tenían resoluciones de pantalla variables. El ERP necesita correr en HD (1366x768) para que los localizadores de TestComplete funcionen correctamente. Si la resolución cambiaba, los tests fallaban sin razón aparente.
Investigué por mi cuenta, encontré una utilidad llamada QRes.exe, y la integré al .bat de ejecución. Antes de que cualquier proyecto arrancara, el script forzaba la resolución correcta en todas las máquinas automáticamente. Un cambio de dos líneas que eliminó una categoría entera de fallos intermitentes.
Velocidad de reacción: ser el primero en los logs
Otro hábito que multiplicó mi detección: ser el primero en revisar los logs de TestExecute.
Conocía los tiempos de cada proyecto. Sabía a qué hora iba a terminar cada corrida. Apenas terminaba una ejecución, ya estaba revisando los resultados para tomar los errores y warnings más prometedores — los que tenían más probabilidad de ser bugs reales del ERP, no falsos negativos.
Mientras otros esperaban a que se asignaran los errores, yo ya los estaba analizando.
Resolución de problemas críticos: cuando el equipo se traba
No todo fue detección de bugs. A veces el problema era que no podíamos testear en absoluto.
CerrarVentana y el pipeline bloqueado
Una función central del framework, CerrarVentana, dejó de funcionar. Una instrucción de Delphi (FindComponent) que usaba internamente empezó a devolver errores. Esto bloqueaba la ejecución de todos los proyectos.
Durante 2–3 semanas, una versión que estaba a punto de salir a producción no podía pasar por TestComplete. Se asumía que desarrollo había cambiado algo en el ejecutable. Desarrollo decía que no habían tocado nada. El problema quedaba sin dueño.
Cuando me asignaron investigarlo, pasé un día entero en llamada con el líder de desarrollo y un programador senior, descartando hipótesis. La solución: en lugar de esperar a que desarrollo encontrara la causa raíz, creé una función alternativa desde QA Automation que reemplazaba las instrucciones problemáticas. Un parche pragmático que nos devolvió la capacidad de testear sin requerir cambios del lado de desarrollo.
El criterio fue claro: teníamos empresas reportando bugs urgentes que necesitaban versiones aprobadas. Había que desbloquear el pipeline ya.
Funciones "atómicas" que el equipo no lograba resolver
Para problemas atípicos de este tipo, fui consistentemente al que recurrían. Dos casos más:
Fn_BuscarEnCombo: Los combos desplegables del ERP aparecen en todas las ventanas. Automatizar la búsqueda dentro de ellos de forma genérica era un problema abierto que el equipo no lograba resolver. Construí una función universal que hoy se usa en todas las suites y proyectos.
Navegación de grillas sin propiedades visibles: En una versión nueva, las grillas cambiaron internamente. El Object Spy de TestComplete no mostraba métodos ni propiedades útiles para recorrerlas. El equipo llevaba dos semanas bloqueado. Encontré que encadenando dos métodos no documentados (invisibles para el Object Spy) se podía acceder a la navegación completa. Armé una función reutilizable y el bloqueo se resolvió.
Estas funciones "atómicas" están hoy distribuidas por todas las suites y proyectos. Cada una resolvió un bloqueo puntual, pero su impacto real es acumulativo: son infraestructura que todo el equipo usa todos los días.
Saber cuándo no automatizar
Un QA Automation valioso necesita algo más que automatizar: necesita criterio de testing.
En una versión crítica, estábamos retrasados. La suite no estaba estabilizada: correr los proyectos con TestComplete implicaba estabilizar código al mismo tiempo (localizadores rotos, lógica desactualizada), lo que consumía tiempo que no teníamos. Cada hora de retraso nuestro era una hora menos para que desarrollo corrigiera bugs.
Tomé una decisión: dejé TestComplete de lado y empecé a testear manualmente las pruebas automatizadas, priorizando los escenarios más críticos.
El resultado: durante 2 semanas y media reporté entre 3 y 4 bugs urgentes por día. Ninguno fue cancelado. La respuesta a cómo avanzaba tan rápido era simple: había eliminado el cuello de botella.
Esto alimentó al equipo de desarrollo con un flujo constante de bugs confirmados para corregir, en lugar de hacerlos esperar a que nuestra automatización estuviera lista. Cuando finalmente volví a TestComplete, la versión ya estaba mucho más estable.
La automatización es un medio, no un fin. Si la herramienta se convierte en el cuello de botella, sácala del camino.
Documentación y estandarización
Cuando entré, existía un Excel de seguimiento para las corridas de versión. En teoría servía para saber el estado de cada proyecto: tiempos, suite, máquina asignada.
En la práctica, tenía datos erróneos. Nadie confiaba en él.
Lo rehíce desde cero. Corregí todos los datos, ordené los proyectos por suite y máquina, y diseñé un sistema de colores para que el estado de la versión fuera visible de un vistazo: celeste para estabilización en progreso, verde para proyecto OK, amarillo para warnings leves, rojo para errores que rechazan la versión.
Ese Excel (que después se migró a SharePoint) se convirtió en la fuente de verdad del equipo. Los 5 QA Automation lo actualizábamos en tiempo real durante cada ciclo de versión.
El impacto medible
El contexto de presión
No testeábamos una versión por vez. Teníamos hasta 3 versiones concurrentes, cada una con un deadline ajustado: versión del jueves con respuesta el viernes, versión del viernes con respuesta el lunes, versión del lunes con respuesta el martes.
El SLA (Service Level Agreement—Acuerdo de Nivel de Servicio) con los clientes era claro: si una empresa reporta un bug, no puede esperar más de 10 días para recibir una versión corregida que haya pasado por QA Automation. Cada hora que nuestro equipo tardaba en aprobar o rechazar era una hora menos para que los desarrolladores corrigieran.
Adelantar el análisis de logs no era "trabajar de más". Era darle al equipo de desarrollo el máximo tiempo posible para corregir bugs antes del deadline. Pensamiento sistémico aplicado al flujo completo, no solo a mi parte del proceso.
Los números
No voy a pintar un cuadro perfecto. De todos los bugs que reporté, alrededor del 21% fue cancelado: no eran bugs reales. Parte se debía a cambios de funcionalidad entre versiones que no estaban documentados. Parte a datos esperados desactualizados en las pruebas automatizadas.
¿Fue un problema? Sí, generaba trabajo extra para analistas y desarrolladores. ¿Fue inútil? No. Cada bug cancelado obligaba a revisar y corregir la prueba automatizada: datos incorrectos, escenarios mal grabados, validaciones desactualizadas. El framework se volvió más confiable como efecto secundario.
Prefiero un 21% de cancelación con +450 bugs reales encontrados que un 5% de cancelación con 80.
En un momento llegué a tener 26 requerimientos en estado pendiente. 26 bugs reportados que desarrollo aún no había tomado. Varios urgentes: cálculos incorrectos de subtotales con anticipos, errores en notas de pedido. El líder de desarrollo me dijo, medio en broma, que parara de reportar tanto.
Pero lo importante vino después. La analista principal informó que habían bajado los bugs "comunes" reportados por clientes. Antes, un mismo error lo reportaban varias empresas. Ahora esos errores los interceptábamos nosotros antes de que llegaran a producción.
Eso se traduce en menos tickets de soporte, menos clientes frustrados y menos urgencias para el equipo.
Lo que aprendí
- Elegir qué testear multiplica el impacto. Los módulos de mayor riesgo pagan más que el trabajo cómodo.
- Los edge cases encuentran los bugs valiosos. El camino feliz rara vez alcanza.
- Optimizar una función base mejora todo el framework.
- Resolver problemas de infraestructura también es testing. Menos ruido equivale a más señal.
- La automatización es un medio. Si frena al equipo, cambiá de estrategia.
- El volumen con criterio puede valer más que la precisión tímida.
- Los errores de proceso son tan dañinos como los bugs de código.
Cierre
La lección no es “encontrar más bugs”. La lección es construir un sistema que aumente la probabilidad de encontrarlos donde más importa.
En mi caso, ese sistema combinó riesgo de negocio, edge cases, mejora del framework, limpieza de infraestructura y criterio para cambiar de estrategia cuando la automatización dejaba de ayudar.
Si trabajás en QA, la pregunta no es solo cuántos tests corrés. La pregunta es cuánto impacto real genera tu forma de testear.
Si te interesó el enfoque, acá tenés un caso técnico puntual:
Cómo optimicé Fn_ValidarGrilla en un framework de TestComplete
El caso completo detrás de una función base del framework: por qué tardaba tanto, qué problema lógico tenía y cómo la optimización redujo un proyecto de 6 horas a 4.

