romanzipp/dto
Lightweight data transfer objects for PHP and Laravel. Define typed properties, cast and validate values, and convert DTOs to and from arrays with ease, keeping request and response data structured and type-safe.
?? fallbacks. This package supports the "explicit typed object at the edge, plain values inside" pattern, which is a roadmap-relevant architectural standard, not a library choice.composer require.Record the caveat in the decision log: 12 stars and 0 dependents is not an ecosystem signal — at best it is a code-quality signal. Any adoption means we are the maintainers now.
Consider it when:
__get/__set indirection so debugging and IDE navigation point at real code.Look elsewhere when:
spatie/laravel-data is the dominant Laravel answer and is the right comparison on maintenance risk alone; symfony/serializer if you are framework-agnostic. Plan to reassess if requirements grow in this direction rather than extending the package yourself.Verification checklist before adoption: confirm the actual API against source rather than the description (hydration, nested DTO handling, nullable/union behavior, collection support); confirm PHP 8.1/8.2/8.3+ support and current Laravel compatibility; confirm a test suite exists and runs; check PHPStan/Psalm friendliness; pin the commit and record the fork point in the ADR.
For executives: This is a small, free, MIT-licensed PHP utility that lets us define explicit, typed data structures at the boundaries of our application instead of passing loose arrays around. It is a low-cost, low-risk experiment — not a platform bet. The only real risk is not cost or licensing; it is that the project has negligible community adoption, so we would effectively own the code. Recommendation: pilot it on one bounded surface area, with the decision treated as reversible within a sprint.
For engineering leads: The appeal is the absence of magic — typed properties, no reflection-heavy hydration, no dynamic accessors, so debugging and IDE navigation stay honest. The trade-off is that we inherit maintenance. Before adopting: read the source (it is small), run the test suite, pin a commit, record the fork point, and isolate it behind an internal base class or adapter so it doesn't spread across the codebase. Start with one endpoint — request → validation → DTO → action → response — and define conventions for nested DTOs, dates, enums, and nullability before expanding. If requirements grow into validation, Eloquent casting, or nested collection mapping, stop and re-evaluate against spatie/laravel-data rather than building that ourselves.
For the delivery plan: integration effort is low; the cost is discipline, not code. Budget for conventions, one reference implementation, static analysis rules, and contract tests on hydration/serialization edge cases. Failure modes to watch: type errors on hydration, missing/extra fields, inconsistent nested handling, serialization drift against API resources, and Composer or PHP-version conflicts.
The one-line framing: Cheap to try, cheap to abandon, and cheap to own — worth a pilot, not worth a dependency you never look at again.
How can I help you explore Laravel packages today?