I have a list CountryList[] defined in my function and I want to check that it is not empty. I initialize it as empty but later on in the function data is put into it. This is the unit test I have typed.
def assertEmpty(self, CountryList):
self.assertFalse(CountryList)
def assertNotEmpty(self, CountryList):
self.assertTrue(CountryList)
This is the method in my program.
def onCountry(self, doc_id):
if(doc_id==None):
return
output_list = self.findBySubjectDocId(doc_id)
country_list=[]
for x in output_list:
country_id=x["visitor_country"]
if(SHOW_FULL_NAMES):
country_id=pc.country_alpha2_to_country_name(country_id)
country_list.append(country_id)
ts=pd.Series(country_list).value_counts().plot(kind='bar',color='purple')
plt.xticks(rotation='horizontal')
plt.xlabel('Country')
plt.ylabel('Number of Viewers')
plt.title("Viewers based on Country")
ts.plot()
plt.show()
print("Countries of Visitors:")
x = []
y = []
for k,v in Counter(country_list).items():
x.append(k)
y.append(v)
print(k,"-",v)
Do you suggest I test out this code some other way? or is the above testing acceptable?
CodePudding user response:
If you are just trying to see if a list is empty someone asked a similar question here: How do I check if a list is empty?
CodePudding user response:
Here are several suggestions:
To properly use Python's
unittest
package, you need to create a class which extendsunittest.TestCase
.Name your test methods
test_*
rather thanassert*
.Tests can only take one argument
self
.You can define a
setUp()
method which runs before eachtest_*
method. Use this to create data that is common to all tests.Tests are code just like any other code and follow all the same rules.
First describe in words the scenario you are trying to test. Often this is of the form "When I call function F with parameters P, then the result will be R". Then write the test to replicate this specific scenario.
CodePudding user response:
Since country_list
is a local variable that isn't returned, there's not an easy way for your unit test to check it directly; your test helpers seem fine, but you don't seem to have any actual testing that uses them, because the code has been written in a way that's difficult to test.
One way to make this easier to test would be to refactor the function into two pieces like this:
def build_country_list(self, doc_id):
output_list = self.findBySubjectDocId(doc_id)
country_list=[]
for x in output_list:
country_id=x["visitor_country"]
if(SHOW_FULL_NAMES):
country_id=pc.country_alpha2_to_country_name(country_id)
country_list.append(country_id)
return country_list
def onCountry(self, doc_id):
if doc_id is None:
return
country_list = self.build_country_list(doc_id)
ts=pd.Series(country_list).value_counts().plot(kind='bar',color='purple')
plt.xticks(rotation='horizontal')
plt.xlabel('Country')
plt.ylabel('Number of Viewers')
plt.title("Viewers based on Country")
ts.plot()
plt.show()
print("Countries of Visitors:")
x = []
y = []
for k,v in Counter(country_list).items():
x.append(k)
y.append(v)
print(k,"-",v)
Now you can write a unit test for build_country_list
that verifies that your logic of building the list is correct, separately from the onCountry
logic that also plots and prints the data, something like:
def test_build_country_list(self):
# probably need to have done some setUp that sets up a test_doc_id?
self.assertNotEmpty(self.test_instance.build_country_list(self.test_doc_id))
If you want to also test the output logic, you'll need to mock out the output functions and write a test that verifies that they get called with the correct arguments when onCountry
is called.