This question already has an answer here:
- Unit testing of “workflow” methods 1 answer
I want to test a method which is not as much as a unit, because it is more of a 'orchestrator' / 'process' / 'controller' / 'coordination' class.
This is the case:
I have four unit tested classes:
- One is a data service which can read/write data from the database
- Second is a textservice which can create content for emails / messages etc.
- Third is a mailservice that can send email
- Fourth is a class dat can create tasks for users in our system (tasks are things they should do)
Now I created a new class, which sends an email all people which are late with paying an invoice. It reads data with the data service, creates the appropriate text with the textservice, sends an email with the email service, writes the new invoice status with the data service and creates a task when the emailing for a specific invoice fails.
Now this new class is my 'orchestrator' or 'process' or 'controller' or 'coordination' class.
I have these kind of classes a lot in our application because we try to make our classes (like the data/email/textservice) as small as possible so when 'work has to be done', like in this case the 'mail all people which are late with paying', we create a new 'orchestrator' or 'process' or 'controller' or 'coordination' class.
I think I have these kind of classes for the most of my actions in my webcontrollers because most input sent from the browser involves coordination between multiple (smaller) classes
Now how do I test these classes / methods?
I used to mock all 4 classes in my test and verify at the end that the classes are called, and in the right order.
But more and more I read that you shoud not do this, because then you test for the internal working of a method, and when you refactor that method, the test fails. So I should test for results, not for inner working. But this method is void, so there is nut much of a result to verify on. The only thing I can think for instance to check for is: is email sent? But the only way to check that is to verify the email service is called, but then I'm back at testing the internals.
I don't see these kind of examples in the unit testing / tdd books, because they most of the time only work with the small classes like the calculator class, but rarely do I see examples for 'orchestrator' classes like I'm describing, but which occur a lot in my code.
For those who think it's a duplicate: I think the answers here provide much more background than the one answer at the other question. That other question was answered with a integration test in mind, and my question is about unit testing, not integration testing. So I can't agree with the duplicate answer mark.