I'm implementing a class which uses a can bus instance (Bus instance is static because all object should use the same).
# ./mymodule/__init__.py
import can
class UsingCanBUS:
_bus = can.ThreadSafeBus(channel='can0', bustype='socketcan')
def __init__(self) -> None:
# other code
# v here every object interacts with the bus
self._listener = can.Listener()
self._listener.on_message_received = self._handle_message
def _send_message(self, id, data) -> bool:
msg = can.Message(arbitration_id=id, data=data, extended_id=False)
try:
self._bus.send(msg)
except can.CanError:
return False
else:
return True
This code will eventually run on a raspberry so the can interface is correctly setup in the system.
Now, if I want to unit test any of the class methods or any file in the module the bus tries to initialize and, since I'm not on the target system, it throws an os error (which is to be expected).
The folder structure is as follows:
.
|- mymodule/
| |- __init__.py
| |- utils.py
|
|- tests/
| |- __init__.py
| |- test_utils/
| | |- __init__.py
| | |- test_utils.py
It's not clear to me how I should test this piece of code. I tried patching the can module:
#./tests/test_utils/test_utils.py
import pytest
from unittest.mock import patch
@patch('mymodule.can')
def test_something():
from mymodule.utils import some_function
# This doesn't work as the real python-can methods get called instead of the mocked ones
assert some_function() == expected_result
I don't understand if I'm using the patch decorator wrong or if my approach is completely off course. I expect every class in the can module imported from mymodule
to be patched with mocked classes but it doesn't seem like it.
The Raspberry Pi doesn't come with the CAN driver so you can't directly install the can-utils and simulate the virtual CAN. Use the CAN transceiver on top of Raspberry Pi. You could go with this particular one, which I'm also using for the simulations.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.