I have code that connects to a MongoDB Client and I'm trying to test it. For testing, I don't want to connect to the actual client, so I'm trying to figure out make a fake one for testing purposes. The basic flow of the code is I have a function somewhere the creates a pymongo
client, then queries that and makes a dict that is used elsewhere.
I want to write some tests using pytest that will test different functions and classes that will call get_stuff
. My problem is that get_stuff
calls mongo()
which is what actually makes the connection to the database. I was trying to just use pytest.fixture(autouse=True)
and mongomock.MongoClient()
to replace mongo()
.
But this isn't replacing the mongo_stuff.mongo()
. Is there some way I can tell pytest to replace a function so my fixture
is called instead of the actual function? I thought making the fixture
would put my testing mongo()
higher priority in the namespace than the function in the actual module.
Here is an example file structure with my example:
.
├── project
│ ├── __init__.py
│ ├── mongo_stuff
│ │ ├── __init__.py
│ │ └── mongo_stuff.py
│ └── working_class
│ ├── __init__.py
│ └── somewhere_else.py
└── testing
├── __init__.py
└── test_stuff.py
mongo_stuff.py
import pymongo
def mongo():
return pymongo.MongoClient(connection_params)
def get_stuff():
db = mongo() # Makes the connection using another function
stuff = query_function(db) # Does the query and makes a dict
return result
somewhere_else.py
from project.mongo_stuff import mongo_stuff
mongo_dict = mongo_stuff.get_stuff()
test_stuff.py
import pytest
import mongomock
@pytest.fixture(autouse=True)
def patch_mongo(monkeypatch):
db = mongomock.MongoClient()
def fake_mongo():
return db
monkeypatch.setattr('project.mongo_stuff.mongo', fake_mongo)
from poject.working_class import working_class # This starts by calling project.mongo_stuff.mongo_stuff.get_stuff()
And this will currently give me a connection error since the connection params
in mongo_stuff.py are only made to work in the production environment. If I put the import
statement from test_stuff.py into a test function, then it works fine and mongomock
db will be used in the testing enviornment. I also tried change the setattr
to monkeypatch.setattr('project.working_class.mongo_stuff.mongo', fake_mongo)
which also does not work.