# Paddle subscription integration ## Sandbox configuration Keep the Paddle API key and webhook secret server-side only. Do not put either value in the macOS application or commit them to Git. Required environment variables: ```dotenv PADDLE_API_KEY=pdl_sdbx_apikey_... PADDLE_API_URL=https://sandbox-api.paddle.com PADDLE_WEBHOOK_SECRET=... PADDLE_PERSONAL_PRODUCT_ID=pro_01m22q4c3vt7yvtv3h3zw1jbn0 PADDLE_PERSONAL_MONTHLY_PRICE_ID=pri_01m22q4cjx177krcpvdph7e2vy PADDLE_PERSONAL_ANNUAL_PRICE_ID=pri_01m22q4cs9sr5gshxp6j56nvmh PADDLE_PROFESSIONAL_PRODUCT_ID=pro_01m22q4d0s6y1557wsq9s7xw8n PADDLE_PROFESSIONAL_MONTHLY_PRICE_ID=pri_01m22q4d6h1yvr1frawtx51gy8 PADDLE_PROFESSIONAL_ANNUAL_PRICE_ID=pri_01m22q4dcndcdbzc20txadaz52 ``` Then run: ```bash php artisan migrate php artisan db:seed --class=Database\\Seeders\\PaddleCatalogSeeder php artisan config:clear ``` The seeder maps the four Paddle price IDs to licensing entitlements. Personal permits one active Mac; Professional permits three. ## Paddle notification destination Configure the sandbox notification destination to POST to: `https://YOUR-HOST/api/v1/webhooks/paddle` Copy the destination endpoint secret into `PADDLE_WEBHOOK_SECRET`. Subscribe to at least: - `subscription.created` - `subscription.updated` - `subscription.activated` - `subscription.trialing` - `subscription.canceled` - `subscription.paused` - `subscription.resumed` - `subscription.past_due` - `transaction.completed` - `transaction.refunded` ## Entitlement behavior - Trialing and active subscriptions are usable. - A scheduled end-of-period cancellation stays usable until Paddle changes the subscription to canceled. - Upgrades/downgrades update the entitlement on the existing licence key. - Canceled or paused subscriptions revoke the licence. - Past-due subscriptions retain access through Paddle's current billing period rather than being revoked on the first failed payment. - Paddle customer details are fetched server-side when the webhook does not carry customer email/name in custom data. ## Important The API key is required only on the licensing server. Use a sandbox key with the sandbox API URL. Live Paddle products/prices have different IDs and should be configured separately when moving to production.