Mi equipo está escribiendo un compilador para un lenguaje específico de dominio (DSL) que se integrará en un IDE. En este momento, estamos enfocados en la fase de análisis del compilador. Estamos no utilizando cualquier analizador-generadores existentes (tales como antlr) porque necesitamos rendimiento en tiempo real y altamente detallado / advertencia / información de los mensajes de error. Tenemos
- clases, cada una de las cuales representa un nodo en el árbol de sintaxis concreta para el lenguaje, así como
- clases que actúan como anotaciones para cada nodo (es decir, para errores e información adicional), así como
- clases internas que construyen y manipulan el árbol de sintaxis concreto (es decir, lexer, parser, caché para cadenas, visitantes de sintaxis).
Estamos tratando de decidir una estrategia general para organizar nuestras pruebas. Nuestra empresa está impulsando el desarrollo basado en el comportamiento (BDD) y el diseño basado en el dominio (DDD). Aunque estamos creando un DSL para el dominio de nuestra empresa, el dominio del compilador es un lenguaje de programación.
Todavía estamos en el proceso de compilar el compilador y ya tenemos algunas pruebas. Nuestro objetivo es tener una cobertura del estado de cuenta del 100%.
Actualmente tenemos pruebas en las que ingresamos el código fuente al generador de árbol de sintaxis, y luego ejecutamos una verificación en cada propiedad de cada nodo del árbol de sintaxis resultante para asegurarnos de que la información esperada (número de línea, error (s) relevante, hijo) / tokens principales, ancho del token, tipo de token, etc.). Ahora, dado que cada nodo es su propia clase, y ciertas anotaciones y errores asociados a un nodo son clases separadas, esta prueba termina haciendo referencia a muchas clases.
Actualmente tenemos pruebas para ciertas clases, como el lexer en el que podemos aislar la entrada (una cadena) y la salida (una lista de tokens) de otras clases (por ejemplo, las clases para los nodos del árbol de sintaxis). Estas pruebas son más granulares.
Ahora, las pruebas en el párrafo inmediatamente anterior se pueden poner en correspondencia con la clase bajo prueba (por ejemplo, lexer, caché de cadenas). Sin embargo, las pruebas del segundo párrafo anterior realmente prueban toda la fase de análisis del compilador; es decir, cada prueba puede tener más de 300 aserciones para el árbol de sintaxis, dado el código fuente de entrada. Las pruebas son para el comportamiento de la fase de análisis.
¿Es esta una estrategia de prueba adecuada? Si no, ¿qué deberíamos estar haciendo de manera diferente? ¿Qué estrategia de organización debemos usar para nuestras pruebas?