Polar
Polar supports subscriptions and a hosted customer portal. Use this page if you want Polar with portal access but no invoice previews.
Configuration
<?php
return [
'bnomei.klub.provider.handler' => \Bnomei\Klub\Provider\PolarProvider::class,
'bnomei.klub.providers.polar' => [
'secret' => fn() => env('POLAR_ACCESS_TOKEN'),
'webhook_secret' => fn() => env('POLAR_WEBHOOK_SECRET'),
'server' => fn() => env('POLAR_SERVER', 'sandbox'),
'organization' => fn() => env('POLAR_ORG_SLUG'),
'field' => 'polar',
],
];
Environment variables:
POLAR_ACCESS_TOKENPOLAR_WEBHOOK_SECRETPOLAR_SERVER(sandboxorproduction)POLAR_ORG_SLUG(optional, required for portal links)
Optional provider keys:
org_slugororg(aliases fororganization)webhook_tolerance(seconds, default300)checkoutfor provider-specific checkout payload overrides
Webhooks
Configure webhooks to POST /klub/webhooks/polar.
Polar uses standard webhook headers: webhook-id, webhook-timestamp, and webhook-signature. Klub validates them with POLAR_WEBHOOK_SECRET.
Portal and invoices
- Portal: supported when an organization slug is set (
organization,org_slug, ororg). - Invoice preview: not supported.
Notes
For portal access, set bnomei.klub.providers.polar.organization (or org_slug) to your Polar organization slug.
Plan data (local)
Polar uses local plans (providers.polar.plans or site plans YAML):
idshould be the Polar product price ID.unit_amountandcurrencyare recommended for consistent local catalog output.type(recurringorone_time) is recommended to help fallback mode detection.- Optional
product_id/productscan be passed through checkout overrides for advanced cases.
Gotchas
- Checkout requires at least one product in the payload. By default Klub uses the selected plan ID.
- The “active” subscription filter may exclude trial or cancel-at-period-end states.
- Portal URLs require the organization slug and correct
serversetting.
See Purchases for flow details.