4 ms·
Yeah, I think this separation of concern misses a step. Let's say you have controller -> Business logic layer -> Data access layer. The controller takes in so
by kraftman 7y ago
Yeah, I think this separation of concern misses a step.
Let's say you have controller -> Business logic layer -> Data access layer.
The controller takes in some input, validates it, passes it to the business logic layer. The business logic layer retrieves some data from the DAL, does some logic, maybe writes data back to the DAL, and passes the data back up to the controller.
The problem is that the business logic layer is usually doing two things at the same time, in the same function: the 'plumbing' (calling other things and passing data round), and the actual business logic.
When you try and define a boundary around the code, it gets messy, because what you want to test, the business logic, is mixed in with the plumbing so you have to use either dependency injection or mocking to force a boundary. This makes your tests more brittle as changes in things you don't want to test (your dependencies) affect your tests.
If you pull out the business logic into its own modules, and instead have a function that orchestrates the business logic (i.e. tell the database what data you want, tell the business logic functions to perform an operation on the data), you end up with a nice clean boundary around your business logic, which can be unit tested easily without mocks.
You then test the 'plumbing' part by using a component test that checks that the inputs and outputs of the component as a whole (business logic + plumbing + data access) are correct.
- closeparen 7y agoI think what you’re describing is what we would call a controller, and management / senior ICs would still demand 90% line coverage by unit tests.