Journal of a software dev

May 24, 2009

Command Query Separation (CQS)

Filed under: best practices, design pattern, oop, software design — Tags: — Michael Cromwell @ 4:58 pm

Introduction

CQS was a term that was coined by Bertrand Meyer and presented itself in his book Object Oriented Software Construction (I haven’t read the book, yet!) the principle states that every method should either be a command that changes state or a query in which case it does not change any state but not both.

In all I agree with the principle I can think of some valid examples that are valid to break it but on the whole it’s makes sense to follow it, however what I want to show in this post is to take this principle and show how it can be applied at various levels rather than just at the method level.

Architectural Level

If we imagine a system which manages lots of amounts of data and the business would like to perform analysis on this data while still providing transactional throughput it would not be uncommon to split the data into separate Online Transaction Processing (OLTP) and Online Analytical Processing (OLAP), this  is a good example of separating the data that will be changing often (OLTP) from the stagnant data that can be analysed (OLAP) I feel this matches strongly to the principle, the benefits gained typically result in better performance and data that reflects the needs of the operations applied to it.

Object Design Level

When we have a complex domain that require numerous behaviours we want to take advantage of domain modelling in our objects by utilising something like DDD to come up with entities, value objects etc… that we can use to represent the domain were working in.

We use these objects to perform transactional operations such as “Submitting an Order” or “Creating a New User” as these represent where we are going to using the behaviours and rules we put together using our objects. What we don’t want to start doing is then using these same objects for displaying result grids on a search screen, this represents a very different usage pattern and if we try to use our objects for this purpose and also for transactional processing we get into a mess quite quickly.

Instead it’s best to take onboard the CQS principle and separate our domain model objects that will be used for out transaction processing from what I think of as reporting or querying objects that are only interested in grabbing data for things such as search screens & reports. So if we were in a issue tracking domain we would probably end up with something like this:

// uses ORM such as nHibernate concerned only with using objects in a transactional
// context does not do any reporting or querying
public class IssueRepository : IIssueRepository
{
	public Issue FindBy(int id)
	{
		// use ORM to get by id
	} 

	public Issue Save(Issue issue)
	{
		// use ORM to save only used when new as object will be tracked
		// for updates automatically
	} 

	public void Delete(Issue issue)
	{
		// use ORM to delete
	}
} 

// probably just uses ADO.NET raw or a light facade on top of ADO.NET
// may use nHibernate but DOES NOT return any transactional objects only
// projections
public class IssueQuerying : IIssueQuerying
{
	public DataTable FindMatchingCriteria(int priorityId, int pageNo, int pageCount, out int virtualCount)
	{
		// use ADO.NET to fill datatable of results, possibly using SP to support paging
		// for older DB
	} 

	public IssueDisplayModel FindAssignedTo(string username)
	{
		// use nHibernate to fill projection object IssueDisplayModel
	}
}

The benefits we get from separating these 2 concerns:

  1. Our domain model objects are not polluted with lots of getters just to be used for reporting/querying
  2. We can utilise databinding because our querying object returns objects that ASP.NET controls know what to do with (one way databinding only)
  3. Our mapping is simplified as we only need to map our domain model objects to other objects for transactional processing needs not querying/reporting.

Summary

Hopefully this post has shown how we can take the original CQS principle and see how it applies to other levels when developing software from the high level architecture right down to the method level.

November 16, 2008

Staff Intranet Updated

Filed under: best practices, c#, code example, design pattern, oop, software design — Tags: , , , — Michael Cromwell @ 7:45 pm

I just updated the staff intranet project over on codeplex, I have now got it under source control now that they have added support for SVN :) And have also uploaded a new release of the source in case you dont have a source control client compatible.

The changes are:

  • Incorporating some of my other projects (log4net-altconf, object2object mapper) to help with the maintainability of the app.
  • Refactorings I have made to the way a staff member is saved. After gaining a better understanding of DDD principles it was quite clear that the validation around the photo upload & checking for name duplication should be separated as Specification objects to reduce the coupling in the Staff object.

Remember any feedback you can post here on my blog or on codeplex

June 27, 2008

New Staff Intranet Release

I have found enough spare time to put up a new release of the staff intranet project, for those who are not aware of this project it is a demonstration of using best practices, principles & patterns in a real world web application so if your looking for pointers or some code to use for your own applications go give it a look on codeplex.

In this newest version I have added AOP support to cut down on cross cutting code and also the ability to delete staff members from the GridView, most of the time spent was fighting against the asp.net controls (suprise, surprise) such as the GridView and the ObjectDataSource, I’m not sure what the guy(s) who created the ObjectDataSource object was smoking at the time but it must have been stronger than just tobacco :-)

My next release I want to demonstrate adding some service support showing how we can re-use existing code so they become little more than a remote facade (in theory!).

Blog at WordPress.com.