Diferencia entre revisiones de «Usuario:Luis.perez/sistemaspyaytozgz/testing»
De WikiEducator
(Una revisión intermedia por el mismo usuario no mostrado) | |||
Línea 197: | Línea 197: | ||
|} | |} | ||
+ | * assertRaises | ||
+ | <source lang="python"> | ||
+ | with self.assertRaises(SomeException) as cm: | ||
+ | do_something() | ||
+ | the_exception = cm.exception | ||
+ | self.assertEqual(the_exception.error_code, 3) | ||
+ | </source> | ||
+ | == Nose == | ||
+ | https://nose.readthedocs.org/en/latest/ | ||
+ | * Librería no estandar, pero muy usada en el mundo python | ||
+ | * No hace falta que los tests extiendan de unittest.TestCase, pueden ser funciones | ||
+ | * Soporta agrupaciones a nivel de paquete, módulo y clase, con sus correspondientes fixtures. | ||
− | + | Ejemplo | |
+ | <source lang="python"> | ||
− | + | #roomtests.py | |
− | + | ||
− | + | from nose.tools import * | |
+ | from room import Room | ||
− | |||
− | |||
− | |||
− | |||
− | |||
− | = | + | def test_room(): |
+ | gold = Room("GoldRoom", | ||
+ | """This room has gold in it you can grab. There's a | ||
+ | door to the north.""") | ||
+ | assert_equal(gold.name, "GoldRoom") | ||
+ | assert_equal(gold.paths, {}) | ||
− | + | </source> | |
− | |||
− | |||
− | |||
− | + | === Ejecutando los tests === | |
− | + | <source lang="bash"> | |
+ | $ nosetests | ||
+ | $ nosetests roomtests.py | ||
+ | $ nosetests roomtests | ||
+ | $ nosetests roomtests:test_room | ||
− | + | </source> | |
+ | |||
+ | |||
+ | === Asserts === | ||
+ | |||
+ | * Soporta todos los asserts de unittest (recomiendan usar la forma assert_equals en lugar de assertEquals) | ||
+ | * mas algunas funciones como: | ||
+ | ** nose.tools.ok_(expr, msg=None): asserTrue | ||
+ | ** nose.tools.eq_(a, b, msg=None): assertEquals | ||
+ | ** nose.tools.raises(*exceptions): | ||
+ | <source lang="python"> | ||
+ | @raises(TypeError, ValueError) | ||
+ | def test_raises_type_error(): | ||
+ | raise TypeError("This test passes") | ||
+ | </source> | ||
+ | ** nose.tools.timed(limit): Tiempo máximo que tiene un test para pasar | ||
+ | |||
+ | <source lang="python"> | ||
+ | @timed(.1) | ||
+ | def test_that_fails(): | ||
+ | time.sleep(.2) | ||
+ | </source> |
Última revisión de 01:07 21 ene 2013
Tests con python:
|
Instalar nose
Puedes usar pip o easy_install:
easy_install nose
o
pip install nose
O instalar desde el código fuente:
python setup.py install
Doctests
- Documentación de código que además sirve como tests
- Buena forma de obligar a mantener los docstrings actualizados
- Tests junto al código, facilitan su mantenimiento
def add(a, b): """ Suma dos números >>> add(5, 2) 7 """
Ejecutamos los doctests de dos formas:
- Con el módulo doctest:
# ... if __name__ == "__main__": import doctest doctest.add()
- Con nose:
$ nosetests --with-doctest
Unittest
http://docs.python.org/2/library/unittest.html
- Parte de la librería estandar
- NUnit
Caracteristicas
- Test cases: Clases que encapsulan un conjunto de tests. Extienden de unittest.TestCase
- fixtures: métodos para preparar o destruir objetos que puedan necesitar todos los tests
Ejemplo
# randomtests.py import random import unittest class TestSequenceFunctions(unittest.TestCase): def setUp(self): self.seq = range(10) def test_shuffle(self): # make sure the shuffled sequence does not lose any elements random.shuffle(self.seq) self.seq.sort() self.assertEqual(self.seq, range(10)) def test_choice(self): element = random.choice(self.seq) self.assertTrue(element in self.seq) def test_sample(self): with self.assertRaises(ValueError): random.sample(self.seq, 20) for element in random.sample(self.seq, 5): self.assertTrue(element in self.seq)
Ejecutando los tests
Se puede hacer añadiendo al código:#... if __name__ == '__main__': unittest.main()
O bien por línea de comando:
#... python -m unittest seqtests python -m unittest seqtests.TestSequenceFunctions python -m unittest seqtests.TestSequenceFunctions.test_shuffle
$ python -m unittest seqtests.TestSequenceFunctions ... ---------------------------------------------------------------------- Ran 3 tests in 0.000s OK
Se puede usar el autodiscover:
$ python -m unittest discover
Busca módulos de test que se llamen test*.py (se puede modificar este comportamiento)
Fixtures
- setUp: Se invoca antes de la ejecución de cada test
- tearDown: Se invoca después de la ejecución de cada test
- setUpClass: Se invoca una única vez antes de la ejecución de los tests del TestCase
@classmethod def setUpClass(cls): ...
- tearDownClass: Se invoca una única vez después de la ejecución de los tests del TestCase
@classmethod def tearDownClass(cls): ...
Asserts
assertEqual(a, b) | a == b |
assertNotEqual(a, b) | a != b |
assertTrue(x) | bool(x) is True |
assertFalse(x) | bool(x) is False |
assertIs(a, b) | a is b |
assertIsNot(a, b) | a is not b |
assertIsNone(x) | x is None |
assertIsNotNone(x) | x is not None |
assertIn(a, b) | a in b |
assertNotIn(a, b) | a not in b |
assertIsInstance(a, b) | isinstance(a, b) |
assertNotIsInstance(a, b) | not isinstance(a, b) |
- assertRaises
with self.assertRaises(SomeException) as cm: do_something() the_exception = cm.exception self.assertEqual(the_exception.error_code, 3)
Nose
https://nose.readthedocs.org/en/latest/
- Librería no estandar, pero muy usada en el mundo python
- No hace falta que los tests extiendan de unittest.TestCase, pueden ser funciones
- Soporta agrupaciones a nivel de paquete, módulo y clase, con sus correspondientes fixtures.
Ejemplo
#roomtests.py from nose.tools import * from room import Room def test_room(): gold = Room("GoldRoom", """This room has gold in it you can grab. There's a door to the north.""") assert_equal(gold.name, "GoldRoom") assert_equal(gold.paths, {})
Ejecutando los tests
$ nosetests $ nosetests roomtests.py $ nosetests roomtests $ nosetests roomtests:test_room
Asserts
- Soporta todos los asserts de unittest (recomiendan usar la forma assert_equals en lugar de assertEquals)
- mas algunas funciones como:
- nose.tools.ok_(expr, msg=None): asserTrue
- nose.tools.eq_(a, b, msg=None): assertEquals
- nose.tools.raises(*exceptions):
@raises(TypeError, ValueError) def test_raises_type_error(): raise TypeError("This test passes")
- nose.tools.timed(limit): Tiempo máximo que tiene un test para pasar
@timed(.1) def test_that_fails(): time.sleep(.2)