Over the last 1–2 months, I stopped chasing new side-project ideas and decided to solve a frustration I’ve had for a long time: The exhausting setup phase before writing actual business logic.
As part of my ongoing engineering work at PulseLabs, I frequently test and prototype product ideas. But every single time, I found myself spending 3–4 weeks repeating the exact same setup:
- Configuring OAuth callback handling
- Designing Entity Framework models and running PostgreSQL migrations
- Handling JWT access & refresh tokens securely
- Wiring up payment gateways and handling brittle webhooks
- Building Docker environments that actually work locally and in production
By the time the app foundation was ready, the initial momentum was gone.
So, I spent the last two months building NetPulse—an enterprise-grade, clean-architecture SaaS boilerplate designed to crush that setup phase down to under 5 minutes.
Here is what I focused on solving during this build, how I structured the project, and the architectural decisions I made along the way.
1. Solving "Multi-Provider Payment Lock-In"
Most SaaS templates lock you into a single payment gateway (usually just Stripe). But depending on where your customers are or how you handle international taxes/MoR (Merchant of Record), you might prefer Polar.sh or Lemon Squeezy.
Instead of hardcoding Stripe everywhere, I engineered a Multi-Gateway Billing Engine in the backend:
┌──────────────────────┐
│ IBillingService │ (Abstraction Layer)
└──────────┬───────────┘
│
┌────────────────────┼────────────────────┐
▼ ▼ ▼
[ StripeProvider ] [ PolarProvider ] [ LemonSqueezyProvider ]
Whether a subscription event (Free, Pro, Enterprise) comes from Stripe, Polar, or Lemon Squeezy, the API standardizes subscription lifecycles, checkout sessions, and webhook processing seamless inside ASP.NET Core.
- The Tech Stack: Clean Architecture + Modern Frontend I wanted a stack that offers blazing performance, type safety, and zero bloat:
Backend: ASP.NET Core (.NET 8 Web API) using Clean Architecture (Domain, Application, Infrastructure, and WebApi presentation layers).
Database & ORM: PostgreSQL 16 + Entity Framework Core 8 (Npgsql) with code-first migrations and connection pooling.
Frontend: Next.js (App Router, React 18, TypeScript, Tailwind CSS, Shadcn UI / Radix primitives).
Auth & Security: ASP.NET Core Identity + JWT Bearer tokens + Google & GitHub OAuth 2.0. Integrated with Audit Logging, Rate Limiting, and Global Exception middleware.
- The "One-Command Setup" Nightmare (Solved with Docker) Setting up a full-stack environment with .NET, Node, PostgreSQL, and local webhook tunnels manually is a headache for developers cloning a starter kit.
I packaged the entire ecosystem into a single docker-compose.yml setup. Running:
docker compose up -d --build
Boots up the Next.js frontend, .NET 8 Web API, PostgreSQL 16 DB, and an automated Stripe CLI webhook tunnel container simultaneously.
Here’s a quick glance at the repository structure:
NetPulse/
├── client/ # Next.js App Router Frontend
├── src/ # .NET 8 Backend Solution
│ ├── Core/ # Domain & Application Business Logic
│ └── WebApi/ # Controllers, Middlewares & Config
├── docker-compose.yml
└── NetPulse.sln
Key Lessons Learned from 2 Months of Building
Separation of Concerns saves sanity: Keeping payment provider integrations inside the Infrastructure layer means swapping gateways doesn't touch the core business logic.
Developer Experience (DX) matters most: A boilerplate shouldn't just be "code"—it needs step-by-step documentation, working .env.example templates, and zero-headache local deployment.
I’d Love Your Feedback! 💬
As I finalize version 1.0 of NetPulse, I’d love to get insights from fellow .NET devs, Next.js builders, and SaaS founders:
Payment Gateways: Do you prefer using traditional processors like Stripe, or Merchant of Record (MoR) platforms like Polar.sh / Lemon Squeezy for your SaaS?
Backend Architecture: Do you prefer strict Clean Architecture (4 layers) for SaaS templates, or a Vertical Slice Architecture approach?
What is the single most annoying feature you hate setting up manually in every new project?
Drop your thoughts in the comments below! I'll be active in the thread replying to architecture questions. 👇
Top comments (0)