¿Mejor manera de integrar maven/qunit/phantomjs?
(5)
Esta es una pregunta antigua, pero pensé que me vincularía a un proyecto mío que utiliza PhantomJS y QUnit para ejecutarse con TestNG:
El proyecto se llama qunit-testng . También tengo un proyecto de muestra que muestra la biblioteca en uso.
Aquí hay una captura de pantalla de la salida de prueba:
He estado investigando la mejor manera de realizar pruebas de unidad JS en nuestro entorno de Maven CI. Lo que actualmente he realizado es el siguiente en mi proyecto de Maven:
- Recursos qunit (archivos JS / CSS)
- qunit prueba archivos html (uno para cada archivo bajo prueba) con html fixture si es necesario
- índice archivo html que hace referencia a los archivos html de prueba como una lista ordenada de hipervínculos
- Archivo del corredor PhantomJS, que:
- abre el archivo html índice y analiza la lista de archivos de prueba
- abre cada archivo de prueba
- toma una captura de pantalla de los resultados de las pruebas qunit para cada archivo
- Si hay fallas, salga con un estado de "1"
- Si no hay fallas, salga con un estado de "0"
- El archivo shell que se cerrará con "0" si phantomjs no está instalado, llamará a las pruebas de phantomjs si está instalado
cambios en pom.xml para ejecutar pruebas phantomjs durante la fase de prueba de la compilación:
<plugins> <plugin> <groupId>org.codehaus.mojo</groupId> <artifactId>exec-maven-plugin</artifactId> <version>1.1</version> <executions> <execution> <id>PhantomJS Unit Testing</id> <phase>test</phase> <goals> <goal>exec</goal> </goals> </execution> </executions> <configuration> <executable>${project.basedir}/src/main/webapp/unittest/phantomcheck</executable> <arguments> <argument>${project.basedir}/src/main/webapp/unittest/qunit-runner.js</argument> <argument>${project.basedir}/src/main/webapp/unittest/tests/index.html</argument> <argument>${project.build.directory}/surefire-reports</argument> </arguments> </configuration> </plugin> </plugins>
Por lo tanto, esto funciona muy bien. Ejecuta las pruebas qunit durante las compilaciones en nuestras máquinas de desarrollo y compilación (siempre que se instale PhantomJS). Las pruebas se ejecutan en un entorno de navegador sin cabeza, sin restricciones en las pruebas qunit. Otras integraciones de maven / qunit que he visto se quedan cortas debido a la ejecución de las pruebas en Rhino u otros entornos JS que imponen restricciones en el tipo de pruebas que podemos escribir. Además, phantomjs nos brinda la posibilidad de realizar capturas de pantalla de las pruebas, que son útiles para solucionar cualquier falla.
El inconveniente de mi enfoque es que se requiere una instalación de PhantomJS en la máquina build / dev. No sé cómo integrar PhantomJS en una dependencia, de modo que los desarrolladores no tengan que preocuparse por instalar PhantomJS. ¿Alguien puede darme un empujón en esta dirección? ¿Cómo empiezo?
Simplemente verificamos phantomJS.exe en el control de código fuente. Y luego estamos seguros de que la misma versión de phantomJS se está utilizando en todas las máquinas.
Sobre la base de la respuesta de , pude encontrar una solución sólida para este problema. ¡Gracias Kyle!
La solución es utilizar el plugin de Maven phantomjs-maven- plugin. Agrego el complemento a mi pom.xml así (necesitarás actualizar Maven a v3.1 o superior para usar el complemento):
<plugin>
<groupId>com.github.klieber</groupId>
<artifactId>phantomjs-maven-plugin</artifactId>
<version>0.4</version>
<executions>
<execution>
<goals>
<goal>install</goal>
<goal>exec</goal>
</goals>
</execution>
</executions>
<configuration>
<version>1.9.7</version>
<checkSystemPath>false</checkSystemPath>
<script>src/test/qunit/run-qunit-testsuite.js</script>
<arguments>
<argument>src/test/qunit/testsuite.qunit.html</argument>
</arguments>
</configuration>
</plugin>
Importante advertencia: en el código pom.xml anterior, asegúrate de usar referencias relativas (no absolutas) a los archivos, como he hecho. Perdí algunas horas después de usar referencias absolutas (comenzando en ${basedir}
) solo para descubrir que hace algo extraño en el directorio de trabajo de PhantomJS. El uso de referencias relativas en su pom.xml permitirá referencias relativas dentro de su archivo HTML (lo que maximizará la portabilidad del código).
En el código del complemento anterior, hago referencia a dos archivos: run-qunit-testsuite.js
y testsuite.qunit.html
. El archivo HTML es solo el archivo QUnit que ejecuta todas sus pruebas. El archivo JS es el controlador para PhantomJS; acepta un argumento: el archivo de prueba HTML QUnit para cargar.
Para completar esta solución, puede descargar controladores de muestra y archivos de prueba desde la página GitHub Gist de GMarik . Puede y debe adaptar estos archivos a sus necesidades (aunque tenga en cuenta que la página de GMarik no incluye una licencia de código abierto, deberá solicitar permiso para cualquier uso que infrinja los derechos de autor).
Al agregar este complemento a su código de Maven, después de ejecutar una compilación de Maven verá un resultado como el siguiente (adaptado de la página de GMarik):
[INFO] --- phantomjs-maven-plugin:0.4:exec (default) @ project.name ---
[INFO] Executing phantomjs command
''waitFor()'' finished in 200ms.
Tests completed in 21 milliseconds.
5 tests of 5 passed, 0 failed.
Si las pruebas pasan, tu compilación pasará. Si las pruebas fallan, tu compilación fallará!
Usando la respuesta de Kyle y otro complemento, pude obtener una solución completa que no requiere nada más que Maven preinstalado y configura phantomjs y qunit para permitir la ejecución de pruebas. Comencé con un complemento de maven-grunt (github.com/eirslett/frontend-maven-plugin) y seguí los pasos de esta guía ( http://blog.trifork.com/2014/10/07/setting-up-maven-to-use-gruntnodejs/ ) para configurarlo. Luego traté de usar qunit dentro de maven y me encontré con un problema de Phantomjs, encontré este post y descubrí el complemento de Kyle (github.com/klieber/phantomjs-maven-plugin). Tuve que usar una fuente qunit personalizada que se explica en esta guía ( http://techblog.dorogin.com/2013/08/issues-with-grunt-contrib-qunit.html ). Esto me permitió usar el complemento kyles para instalar phantomjs y luego vincular el binario a través de las opciones de grunt al qunit personalizado. Al final mi pom se veía como:
` <plugin>
<groupId>com.github.klieber</groupId>
<artifactId>phantomjs-maven-plugin</artifactId>
<version>0.4</version>
<executions>
<execution>
<phase>generate-resources</phase>
<goals>
<goal>install</goal>
</goals>
</execution>
</executions>
<configuration>
<version>1.9.8</version>
</configuration>
</plugin>
<plugin>
<groupId>com.github.eirslett</groupId>
<artifactId>frontend-maven-plugin</artifactId>
<version>0.0.20</version>
<executions>
<execution>
<id>install node and npm</id>
<phase>generate-resources</phase>
<goals>
<goal>install-node-and-npm</goal>
</goals>
<configuration>
<nodeVersion>v0.10.33</nodeVersion>
<npmVersion>1.3.6</npmVersion>
</configuration>
</execution>
<execution>
<id>npm install</id>
<phase>generate-resources</phase>
<goals>
<goal>npm</goal>
</goals>
<configuration>
<arguments>install</arguments>
</configuration>
</execution>
<execution>
<id>grunt build</id>
<phase>generate-resources</phase>
<goals>
<goal>grunt</goal>
</goals>
<configuration>
<arguments>--phantomPath=${phantomjs.binary}</arguments>
</configuration>
</execution>
</executions>
</plugin>
`
Mi Gruntfile.js se veía como:
` module.exports = function(grunt) {
grunt.loadNpmTasks(''grunt-croc-qunit'');
grunt.initConfig({
pkg: grunt.file.readJSON(''package.json''),
qunit: {
options: {
''phantomPath'': grunt.option(''phantomPath'')
},
all:[''src/test/*.html'']
}
});
grunt.registerTask(''default'',[''qunit'']);
};`
Y mi package.json se veía como:
` {
"name":"reporting",
"version":"0.0.1",
"dependencies": {
"grunt": "~0.4.5",
"grunt-cli": "~0.1.13",
"grunt-croc-qunit":"~0.3.0"
},
"devDependencies":{ }
}`
phantomjs-maven-plugin proporciona un objetivo de instalación para instalar phantomjs para que no lo necesite preinstalado. Después de instalar phantomjs, establece una propiedad con la ruta al ejecutable que otros complementos pueden usar. También tiene un objetivo exec
para ejecutar scripts phantomjs. Revelación completa: escribí el plugin.