Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Mock patch with __init__.py

My code is organized as follows:

dir/A.py:

from X import Y

class A:
    ...

dir/__init__.py:

from .A import A
__all__ = ['A']

tests/test_A.py:

class test_A:
    @patch("dir.A.Y")
    def test(self, mock_Y):
        ....

On running tests/test_A.py, I (as expected) get the error:

AttributeError: <class 'dir.A.A'> does not have the attribute 'Y'

The issue is that @patch("dir.A.y") tries to find Y in class dir.A.A, rather than in the module dir.A (where it is actually present).

This is clearly because of my __init__.py. I could overcome this by changing the module-name A and the class-name A to different symbols.

The way the code is organized, I want to avoid such a naming change. How can I use patch in a way that it finds Y in the correct place?

like image 562
piggs_boson Avatar asked Aug 15 '15 16:08

piggs_boson


1 Answers

You can use the patch.object() decorator instead, and retrieve the module from sys.modules:

@patch.object(sys.modules['dir.A'], 'Y')
def test(self, mock_Y):
    ...
like image 178
Sven Marnach Avatar answered Nov 18 '22 14:11

Sven Marnach