{"id":936,"date":"2019-04-30T14:23:26","date_gmt":"2019-04-30T14:23:26","guid":{"rendered":"http:\/\/tech.avant.net\/q\/?p=936"},"modified":"2019-04-30T15:18:04","modified_gmt":"2019-04-30T15:18:04","slug":"python-unittest","status":"publish","type":"post","link":"https:\/\/tech.avant.net\/q\/python-unittest\/","title":{"rendered":"python unittest"},"content":{"rendered":"<p>I would like to setup unit tests for a python application. There are many ways to do this, including <a href=\"https:\/\/docs.python.org\/3\/library\/doctest.html\" target=\"_blank\" rel=\"noopener noreferrer\">doctest<\/a> and <a href=\"https:\/\/docs.python.org\/3\/library\/unittest.html\" target=\"_blank\" rel=\"noopener noreferrer\">unittest<\/a>, as well as 3rd-party frameworks that leverage python&#8217;s unittest, such as <a href=\"https:\/\/docs.pytest.org\/en\/latest\/\" target=\"_blank\" rel=\"noopener noreferrer\">pytest<\/a> and <a href=\"https:\/\/nose.readthedocs.io\/en\/latest\/\" target=\"_blank\" rel=\"noopener noreferrer\">nose<\/a>.<\/p>\n<p>I found the plain-old unittest framework to be the easiest to work with, although I often run into questions about how best to organize tests for various sized projects. Regardless of the size of the projects, I want to be able to easily run all of the tests, as well as run specific tests for a module.<\/p>\n<p>The standard naming convention is &#8220;test_ModuleName.py&#8221;, which would include all tests for the named module. This file can be located in the same directory (package) as the module, although I prefer to keep the tests in their own subdirectory (which can easily be excluded from production deployments).<\/p>\n<p>In other words, I end up with the following:<\/p>\n<pre class=\"EnlighterJSRAW\" data-enlighter-language=\"null\">package\/\n - __init__.py\n - Module1.py\n - Module2.py\n - test\/\n    - all_tests.py\n    - test_Module1.py\n    - test_Module2.py<\/pre>\n<p>Each of the test_*.py files looks something like this:<\/p>\n<pre class=\"EnlighterJSRAW\" data-enlighter-language=\"python\">#!\/usr\/bin\/env python\n# vim: set tabstop=4 shiftwidth=4 autoindent smartindent:\nimport os, sys, unittest\n\n## parent directory\nsys.path.insert(0, os.path.join( os.path.dirname(__file__), '..' ))\nimport ModuleName\n\nclass test_ModuleName(unittest.TestCase):\n\n    def setUp(self):\n        ''' setup testing artifacts (per-test) '''\n        self.moduledb = ModuleName.DB()\n\n    def tearDown(self):\n        ''' clear testing artifacts (per-test) '''\n        pass\n\n    def test_whatever(self):\n        self.assertEqual( len(self.moduledb.foo()), 16 )\n\n\nif __name__ == '__main__':\n    unittest.main()<\/pre>\n<p>With this approach, the tests can be run by all_tests.py, or I can run the individual test_ModuleName.py.<\/p>\n<p>The all_tests.py script also must add the parent directory on the path, i.e.,<\/p>\n<pre class=\"EnlighterJSRAW\" data-enlighter-language=\"python\">#!\/usr\/bin\/env python\n# vim: set tabstop=4 shiftwidth=4 autoindent smartindent:\nimport sys, os\nimport unittest\n\n## set the path to include parent directory\nsys.path.insert(0, os.path.join( os.path.dirname(__file__), '..' ))\n\n## run all tests\nloader = unittest.TestLoader()\ntestSuite = loader.discover(\".\")\ntext_runner = unittest.TextTestRunner().run(testSuite)<\/pre>\n","protected":false},"excerpt":{"rendered":"<p>I would like to setup unit tests for a python application. There are many ways to do this, including doctest and unittest, as well as 3rd-party frameworks that leverage python&#8217;s unittest, such as pytest and nose. I found the plain-old unittest framework to be the easiest to work with, although I often run into questions [&hellip;]<\/p>\n","protected":false},"author":2,"featured_media":0,"comment_status":"closed","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":[],"categories":[6],"tags":[],"_links":{"self":[{"href":"https:\/\/tech.avant.net\/q\/wp-json\/wp\/v2\/posts\/936"}],"collection":[{"href":"https:\/\/tech.avant.net\/q\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/tech.avant.net\/q\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/tech.avant.net\/q\/wp-json\/wp\/v2\/users\/2"}],"replies":[{"embeddable":true,"href":"https:\/\/tech.avant.net\/q\/wp-json\/wp\/v2\/comments?post=936"}],"version-history":[{"count":5,"href":"https:\/\/tech.avant.net\/q\/wp-json\/wp\/v2\/posts\/936\/revisions"}],"predecessor-version":[{"id":942,"href":"https:\/\/tech.avant.net\/q\/wp-json\/wp\/v2\/posts\/936\/revisions\/942"}],"wp:attachment":[{"href":"https:\/\/tech.avant.net\/q\/wp-json\/wp\/v2\/media?parent=936"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/tech.avant.net\/q\/wp-json\/wp\/v2\/categories?post=936"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/tech.avant.net\/q\/wp-json\/wp\/v2\/tags?post=936"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}