Ahora que has mejorado tus habilidades en python, ¿cómo probarlas? Muy simple, hoy quiero mostrarte como probar tus módulos y paquetes que desarrollas en tu tiempo libre o en el trabajo.
Testear módulos de python puede hacerse fácilmente con el módulo unittest. Con este módulo (y el tuyo), puedes explorar cuánto de bueno es tu código. El módulo debe ser usado con algunos truquitos para obtener todo su potencial, por lo que espero que mi ejemplo sea instructivo.
Para empezar, quiero mostrarte algo de teoría de test. Testear un módulo o un programa se divide en testsuites, una testsuite está compuesta de testcases. Cada testsuite prueba una feature (o característica) del módulo, y cada testcase debe probar una o más funciones o métodos de esa feature. Un ejemplo:
- testsuite1 <-> Feature 1
- testcase1
- testcase2
- testsuite2 <-> Feature 2
- testcase1
- testcase2
Todo eso esta muy bien, pero ¿cómo aplicarlo a un ejemplo? Lo primero de todo, cuando desarrollo un nuevo módulo, creo un nuevo test para ese módulo en un directorio llamado test (no muy original
. En ese directorio, guardo los tests de una serie de módulos relacionados, y a continuación muestro un ejemplo (no real) de uno de estos tests:
from sys import path
path.append ('..')from Module import Module, ModuleError
import unittest, logging
class ModuleMethods (unittest.TestCase):
logging.basicConfig (level = logging.DEBUG,
format = '%(asctime)s %(levelname)-8s %(message)s')
def setUp (self): # Esto se ejecuta cada vez que se lanza un test
self.instance = Module (parameters)
def test_method1 (self): # Primer método, comprueba el valor devuelto
r = self.instance.method1 (params)
logging.debug ('r = %s' % str (r))
self.failUnless (r[0] == 0)
def test_method2 (self): # Segundo método, comprueba si lanza una excepción
self.failUnlessRaises (ModuleError, self.instance.method2, params)
def tearDown (self): # Ésto se ejecuta después de que cada test haya finalizado
pass # Some test tearDown
def run (): # Función de lanzamiento del testcase
suite = unittest.TestLoader ().loadTestsFromTestCase (ModuleMethods)
unittest.TextTestRunner (verbosity = 2).run (suite)
#Punto de entrada de los test
if __name__ == '__main__':
run ()
Este ejemplo muestra un ejemplo sencillo de cómo crear un testcase, suficiente para un módulo o una clase con algunos pocos métodos o funciones. El ejemplo crea una nueva clase de testing (heredando de unittest.TestCase) y define algunos métodos test_*, estos métodos serán automáticamente invocados cuando el testRunner sea lanzadao en la función run.
En cada método, se prueba un método objetivo, estos métodos son muy simples, pero puedes crear otros mucho más complejos. Una definición de uno de estos métodos es la siguiente:
- Alguna (o ninguna) configuración del objetivo.
- Ejecución del método objetivo.
- Manejo de retornos o exceptiones para determinar si el test es PASS (OK) o FAIL (Fallido).
Puedes observar funciones como failUnless o failUnlessRaises que hacen comprobaciones condicionales. Si una o más fallan, el test se considera FAIL. Hay dos tipos de FAIL:
- Error: Un error es un test que no ha fallado alguna verificación, sino que lanza alguna excepción inesperada, bien sea por fallo en el módulo o por fallo en la escritura del testcase.
- Failure: Un test que no cumple con las condiciones de todos los chequeos establecidos.
Por ahora, toda esta información es suficiente. Para más información acerca del framework de pruebas, visita este enlace.
Nos vemos! Se aprecia cualquier comentario.
Muy bueno el articulo. ¿Conoces algun modulo para testear la eficiencia de una porcion de codigo?
Hola Lucas, muchas gracias por tu comentario, te contesto con otro post de mi blog.
http://pyzone.wordpress.com/2008/01/22/decoradores/
Espero que sea lo que buscas, un saludo.