最近翻了下写unit test 的文章,总结如下
What’s unit test?
“Unit testing is a software testing method by which individual units of source code.” – –Wikipedia
What’s integration test?
“Integration testing is the phase in software testing in which individual software modules are combined and tested as a group” – Wikipedia
Goal for unit test
- Defects obvious bugs
- Provide an example about how to call it
- Refactor
Effective way to find bugs
- Integration test
- Manual test
How to write good unit test?
Arrange -> Act -> Assert
# zoo.py
class Zoo:
def __init__(self, animals):
self.animals = animals
def sort_by_name(self):
self.animals = sorted(self.animals)
def get_animals(self):
return self.animals
# test_zoo.py
import unittest
class Zoo:
def __init__(self, animals):
self.animals = animals
def sort_by_name(self):
self.animals = sorted(self.animals)
def get_animals(self):
return self.animals
class TestZoo(unittest.TestCase):
def test_sort_by_name(self):
# Arrange: Set up test data
bj_zoo = Zoo(['panda', 'elephant', 'tiger'])
# Act: Execute the unit under test
bj_zoo.sort_by_name()
# Assert: Verify and log the result
self.assertEqual(bj_zoo.animals[0], 'elephant')
Tests verify facts about the application, not exact results
Separate requirements into individual clauses
import cipher
import decrypt
import unittest
def encrypt(str):
# Encryption followed by decryption should return the original:
# the encrypted text is as long as the original:
# no character is encrypted to itself:
entrypted_str = cipher.encrypt(str)
return entrypted_str
class TestEncypt(unittest.TestCase):
def test_encrypt_bad(self):
actual_encryption = encrypt('hello')
expected_encryuption = 'ASDFG'
self.assertEqual(actual_encryption, expected_encryuption)
def test_encrypt_good(self):
original_str = 'hello'
self.assertEqual(original_str, decrypt(encrypt(original_str)))
self.assertEqual(len(original_str), len(encrypt(original_str)))
for i in xrange(0, len(original_str)):
self.assertNotEqual(original_str[i], encrypt(original_str))
Test exception handling
import unittest
from exceptions import ValueError
def raise_exception():
raise ValueError('error msg foo')
class TestRaiseException(unittest.TestCase):
def test_raise_exception(self):
self.assertRaises(ValueError, raise_exception)
Don’t only test one input value or state
import unittest
from ddt import ddt, data, unpack
def larger_than_two(num):
if num > 2:
return True
@ddt
class FooTestCase(unittest.TestCase):
@data(3, 4, 12, 23)
def test_larger_than_two(self, value):
self.assertTrue(larger_than_two(value))
@data((3, 2), (4, 3), (5, 3))
@unpack
def test_tuples_extracted_into_arguments(self, first_value, second_value):
self.assertTrue(first_value > second_value)
Mock out all external services and state
# rm.py
import os
def rm(filename):
os.remove(filename)
# test_rm.py
from rm import rm
import mock
import unittest
import os
def rm(filename):
os.remove(filename)
class RmTestCase(unittest.TestCase):
@mock.patch('foomodule.os')
def test_rm(self, mock_os):
rm("any path")
mock_os.remove.assert_called_with("any path")
Avoid unnecessary preconditions
Name clearly and consistently
Example
test_divide_zero_raise_exception
When and where to add unit test?
- When you need a block of comment
- Parts likely to fail
- Parts keep getting questions
Reference
https://developer.salesforce/page/How_to_Write_Good_Unit_Tests
http://blog.stevensanderson/2009/08/24/writing-great-unit-tests-best-and-worst-practises/
http://www.ibm/developerworks/cn/linux/l-tdd/index.html
https://msdn.microsoft/en-us/library/jj159340.aspx
更多推荐
写好unit test的建议和例子
发布评论