I am considering implementing Robert Martin's Clean Architecture in a project and I am trying to find out how to handle non-trivial use cases.
I am finding it difficult to scale the architecture to complex/composed use cases, especially use cases where the actor is the system as opposed to a user, as in system performing some sort of batch processing.
For illustration purposes, let's assume a use case like "System updates all account balances" implemented in pseudocode like
class UpdateAllAccountBalancesInteraction {
function Execute() {
Get a list of all accounts
For each account
Get a list of all new transactions for account
For each transaction
Perform some specific calculation on the transaction
Update account balance
}
}
In addition, "Get a list of all accounts", "Get a list of all new transactions for account", "Perform some specific calculation on the transaction", "Update account balance" are all valid use cases of their own and each of them is already implemented in its own interaction class.
A few questions arise:
- Is the use case "System updates all account balances" even a valid use case or should it be broken down into smaller use cases (although from a business prospective it seems to make sense, it is a legitimate business scenario)?
- Is UpdateAllAccountBalancesInteraction a legitimate interaction?
- Is an interaction allowed to/supposed to orchestrate other interactions?
- Is code that orchestrates other interactions really belonging somewhere else?
- Is it just OK to have UpdateAllAccountBalancesInteraction as an interaction, but have it call functions shared by the other interactors rather than act as an orchestrator of other interactors?
Execute()
method should not call another interaction'sExecute()
method, but they can definitely share code in the same layer. – Jeepers