theofidry/eloquent-serializer
A lightweight serialization layer for Laravel Eloquent models. Define dedicated serializer classes to control which attributes and relationships are exposed, then turn models, collections, and paginated results into clean arrays for APIs and JSON responses.
Architecture fit: This release clarifies what the package actually is: a Laravel package (service provider with auto-discovery, ~5.5.0 Laravel constraint) that swaps Symfony Serializer in as the normalization/denormalization layer over Eloquent models. That corrects the prior framing—it is not a bridge for Symfony apps using Eloquent, it is an alternative serialization stack for Laravel apps that prefer Serializer's normalizer/encoder/context model over toArray/toJson, API Resources, and casts. The fit question therefore narrows to: do we have a Laravel application whose serialization requirements (context-driven groups, versioning, encoder negotiation, denormalization into models) genuinely exceed what API Resources provide? Laravel 5.5-era apps with heavy DTO/serialization needs were the design target. For any current Laravel application this remains architecturally redundant: first-party API Resources, model casts, and JsonResource cover the same ground with supported code. It is still a niche tool, just niche in a different direction than previously assessed.
Integration feasibility: The wiring got marginally easier—auto-discovery removes the manual provider registration, and the added Symfony normalizers mean the serializer service is more complete out of the box. But this release does not improve feasibility against a supported stack, it documents the ceiling. The constraints are now explicit and hard: PHP ^7.1, Laravel ~5.5.0 (caret-tilde, i.e. >=5.5.0 <5.6.0—not 5.6, not 6+, not 8/10/11/12), Symfony ^3.4 || ^4.0. Composer will refuse to install this alongside any current Laravel. It is a PHP 7.1 / Laravel 5.5 artifact, and the PHPUnit ^6.4 bump confirms the test suite is pinned to that era and will not run on modern PHPUnit without rework. Adoption still requires a fork or reimplementation; it just requires it more emphatically.
Technical risk: Unchanged at High, with the lifecycle evidence now stronger rather than weaker. A release that moves PHP from ^7.0 to ^7.1 and Laravel to ~5.5.0 is consolidation within an already-obsolete band, not modernization—there is still no PHP 8, no Laravel 6+, no Symfony 5+, and no getSupportedTypes() support. Secondary risks persist: denormalization is a mass-assignment surface requiring explicit attribute/relation allow-lists; recursive relation normalization invites N+1 queries and circular references; cast/date/hidden-visible semantics can diverge from native Laravel output and drift the API contract if this becomes the boundary. Added normalizers widen the surface slightly—more encoders/normalizers registered by default means more implicit behavior to audit.
Key questions:
ObjectNormalizer subclass or a JsonResource equivalent lower than the fork? For a small normalizer, usually yes.Stack fit: Fit is now precisely bounded: a Laravel 5.5.x application on PHP 7.1–7.4 that has standardized on Symfony Serializer contracts. Outside that band—Laravel 5.6 through 12, or PHP 8.x—the package does not install. It remains a poor fit for greenfield Laravel, for Doctrine-based Symfony, and for teams without Serializer expertise.
Migration path: Adoption-by-fork only. Two routes: (1) vendor the package under our namespace, relax the ~5.5.0/^3.4||^4.0 constraints to our actual versions, port the normalizer interfaces to Symfony 5/6/7 (getSupportedTypes()), and assign an explicit owner; or (2) skip the dependency and implement the normalizer directly on AbstractNormalizer/ObjectNormalizer. Given the code is a few hundred lines and every line would need touching during a port anyway, route 2 remains the better trade—the fork's only lasting value is the Eloquent attribute/cast/relation traversal logic, which is the part most likely to need rewriting against modern Eloquent.
Compatibility: The release gives us a definitive floor and ceiling rather than removing uncertainty. Build the matrix as PHP 7.1–7.4 (as-shipped) versus PHP 8.1/8.2/8.3 (requires port), crossed with Laravel 5.5 (supported) versus 8/10/11/12 (requires port), crossed with Symfony Serializer 3.4/4.0 (supported) versus 5.4/6.x/7.x (requires port). Expect breakage first at the normalizer interface level, then at Eloquent attribute/cast/relation APIs, then in the test suite (PHPUnit 6.4 → 9/10).
Sequencing:
Maintenance: Total ownership, unchanged. Archived repository, no upstream patches, no PHP 8 or Symfony 5+ work, no CVE response. This release is the last known state: PHP 7.1, Laravel 5.5, Symfony 3.4/4.0, PHPUnit 6.4. Budget for dependency-bump reviews, interface-drift fixes, test-suite modernization, and security review of the denormalization path. Small code surface keeps steady-state cost low, but the test-suite pin means even running the existing tests on a modern toolchain is work.
Support: None externally. Twelve stars, zero dependents, no community, no Stack Overflow corpus, no upstream fixes to cherry-pick. The added documentation and Travis updates are internal housekeeping in a dead repo, not a support signal. Internal documentation and a named owner are prerequisites.
Scaling: Unchanged—CPU-bound object-graph traversal on Symfony Serializer, with reflection and metadata overhead. Watch lazy-loaded relation traversal firing queries during normalization (invisible N+1), and unbounded recursion on bidirectional relations. Cache normalizer metadata, eager-load explicitly before normalizing, set circular-reference and depth limits, and benchmark against native Laravel array conversion before committing high-volume endpoints. The newly registered default normalizers add a small fixed per-serialization cost worth measuring.
Failure modes:
~5.5.0 Laravel pin on any non-5.5 application.Ramp-up: Low for engineers fluent in Symfony Serializer and Eloquent—half a day to read the code, one to two days to spike and write contract tests. Higher for Laravel-only teams unfamiliar with Serializer's normalizer/encoder/context model. The real cost is not learning the package; it is the organizational work of accepting permanent ownership of an archived, version-pinned dependency in exchange for a serialization convenience that first-party Laravel facilities already largely provide.
How can I help you explore Laravel packages today?