views:

472

answers:

3

One of the basic tenets of CQRS, as I understand it, is that commands should be behaviour-centric, and have a value in the business or the UL, and not data-centric, ie., CRUD. Instead of focusing on updating a customer, we have commands like CustomerHasMoved. What if you have CRUD screens which are there to correct certain data. For example, we need to change the name of a customer which is misspelled. This doesn't really have much value in the business. Should this just be under the umbrella of an UpdateCustomer command?

A: 

CustomerHasMoved is the event that is fired after you have updated the customers location. This event updates the read databases/cache databases. The command from the gui should be MoveCustomer or something like that. I think I would put the update of the customer name in a command like UpdateCustomer.

Fossmo
+4  A: 

Actually, there could be various reasons to update the name of a customer. As you were saying, it could be misspelled or... you could get married and change your name to your husband's.

If you had only an UpdateCustomer command, you would loose the original intent and you would not be able to have different behaviours for each of them. If the name was misselled it could be as simple as updating the database, whereas if your customer got married you might need to notify the marketing departement so tthat they can offer a discount.

Julien
Exactly, so what is one to do? Create a command for every single possible scenario?
blockhead
Yes, or at least for each scenario you want to handle. In my example, you would start with CorrectMisspelledCustomerName then later, if you need to, you'll add a MakeCustomerMarried command.CQRS is about behaviour, not about updating data. Therefore you should not have generic commands for updating stuff in your system
Julien
What if I had a big screen with all fields for my customer. Would I fire off several commands to handle that, or somehow come up with some kind of "behaviour" for that. Perhaps I should just never show all the fields.
blockhead
you should probably not show all the fields in an editable way at once, but have a "task based" UI. I.E. only show the fields after the user choosed the action he intent to perform
Julien
I second Julien's answer. Task based UI is definitely what CQRS pushing towards. Don't be too caught up having screens for every single tasks. The big screen with all your customer fields may still exist, for e.g Call Center people wants to be able to see all fields in one quick glace. But this view should be read only. All updates can be context specific (mark as read, upgrade, correct name, etc).
ronaldwidha
@blockhead It might be a good idea to create abstract `ChangeCustomerAddressCommand` and derive more specific commands from it like `CustomerHasMovedCommand` if derived commands doesn't conflict with each other.
Arnis L.
+4  A: 

I just want to put a comment on this quickly as it popped up.

It is important to note that some objects are actually CRUD and thats ok. I may not really care why a name is changing in my domain where I ship products to people and only need that data to print mailing labels. The trick is in making behavior the default and THEN reverting to a CRUD interface once you are sure you really don't care about the reasons as opposed to vice versa.

Greg

Greg Young