ddd-toolkit-core
Traits and reference implementations for Domain-Driven Design building blocks in Rust: entities, value objects, aggregates, repositories, and event dispatch. No macro dependency - everything here can be implemented by hand.
If you want #[derive(...)] support for the value-object-shaped traits, add
ddd-toolkit-macro
alongside this crate, or depend on
ddd-toolkit instead, which
bundles both behind a single dependency. Reach for this crate directly when
you want the traits with zero macro machinery and full control over every
impl; reach for ddd-toolkit when you'd rather generate the boilerplate for
ValueObject/EntityId/etc.
Installation
Or add it to Cargo.toml directly, enabling the adapter features you need:
[]
= { = "0.2", = ["chrono", "uuid"] }
chronoenablesadapter::clock::SystemClockandmock::clock::FixedClock.uuidenablesadapter::id::UuidV4Generator/UuidV7Generator.serdederivesSerialize(notDeserialize- seeValidationError's docs for why) fordomain::ValidationError.
None of these features is required: the domain, port, application
modules and the rest of mock build with no default features. Requires
Rust 1.85 or newer (edition 2024).
What's here
domain-Entity,AggregateRoot,ValueObject/Wrapped,EntityId,SecretVo,EnumVo,DomainEvent,ValidationError.port-Load/Save/Deleterepository traits,EventDispatcher(withDispatchError<E>reporting undelivered events on partial failure),Clock,IdGenerator,PortError.adapter- real port implementations, gated per feature so you only pull in what you use:SystemClockbehindchrono,UuidV4Generator/UuidV7Generatorbehinduuid.mock- test doubles:InMemoryStore(aLoad/Save/Deleteimplementation backed by aHashMap) andFixedIdGeneratorbuild unconditionally;FixedClockis behind thechronofeature.application-UseCase.
Example
use ;
use Display;
;
Entity is the smallest building block; a real aggregate also implements
AggregateRoot to record domain events, and is persisted through the
Load/Save ports - here via mock::repository::InMemoryStore, a drop-in
test double:
use ;
use InMemoryStore;
use ;
use Display;
;
;
// This crate has no async-runtime dependency of its own; `tokio` here is
// just an example caller driving the async `Load`/`Save` ports.
async
More usage, including EventDispatcher and the chrono/uuid adapters, is
covered in the API docs.
Changelog
See CHANGELOG.md for release history.
License
Licensed under either of Apache License, Version 2.0 or MIT license at your option.