Open lasuk opened 2 months ago
Objective: Implement a test strategy that allows for testing multiple implementations of the LedgerEngine
abstract class without duplicating test logic. This strategy should be scalable, allowing new implementations to be added with minimal changes to the test code.
Abstract Base Test Class:
LedgerEngine
implementations.test_create_entry
, test_update_entry
, and test_delete_entry
.pytest
fixtures to manage the setup for each implementation.Concrete Test Classes:
LedgerEngine
implementation, create a concrete test class that inherits from the abstract base test class.ledger
fixture that returns an instance of the specific LedgerEngine
implementation.Support for Future Implementations:
LedgerEngine
implementations with minimal changes.ledger
fixture.# tests/base_test_ledger.py
import pytest
import pandas as pd
from abc import ABC, abstractmethod
class BaseLedgerTest(ABC):
@abstractmethod
@pytest.fixture
def ledger(self):
pass
def test_create_entry(self, ledger):
entry = pd.DataFrame([{"id": "1", "data": "test data"}])
ledger.create(entry)
assert ledger.get("1") is not None
def test_update_entry(self, ledger):
entry = pd.DataFrame([{"id": "1", "data": "test data"}])
ledger.create(entry)
updated_entry = pd.DataFrame([{"id": "1", "data": "updated data"}])
ledger.update("1", updated_entry)
assert ledger.get("1").iloc[0]["data"] == "updated data"
def test_delete_entry(self, ledger):
entry = pd.DataFrame([{"id": "1", "data": "test data"}])
ledger.create(entry)
ledger.delete("1")
assert ledger.get("1") is None
# tests/test_memory_ledger.py
import pytest
from .base_test_ledger import BaseLedgerTest
from yourpackage.memory_ledger import MemoryLedger
class TestMemoryLedger(BaseLedgerTest):
@pytest.fixture
def ledger(self):
return MemoryLedger()
# tests/test_cashctrl_ledger.py
import pytest
from .base_test_ledger import BaseLedgerTest
from yourpackage.cashctrl_ledger import CashCtrlLedger
from yourpackage.api_client import ApiClient # Assuming a mock or test client
class TestCashCtrlLedger(BaseLedgerTest):
@pytest.fixture
def ledger(self):
client = ApiClient()
return CashCtrlLedger(client)
# tests/test_new_ledger.py
import pytest
from .base_test_ledger import BaseLedgerTest
from newpackage.new_ledger import NewLedger # Your new ledger implementation
class TestNewLedger(BaseLedgerTest):
@pytest.fixture
def ledger(self):
return NewLedger()
BaseLedgerTest
abstract test class.MemoryLedger
, CashCtrlLedger
, and any new LedgerEngine
implementations.This approach follows best practices seen in large open-source projects like Django and Pandas, ensuring a scalable and maintainable testing strategy for your LedgerEngine
implementations.
Tasks:
TestLedger
orMemoryLedger
. Copy existing test code fromCashCtrlLedger
where helpful.Test Architecture
TestLedger
. The same tests can then be used to test accessors and mutators on other ledger implementations, such asCashCtrlLedger
.