Skip to content

Commit cdee67e

Browse files
committed
Documentation for Stripe
1 parent 9d4c680 commit cdee67e

File tree

1 file changed

+125
-0
lines changed

1 file changed

+125
-0
lines changed

docs/stripe.md

Lines changed: 125 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,125 @@
1+
---
2+
title: Stripe (credits and local testing)
3+
---
4+
5+
# Stripe (credits and local testing)
6+
7+
PlanExe uses Stripe Checkout for buying credits. This page explains how the flow works, why credits may not update when running locally, and how to test without real money.
8+
9+
---
10+
11+
## How credits are applied
12+
13+
1. User clicks "Pay with Stripe" on the Account page and completes checkout on Stripe’s site.
14+
2. Stripe redirects the user back to your app (e.g. `/account?stripe=success`).
15+
3. **Credits are added only when Stripe sends a webhook.** Stripe calls your app at `/billing/stripe/webhook` with a `checkout.session.completed` event; the app then creates a `PaymentRecord` and a `CreditHistory` entry and updates `UserAccount.credits_balance`.
16+
17+
So the redirect back to `/account` does **not** by itself add credits. The webhook does.
18+
19+
---
20+
21+
## Why credits stay 0 on localhost
22+
23+
When the app runs on `localhost` (e.g. `http://localhost:5001`), Stripe’s servers cannot reach your machine. They need to POST to your webhook URL; `localhost` is only reachable from your own computer. So the `checkout.session.completed` webhook never hits your app, and credits are never applied.
24+
25+
**Fix:** use the Stripe CLI to forward webhooks from Stripe to your local server.
26+
27+
---
28+
29+
## Stripe CLI (forward webhooks to localhost)
30+
31+
The Stripe CLI is a separate developer tool (not listed with the [Stripe SDKs](https://docs.stripe.com/sdks)). It can tunnel webhook events to your local app.
32+
33+
### Where to find it
34+
35+
- **Install:** [Install the Stripe CLI](https://docs.stripe.com/stripe-cli/install)
36+
- **Overview:** [Stripe CLI](https://stripe.com/docs/stripe-cli)
37+
38+
### Install (macOS, Homebrew)
39+
40+
```bash
41+
brew install stripe/stripe-cli/stripe
42+
```
43+
44+
Other platforms: see the [install guide](https://docs.stripe.com/stripe-cli/install).
45+
46+
### Use it for webhooks
47+
48+
1. Log in (opens browser with a pairing code):
49+
50+
```bash
51+
stripe login
52+
```
53+
54+
2. Start forwarding webhooks to your app (adjust port if needed):
55+
56+
```bash
57+
stripe listen --forward-to localhost:5001/billing/stripe/webhook
58+
```
59+
60+
3. The CLI prints a **webhook signing secret** (`whsec_...`). Add it to your environment:
61+
62+
```env
63+
PLANEXE_STRIPE_WEBHOOK_SECRET='whsec_xxxxx'
64+
```
65+
66+
4. Restart the PlanExe frontend so it loads the new secret. Keep `stripe listen` running while you test payments.
67+
68+
Events sent to the CLI are forwarded to your local `/billing/stripe/webhook` and signed with the secret the CLI showed you. Your app can then verify the signature and apply credits.
69+
70+
---
71+
72+
## Testing without real money (test mode)
73+
74+
Use Stripe **test mode** so no real charges are made.
75+
76+
### 1. Use test API keys
77+
78+
In the [Stripe Dashboard](https://dashboard.stripe.com), turn on **Test mode** (toggle top right).
79+
80+
- Go to **Developers → API keys** ([dashboard.stripe.com/test/apikeys](https://dashboard.stripe.com/test/apikeys)).
81+
- Use the **Secret key** that starts with `sk_test_...` (not `sk_live_...`).
82+
83+
In your `.env` (or environment) for local/dev:
84+
85+
```env
86+
PLANEXE_STRIPE_SECRET_KEY='sk_test_...'
87+
```
88+
89+
Use the test key only for development; keep the live key for production.
90+
91+
### 2. Test card numbers
92+
93+
At checkout, use Stripe’s [test card numbers](https://docs.stripe.com/testing#cards). No real payment is processed.
94+
95+
| Result | Card number |
96+
|---------------|-------------------------|
97+
| Success | `4242 4242 4242 4242` |
98+
| Card declined | `4000 0000 0000 0002` |
99+
| Requires auth | `4000 0025 0000 3155` |
100+
101+
- **Expiry:** any future date (e.g. `12/34`).
102+
- **CVC:** any 3 digits (e.g. `123`).
103+
- **ZIP:** any value (e.g. `12345`).
104+
105+
### 3. Webhook secret when using the CLI
106+
107+
When you run `stripe listen`, the signing secret it prints is for **test** events. Put that value in `PLANEXE_STRIPE_WEBHOOK_SECRET`. In production you will configure a separate webhook endpoint in the Stripe Dashboard and use that endpoint’s secret.
108+
109+
---
110+
111+
## Environment variables
112+
113+
| Variable | Purpose |
114+
|----------|---------|
115+
| `PLANEXE_STRIPE_SECRET_KEY` | Stripe secret key (`sk_test_...` or `sk_live_...`). Required for checkout and webhooks. |
116+
| `PLANEXE_STRIPE_WEBHOOK_SECRET` | Webhook signing secret (`whsec_...`). Required to verify that webhook requests come from Stripe. For local dev, use the secret from `stripe listen`. |
117+
| `PLANEXE_STRIPE_CURRENCY` | Currency for Checkout (default: `usd`). |
118+
| `PLANEXE_CREDIT_PRICE_CENTS` | Price per credit in cents (default: `100`). |
119+
| `PLANEXE_PUBLIC_BASE_URL` | Public base URL used for Stripe success/cancel redirects (e.g. `http://localhost:5001` or your production URL). |
120+
121+
---
122+
123+
## See also
124+
125+
- [User accounts and billing (database)](user_accounts_and_billing.md) — tables and flows for credits, payments, and refunds.

0 commit comments

Comments
 (0)