serverlesstechnology / cqrs

A lightweight, opinionated CQRS and event sourcing framework.
Other
346 stars 36 forks source link

Why are aggregates aware of commands? #75

Closed StephenGilboy closed 9 months ago

StephenGilboy commented 10 months ago

Moved to Discussions

I just realized this should be in the discussion area, sorry about that. Feel free to delete this.

Hi there. I'm just getting started with the framework, I'm coming from the C#/.NET world of DDD/CQRS. I am enjoying the library but I did have a question about why aggregates are handling commands and the reason for that?


.NET World

In .NET, from my experience, the CQRS is separated from the domain/aggregates.

  \domain\
     bank_account_aggregate.rs
     bank_account_events.rs
   \appllication\
     deposit_funds_command.rs
     deposit_funds_command_handler.rs
   \infrastructure\
     bank_account_repository.rs
     event_store.rs
   \api\
     bank_account_controller.rs

bank_account_aggregate.rs: implements all the business logic functions and emits events. It'll open the account, handle deposits, withdraw, etc... and then return events.

deposit_funds_command_handler.rs: Handles the deposit_funds_command.rs by using the bank_account_repository.rs to get the bank account from the data store then calls the deposit function on the aggregate and then handles emitting the returned event or error.

bank_account_controller.rs: Is the HTTP endpoint that receives/validates user input then creates the command to hand off to the command handler.

The benefits of this is that I can swap out any and all 3rd party dependencies, since the domain library should have no dependencies, and the business logic isn't cluttered with external calls since the aggregate has, either from it's state or from the function parameters, everything it requires to do what it needs to do.


Hopefully that helps set the context for my question. It wouldn't be too much work for me to pull the business logic out of the aggregate handler but I was I just want to know the reason for the aggregate being the command handler. Perhaps in your experience you've found the command handler isn't worth it or maybe it helps with Rust lifetimes. I'm not criticizing the choice I just want to understand the reasoning.

Thanks!

davegarred commented 9 months ago

Moved to discussions.