Qt Test Visión general
Qt Test es un marco de trabajo para probar aplicaciones y bibliotecas basadas en Qt. Qt Test proporciona todas las funciones habituales de los marcos de trabajo de pruebas unitarias, así como extensiones para probar interfaces gráficas de usuario.
Qt Test está diseñado para facilitar la escritura de pruebas unitarias para aplicaciones y librerías basadas en Qt:
| Características | Detalles |
|---|---|
| Peso ligero | Qt Test consta de unas 6000 líneas de código y 60 símbolos exportados. |
| Autónomo | Qt Test sólo requiere unos pocos símbolos del módulo Qt Core para las pruebas nogui. |
| Pruebas rápidas | Qt Test no necesita ejecutores de pruebas especiales; ni registro especial para las pruebas. |
| Pruebas basadas en datos | Una prueba puede ejecutarse varias veces con datos de prueba diferentes. |
| Pruebas GUI básicas | Qt Test ofrece funciones de simulación de ratón y teclado. |
| Evaluación comparativa | Qt Test admite la evaluación comparativa y ofrece varios back-ends de medición. |
| IDE amigable | Qt Test genera mensajes que pueden ser interpretados por Qt Creator, Visual Studio y KDevelop. |
| Seguridad de subprocesos | La notificación de errores es atómica y segura para los subprocesos. |
| Seguridad de tipos | El uso extensivo de plantillas previene errores introducidos por la conversión implícita de tipos. |
| Fácilmente extensible | Se pueden añadir fácilmente tipos personalizados a los datos y resultados de las pruebas. |
Puede utilizar un asistente de Qt Creator para crear un proyecto que contenga pruebas Qt y construirlas y ejecutarlas directamente desde Qt Creator. Para obtener más información, consulte Qt Creator: Build and run tests.
Creación de una prueba
Para crear una prueba, subclase QObject y añadir una o más ranuras privadas a la misma. Cada espacio privado es una función de prueba. QTest::qExec() puede utilizarse para ejecutar todas las funciones de prueba del objeto de prueba.
Además, puede definir las siguientes ranuras privadas que no se tratan como funciones de prueba. Cuando están presentes, serán ejecutadas por el marco de pruebas y pueden utilizarse para inicializar y limpiar toda la prueba o la función de prueba actual.
initTestCase()se llamará antes de ejecutar la primera función de prueba.initTestCase_data()se ejecutará para crear una tabla de datos de prueba global.cleanupTestCase()Después de ejecutar la última función de prueba.init()se llamará antes de ejecutar cada función de prueba.cleanup()se llamará después de cada función de prueba.
Utilice initTestCase() para preparar la prueba. Cada prueba debe dejar el sistema en un estado utilizable, para que pueda ejecutarse repetidamente. Las operaciones de limpieza deben manejarse en cleanupTestCase(), de modo que se ejecuten incluso si la prueba falla.
Utilice init() para preparar una función de prueba. Cada función de prueba debe dejar el sistema en un estado utilizable, para que pueda ejecutarse repetidamente. Las operaciones de limpieza deben gestionarse en cleanup(), para que se ejecuten incluso si la función de prueba falla y sale antes de tiempo.
Alternativamente, puedes usar RAII (adquisición de recursos es inicialización), con operaciones de limpieza llamadas en destructores, para asegurar que ocurren cuando la función de prueba retorna y el objeto se mueve fuera del ámbito.
Si initTestCase() falla, no se ejecutará ninguna función de prueba. Si init() falla, la siguiente función de prueba no se ejecutará, la prueba pasará a la siguiente función de prueba.
Ejemplo:
clase MiPrimeraPrueba: public QObject { Q_OBJECTprivate: bool miCondición() { return true; }private slots: void initTestCase() { qDebug("Called before everything else."); } void myFirstTest() { QVERIFY(true); // comprueba que se cumple una condiciónQCOMPARE(1, 1); // compara dos valores} void mySecondTest() { QVERIFY(myCondition()); QVERIFY(1 != 2); } void cleanupTestCase() { qDebug("Called after myFirstTest and mySecondTest."); } };
Finalmente, si la clase de prueba tiene un método estático público void initMain(), es llamado por las macros QTEST_MAIN antes de que el objeto QApplication sea instanciado. Esto se añadió en 5.14.
Para más ejemplos, consulte el tutorialQt Test .
Aumentar el tiempo de espera de la función de prueba
QtTest limita el tiempo de ejecución de cada prueba para detectar bucles infinitos y errores similares. Por defecto, cualquier llamada a una función de prueba se interrumpirá transcurridos cinco minutos. Para las pruebas basadas en datos, esto se aplica a cada llamada con una etiqueta de datos distinta. Este tiempo de espera puede configurarse ajustando la variable de entorno QTEST_FUNCTION_TIMEOUT al número máximo de milisegundos que es aceptable que tarde una sola llamada. Si una prueba dura más que el tiempo de espera configurado, se interrumpe y se llama a qFatal(). Como resultado, la prueba se aborta por defecto, como si se hubiera bloqueado.
Para configurar QTEST_FUNCTION_TIMEOUT desde la línea de comandos en Linux o macOS, introduzca:
QTEST_FUNCTION_TIMEOUT=900000 export QTEST_FUNCTION_TIMEOUT
En Windows:
SET QTEST_FUNCTION_TIMEOUT=900000
A continuación, ejecute la prueba dentro de este entorno.
Alternativamente, puede establecer la variable de entorno mediante programación en el propio código de la prueba, por ejemplo llamando, desde el método especial initMain() de su clase de prueba:
qputenv("QTEST_FUNCTION_TIMEOUT", "900000");Para calcular un valor adecuado para el tiempo de espera, observa cuánto tiempo suele tardar la prueba y decide cuánto más puede tardar sin que eso sea síntoma de algún problema. Convierta ese mayor tiempo en milisegundos para obtener el valor del tiempo de espera. Por ejemplo, si decides que una prueba que tarda varios minutos podría tardar razonablemente hasta veinte minutos, por ejemplo en una máquina lenta, multiplica 20 * 60 * 1000 = 1200000 y establece la variable de entorno en 1200000 en lugar de la 900000 anterior.
Creación de una prueba
Puede construir un ejecutable que contenga una clase de prueba que normalmente prueba una clase de código de producción. Sin embargo, normalmente querrás probar varias clases en un proyecto ejecutando un comando.
Vea Escribiendo una Prueba Unitaria para una explicación paso a paso.
Construyendo con CMake y CTest
Puede utilizar CMake y CTest para crear una prueba. CTest le permite incluir o excluir pruebas basándose en una expresión regular que se compara con el nombre de la prueba. Además, puede aplicar la propiedad LABELS a una prueba y CTest puede entonces incluir o excluir pruebas basadas en esas etiquetas. Todos los objetivos etiquetados se ejecutarán cuando se llame a test target en la línea de comandos.
Nota: En Android, si tiene un dispositivo o emulador conectado, las pruebas se ejecutarán en ese dispositivo. Si tiene más de un dispositivo conectado, establezca la variable de entorno ANDROID_DEVICE_SERIAL con el número de serie ADB del dispositivo en el que desea ejecutar las pruebas.
Hay varias otras ventajas con CMake. Por ejemplo, el resultado de una prueba se puede publicar en un servidor web utilizando CDash prácticamente sin esfuerzo.
CTest escala a muy diferentes marcos de pruebas unitarias, y trabaja fuera de la caja con QTest.
El siguiente es un ejemplo de un archivo CMakeLists.txt que especifica el nombre del proyecto y el lenguaje utilizado (aquí, mytest y C ++), los módulos Qt necesarios para la construcción de la prueba (Qt Test), y los archivos que se incluyen en la prueba(tst_mytest.cpp).
project(mytest LANGUAGES CXX) find_package(Qt6 REQUIRED COMPONENTS Test) set(CMAKE_INCLUDE_CURRENT_DIR ON) set(CMAKE_AUTOMOC ON) enable_testing(true) qt_add_executable(mytest tst_mytest.cpp) add_test(NAME mytest COMMAND mytest) target_link_libraries(mytest PRIVATE Qt::Test)
Para obtener más información acerca de las opciones que tiene, consulte Construir con CMake.
Construir con qmake
Si está utilizando qmake como su herramienta de compilación, sólo tiene que añadir lo siguiente a su archivo de proyecto:
QT += testlib
Si desea ejecutar la prueba a través de make check, añada la línea adicional:
CONFIG += testcase
Para evitar que la prueba se instale en su objetivo, añada la línea adicional:
CONFIG += no_testcase_installs
Consulte el manual de qmake para obtener más información sobre make check.
Compilación con otras herramientas
Si está utilizando otras herramientas de compilación, asegúrese de añadir la ubicación de los archivos de cabecera Qt Test a su ruta de inclusión (normalmente include/QtTest bajo el directorio de instalación de Qt). Si estás usando una versión de Qt, enlaza tu test a la librería QtTest. Para versiones de depuración, utilice QtTest_debug.
Qt Test Argumentos de la línea de comandos
Sintaxis
La sintaxis para ejecutar un autotest adopta la siguiente forma simple:
testname [options] [testfunctions[:testdata]]...
Sustituya testname por el nombre de su ejecutable. testfunctions puede contener nombres de funciones de prueba a ejecutar. Si no se pasa testfunctions, se ejecutan todas las pruebas. Si añade el nombre de una entrada en testdata, la función de prueba se ejecutará sólo con los datos de esa prueba.
Por ejemplo:
/myTestDirectory$ testQString toUpperEjecuta la función de prueba llamada toUpper con todos los datos de prueba disponibles.
/myTestDirectory$ testQString toUpper toInt:zeroEjecuta la función de prueba toUpper con todos los datos de prueba disponibles, y la función de prueba toInt con la fila de datos de prueba llamada zero (si los datos de prueba especificados no existen, la prueba asociada fallará y se informará de las etiquetas de datos disponibles).
/myTestDirectory$ testMyWidget -vs -eventdelay 500
Ejecuta la función de prueba testMyWidget, emite cada emisión de señal y espera 500 milisegundos después de cada evento simulado de ratón/teclado.
Opciones
Opciones de registro
Las siguientes opciones de línea de comandos determinan cómo se informan los resultados de las pruebas:
-onombre de archivo,formato
Writes output to the specified file, in the specified format (one oftxt,csv,junitxml,xml,lightxml,teamcityortap). Use the special filename-(hyphen) to log to standard output.-ofilename
Escribe los resultados en el archivo especificado.-txt
Envía los resultados en texto plano.-csv
Envía los resultados como valores separados por comas (CSV) adecuados para su importación en hojas de cálculo. Este modo sólo es adecuado para pruebas comparativas, ya que suprime los mensajes normales de correcto/incorrecto.-junitxml
Envía los resultados como un documento XML de JUnit- .
-xml
Envía los resultados como un documento XML. -lightxml
Envía los resultados como un flujo de etiquetas XML.-teamcity
Envía los resultados en formato TeamCity.-tap
Envía los resultados en formato Test Anything Protocol (TAP).
La primera versión de la opción -o puede repetirse para registrar los resultados de las pruebas en varios formatos, pero sólo una instancia de esta opción puede registrar los resultados de las pruebas en la salida estándar.
Si se utiliza la primera versión de la opción -o, no deben utilizarse ni la segunda versión de la opción -o ni las opciones -txt, -xml, -lightxml, -teamcity, -junitxml o -tap.
Si no se utiliza ninguna de las dos versiones de la opción -o, los resultados de la prueba se registrarán en la salida estándar. Si no se utiliza ninguna opción de formato, los resultados de la prueba se registrarán en texto sin formato.
Opciones detalladas del registro de pruebas
Las siguientes opciones de línea de comandos controlan el grado de detalle de los registros de las pruebas:
-silent
- Salida
- silenciosa; sólo muestra errores fatales, fallos de prueba y mensajes de estado mínimos.
-v1
Salida detallada; muestra cuándo se introduce cada función de prueba. (Esta opción sólo afecta a la salida de texto sin formato.)-v2
Extended verbose output; shows each QCOMPARE() and QVERIFY(). (This option affects all output formats and implies-v1for plain text output.)-vs
Muestra todas las señales que se emiten y las invocaciones de ranura resultantes de esas señales. (Esta opción afecta a todos los formatos de salida.)
Opciones de prueba
Las siguientes opciones de línea de comandos influyen en cómo se ejecutan las pruebas:
-functions
- Muestra todas las funciones de prueba disponibles en la prueba y, a continuación, se cierra.
-datatags
Muestra todas las etiquetas de datos disponibles en la prueba. Una etiqueta de datos global va precedida de ' __global__ '.-eventdelayms
If no delay is specified for keyboard or mouse simulation (QTest::keyClick(), QTest::mouseClick() etc.), the value from this parameter (in milliseconds) is substituted.-keydelayms
Como -eventdelay- , pero sólo influye en la simulación
- del teclado y no en la del ratón.
-mousedelayms
Como -eventdelay, pero sólo influye en la simulación del ratón y no en la del teclado.-maxwarningsnumber
Establece el número máximo de advertencias a mostrar. 0 para ilimitado, por defecto 2000.-nocrashhandler
Desactiva el gestor de fallos en plataformas Unix. En Windows, reactiva el cuadro de diálogo de informe de errores de Windows, que está desactivado por defecto. Esto es útil para depurar fallos.-repeatn
Ejecute el testsuite n veces o hasta que la prueba falle. Útil para encontrar pruebas defectuosas. Si da negativo, las pruebas se repiten para siempre. Se trata de una herramienta para desarrolladores y sólo es compatible con el registrador de texto sin formato.-skipblacklisted
Omitir las pruebas de la lista negra. Esta opción está pensada para permitir una medición más precisa de la cobertura de las pruebas evitando que las pruebas de la lista negra inflen las estadísticas de cobertura. Cuando no se mide la cobertura de las pruebas, se recomienda ejecutar las pruebas incluidas en la lista negra para revelar cualquier cambio en sus resultados, como un nuevo fallo o la resolución del problema que causó la inclusión en la lista negra.-platformname
This command line argument applies to all Qt applications, but might be especially useful in the context of auto-testing. By using the "offscreen" platform plugin (-platform offscreen) it's possible to have tests that use QWidget or QWindow run without showing anything on the screen. Currently the offscreen platform plugin is only fully supported on X11.
Opciones de evaluación comparativa
Las siguientes opciones de línea de comandos controlan las pruebas comparativas:
-callgrind
Utiliza Callgrind para cronometrar las pruebas (Linux y macOS).-perf
Utiliza eventos perf de Linux para cronometrar las pruebas-tickcounter
Utiliza contadores de ticks de CPU para cronometrar las pruebas. Requiere soporte de hardware.-eventcounter
Cuenta los eventos recibidos durante las pruebas.-minimumvaluen
Establece el valor de medición mínimo aceptable.-minimumtotaln
Establece el total mínimo aceptable para ejecuciones repetidas de una función de prueba.-iterationsn
Establece el número de iteraciones de acumulación.-mediann
Establece el número de iteraciones de mediana.-vb
Muestra información detallada del benchmarking.
Opciones varias
-help
Muestra los posibles argumentos de la línea de comandos y proporciona ayuda útil.
Qt Test Variables de entorno
Puede establecer ciertas variables de entorno para afectar a la ejecución de un autotest:
QTEST_DISABLE_CORE_DUMP
Establecer esta variable a un valor distinto de cero desactivará la generación de un archivo de volcado del núcleo.QTEST_DISABLE_STACK_DUMP
Establecer esta variable a un valor distinto de cero evitará que Qt Test imprima un stacktrace en caso de que un autotest se agote o se bloquee.QTEST_FATAL_FAIL
Establecer esta variable a un valor distinto de cero hará que un fallo en un autotest aborte inmediatamente todo el autotest. Esto es útil para, por ejemplo, depurar un fallo inestable o intermitente en una prueba, lanzando la prueba en un depurador. El soporte para esta variable se añadió en Qt 6.1.
Creación de un Benchmark
Para crear una prueba de rendimiento, siga las instrucciones para crear una prueba y, a continuación, añada una macro QBENCHMARK o QTest::setBenchmarkResult() a la función de prueba que desee evaluar. En el siguiente fragmento de código, se utiliza la macro:
class MyFirstBenchmark: public QObject { Q_OBJECT private slots: void myFirstBenchmark() { QString string1; QString string2; QBENCHMARK { string1.localeAwareCompare(string2); } } };
Una función de prueba que mida el rendimiento debe contener una única macro QBENCHMARK o una única llamada a setBenchmarkResult(). No tiene sentido que haya varias, ya que sólo se puede informar de un resultado de rendimiento por función de prueba o por etiqueta de datos en una configuración basada en datos.
Evite cambiar el código de prueba que forma (o influye en) el cuerpo de una macro QBENCHMARK, o el código de prueba que calcula el valor pasado a setBenchmarkResult(). Lo ideal es que las diferencias en los sucesivos resultados de rendimiento se deban únicamente a cambios en el producto que se está probando. Los cambios en el código de prueba pueden dar lugar a un informe engañoso de un cambio en el rendimiento. Si necesitas cambiar el código de prueba, déjalo claro en el mensaje de confirmación.
En una función de prueba de rendimiento, las funciones QBENCHMARK o setBenchmarkResult() deben ir seguidas de un paso de verificación mediante QCOMPARE(), QVERIFY(), y así sucesivamente. A continuación, puede marcar un resultado de rendimiento como no válido si se midió una ruta de código distinta de la prevista. Una herramienta de análisis del rendimiento puede utilizar esta información para filtrar los resultados no válidos. Por ejemplo, una condición de error inesperada normalmente causará que el programa abandone prematuramente la ejecución normal del programa y, por lo tanto, mostrará falsamente un aumento drástico del rendimiento.
Selección del back-end de medición
El código dentro de la macro QBENCHMARK será medido, y posiblemente repetido varias veces para obtener una medición precisa. Esto depende del back-end de medición seleccionado. Hay varios back-ends disponibles. Se pueden seleccionar en la línea de comandos (ver Opciones de Benchmarking):
| Nombre | Argumento de la línea de comandos | Disponibilidad |
|---|---|---|
| Walltime | (por defecto) | Todas las plataformas |
| Contador de ticks de la CPU | -contador de ticks | Windows, macOS, Linux, muchos sistemas tipo UNIX. |
| Contador de eventos | -eventcounter | Todas las plataformas |
| Valgrind Callgrind | -callgrind | Linux (si está instalado) |
| Linux Perf | -perf | Linux |
En resumen, walltime está siempre disponible pero requiere muchas repeticiones para obtener un resultado útil. Los contadores de ticks suelen estar disponibles y pueden proporcionar resultados con menos repeticiones, pero pueden ser susceptibles a problemas de escalado de frecuencia de la CPU. Valgrind proporciona resultados exactos, pero no tiene en cuenta las esperas de E/S y sólo está disponible en un número limitado de plataformas. El recuento de eventos está disponible en todas las plataformas y proporciona el número de eventos que fueron recibidos por el bucle de eventos antes de ser enviados a sus correspondientes objetivos (esto puede incluir eventos no-Qt).
La solución Linux Performance Monitoring sólo está disponible en Linux y proporciona muchos contadores diferentes, que pueden seleccionarse pasando una opción adicional -perfcounter countername, como -perfcounter cache-misses, -perfcounter branch-misses, o -perfcounter l1d-load-misses. El contador por defecto es cpu-cycles. La lista completa de contadores puede obtenerse ejecutando cualquier ejecutable de benchmark con la opción -perfcounterlist.
- El uso del contador de rendimiento puede requerir habilitar el acceso a aplicaciones sin privilegios.
- Los dispositivos que no soportan temporizadores de alta resolución tienen por defecto una granularidad de un milisegundo.
Consulte Escribiendo un Benchmark en el Tutorial Qt Test para más ejemplos de benchmarking.
Uso de datos de prueba globales
Puede definir initTestCase_data() para configurar una tabla de datos de prueba global. Cada prueba se ejecuta una vez por cada fila de la tabla de datos de prueba global. Cuando la propia función de prueba se basa en datos, se ejecuta para cada fila de datos locales, por cada fila de datos globales. Así, si hay g filas en la tabla de datos global y d filas en la tabla de datos propia de la prueba, el número de ejecuciones de esta prueba es g veces d.
Los datos globales se obtienen de la tabla mediante la macro QFETCH_GLOBAL().
A continuación se describen los casos típicos de uso de los datos globales de la prueba:
- Seleccionar entre los backends de bases de datos disponibles en pruebas QSql para ejecutar cada prueba contra cada base de datos.
- Realizar todas las pruebas de red con y sin SSL (HTTP frente a HTTPS) y proxy.
- Probar un temporizador con un reloj de alta precisión y con uno de precisión gruesa.
- Seleccionando si un analizador debe leer de un QByteArray o de un QIODevice.
Por ejemplo, para probar cada número proporcionado por roundTripInt_data() con cada configuración regional proporcionada por initTestCase_data():
void TestQLocale::roundTripInt() { QFETCH_GLOBAL(QLocale, locale); QFETCH(int, number); bool ok; QCOMPARE(locale.toInt(locale.toString(number), &ok), number); QVERIFY(ok); }
En la línea de comandos de una prueba puede pasar el nombre de una función (sin el prefijo test-class-name) para ejecutar sólo las pruebas de esa función. Si la clase de prueba tiene datos globales, o la función se basa en datos, puede añadir una etiqueta de datos, después de dos puntos, para ejecutar sólo el conjunto de datos de esa etiqueta para la función. Para especificar tanto una etiqueta global como una etiqueta específica para la función de prueba, combínelas con dos puntos entre ellas, poniendo primero la etiqueta de datos global. Por ejemplo
./testqlocale roundTripInt:zero
ejecutará el caso de prueba zero de la prueba roundTripInt() anterior (suponiendo que su clase TestQLocale se haya compilado en un ejecutable testqlocale) en cada una de las configuraciones regionales especificadas por initTestCase_data(), mientras que
./testqlocale roundTripInt:C
ejecutará los tres casos de prueba de roundTripInt() sólo en la configuración regional C y
./testqlocale roundTripInt:C:zero
sólo ejecutará el caso de prueba zero en la configuración regional C.
Proporcionar un control tan preciso sobre las pruebas que se van a ejecutar puede facilitar considerablemente la depuración de un problema, ya que sólo es necesario pasar por el caso de prueba que ha fallado.
© 2026 The Qt Company Ltd. Documentation contributions included herein are the copyrights of their respective owners. The documentation provided herein is licensed under the terms of the GNU Free Documentation License version 1.3 as published by the Free Software Foundation. Qt and respective logos are trademarks of The Qt Company Ltd. in Finland and/or other countries worldwide. All other trademarks are property of their respective owners.