Grabadora de cinta: una herramienta para grabar autotests



Buenas tardes, queridos lectores. Me llamo Victor Burov. Trabajo como desarrollador en ISPsystem y quiero compartir mi experiencia en la automatización de pruebas.

Sucedió que las pruebas manuales prevalecieron en nuestro país, y los evaluadores pasaron mucho tiempo realizando las mismas acciones. Una vez pensamos: ¿por qué no enseñar al panel a repetir las acciones del probador, porque, de hecho, todas se convierten en llamadas API específicas? Esto permitiría a las personas escribir pruebas incluso sin habilidades de programación.

Decidimos escribir un módulo para crear pruebas automáticas. Para que el probador pueda simplemente presionar el botón para crear una prueba, cumplir con las condiciones del caso de prueba, al final haga clic en "finalizar" - y eso es todo, ¡la prueba estaba lista! Una idea simple, pero darse cuenta de que no fue fácil. Porque queríamos que este módulo se adaptara al máximo para nuestros productos y aprovechara una interfaz unificada: para que el video grabado se viera como un caso de prueba listo para usar. Esto eliminaría por completo el trabajo manual de escribir pruebas. El sistema resultante se llamaba "grabadora de cinta".


Interfaz para ver condiciones de casos de prueba

Principio de funcionamiento


Todos los parámetros de solicitud (encabezados HTTP, variables de entorno, datos POST, si los hay) y la respuesta completa se escriben en el archivo xml. A cada registro se le asigna un número de serie. Todas las solicitudes se dividen en modificables y no modificables. Después de grabar la prueba, muchas de las consultas que no se modifican se cortan, ya que no afectan la ejecución de las pruebas y solo retrasan y confunden el proceso de ejecución (de ahí los números de secuencia que faltan en la captura de pantalla).

Durante la grabación, la grabadora le permite configurar la verificación de valores en los campos de los formularios y en las columnas de las listas con un solo clic. También le permite grabar pruebas negativas, recordando qué error devolvió el panel mientras grababa una prueba.

Durante la reproducción, las solicitudes se envían directamente a la API de la aplicación sin usar un navegador.

De hecho, una grabadora de cinta es un módulo que se integra en todos nuestros productos y le permite instalar procesadores sensibles a eventos. Escrito usando COREmanager.

Un ejemplo de grabación de una llamada realizada por una grabadora:

Registro
<params> <param name="CONTENT_LENGTH">210</param> <param name="CONTENT_TYPE">application%2Fx%2Dwww%2Dform%2Durlencoded%3B%20charset%3DUTF%2D8</param> <param name="HTTPS">on</param> <param name="HTTP_ACCEPT">text%2Fhtml%2C%20%2A%2F%2A%3B%20q%3D0%2E01</param> <param name="HTTP_ACCEPT_LANGUAGE">en%2DUS%2Cen%3Bq%3D0%2E5</param> <param name="HTTP_CACHE_CONTROL">no%2Dcache</param> <param name="HTTP_CONNECTION">keep%2Dalive</param> <param name="HTTP_COOKIE">corelang5%3Dorion%3Aru%3B%20ispmgrlang5%3Dorion%3Aru%3B%20ipmgrlang5%3Dorion%3Aru%3B%20ipmgrses5%3Dbdd69179d627%3B%20ispmgrses5%3D14157f7bbc5e%3B%20menupane%3D30%5Faccount%2D1%253A30%5Fdomains%2D1%253A30%5Fwebserver%2D1%253A30%5Fantispam%2D1%253A30%5Fmaintain%2D1%253A30%5Ftool%2D1%253A30%5Fstat%2D1%253A30%5Fsrvset%2D1%253A30%5Fsysstat%2D1%253A30%5Fintegration%2D1%253A30%5Fset%2D1%253A30%5Fmgrhelp%2D1</param> <param name="HTTP_HOST">172%2E31%2E240%2E175%3A1500</param> <param name="HTTP_ISP_CLIENT">Web%2Dinterface</param> <param name="HTTP_PRAGMA">no%2Dcache</param> <param name="HTTP_REFERER">https%3A%2F%2F172%2E31%2E240%2E175%3A1500%2Fispmgr</param> <param name="HTTP_USER_AGENT">Mozilla%2F5%2E0%20%28X11%3B%20Ubuntu%3B%20Linux%20x86%5F64%3B%20rv%3A24%2E0%29%20Gecko%2F20100101%20Firefox%2F24%2E0</param> <param name="HTTP_X_REQUESTED_WITH">XMLHttpRequest</param> <param name="QUERY_STRING"/> <param name="REMOTE_ADDR"></param> <param name="REMOTE_PORT">38640</param> <param name="REQUEST_METHOD">POST</param> <param name="REQUEST_URI">%2Fispmgr</param> <param name="SCRIPT_NAME">%2Fispmgr</param> <param name="SERVER_ADDR">172%2E31%2E240%2E175</param> <param name="SERVER_NAME">172%2E31%2E240%2E175</param> <param name="SERVER_PORT">1500</param> </params> <postdata>func%3Demaildomain%2Eedit%26elid%3D%26name%3Dtest%2Eemail%26owner%3Dusr%26ipsrc%3Dauto%26defaction%3Derror%26redirval%3D%26spamassassin%3Doff%26avcheck%3Doff%26clicked%5Fbutton%3Dok%26progressid%3Dfalse%5F1424243906672%26sok%3Dok%26sfrom%3Dajax%26operafake%3D1424243906673</postdata> <answer> <doc lang="ru" func="emaildomain.edit" binary="/ispmgr" host="https://172.31.240.175:1500" features="cba82687e7756e2c0195c88d4180f5d50" notify="0" theme="/manimg/orion/" css="main.css" logo="logo-ispmgr.png" logolink="" favicon="favicon-ispmgr.ico" localdir="default/"> <metadata name="emaildomain.edit" type="form" mgr="ispmgr" decorated="yes"> <form> <field name="name"> <input type="text" name="name" required="yes" check="domain" convert="punycode" maxlength="255"/> </field> //   <buttons> <button name="ok" type="ok"/> <button name="cancel" type="cancel"/> </buttons> </form> </metadata> <messages name="emaildomain.edit" checked="cba82687e7756e2c0195c88d4180f5d5"> <msg name="currentmonth"> </msg> // </messages> <doc lang="ru" func="emaildomain.edit" binary="/ispmgr" host="https://172.31.240.175:1500" features="cba82687e7756e2c0195c88d4180f5d50" notify="0" theme="/manimg/orion/" css="main.css" logo="logo-ispmgr.png" logolink="" favicon="favicon-ispmgr.ico" localdir="default/"> <slist name="owner"> <val key="usr">usr</val> </slist> <slist name="defaction"> <val msg="yes" key="error">  </val> </slist> <slist name="ipsrc"> <val msg="yes" key="auto"> </val> </slist> <name/> <avcheck>off</avcheck> <owner>usr</owner> <ipsrc>auto</ipsrc> </doc> <id>test.email</id> <ok/> <tparams> <clicked_button>ok</clicked_button> </tparams> </doc> </answer> <localmacro> <macros name="mpre_HostIP" field="ipsrc">auto</macros> </localmacro> 

Mejoras (sobre las cuales no pensamos de antemano)


Esperando


Una persona puede "solo esperar", una computadora - no. Uno de los primeros problemas que la grabadora debía resolver era la escritura de vaters. Lo que la gente no inventó para esperar la finalización de la operación. Se implementó la expectativa de tareas en segundo plano y la capacidad de agregar una parada en el paso especificado durante un número específico de segundos.

Grabación y edición de pasos de prueba


Probablemente, todos recuerdan los tiempos de las máquinas de escribir: un error, y hay que reimprimir toda la página.



Para que el probador no tuviera que reescribir toda la prueba con una acción errónea, se agregó un mecanismo para volver a grabar la prueba desde cualquier paso después de guardarla. La capacidad de editar es útil cuando necesita adaptar la prueba a los cambios en el comportamiento de las funciones probadas.

Macros para variables


Durante las pruebas, los valores en los parámetros transmitidos y verificados cambiaron según el servidor en el que se ejecutaban. Un ejemplo de tales datos son las direcciones IP. Es imposible reconocerlos en la etapa de grabación de prueba, así que agregué un sistema macro. Esto nos permitió crear pruebas que no están tan rígidamente ligadas al medio ambiente. El inconveniente de la solución es que después de la grabación, las macros deben especificarse manualmente.

Otro problema que complica significativamente el trabajo con la grabadora es el uso de claves no nativas. No lo notamos de inmediato, ya que probamos la grabadora en ISPmanager, que utiliza identificadores nativos. Pero en algunos otros paneles, el registro se identifica mediante una identificación única. Por lo tanto, tuve que enseñarle a la grabadora no solo a obtener el identificador después de crear el registro u objeto (ya que el ID puede cambiar de principio a inicio), sino también a sustituirlo en todas las solicitudes posteriores.

Soporte de formato JUnit


Las pruebas generadas en cinta se ejecutan automáticamente en el entorno de integración continua de Jenkins. Después de completar las pruebas, se crea un archivo xml que contiene los datos en el formato JUnit. Para que el archivo se formara correctamente, se introdujo una restricción en el nombre de las pruebas. Por ejemplo, la prueba User.Create.xml cayó en testuite con el nombre User y, por lo tanto, tenía un caso de prueba llamado Create. En caso de error, se agregó un nodo de falla con una descripción completa del error.

Métricas


El número de funciones llamadas únicas se calcula durante el paso de las pruebas y la proporción se determina como un porcentaje del número total de funciones, excluyendo aquellas disponibles solo para uso interno. Por lo tanto, se mide la cobertura de prueba más simple. Además, las métricas muestran el tiempo total necesario para completar la prueba y el número de pruebas exitosas y fallidas.

Repositorio de prueba


El repositorio de pruebas, en primer lugar, resuelve el problema de transferir pruebas ya hechas a otros servidores. También resulta útil cuando varios probadores escriben pruebas. Se desarrolló e implementó un pequeño panel para almacenar las pruebas de Almacenamiento también sobre la base de nuestro COREmanager. La grabadora tiene un módulo para sincronizar las pruebas con el almacenamiento. Al escribir una nueva prueba o descargar pruebas desde el repositorio, automáticamente no estarán disponibles para cargar en el repositorio para que no haya confusión. Después de cambiar la prueba, el número de revisión aumenta para que solo las pruebas después de que los cambios se carguen en el repositorio.

Dificultades (bueno, sin ellas)


El uso de una grabadora de cinta mostró que no todas las funciones de la API siguieron nuestras recomendaciones internas. En particular, no todas las funciones devolvieron el identificador de registro después de su creación. Tuve que regresar, incluso a un código de trabajo, y adaptarlo a los requisitos.

El punto muerto es otro problema. El panel implica la realización de algunas acciones críticas en modo exclusivo. Y la grabadora, al ser parte del mismo panel, causando tales funciones, hizo que todo el sistema se congelara. Fue posible determinar esto solo con la ayuda de GDB (nadie recordaba esta característica). Desafortunadamente, hubo muletas, porque se decidió al ejecutar las pruebas de la grabadora para realizar estas funciones en modo de subprocesos múltiples. Teóricamente, fue posible diseñar una grabadora de cinta no con un módulo, sino con un panel separado. Pero no lo intentamos.

Desafortunadamente, la escritura y el olvido también fallaron. La interfaz de nuestros productos está cambiando y se está volviendo más complicada. Además, el número de componentes de la interfaz está creciendo activamente. Por lo tanto, la grabadora debe modificarse de vez en cuando, de modo que cuando aparezcan nuevos componentes, pueda analizar su estructura y procesar los resultados de las consultas.

Conclusión


La creación de una grabadora ha ayudado a mejorar la calidad de los productos probados. Ahorro de tiempo y recursos para capacitar a los evaluadores. En el camino, la grabadora nos permitió revisar nuestra API para verificar el cumplimiento de las recomendaciones internas y, por lo tanto, hacer que la API sea un poco más "lógica".

Source: https://habr.com/ru/post/es421007/


All Articles