In most cases I understand the distinction between a command and an event in a CQRS + ES system. However, there is one situation that I can\'t figure out.
Suppose I am b
I found this question while wondering the same thing.
I liked Mikael's answer and upvoted it. However, I found another answer on the DDD/CQRS forum that takes a different approach, so figured I'd post it here for others who are looking too.
Here's a quote from Greg Young on a similar question about tracking external state:
In most inventory systems there are no commands.
Or to paraphrase:
Systems that exclusively track external state will have no commands.
Let's rewind and think through how your system might evolve based on this idea (let's also assume you're not building it for yourself):
Note that this variant accepts both commands and events. You wouldn't go back and convert all existing events to commands just because you now allow the user to change things. Instead, you have a system that accepts external transaction events, commands for user-entered transactions and transaction corrections (which create events that modify internal state), and projections to combine these internal and external events for display in the app.
I'm curious though. In hindsight, did the accepted answer end up being a good approach? Or would recording and handling events from the Florist directly like Greg suggests be better?
This is a perfect example of bounded contexts.
An event that has occurred in another system (or bounded context) that represent the same or business process step, should not be treated as an event that has occurred in the receiving system.
The Florist System Debit event might have a different structure than the Debit event that would have occurred in the Finance Tracking System.
To solve this I would have an endpoint that would listen to the Florist System events and from that I would make the Finance Tracking System issue a command based on the information in the event and maybe combine it with information in the Finance Tracking System if needed. Where this happens could be thought of as a client to the Finance Tracking System or maybe even a "domain service" if you will.
In this particular case an event from the Florist system comes in with information of a transaction that has occurred in the Florist system (bounded context). I would not make any decisions in the domain service, but issue a command to the Finance Tracking System domain where the decision takes place and Finance Tracking System events may be emitted. If the Florist system event appears malformed in the Finance Tracking System you probably don't want to tell the Florist system about that in a Request/Response or Ack/Nack manner. The event was published from the Florist and you would break messaging patterns if you implement something like that. Your messaging infrastructure should allow you to retry the message or even fix the receiving code and retry the message with the new code.
However, if you really need to communicate back the Florist bounded context, the Florist system could subscribe to events from the Finance Tracking System in order to find out whether the transaction was successfully handled. That would only be needed if the main system is deciding whether a transaction may occur or not.
In the case you are describing the Finance Tracking System is more of a transaction log and the only thing you should have to do is to not treat Florist events as Finance Tracking System events. Put something in between that issues commands that result in Finance Tracking System events.
EDIT:
As a response to your edit. You receiving component should send commands to the Finance Tracking System domain which in turn would emit events (as usual).