Entities
Entities are domain objects with a unique identity that persists over time. Unlike Value Objects, entities are identified by their ID rather than their attributes.
Characteristics
- Identity: Each entity has a unique identifier
- Lifecycle: Entities are created, modified, and deleted
- Equality by ID: Two entities with the same ID are the same entity
- Encapsulation: Entities protect invariants through behavior methods
Structure
Entities extend EntityAbstract and implement EntityInterface:
class Book extends EntityAbstract implements EntityInterface
{
public function __construct(
private readonly IdInterface $id,
private readonly Title $title,
private readonly Author $author,
private readonly ISBN $isbn,
private BookStatus $status = BookStatus::Available
) {}
public function getId(): IdInterface
{
return $this->id;
}
public function markAsBorrowed(): void
{
$this->status = BookStatus::Borrowed;
}
}
Identity Types
Available implementations via IdInterface:
UuidV4- Random UUID (version 4)UuidV7- Timestamp-ordered UUID (version 7)Ulid- Lexicographically sortable identifierTimestampId- Base32-encoded timestamp ID
Entity vs Value Object
| Aspect | Entity | Value Object |
|---|---|---|
| Identity | Has unique ID | No identity |
| Equality | By ID | By value |
| Mutability | Can change | Immutable |
| Example | Book, User | Title, ISBN |
Best Practices
- Compose with Value Objects for entity properties
- Protect invariants in behavior methods
- Name methods after domain actions (
markAsBorrowed, notsetStatus) - One repository per aggregate root
See Also
- ID Generator - Generating unique identifiers