USE FOR: Integrating Stripe payment processing into .NET applications using the Stripe.NET SDK. Use when implementing checkout flows, subscriptions, payment intents, customer management, webhook handling, and Connect platform payments.
DO NOT USE FOR: PayPal, Square, or Braintree payments (use their respective SDKs), cryptocurrency payments (use Coinbase Commerce or similar), or payment processing without Stripe as the provider.
USE FOR: Integrating Stripe payment processing into .NET applications using the Stripe.NET SDK. Use when implementing checkout flows, subscriptions, payment intents, customer management, webhook handling, and Connect platform payments.
DO NOT USE FOR: PayPal, Square, or Braintree payments (use their respective SDKs), cryptocurrency payments (use Coinbase Commerce or similar), or payment processing without Stripe as the provider.
[{"title":"Stripe API Reference (.NET)","url":"https://docs.stripe.com/api?lang=dotnet"},{"title":"Stripe .NET SDK GitHub Repository","url":"https://github.com/stripe/stripe-dotnet"},{"title":"Stripe.net NuGet Package","url":"https://www.nuget.org/packages/Stripe.net"}]
Stripe
Overview
Stripe.NET is the official .NET SDK for the Stripe payment platform. It provides strongly-typed service classes for every Stripe API resource including customers, payment intents, subscriptions, invoices, products, prices, and Connect accounts. The SDK handles serialization, error handling, retry logic, and idempotency. Stripe follows a payment intents workflow where the server creates a payment intent, the client confirms it with payment details, and webhooks notify the server of the final payment status. Stripe.NET targets .NET Standard 2.0+ and supports both synchronous and asynchronous operations.
Payment Intent Flow
Create and confirm payments using the Payment Intents API.
Store Stripe secret keys in environment variables or a secret manager (Azure Key Vault, AWS Secrets Manager) and never in appsettings.json or source code, using builder.Configuration["Stripe:SecretKey"] to load them at startup, because committed API keys grant full access to your Stripe account.
Use Payment Intents instead of Charges for all new payment flows, because Payment Intents handle SCA (Strong Customer Authentication), 3D Secure, and multi-step payment confirmations that Charges do not support, and Stripe recommends Payment Intents as the standard API.
Verify webhook signatures using EventUtility.ConstructEvent() with your webhook signing secret before processing any event, because unsigned webhooks can be forged by attackers to mark orders as paid without actual payment.
Make webhook handlers idempotent by checking whether the event has already been processed (store processed event IDs in a database) before performing side effects, because Stripe retries failed webhook deliveries and may send the same event multiple times.
Use Metadata on Payment Intents, Customers, and Subscriptions to store your application's identifiers (order IDs, user IDs, plan names) so that webhook handlers can correlate Stripe events back to your domain objects without additional database lookups.
Set PaymentBehavior = "default_incomplete" on subscriptions and expand latest_invoice.payment_intent to get the client secret for frontend confirmation, rather than using allow_incomplete which creates subscriptions without collecting payment.
Handle StripeException by switching on StripeError.Type to differentiate between card errors (show to user), invalid request errors (log and fix), rate limit errors (retry with backoff), and authentication errors (configuration problem), rather than showing raw Stripe error messages to end users.
Cancel subscriptions with CancelAtPeriodEnd = true rather than immediate cancellation, so that customers retain access until the end of their billing period and can reactivate without creating a new subscription.
Use RequestOptions with IdempotencyKey for payment-critical operations (creating payment intents, confirming payments, creating subscriptions) to prevent duplicate charges when retrying failed network requests, setting the key to a deterministic value derived from the order or transaction.
Test with Stripe's test card numbers (4242424242424242 for success, 4000000000000002 for decline) and the Stripe CLI for webhook testing (stripe listen --forward-to localhost:5000/api/payments/webhook), rather than using live mode for development, because test mode operations do not process real charges and provide detailed error simulation.