Use Case Include Relationships
What is the include relationship?
When we capture a number of use cases, we very soon discover that they tend to share common sequences of interactions. Rather than repeating this documentation for each of the similar use cases, we try to rationalise the common sequences out of the use cases concerned into a ‘sub-use case’, then refer to it from the original use cases that use it.
For example, consider the following two brief use case descriptions from a vending machine (note our coke machine example has expanded to become a generalised vending machine!).
Buy can of coke
The user selects coke from the list of items appearing on the vending machine. The machine displays the amount of money to be inserted. The user inserts coins and notes until at least the amount required has been inserted. The machine returns any change to the cash tray. The machine dispenses a can of coke to the collection hopper. The system records the transaction internally on its cash ledger and adjusts its inventory.
Buy phone top-up
The user selects phone top-up with a particular amount of money from the list of items appearing on the vending machine. The machine prompts the user to enter their cell phone number on the keypad. The user enters their phone number followed by the enter key. The machine prompts them to re-enter their phone number, and the user enters their number again followed by the enter key. The machine displays the amount of money to be inserted. The user inserts coins and notes until at least the amount required has been inserted. The machine returns any change to the cash tray. The machine sends a top-up request to the phone company, and dispenses a paper receipt with the top-up details from the vending machine receipt printer. The system records the transaction internally on its cash ledger.
Note that these two brief use cases contain an example of shared sequences of steps. This is the sequence from displaying the amount of cash to be inserted up to returning change to the cash tray. By factoring this sequence out into an included use case that we shall call ‘Take payment‘, the two original use cases are simplified:
Take payment
The machine displays the amount to be inserted. The user inserts coins and notes until at least the amount required has been inserted. The machine returns any change to the cash tray.
Buy can of coke
The user selects coke from the list of items appearing on the vending machine. Payment is taken (see Take payment). The machine dispenses a can of coke to the collection hopper. The system records the transaction internally on its cash ledger and adjusts its inventory.
Buy phone top-up
The user selects phone top-up with a particular amount of money from the list of items appearing on the vending machine. The machine prompts the user to enter their cell phone number on the keypad. The user enters their phone number followed by the enter key. The machine prompts them to re-enter their phone number, and the user enters their number again followed by the enter key. Payment is taken (see Take payment). The machine sends a top-up request to the phone company, and dispenses a paper receipt with the top-up details from the vending machine receipt printer. The system records the transaction internally on its cash ledger.
In any final implementation, the factored out sequence of interactions will probably also be a shared implementation. Hence factoring out common sequences is a useful hint to the developers that the requirements at this point are genuinely the same.
Factoring out include relationships in this way also allows us to question the truth of that factoring with the stakeholders during iterative refinement of requirements. For example, the taking of payment above may get elaborated by the stakeholder to require the outstanding amount left to be inserted to be displayed afresh after each coin or note has been inserted. They might also say that if the machine has insufficient change, it should display a suitable message and give the customer the chance to abort the transaction getting all their money back. Because we have refactored the use cases to have an include relationship for payment taking, these extensions can also automatically become part of the other use cases too (subject to stakeholder confirmation that this is the behaviour they want to see).