Stripe ist der De-facto-Standard für Online-Zahlungen. Mit Claude Code lassen sich Payment Intents, Webhooks und Subscriptions in Minuten statt Stunden aufsetzen. Claude Code
1. Stripe SDK Setup (Node.js / TypeScript)
Zuerst installieren wir das offizielle Stripe Node.js SDK und typsichere Typen. Claude Code erkennt automatisch das Projektsetup und schlägt die passende Konfiguration vor.
npm install stripe
npm install -D @types/stripe
import Stripe from 'stripe';
if (!process.env.STRIPE_SECRET_KEY) {
throw new Error('STRIPE_SECRET_KEY fehlt in .env');
}
export const stripe = new Stripe(process.env.STRIPE_SECRET_KEY, {
apiVersion: '2025-01-27.acacia',
typescript: true,
});
Niemals Stripe-Keys hardcoden. Claude Code liest automatisch aus .env.local und ergänzt fehlende Keys mit einem Hinweis.
2. Payment Intent erstellen und bestätigen
Der Payment Intent ist das Herzstück jeder Stripe-Transaktion. Er repräsentiert eine Zahlungsabsicht und verwaltet den gesamten Zahlungsfluss — von der Erstellung bis zur Bestätigung.
import { NextRequest, NextResponse } from 'next/server';
import { stripe } from '@/lib/stripe';
export async function POST(req: NextRequest) {
const { amount, currency, metadata } = await req.json();
// Betrag immer in kleinster Einheit (Cent)
const paymentIntent = await stripe.paymentIntents.create({
amount: Math.round(amount * 100),
currency: currency ?? 'eur',
automatic_payment_methods: { enabled: true },
metadata,
});
return NextResponse.json({
clientSecret: paymentIntent.client_secret,
});
}
import { useStripe, useElements, PaymentElement } from '@stripe/react-stripe-js';
export function CheckoutForm() {
const stripe = useStripe();
const elements = useElements();
const handleSubmit = async (e: React.FormEvent) => {
e.preventDefault();
if (!stripe || !elements) return;
const { error } = await stripe.confirmPayment({
elements,
confirmParams: {
return_url: `${window.location.origin}/success`,
},
});
if (error) console.error(error.message);
};
return (
<form onSubmit={handleSubmit}>
<PaymentElement />
<button type="submit">Jetzt bezahlen</button>
</form>
);
}
3. Webhooks: Events sicher verarbeiten Webhook
Webhooks sind entscheidend für zuverlässige Zahlungsverarbeitung. Stripe signiert jede Nachricht mit einem Secret — Claude Code prüft diese Signatur automatisch.
Webhook-Endpoints IMMER mit stripe.webhooks.constructEvent() verifizieren. Ohne Signaturprüfung können Angreifer gefälschte Events senden.
import { NextRequest, NextResponse } from 'next/server';
import { stripe } from '@/lib/stripe';
import Stripe from 'stripe';
export async function POST(req: NextRequest) {
const body = await req.text();
const sig = req.headers.get('stripe-signature')!;
let event: Stripe.Event;
try {
event = stripe.webhooks.constructEvent(
body, sig,
process.env.STRIPE_WEBHOOK_SECRET!
);
} catch (err) {
return NextResponse.json({ error: 'Ungültige Signatur' }, { status: 400 });
}
switch (event.type) {
case 'payment_intent.succeeded':
await handlePaymentSuccess(event.data.object);
break;
case 'payment_intent.payment_failed':
await handlePaymentFailed(event.data.object);
break;
case 'customer.subscription.updated':
await handleSubscriptionUpdate(event.data.object);
break;
default:
console.log(`Unbehandeltes Event: ${event.type}`);
}
return NextResponse.json({ received: true });
}
Wichtige Webhook-Events im Überblick
payment_intent.succeeded— Zahlung erfolgreich abgeschlossenpayment_intent.payment_failed— Zahlung fehlgeschlagen (Retry-Logik)customer.subscription.created— Neue Subscription angelegtcustomer.subscription.deleted— Subscription gekündigtinvoice.payment_succeeded— Wiederkehrende Zahlung erfolgreichinvoice.payment_failed— Wiederkehrende Zahlung fehlgeschlagen
4. Stripe Checkout: Fertige Zahlungsseite
Stripe Checkout ist eine von Stripe gehostete Zahlungsseite — optimiert für Conversion, PCI-konform und sofort einsatzbereit. Claude Code erstellt die Session-API in Sekunden.
import { stripe } from '@/lib/stripe';
import { NextResponse } from 'next/server';
export async function POST(req: Request) {
const { priceId, customerId } = await req.json();
const session = await stripe.checkout.sessions.create({
mode: 'payment', // oder 'subscription'
customer: customerId,
line_items: [{
price: priceId,
quantity: 1,
}],
success_url: `${process.env.NEXT_PUBLIC_URL}/success?session_id={CHECKOUT_SESSION_ID}`,
cancel_url: `${process.env.NEXT_PUBLIC_URL}/cancel`,
allow_promotion_codes: true,
billing_address_collection: 'auto',
automatic_tax: { enabled: true },
});
return NextResponse.json({ url: session.url });
}
Stripe Checkout eignet sich für schnelle Implementierungen. Payment Intents bieten mehr Kontrolle über das UI. Claude Code empfiehlt Checkout für 80% der Use Cases.
5. Subscriptions und Recurring Billing Subscription
Wiederkehrende Zahlungen sind das Fundament von SaaS-Produkten. Stripe Subscriptions verwalten automatisch Rechnungen, Zahlungsversuche und Dunning.
import { stripe } from './stripe';
/** Neuen Kunden + Subscription anlegen */
export async function createSubscription({
email, name, priceId, trialDays = 14
}: {
email: string; name: string;
priceId: string; trialDays?: number;
}) {
// 1. Customer erstellen (idempotent via email lookup)
const existing = await stripe.customers.list({ email, limit: 1 });
const customer = existing.data[0] ??
await stripe.customers.create({ email, name });
// 2. Subscription mit Trial erstellen
const subscription = await stripe.subscriptions.create({
customer: customer.id,
items: [{ price: priceId }],
trial_period_days: trialDays,
payment_behavior: 'default_incomplete',
expand: ['latest_invoice.payment_intent'],
});
return { subscription, customerId: customer.id };
}
/** Subscription sofort kündigen */
export async function cancelSubscription(subscriptionId: string) {
return stripe.subscriptions.cancel(subscriptionId);
}
/** Plan upgraden / downgraden (Proration) */
export async function changePlan(subscriptionId: string, newPriceId: string) {
const sub = await stripe.subscriptions.retrieve(subscriptionId);
return stripe.subscriptions.update(subscriptionId, {
items: [{ id: sub.items.data[0].id, price: newPriceId }],
proration_behavior: 'create_prorations',
});
}
6. Stripe Portal für Kundenverwaltung
Das Stripe Customer Portal ermöglicht Kunden, ihre Subscriptions selbst zu verwalten — Kreditkarte ändern, Plan wechseln, kündigen. Kein eigenes UI nötig.
import { stripe } from '@/lib/stripe';
import { auth } from '@/lib/auth';
import { NextResponse } from 'next/server';
export async function POST(req: Request) {
const user = await auth();
if (!user) return NextResponse.json({ error: 'Nicht autorisiert' }, { status: 401 });
const session = await stripe.billingPortal.sessions.create({
customer: user.stripeCustomerId,
return_url: `${process.env.NEXT_PUBLIC_URL}/dashboard`,
});
return NextResponse.json({ url: session.url });
}
Checkliste: Stripe-Integration mit Claude Code
- Stripe SDK installieren und mit Umgebungsvariablen konfigurieren
- Payment Intent API-Route erstellen (serverseitig, Keys niemals im Client)
- Webhook-Endpoint mit Signaturverifizierung implementieren
- Stripe Checkout Session für einfache Einmalzahlungen einrichten
- Subscription-Logik mit Customer-Lookup (idempotent) aufbauen
- Customer Portal aktivieren im Stripe Dashboard
- In Produktion: Stripe CLI für lokales Webhook-Testing nutzen
Nutze stripe listen --forward-to localhost:3000/api/webhooks/stripe um Webhook-Events lokal zu empfangen. Claude Code konfiguriert das automatisch in der Entwicklungsumgebung.
Stripe in deinem Projekt integrieren?
Claude Code setzt Payment Intents, Webhooks und Subscriptions in Minuten auf — mit echtem TypeScript, Tests und Webhook-Handler.
Kostenlos testen →