Summary: Using PyDev, I can't get one Python module (FooTest) to import another (FooMock) in the same (test) source folder.
I have two source folders and four Python modules, with the directory structure below. The minimal example code is at the end of the question. Although I have provided a lot of information, please don't let this intimidate you - it's a simple problem scenario.
PyDevProject/
src/ (source folder for prod code)
foo/
__init__.py
Bar.py
Foo.py
test/ (source folder for tests)
foo/
__init__.py
FooMock.py
FooTest.py
The issue here is that when I attempt to import FooMock class in the FooTest module, I get the following error (running PyUnit to run the FooTest tests):
Finding files... done.
Importing test modules ... Traceback (most recent call last):
File "/Applications/Eclipse.app/Contents/Eclipse/plugins/org.python.pydev_4.5.4.201601292234/pysrc/_pydev_runfiles/pydev_runfiles.py", line 468, in __get_module_from_str
mod = __import__(modname)
File "/Users/me/Development/krtiWorkspace/ImportTest/test/foo/FooTest.py", line 4, in <module>
from foo.FooMock import FooMock
ImportError: No module named FooMock
ERROR: Module: FooTest could not be imported (file: /Users/me/Development/krtiWorkspace/ImportTest/test/foo/FooTest.py).
done.
----------------------------------------------------------------------
Ran 0 tests in 0.000s
OK
Things I've tried:
- Even though FooMock and FooTest are both in the same Python package, FooMock can't be imported.
- Moving FooMock to under the
src/
directory works, even if placed under a unique Python package (as long as it's undersrc/
). But this isn't acceptable for me (to have test code in production source folders). - I've ensured the PYTHONPATH settings in PyDev are set to specify both folders are source folders.
- Copying and pasting the FooMock code into the FooTest code works. But this isn't acceptable for me (since I'd like to reference FooMock elsewhere, in multiple test files and I don't want multiple copies of FooMock floating around consequently).
Is there anything I can do about this?
Code:
# Code for Bar.py -----------------------------------------------------
class Bar(object):
def __init__(self, foo):
self.foo = foo
def next(self):
self.foo.incr()
# Code for Foo.py -----------------------------------------------------
class Foo(object):
def __init__(self):
self.num = 0
def incr(self):
self.num = self.num + 1
# Code for FooMock.py -------------------------------------------------
class FooMock(object):
def mock_incr(self):
self.hit = True
# Code for FooTest.py -------------------------------------------------
import unittest
from foo.Foo import Foo
from foo.Bar import Bar
from foo.FooMock import FooMock
class Test(unittest.TestCase):
def test_Foo(self):
foo = Foo()
foo.incr()
self.assertEquals(1, foo.num, "should be 1")
def test_Bar(self):
foo = FooMock()
bar = Bar(foo)
bar.next()
if __name__ == "__main__":
unittest.main()
Screenshot of directory: Image showing directory structure and PYTHONPATH as previously explained