unit test nodejs kent framework for end best javascript testing tdd bdd browser-extension

javascript - kent - nodejs test



Prueba de extensiones de navegador (2)

Practico dos formas diferentes de probar mis extensiones de navegador:

  • Pruebas unitarias
  • Examen de integración

Introducción

Utilizaré la extensión de extensiones de YouTube Explorer de RobWW como ejemplo a lo largo de esta respuesta. El núcleo de esta extensión está escrito en JavaScript y organizado con módulos de AMD. Un script de compilación genera los archivos de extensión para cada navegador. Con r.js , r.js la inclusión de módulos específicos del navegador, como el de solicitudes HTTP de origen cruzado y el almacenamiento persistente (para preferencias), y un módulo con toneladas de polyfills para IE.

La extensión inserta un panel con letras para la canción que se reproduce actualmente en YouTube, Grooveshark y Spotify. No tengo control sobre estos sitios de terceros, por lo que necesito una forma automatizada para verificar que la extensión aún funcione bien.

Flujo de trabajo

Durante el desarrollo:

  1. Implementa / edita la función y escribe una prueba unitaria si la característica no es trivial.
  2. Ejecute todas las pruebas unitarias para ver si algo se rompió. Si algo está mal, vuelve a 1.
  3. Comprométete con git.

Antes del lanzamiento:

  1. Ejecute todas las pruebas unitarias para verificar que los módulos individuales sigan funcionando.
  2. Ejecute todas las pruebas de integración para verificar que la extensión como un todo esté funcionando.
  3. Versiones de Bump, extensiones de compilación.
  4. Suba la actualización a las galerías de extensiones oficiales y a mi sitio web (las extensiones de Safari e IE deben ser alojadas por usted) y comprométase con git.

Examen de la unidad

Yo uso mocha + expect.js para escribir pruebas. No pruebo cada método para cada módulo, solo los que importan. Por ejemplo:

  • El método de análisis DOM. La mayoría de los métodos de análisis DOM en la naturaleza (incluido jQuery) son defectuosos: se cargan todos los recursos externos y se ejecuta JavaScript.
    Verifico que el método de análisis DOM analiza correctamente el DOM sin efectos secundarios negativos.

  • El módulo de preferencia: verifico que los datos se pueden guardar y devolver.

  • Mi extensión obtiene letras de fuentes externas. Estas fuentes se definen en módulos separados. Estas definiciones son reconocidas y utilizadas por el módulo InfoProvider , que toma una consulta (recuadro negro) y genera los resultados de la búsqueda.

    • Primero InfoProvider si el módulo InfoProvider funciona correctamente.
    • Luego, para cada una de las 17 fuentes, paso una consulta predefinida al origen (con InfoProvider ) y verifico que se esperan los resultados:
      • La consulta tiene éxito
      • El título de la canción devuelta coincide ( applying un algoritmo de similitud de palabras)
      • La longitud de la letra devuelta cae dentro del rango esperado.
  • Si la interfaz de usuario no está obviamente rota, por ejemplo, al hacer clic en el botón Cerrar.

Estas pruebas se pueden ejecutar directamente desde un servidor local o dentro de una extensión del navegador. La ventaja del servidor local es que puede editar la prueba y actualizar el navegador para ver los resultados. Si todas estas pruebas pasan, ejecuto las pruebas desde la extensión del navegador.
Al pasar una debug parámetros extra a mi script de compilación, las pruebas de unidad se incluyen con mi extensión.

Ejecutar las pruebas dentro de una página web no es suficiente, porque el entorno de la extensión puede diferir de la página normal. Por ejemplo, en una extensión de Opera 12, no hay un objeto de location global.

Observación: No incluyo las pruebas en la compilación de lanzamiento. La mayoría de los usuarios no se esfuerzan por informar e investigar errores, simplemente darán una calificación baja y dirán algo como "No funciona". Asegúrese de que su extensión funcione sin errores obvios antes de enviarlo.

Resumen

  • Ver los módulos como cuadros negros. No le importa lo que hay dentro, siempre y cuando se espera el resultado o una entrada determinada.
  • Comience probando las partes críticas de su extensión.
  • Asegúrese de que las pruebas puedan compilarse y ejecutarse fácilmente, posiblemente en un entorno que no sea de extensión.
  • No olvide ejecutar las pruebas dentro del contexto de ejecución de la extensión, para asegurarse de que no haya ninguna restricción o condición inesperada dentro del contexto de la extensión que rompa su código.

Pruebas de integración

Uso Selenium 2 para probar si mi extensión aún funciona en YouTube, Grooveshark (3x) y Spotify.

Inicialmente, acabo de utilizar el Selenium IDE para registrar pruebas y ver si funcionó. Eso fue bien, hasta que necesité más flexibilidad: quería ejecutar una prueba de manera condicional dependiendo de si la cuenta de prueba había ingresado o no. Eso no es posible con el Selenium IDE predeterminado (se dice que es posible con el complemento FlowControl , no lo he intentado).

El Selenium IDE ofrece una opción para exportar las pruebas existentes en otros formatos, incluidas las pruebas JUnit 4 (Java). Lamentablemente, este resultado no fue satisfactorio. Muchos comandos no fueron reconocidos.

Entonces, abandoné el Selenium IDE y cambié al Selenium.
Tenga en cuenta que cuando busca "Selenio", encontrará información sobre Selenium RC (Selenium 1) y Selenium WebDriver (Selenium 2). El primero es el viejo y obsoleto, el último (Selenium WebDriver) se debe utilizar para nuevos proyectos.

Una vez que descubrió cómo funciona la documentación, es bastante fácil de usar.
Prefiero la documentación en la página del proyecto, porque generalmente es concisa (la wiki ) y completa (los documentos de Java ).

Si desea comenzar rápidamente, lea la página de la wiki de Introducción . Si tiene tiempo libre, consulte la documentación en SeleniumHQ , en particular, Selenium WebDriver y WebDriver: Uso avanzado .
Selenium Grid también vale la pena leer. Esta característica le permite distribuir pruebas en diferentes máquinas (virtuales). Excelente si quieres probar tu extensión en IE8, 9 y 10, simultáneamente (para ejecutar múltiples versiones de Internet Explorer, necesitas virtualización).

La automatización de pruebas es agradable. ¿Qué es más agradable? ¡Automatizando la instalación de extensiones!
ChromeDriver y FirefoxDriver admiten la instalación de extensiones, como se ve en este ejemplo .

Para SafariDriver , he escrito dos clases para instalar una extensión Safari personalizada. Lo publiqué y envié un mensaje publicitario a Selenium, por lo que podría estar disponible para todos en el futuro: https://github.com/SeleniumHQ/selenium/pull/87

OperaDriver no admite la instalación de extensiones personalizadas (técnicamente, debería ser posible).
Tenga en cuenta que con la llegada de Opera operada por Chromium , el antiguo OperaDriver ya no funciona.

Hay un controlador de Internet Explorer , y este definitivamente no permite que uno instale una extensión personalizada. Internet Explorer no tiene soporte integrado para extensiones. Las extensiones se instalan a través de instaladores MSI o EXE, que ni siquiera están integrados en Internet Explorer. Por lo tanto, para instalar automáticamente su extensión en IE, debe poder ejecutar silenciosamente un instalador que instale su complemento de IE. No he intentado esto todavía .

Voy a escribir varias extensiones de navegador (la misma funcionalidad para cada navegador popular). Espero que parte del código se comparta, pero aún no estoy seguro de esto. Seguro algunas de las extensiones usarán API nativa. No tengo mucha experiencia con TDD / BDD, y pensé que era un buen momento para empezar a seguir estas ideas de este proyecto.

El problema es que no tengo idea de cómo manejarlo. ¿Debo escribir diferentes pruebas para cada navegador? ¿Qué tan lejos debo ir con estas pruebas? Estas extensiones serán bastante simples: algunos datos en un almacenamiento local, actualización de una página y escucha a través de sockets web.

Y mi observación sobre por qué es difícil para mí, porque hay mucho comportamiento, y no tanto modelos, que también dependen de una plataforma.


Probar las extensiones del navegador también me planteó algunas dificultades, pero me he decidido por la implementación de pruebas en algunas áreas diferentes que puedo invocar simultáneamente desde los navegadores manejados por Selenium.

Los pasos que uso son:

Primero, escribo un código de prueba integrado en el código de extensión que se puede activar simplemente yendo a una URL específica. Cuando la extensión ve esa URL, comienza a ejecutar las pruebas.

Luego, en la página que activa las pruebas en la extensión, ejecuto pruebas en el lado del servidor para asegurarme de que la API funciona, y registro y registro de problemas allí. Grabo los métodos invocados, el tiempo que tomaron y cualquier error. De modo que puedo ver el método invocado por la extensión, el rendimiento web, el rendimiento de la lógica empresarial y el rendimiento de la base de datos.

Por último, invoco automáticamente a los navegadores para que apunten a esa URL específica y graben su rendimiento junto con otra información de prueba, errores, etc. en cualquier sistema cliente dado que use Selenium:

http://docs.seleniumhq.org/

De esta forma puedo desglosar las pruebas en términos de navegador, extensión, servidor, aplicación y base de datos y vincularlas todas de acuerdo con conjuntos de prueba específicos. Se necesita un poco de trabajo para ponerlo todo junto, pero una vez hecho esto, puede tener un marco de prueba de extensión muy agradable.

Normalmente, para el desarrollo de extensiones entre navegadores para mantener una única base de código, utilizo crossrider, pero puede hacerlo con cualquier framework o con extensiones nativas como desee, a Selenium no le importa, solo está impulsando la extensión a un página particular y que le permite interactuar y realizar pruebas.

Una cosa buena de este enfoque es que puedes usarlo también para usuarios en vivo. Si está brindando soporte para su extensión, haga que un usuario vaya a su url de prueba e inmediatamente verá la extensión y el rendimiento del lado del servidor. Por supuesto, no obtendrá las pruebas de Selenium, pero capturará muchos problemas de esta manera, muy útil cuando está codificando contra una variedad de navegadores y versiones de navegador.