crell/attributeutils
Utilities for PHP 8+ attributes: a cached AttributeReader that fetches and instantiates attributes on classes, methods, properties, and parameters, with helpers for repeatable attributes, inheritance, and object mapping. A lightweight base for attribute-driven config and dependency injection.
Architecture fit. crell/attributeutils is a PHP 8 attribute-reflection toolkit, not a framework or a persistence layer. It operates at the same altitude as native ReflectionClass and the Laravel service container, so its natural role is a declarative metadata engine: turning #[...] attributes on classes, properties, methods and parameters into typed, validated value objects that the rest of the application consumes. That fits well when the product wants configuration-as-code (e.g. #[Auditable], #[Sensitive], #[FeatureFlag], #[MapTo(...)]) instead of array config, but it is a poor fit for teams expecting Laravel convention to already provide the behavior. Laravel's own idioms (config files, policies, service providers, form requests) overlap heavily, so the package must earn its place in a subsystem that is genuinely metadata-heavy — typically DTO hydration/serialization, request-to-domain mapping, permission/audit annotations, or generating API docs from class shape.
Integration feasibility. Mechanically straightforward: Composer package, PSR-4, no framework coupling, no bootstrapping beyond registering analyzers in a service provider. It is purely additive — it does not replace the container, Eloquent, or routing. The real integration work is design work: deciding which attributes exist, writing the analyzer classes that implement its analysis interfaces, and deciding the caching boundary. Two gates must clear before any code is written: the registry reports license NOASSERTION and an unknown repository, so legal/IP provenance review is a hard prerequisite, and the supported PHP/Laravel version matrix must be confirmed from the actual composer.json rather than assumed.
Technical risk. Moderate and well-bounded. The codebase is small and the public surface is narrow, which limits blast radius. The dominant risks are (a) bus factor — a single maintainer and ~102 stars means low market validation and no commercial support; (b) pre-1.0 API drift — interface names and analyzer semantics can shift across minor versions; (c) cache correctness — the package's performance story depends entirely on how analysis results are cached, and a stale cache after deploy will produce wrong behavior silently; (d) reflection fragility — malformed attribute arguments throw at reflection time, which is easy to trigger and painful to debug in production.
Key questions. What is the actual license text, and is it compatible with our distribution model? Which PHP versions are declared, and does it run cleanly on the PHP we standardize on? Which analysis targets are supported (class / property / method / parameter / function) versus what our use case needs? What does the author recommend for cache invalidation across deploys? Is there a supported path to pin and audit upgrades? And finally: does this beat a thin in-house wrapper over native Reflection plus Symfony PropertyInfo — a build-vs-buy call a TPM should force early.
Stack fit. Works naturally with Laravel's service container: bind analyzer instances as singletons, inject Cache (or a precomputed array cache) into the analysis layer, and expose a single AttributeMetadataService-style facade to the rest of the app. Because the package is unopinionated, the team defines the conventions — attribute naming, target restrictions, default handling — and those conventions become the real integration artifact.
Migration path. There is no migration in the data sense; this is an additive capability. The correct path is greenfield inside one bounded context, never as a retrofit across the whole application. Pick the highest-value, lowest-blast-radius use case first — a serialization/DTO hydration pipeline or an audit-attribute scanner — and keep the package behind an internal interface so it remains swappable with an in-house implementation.
Compatibility. Confirm PHP version bounds and run the test suite against the Laravel versions we actually deploy. Watch for PHP minor-version deprecations in reflection APIs; a minor bump in the runtime should not be allowed to break the metadata layer unreviewed. Ensure no transitive dependency conflicts with our existing Composer graph.
Sequencing. (1) License and provenance clearance; (2) proof of concept in one module with a defined success metric (e.g. lines of config removed, or hydration correctness); (3) wrap behind an abstraction and add caching keyed on class name plus deploy/build identifier; (4) document attribute conventions and analyzer patterns; (5) expand to a second subsystem only after the first has survived a release cycle.
Maintenance. Low ongoing cost by dependency count, but the maintenance burden is ours, not the vendor's. Pin the version exactly, subscribe to releases, and budget a small recurring effort for upstream review. No formal deprecation or security policy should be assumed.
Support. Community/author-driven only. Operational ownership must be explicitly assigned to a named senior engineer; there is no one to escalate to at 2 a.m.
Scaling. Reflection is CPU-bound, so the layer must be treated as a build-time or cache-warm concern rather than something executed per request at volume. With a persistent cache the per-request cost approaches a lookup; without one it degrades linearly with class count and will show up in profiling. Horizontal scaling is fine provided the cache is shared and invalidated on deploy.
Failure modes. Expect: attribute constructor errors from malformed arguments; attributes applied to unsupported targets; stale cache after a deploy producing silently wrong metadata; anonymous or dynamically generated classes bypassing analysis; and analyzers returning silent defaults where an exception would be safer. Each needs an explicit policy — fail-fast in development, structured logging plus fallback in production, and cache versioning tied to release.
Ramp-up. Medium. The package itself is learnable in a day, but attribute-driven design is a genuine paradigm shift for developers used to Laravel config arrays, and the analyzer interface model is non-obvious until seen in an example. Plan for one owner, a written convention doc, and a working reference implementation before broad adoption.
How can I help you explore Laravel packages today?