Open sagiomc opened 4 years ago
@sagiomc Thanks for your comment!
...they contain rules that are not application-specific (Use Cases) and should not be affected by any external change
Remember the "Stable Dependency Principle"? In my eyes, lodash
and uuid/v4
are stable dependencies because it is extremely unlikely that they will change. I would even argue that they have similar levels of stability as language features like JSON.stringify
. That being said, I would still recommend choosing your dependencies carefully, but if you need to use a library to build your entity, and you can be sure that that library is small, stable, and unlikely to change, I think it's OK.
For example, if you needed to build an entity for a domain that involved really complex math and you knew that there was a library that was good at doing that math, you get to deduce whether that library is performant, serving the needs of the customer and stable. If not, you may have to build it yourself.
I believe this is a matter of principle vs practice/rules. Principles
are more abstract and encompass more opportunities to help you decide how you should act in certain scenarios, while practices/rules
are pretty rigid and don't leave too much room for adjustment.
Instead of the practice/rule
of "entities are pure objects and data structures that don't have any dependencies", let's be reasonable; we could also write the uuid/v4
logic ourselves, but that would likely be wasted effort.
Here's how we're using lodash
to check for the property of an object:
import { has } from 'lodash'
...
const defaultCommentProps: CommentProps = {
...props,
points: has(props, 'points') ? props.points : 0,
votes: props.votes ? props.votes : CommentVotes.create([])
}
Looking at this again, it may be more performant to adjust the Lodash import to prevent loading all of it into memory:
import has from 'lodash/has'
...
const defaultCommentProps: CommentProps = {
...props,
points: has(props, 'points') ? props.points : 0,
votes: props.votes ? props.votes : CommentVotes.create([])
}
Hi @stemmlerjs,
Thanks for your clear explanation. I completely agree with the tradeoffs of injecting some dependencies directly into entities, but I didn't know how to justify that. With the "Stable Dependency Principle" it's easier to make these kinds of decisions 😄
@stemmlerjs would it not be a good idea to remove the direct dependency, and allow the injection of it at runtime?
First of all thank you for share your knowledge with the community. I'm new to concepts like clean architecture and DDD so this repo and your blog has helped me a LOT for understanding. 🎉
The last two weeks I've been reading Uncle Bob - "Clean Architecture" and has been hard to me get the concept of an Entity(Enterprise Business Rules). According to the book(p. 190):
I understand that they contain rules that are not application specific(Use Cases) and should not be affected by any external change, basically pure objects or data structures. So I thought that is broken when
lodash
is imported directly in theComment
entity.Also, I don't know if it's the same case in class
UniqueEntityID
when importing the libraryuuid/v4
and then importing it in base entityEntity
.Would this make entities dependent on the
lodash
anduuid/v4
libraries?