Question

I'm learning python and I'm having some trouble with some simple unit tests I'm trying to run. I'm using nosetests to run some manually written tests, and I've got my github repository set up with Travis Continuous Integration for a bit of CI practice. I noticed that it was failing all builds for python 3.x, but passing anything for 2.x.

First, here are my two files.

fib.py

#! /usr/bin/python3
#fib.py

import sys

def fib(n):
    if (n == 0):
        return 0
    if (n == 1):
        return 1    
    return fib(n -1) + fib(n - 2)        

def main():
   if (len(sys.argv) == 2):    
       print(fib(sys.argv[1]))   
   else:
       print("Usage: ", sys.argv[0], " [number]")

if __name__ == "__main__":
        main()

test_fib.py

#! /usr/bin/python3
#testfib.py

import unittest
from fib import fib

class TestFib(unittest.TestCase):
    def test_fib_0(self):
        self.assertEqual(fib(0), 0)

    def test_fib_1(self):
        self.assertEqual(fib(1), 1)

    def test_fib_2(self):
        self.assertEqual(fib(2), 1)

    def test_fib_range(self):
        for x in range(2,13):
            self.assertEqual(fib(x), fib(x - 1) + fib(x - 2))

if __name__ == "__main__":
       unittest.main()

running python test_fib.py :

....
----------------------------------------------------------------------
Ran 4 tests in 0.018s

OK

running nosetests

....
----------------------------------------------------------------------
Ran 4 tests in 0.053s

OK
pi@kepler:~/dev/Projects/Numbers/fib$ 

However, when I deploy to Travis CI and it runs nosetests with python3.x, or I run nosetests3 on my machine, I see this:

EEEE
======================================================================
ERROR: test_fib_0 (fib.test_fib.TestFib)
----------------------------------------------------------------------
Traceback (most recent call last):
  File "/home/pi/dev/Projects/Numbers/fib/test_fib.py", line 9, in test_fib_0
    self.assertEqual(fib(0), 0)
TypeError: 'module' object is not callable

======================================================================
ERROR: test_fib_1 (fib.test_fib.TestFib)
----------------------------------------------------------------------
Traceback (most recent call last):
  File "/home/pi/dev/Projects/Numbers/fib/test_fib.py", line 12, in test_fib_1
    self.assertEqual(fib(1), 1)
TypeError: 'module' object is not callable

======================================================================
ERROR: test_fib_2 (fib.test_fib.TestFib)
----------------------------------------------------------------------
Traceback (most recent call last):
  File "/home/pi/dev/Projects/Numbers/fib/test_fib.py", line 15, in test_fib_2
    self.assertEqual(fib(2), 1)
TypeError: 'module' object is not callable

======================================================================
ERROR: test_fib_range (fib.test_fib.TestFib)
----------------------------------------------------------------------
Traceback (most recent call last):
  File "/home/pi/dev/Projects/Numbers/fib/test_fib.py", line 19, in test_fib_range
    self.assertEqual(fib(x), fib(x - 1) + fib(x - 2))
TypeError: 'module' object is not callable

----------------------------------------------------------------------
Ran 4 tests in 0.034s

FAILED (errors=4)

I'm pretty new to python, so I'm not sure if my problem is with my code or with how I'm using nose. Any ideas on what I'm doing wrong?

Here are the versions of everything I'm running:

$ python -V
Python 2.7.3
$ python3 -V
Python 3.2.3
$ nosetests -V
nosetests version 1.3.0
$ nosetests3 -V
nosetests3 version 1.1.2
$ cat /etc/*-release
PRETTY_NAME="Debian GNU/Linux 7 (wheezy)"
NAME="Debian GNU/Linux"
VERSION_ID="7"
VERSION="7 (wheezy)"
ID=debian
ANSI_COLOR="1;31"
HOME_URL="http://www.debian.org/"
SUPPORT_URL="http://www.debian.org/support/"
BUG_REPORT_URL="http://bugs.debian.org/"
Was it helpful?

Solution

Make sure you don't have some old files laying around, such as a fib/fib.pyc or something under __pycache__ perhaps, because for me, everything works correctly under Python 3.3.2 with nosetests as well as without:

(python3.3.2)~/code/python/stackoverflow$ nosetests test_fib.py 
....
----------------------------------------------------------------------
Ran 4 tests in 0.001s

OK

for example, run python (or ipython) in that directory and execute:

>>> from fib import fib
>>> fib
???

and see what it reports: if fib is reported to be a <function ...>, everything should be correct; if <module ...>, you have to investigate why it is so. For example, this is what I get:

>>> from fib import fib
>>> fib
<function fib at 0x10cb7d9e0>

You can also try adding from __future__ import absolute_import and see how Python 2.x behaves then; if the same problem starts occurring, it's an indication that you have a top-level package fib somewhere which Python 3.x imports by default but in Python 2.x gets overrided with the sibling package (i.e. a package in the same folder as test_fib), which is changed to Python 3.x behavior with the __future__ import. For more information about future imports, see Future statement definitions; about absolute_import, see PEP 328 -- Imports: Multi-Line and Absolute/Relative.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top