LarsaSub is launching soon. Purchases and account registration open shortly.

Documentation for larsasub v0.38.2. On an older version? Your release notes ship with the package (CHANGELOG.md).

Filament integration

Filament admin screens for LarsaSub ship as a separate package, peters-development/larsasub-filament: a panel plugin with resources for plans, subscriptions, charges, reminder series and payment methods, plus three dashboard widgets. Read this page when you run a Filament panel and want to manage billing from it.

Installation

The plugin installs from the same private repository as the core package and is included with every license tier.

composer require peters-development/larsasub-filament

Then register the plugin on the panel that manages billing:

use Filament\Panel;
use PetersDevelopment\LarsaSub\Filament\LarsaSubPlugin;

public function panel(Panel $panel): Panel
{
    return $panel
        // ...
        ->plugin(LarsaSubPlugin::make());
}

That is all: five resources appear in a "Billing" navigation group ("Facturatie" in Dutch) and three widgets are registered on the panel's dashboard. The service provider is auto-discovered.

Requirement Version
PHP ^8.3
Filament ^5.7
peters-development/larsasub The same major.minor as the plugin (plugin 0.38 requires ^0.38)

Releases are paired with the core package: plugin 0.38.x is the companion of larsasub 0.38. Update the two together.

What it gives you

Subscription lifecycle changes go through LarsaSub's services, and the forms save through the models, so the models' own validation and activity logging apply. The widgets aggregate with the package's own scopes. The plugin holds no money logic of its own.

Resources

Resource Model What you can do
Subscriptions (plans) Subscription Create and edit plans: active flag, name, description and content, internal note, features, availability window, duration, billing interval, cancellation and renewal notice, automatic renewal, price, per-plan VAT rate (a change reaches running subscriptions without a rate of their own from their next charge), introduction period and price. Change targets are attached and detached in a relation manager. In Connect mode a section for the per-plan application fee override (fee_type, fee_value) appears. There is no delete action.
Billable subscriptions BillableSubscription List with filters (active, upcoming, deactivated, trashed), a detail page and a limited edit form: name and description, end date, duration, notice and renewal terms, whether it is charged, billing interval, price, introduction, and a VAT rate for this subscription only (empty follows the plan). The start date moves only through the action below. The detail page shows the VIES status of the registration's VAT number and the paid-through date. Cost lines and charges are listed in relation managers. Subscriptions cannot be created here: they come from the billing flow.
Recurring charges RecurringCharge Read-only, with filters (needs attention, paid, superseded, chargeback follow-up, trashed) and a red navigation badge counting the charges that need attention. The detail page shows the VAT treatment, the VIES consultation number the VAT decision rested on, why the charge is not payable, the platform fee (Connect mode), its chargeback follow-ups and its reminder series.
Reminder series DunningCase Read-only list and detail of the reminder series: status, why it is paused or closed, the schedule beside the steps taken. Filters by status, origin and "paused for over 7 days". While the series and the scheduler are on, a navigation badge counts those long pauses.
Payment methods PaymentMethod Create and edit methods, including the active, single and recurring flags. There is no delete: payments reference their method, so deactivate it instead.

Two details come back from the core package:

Actions

Action Where What it does
Change plan Billable subscription (row menu and detail page) BillableSubscriptionService::changeSubscription() to one of the plan's allowed change targets, with the subscription's current payment method. The unused part of the period becomes credit.
Cancel Billable subscription cancelSubscription(), respecting the plan's notice period, with an optional reason.
Terminate Billable subscription terminateSubscription(): ends the subscription at once, with an optional reason.
Move start date Billable subscription moveStartDate(), which moves the cost lines with it. Disabled once the subscription has been charged; end the cost lines and add them again from the right date instead.
Mark handled Recurring charge (needs attention only) Clears the attention flag through clearNeedsAttentionByKey(), conditional on the reason you read still being the current one. For a charge that was never submitted to Mollie, the next larsasub:execute-charges run submits it. A failed payment is not collected again: the customer pays it on the payments page (manual payment). An unresolved claim is looked up by reconciliation. The confirmation explains what clearing means for the marker the flag carries. Requires the update ability.
Close series Reminder series (not yet resolved) DunningService::close(): ends the reminders for that charge for good. It does not change whether the charge can be paid. Requires the close ability.

Each action reports a failure as a Filament notification carrying the service's message.

Mark handled is not a repair. Clearing the flag books nothing and regenerates no invoice (that is larsasub:generate-missing-invoices). On a charge flagged mandate-registration:failed it also switches the scheduler's own mandate recovery off for that charge, and a reminder series that the flag paused continues once the charge is payable again.

Widgets

Widget Shows
Stats overview MRR, active subscriptions, charges that need attention (links to the charges list), and the planned amount not yet submitted to the provider. Chargeback follow-ups are not counted as planned revenue.
Revenue per month Money received from recurring charges and from single payments, last 12 months: the charged amount less standing chargebacks and completed refunds, in the month the payment was paid.
Subscription flow Activations against cancellations per month, last 12 months.

MRR is, per active, charged subscription, its price_amount divided by its billing_interval_months, plus the amount of its cost lines active today; introduction prices and proration are left out. A plan's price_amount is the price per billing period, so a quarterly plan counts a third of it; a cost line's amount is already monthly.

Planned amount. Subscription charges are planned on their collection day and normally submitted in the same scheduler run, so this figure mostly holds standalone charges planned ahead and charges no execution run has taken up yet.

Configuration

Publish the configuration only if you want to change it:

php artisan vendor:publish --tag=larsasub-filament-config
// config/larsasub-filament.php
return [
    'resources' => [
        'subscriptions' => true,
        'billable_subscriptions' => true,
        'recurring_charges' => true,
        'dunning_cases' => true,
        'payment_methods' => true,
    ],
    'widgets' => [
        'stats_overview' => true,
        'revenue_chart' => true,
        'subscription_flow_chart' => true,
    ],
    'navigation' => [
        'group' => null, // null = the translated default ("Billing" / "Facturatie")
    ],
];

These toggles apply to every panel. To leave something out of one panel only, use the plugin's fluent methods; they apply on top of the config:

use PetersDevelopment\LarsaSub\Filament\LarsaSubPlugin;
use PetersDevelopment\LarsaSub\Filament\Resources\RecurringCharges\RecurringChargeResource;

LarsaSubPlugin::make()
    ->except([RecurringChargeResource::class]) // the plugin's resource or widget classes
    ->withoutWidgets();                         // no widgets on this panel

Authorization

The plugin adds no authorization layer of its own. LarsaSub's model policies, which the core package always registers, apply to every resource and action, configured under larsasub.policies.* (Policies). With the default policy configuration, plans, payment methods and reminder series are admin-only, and changing a charge or a subscription requires an admin. Who is an admin is larsasub.policies.admin_role: empty means nobody, and the resources then deny everyone.

Access to the panel itself is yours to decide, through Filament's own canAccessPanel().

Admin links in company mails

On boot the plugin registers the panel with LarsaSub's AdminUrlResolver, so the "go to admin" button in company mails links to the subscription or charge page in this panel. A model without its own page links to the panel's home; when the URL cannot be generated (a queued mail outside any request), the link falls back to the application's root URL.

This registration answers for the platform audience only. In Connect mode, tenant admins receive the same company mails and get their link from notifications.tenant_admin_url instead; see The admin button knows who is reading.

Scope and limits

Not using Filament?

The Nova companion covers the same ground and more. Without either admin panel, the bundled management dashboards handle plans, subscribers, charges and invoices: in Connect mode as the tenant owner's view, in simple mode as operator management through larsasub.policies.admin_role.