Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Python unittest passing arguments

In Python, how would I pass an argument from the command line to a unittest function?

Here is the code so far… I know it's wrong.

class TestingClass(unittest.TestCase):      def testEmails(self):         assertEqual(email_from_argument, "[email protected]")   if __name__ == "__main__":     unittest.main(argv=[sys.argv[1]])     email_from_argument = sys.argv[1] 
like image 955
Christopher H Avatar asked Jul 08 '12 03:07

Christopher H


People also ask

Which is better Pytest or Unittest?

Which is better – pytest or unittest? Although both the frameworks are great for performing testing in python, pytest is easier to work with. The code in pytest is simple, compact, and efficient. For unittest, we will have to import modules, create a class and define the testing functions within that class.

What does Unittest main () do?

Internally, unittest. main() is using a few tricks to figure out the name of the module (source file) that contains the call to main() . It then imports this modules, examines it, gets a list of all classes and functions which could be tests (according the configuration) and then creates a test case for each of them.


2 Answers

So the doctors here that are saying "You say that hurts? Then don't do that!" are probably right. But if you really want to, here's one way of passing arguments to a unittest test:

import sys import unittest  class MyTest(unittest.TestCase):     USERNAME = "jemima"     PASSWORD = "password"      def test_logins_or_something(self):         print('username:', self.USERNAME)         print('password:', self.PASSWORD)   if __name__ == "__main__":     if len(sys.argv) > 1:         MyTest.USERNAME = sys.argv.pop()         MyTest.PASSWORD = sys.argv.pop()     unittest.main() 

That will let you run with:

python mytests.py myusername mypassword 

You need the argv.pops, so your command line parameters don't mess with unittest's own...

The other thing you might want to look into is using environment variables:

import os import unittest  class MyTest(unittest.TestCase):     USERNAME = "jemima"     PASSWORD = "password"      def test_logins_or_something(self):         print('username:', self.USERNAME)         print('password:', self.PASSWORD)  if __name__ == "__main__":     MyTest.USERNAME = os.environ.get('TEST_USERNAME', MyTest.USERNAME)     MyTest.PASSWORD = os.environ.get('TEST_PASSWORD', MyTest.PASSWORD)     unittest.main() 

That will let you run with:

TEST_USERNAME=ausername TEST_PASSWORD=apassword python mytests.py 

And it has the advantage that you're not messing with unittest's own argument parsing. The downside is it won't work quite like that on Windows...

like image 171
hwjp Avatar answered Oct 06 '22 06:10

hwjp


Another method for those who really want to do this in spite of the correct remarks that you shouldn't:

import unittest  class MyTest(unittest.TestCase):      def __init__(self, testName, extraArg):         super(MyTest, self).__init__(testName)  # calling the super class init varies for different python versions.  This works for 2.7         self.myExtraArg = extraArg      def test_something(self):         print(self.myExtraArg)  # call your test suite = unittest.TestSuite() suite.addTest(MyTest('test_something', extraArg)) unittest.TextTestRunner(verbosity=2).run(suite) 
like image 44
steffens21 Avatar answered Oct 06 '22 07:10

steffens21