How to validate a unit test with random values? I need guarantee that gen_age returns an integer between 15 and 99, but this code is not correct.
import random
import unittest
def gen_age():
# generate integer between 15 and 99
return random.randint(15, 99)
class AgeTest(unittest.TestCase):
def setUp(self):
self.a = gen_age()
def test_choice(self):
element = random.choice(self.a)
self.assertTrue(element in self.a)
def test_sample(self):
for element in random.sample(self.a, 98):
self.assertTrue(element in self.a)
if __name__ == '__main__':
unittest.main()
The best way to test a similar behaviors is to set a seed to the Random object.
The random package provide a Random class. Instances of Random have the same methods than the random package; random(), randint(), sample(), ... In addition, Random accepts a seed. Adding a seed to Random makes it outputs deterministic. For example,
from random import Random
random = Random(666)
assert random.randint(0, 1000) == 467 # will never break
Consequently, you would like to tests your function as
from random import Random
import unittest
random = Random()
def gen_age():
# generate integer between 15 and 99
return random.randint(15, 99)
class AgeTest(unittest.TestCase):
def setUp(self):
global random
random = Random(666)
def test_gen_age(self):
self.assertEqual(gen_age(), 53)
if __name__ == '__main__':
unittest.main()
Note that if your test is not in the same file, you will need to patch random using unittest.mock.patch. Something like that should work
from random import Random
from package.file import gen_age
import unittest
class AgeTest(unittest.TestCase):
def setUp(self):
self.random = Random(666)
@patch('package.file.random')
def test_gen_age(self, random):
random.randint._mock_side_effect = self.random.randint
self.assertEqual(gen_age(), 53)
所有评论(0)