The
command pattern
is one of the patterns defined in the gang of four’s behavioural patterns but I rarely see it get much use. The idea behind the pattern is to encapsulate all of the information required to execute an action within a single object or class:
publicinterfaceICommand{voidExecute();}publicclassAdmitPatient:ICommand{stringfirstname;stringsurname;publicAdmitPatient(stringfirstname,stringsurname){this.firstname=firstname;this.surname=surname;}publicvoidExecute(){// do something here
}}
Now the reason I want to highlight this pattern is because of something I’ve been seeing in a lot software projects. That’s the abuse of the “service class” in your typical n-tier architecture. These classes often get filled with tens of methods for manipulating some object making them bloated and difficult to understand. They will take a ton of dependencies and are often called
PatientService
or
DoctorService
. Over time these become bloated and unmaintainable.
The best way I find of combating this atrophy is to use the command pattern instead. This allows you to break down you service layers into indvidual classes that are each responsible for only one thing. They only take the dependencies that are needed and are much easier to refactor as there is less chance of the methods depending upon anothers.
However, as much as I feel the command pattern is better I always find there’s a couple of problems with it. For one it’s awkward to pass in any dependencies as they would have to be included with the information required to execute the command. Theres a couple of obvious ways around this, such as allowing the
firstname
and
surname
to be setable properties but thats a bit mess. What would be better is to actually take things a little further and seperate the execution of the command from the information required to execute it.
This is where the command handler comes in:
publicinterfaceICommandHandler<T>{voidExecute(Tcommand);}publicclassAdmitPatient{publicstringFirstName{get;}publicstringSurname{get;}publicAdmitPatient(stringfirstname,stringsurname){FirstName=firstname;Surname=surname;}}publicclassAdmitPatientHandler:ICommandHandler<AdmitPatient>{IRepositoryrepo;publicAdmitPatientHandler(IRepositoryrepo){this.repo=repo}publicvoidExecute(AdmitPatientcommand){// do something here
}}
This is much better as it gives you a clean way to inject some dependencies and it also works much better with message based architectures where you can make use of some basic infrastructure code to marry the command up with the correct handler:
I am using an IOC container here to resolve the handlers but if you are against this you could also manually register each of your handlers. I find this is better as its more explicit instead of all that IOC magic.
Here
is the gist for the full sample. This idea was influenced by
@jageall
.
You can always take things further and include code to validate your command before it gets executed or add in authorisation to make sure the user is able to execute the command.