filagora/filagora-memberships
Filagora Memberships is a Laravel package for adding membership plans and subscriber management to your application. Define tiers, assign memberships to users, and control access to features or content through a simple, flexible API. Keep plan logic clean, extensible, and easy to integrate with exis...
Architecture fit. This is a Laravel integration package that bridges a memberships domain (Filagora\Memberships) into a forums package's announcement-targeting rule registry. The architecture is a standard Laravel service-provider + contract-binding pattern: the host application binds an access checker, and the memberships package contributes a membership targeting rule that the forums package consumes when resolving who should see a given announcement. For a TPM, the relevant takeaway is that this is glue code with a small public surface — one rule class and one registration path — rather than a framework or a standalone subsystem. That makes it cheap to adopt and cheap to remove, which materially lowers the cost of being wrong.
Integration feasibility. The v0.1.1 changes actively improve feasibility. The prior behavior registered the membership rule during application boot, which meant the package resolved the host's access checker at a point in the lifecycle where the container may not yet be fully bound. That is a well-known failure shape in Laravel: it breaks static-analysis bootstraps, package-discovery-adjacent tooling, config/route caching flows, and any harness that boots the container without the full host application. Moving registration to first use of the rule registry converts a hard boot-time dependency into a lazy one, so the package no longer imposes a binding order on the host. This is the correct fix direction and removes the single most likely source of "it won't start" tickets.
Technical risk. Moderate but well-contained, concentrated in three areas:
final removal as an extension contract. Making MembershipRule non-final signals that host subclassing is now a supported customization path. Subclassing is a weaker contract than an interface: hosts override methods whose signatures and semantics the maintainer has not committed to. This is a long-term compatibility liability, not a v0.1.1 defect.membership rule registered first — including a host's own — is kept. That gives hosts an override mechanism, but it makes effective behavior depend on when the registry is first touched rather than on an explicit priority. Under long-lived workers this ordering is established once per process, so behavior can differ between a fresh boot and a warm worker.Key questions for the maintainer. What is the supported Laravel and PHP version matrix, and is it CI-enforced? Does the lazy registration guarantee hold under php artisan config:cache, optimize, queue workers, and Octane/RoadRunner? Is subclassing MembershipRule officially supported, and what is the policy for parent-class changes in 0.x releases? Is there an interface or named extension point planned to replace subclassing before 1.0? What does the host's access-checker contract look like, and what happens if it is bound but returns an unexpected result? What is the test suite's coverage of the boot-vs-lazy paths?
Stack fit. The package assumes Laravel's service container, package auto-discovery, and a host that owns both a memberships domain and a forums package exposing a targeting-rule registry. It is a poor fit for any application that has not already adopted the Filagora forums package, and it is a poor fit for non-Laravel or non-container-managed PHP. For applications already inside that ecosystem, integration is a composer require plus a container binding — realistically hours, not weeks.
Migration path. Because this is v0.1.1 with no prior assessment, there is no migration in the upgrade sense; the work is first-time adoption. The sequence is: (1) require the package at an exact version; (2) confirm the forums package version exposes a rule registry and that the registry is reachable; (3) bind the host's access checker in a service provider's register() method — not boot(), and not in a closure that resolves the checker eagerly; (4) verify the membership rule appears in the registry on first use; (5) only then add announcement targeting rules that depend on it. If a host already registers its own rule named membership, decide deliberately whether to keep the host rule (which now wins by being first) or defer to the package rule.
Compatibility. The two changes are individually low-risk but should be verified, not assumed. The lazy-registration change is observable if the host inspects the registry before the forums package has been used — code that asserted the rule's presence at boot will now see an empty or partial registry. Any host test that boots the application and immediately asserts on targeting rules needs to be revised to trigger registry resolution first. The final removal is source-compatible in both directions; the compatibility concern is forward-looking, since hosts that subclass inherit whatever the parent does next.
Sequencing. Land the dependency and the access-checker binding first, with a smoke test asserting the rule resolves on demand. Defer subclassing MembershipRule until the maintainer clarifies the extension policy — there is no reason to take on that coupling on day one when configuration may suffice. Run the full suite against config:cache and, if applicable, an Octane-flavored worker before rollout. Pin the version explicitly in composer.json rather than using a caret constraint that would auto-adopt future 0.x releases.
Maintenance. The surface is small: one rule class, one registration path, no migrations, no scheduled jobs, no external services, no persistence of its own. Ongoing cost is dominated by dependency tracking rather than by the package's own code — the team must watch the forums package and the memberships domain, since a change in either could invalidate assumptions here. Set a quarterly review to re-evaluate the version pin, and treat any 0.x minor bump as requiring a read of the changelog rather than an automatic update.
Support. Support burden should be near zero in steady state, with the caveat that failures will present inside the host application's boot path rather than inside this package, which makes triage ambiguous. Whoever is on call should know that "application fails to start after a composer update" is a plausible symptom of this dependency. The v0.1.1 fix removes the most common cause, but the diagnostic path should be documented anyway.
Scaling. Negligible. Rule evaluation is in-process and inexpensive; the registry is built once per process and reused. There is no per-request I/O, no network hop, and no queue interaction. Scaling concerns, if they ever appear, will originate in the forums package's announcement queries, not here.
Failure modes. Four to plan for. Container binding absent — the original v0.1.1 bug; now deferred to first use rather than boot, which means it surfaces as a runtime error during a request instead of a clean startup failure. This is a better trade for tooling but a worse one for debuggability: the failure moves from deploy time to traffic time, so ensure the smoke test exercises rule resolution. Registry resolved too early by host code — produces an incomplete registry and silently missing targeting rules. Subclass drift — a host subclass overriding a method whose parent semantics change in a later 0.x release, with no deprecation warning. Worker state — under Octane or a long-lived queue worker, the registry and any host override decision are frozen at first touch per process, so a code deploy that changes rule registration requires a worker restart to take effect.
Ramp-up. Low. A Laravel-fluent engineer can read the whole package in an afternoon. The genuinely non-obvious part is lifecycle, not logic: understanding why lazy registration matters, and knowing that register() is for bindings while boot() is for behavior that depends on other packages. Budget a short pairing session or a written note on that distinction, because it is the exact class of mistake this release was fixing, and a host integrator can reintroduce it by resolving the access checker eagerly in their own provider. Overall recommendation: adopt for evaluation with an exact version pin, do not subclass until the extension policy is confirmed, and gate rollout on a test that asserts the membership rule resolves on demand.
How can I help you explore Laravel packages today?