/check-stripe
Audit Stripe integration. Output findings as structured report.
What This Does
- Check Stripe configuration (env vars, SDK)
- Audit webhook setup and handling
- Review subscription logic
- Check security practices
- Verify test/production separation
- Output prioritized findings (P0-P3)
This is a primitive. It only investigates and reports. Use /log-stripe-issues to create GitHub issues or /fix-stripe to fix.
Process
1. Configuration Check
# Stripe SDK installed?
grep -q "stripe" package.json 2>/dev/null && echo "✓ Stripe SDK" || echo "✗ Stripe SDK not installed"
# Environment variables
[ -n "$STRIPE_SECRET_KEY" ] || grep -q "STRIPE_SECRET_KEY" .env.local 2>/dev/null && echo "✓ STRIPE_SECRET_KEY" || echo "✗ STRIPE_SECRET_KEY missing"
[ -n "$STRIPE_WEBHOOK_SECRET" ] || grep -q "STRIPE_WEBHOOK_SECRET" .env.local 2>/dev/null && echo "✓ STRIPE_WEBHOOK_SECRET" || echo "✗ STRIPE_WEBHOOK_SECRET missing"
[ -n "$NEXT_PUBLIC_STRIPE_PUBLISHABLE_KEY" ] || grep -q "STRIPE_PUBLISHABLE_KEY" .env.local 2>/dev/null && echo "✓ Publishable key" || echo "✗ Publishable key missing"
[ -n "$CONVEX_WEBHOOK_TOKEN" ] || grep -q "^CONVEX_WEBHOOK_TOKEN=[a-f0-9]\\{64\\}$" .env.local 2>/dev/null && echo "✓ CONVEX_WEBHOOK_TOKEN" || echo "✗ CONVEX_WEBHOOK_TOKEN missing/invalid"
# Test vs Production keys
grep "STRIPE_SECRET_KEY" .env.local 2>/dev/null | grep -q "sk_test" && echo "✓ Using test key (dev)" || echo "⚠ Check key type"
2. Webhook Audit
# Webhook endpoint exists?
find . -path "*/api/*webhook*" -name "route.ts" 2>/dev/null | head -3
# Webhook signature verification?
grep -rE "constructEvent|stripe\.webhooks\.constructEvent" --include="*.ts" . 2>/dev/null | grep -v node_modules | head -3
# Webhook event handling?
grep -rE "checkout\.session\.completed|invoice\.paid|customer\.subscription" --include="*.ts" . 2>/dev/null | grep -v node_modules | head -5
3. Security Check
# Hardcoded keys?
grep -rE "sk_live_|sk_test_|pk_live_|pk_test_" --include="*.ts" --include="*.tsx" . 2>/dev/null | grep -v node_modules | grep -v ".env"
# Secret key exposure?
grep -rE "STRIPE_SECRET_KEY" --include="*.tsx" . 2>/dev/null | grep -v node_modules
# Proper server-side usage?
grep -rE "stripe\." --include="*.tsx" . 2>/dev/null | grep -v node_modules | grep -v "loadStripe" | head -5
4. Subscription Logic
# Subscription status handling?
grep -rE "subscription\.status|active|canceled|past_due|trialing" --include="*.ts" . 2>/dev/null | grep -v node_modules | head -5
# Customer portal?
grep -rE "createBillingPortalSession|billing.*portal" --include="*.ts" . 2>/dev/null | grep -v node_modules | head -3
# Price/product IDs?
grep -rE "price_|prod_" --include="*.ts" . 2>/dev/null | grep -v node_modules | head -5
5. CLI Profile Check
# Stripe CLI configured?
command -v stripe >/dev/null && echo "✓ Stripe CLI installed" || echo "✗ Stripe CLI not installed"
# Check profiles
stripe config --list 2>/dev/null | head -5 || echo "Stripe CLI not configured"
6. Local Dev Webhook Sync Check
# Does bun run dev auto-start stripe listener?
if grep -q "stripe.*listen" package.json 2>/dev/null; then
echo "✓ Auto-starts stripe listen"
# Is there a sync script?
if [ -f scripts/dev-stripe.sh ] && grep -q "print-secret" scripts/dev-stripe.sh 2>/dev/null; then
echo "✓ Webhook secret auto-sync configured"
else
echo "⚠ No webhook secret auto-sync - will get 400 errors after CLI restart"
fi
else
echo "○ Manual stripe listen (no auto-sync needed)"
fi
7. Token Parity (Next ↔ Convex)
If checkout succeeds but access stays locked, this is often token drift.
local_token=$(grep "^CONVEX_WEBHOOK_TOKEN=" .env.local 2>/dev/null | head -n1 | cut -d= -f2-)
convex_token=$(bunx convex env list 2>/dev/null | grep "^CONVEX_WEBHOOK_TOKEN=" | head -n1 | cut -d= -f2-)
if [ -n "$local_token" ] && [ -n "$convex_token" ] && [ "$local_token" = "$convex_token" ]; then
echo "✓ CONVEX_WEBHOOK_TOKEN matches (local ↔ Convex dev)"
else
echo "✗ CONVEX_WEBHOOK_TOKEN mismatch or missing (local ↔ Convex dev)"
fi
8. Deep Audit
Spawn stripe-auditor agent for comprehensive review:
- Checkout session parameters
- Subscription creation patterns
- Error handling in payment flows
- Idempotency key usage
- Customer creation/retrieval
Output Format
## Stripe Audit
### P0: Critical (Payment Failures)
- STRIPE_WEBHOOK_SECRET missing - Webhooks unverified (security risk)
- Hardcoded test key in production code
- CONVEX_WEBHOOK_TOKEN missing/mismatched - Payments may process but access never unlocks
### P1: Essential (Must Fix)
- Webhook signature not verified - Security vulnerability
- No customer portal configured - Users can't manage subscriptions
- Subscription status not checked on protected routes
- Missing STRIPE_SECRET_KEY in production env
### P2: Important (Should Fix)
- No idempotency keys on payment operations
- Subscription cancellation not handled gracefully
- No retry logic on transient Stripe errors
- Stripe CLI not using profiles (sandbox vs production)
- No auto-sync of local webhook secret - dev script auto-starts `stripe listen` but doesn't sync the ephemeral secret to `.env.local`. After CLI restart, webhooks will return 400.
### P3: Nice to Have
- Consider adding Stripe Tax
- Consider adding usage-based billing
- Add subscription analytics dashboard
## Current Status
- SDK: Installed
- Webhooks: Configured but unverified
- Subscriptions: Basic implementation
- Security: Issues found
- Test/Prod separation: Not enforced
## Summary
- P0: 2 | P1: 4 | P2: 4 | P3: 3
- Recommendation: Fix webhook verification and add customer portal
Priority Mapping
| Gap | Priority | |-----|----------| | Missing webhook secret | P0 | | Hardcoded keys | P0 | | Missing/mismatched CONVEX_WEBHOOK_TOKEN | P0 | | Webhook verification missing | P1 | | No customer portal | P1 | | Subscription status not checked | P1 | | No idempotency keys | P2 | | Poor error handling | P2 | | Missing CLI profiles | P2 | | No webhook secret auto-sync | P2 | | Advanced features | P3 |
Related
/log-stripe-issues- Create GitHub issues from findings/fix-stripe- Fix Stripe issues/stripe- Full Stripe lifecycle management/stripe-audit- Comprehensive Stripe audit/stripe-health- Webhook health diagnostics