ASP.NET Core 9 Web API demonstrating payment mimicking patterns: idempotent APIs, webhook signature verification, async background workers, and MongoDB integration. Built a payment-mimicking ASP.NET Core 9 Web API using MongoDB, featuring idempotent payment endpoints, verified webhooks, and async background workers for reliable, fault-tolerant payment flows.
Simulates order-to-payment workflow with patterns used by Stripe, PayPal, and Shopify:
- Client creates order →
POST /api/orders(idempotency key required) - Order saved to MongoDB (
Pendingstatus) - Background worker simulates payment (5s delay)
- Worker POSTs signed webhook →
/api/webhooks/payments - Signature verified (HMAC SHA-256)
- Order status →
Paid, event stored for audit
Idempotency (Stripe-style)
Idempotency-Keyheader required- Response cached in MongoDB
- Duplicate requests return cached response
- Unique index prevents concurrent duplicates
Webhook Security
- HMAC SHA-256 signatures
- Timestamp-based replay protection
- Constant-time comparison (timing attack prevention)
Async Processing
- In-memory
Channel<T>job queue (⚠️ not persistent) - Background worker (
IHostedService) - Event persistence for audit trail
Ecommerce.Api/
├── Controllers/ # OrdersController, WebhooksController
├── Services/ # OrderService, IdempotencyService, WebhookSigner, PaymentSimulationWorker
├── Data/ # MongoContext, Collections
└── Domain/ # Order, PaymentEvent, IdempotencyRecord
1. Start MongoDB
docker run -d --name mongo -p 27017:27017 mongo:latest2. Run API
cd Ecommerce.Api && dotnet runServer: https://localhost:5001 | Swagger: https://localhost:5001/swagger
3. Test
# Create order
curl -X POST https://localhost:5001/api/Orders \
-H "Content-Type: application/json" \
-H "Idempotency-Key: test-001" \
-d '{"orderNumber": "ORD-001", "amount": 99.99, "currency": "USD"}' -k
# Run automated tests
chmod +x test-api.sh && ./test-api.sh
# Check MongoDB (wait 5s for payment processing)
docker exec mongo mongosh ecommerce_local --eval 'db.orders.find().pretty()'POST /api/orders - Create order (requires Idempotency-Key header)
{"orderNumber": "ORD-001", "amount": 99.99, "currency": "USD"}POST /api/webhooks/payments - Webhook callback (requires X-Signature header)
Edit appsettings.Development.json:
{
"Mongo": {
"ConnectionString": "mongodb://localhost:27017",
"Database": "ecommerce_local"
},
"Webhook": {
"SharedSecret": "super_secret_change_me",
"ToleranceSeconds": 300
}
}⚠️ In-memory job queue (jobs lost on restart)⚠️ No retry policies or health checks⚠️ No query endpoints for order status
Production needs: Persistent outbox (MongoDB-backed queue), Polly retry policies, health checks, observability.
MIT License