Home / Articles / Blog

How to Estimate What Your SaaS Will Cost to Run (Before the Bill Surprises You)
SaaSHosting CostsOpen SourceIndie HackersVercelCloudflareClaude Code

How to Estimate What Your SaaS Will Cost to Run (Before the Bill Surprises You)

How to estimate your SaaS running cost by hand: read the repo like a bill, find hidden costs, swap to cheaper stacks, and share the estimate with a free open-source calculator.

Shrey Vijayvargiya

How this started

I kept getting the same question in two different shapes.

The first shape came from me. I like running open-source tools on my own infrastructure instead of paying for the hosted version. Before I clone a repo and deploy it, I want to know one thing: what will this cost me every month? Not the server alone. The database, the email provider, the analytics, the queue, the storage, all of it. Most READMEs tell you how to run a project. Almost none tell you what it costs to keep it running.

The second shape came from clients. When I build something for a client, the conversation always gets to "so what will this cost us per month?" I used to answer in a chat message. Then the client would forward my message to their CTO or their co-founder, someone would ask "what if we get 10x the users?", and I'd redo the maths in another message. The numbers lived in screenshots and WhatsApp threads.

What I wanted was one file. Something I could hand to a client, they could open in a browser, change the user count themselves, and forward to whoever signs the cheques. That's how StackBudget started: a Claude Code skill that reads a repo and returns a single HTML cost calculator anyone can open.

But the skill only automates a process you can do by hand. So this post covers the manual way first, the hidden costs most estimates miss, and the cheaper swaps that cut the bill. The skill is at the end.

Running cost vs building cost

These are two different numbers, and mixing them up is how estimates go wrong.

  • Building cost is the one-time work: design, development, your time or a developer's invoice.
  • Running cost is the monthly bill to keep the product alive: hosting, database, email, analytics, AI tokens, storage, logs and payment fees.

This post is about running cost. It's the number that grows with every user you add, and the one that quietly kills small SaaS products. A product that costs $20 a month at launch can cost thousands at scale if the stack charges per request, per event or per seat.

I've written about how we keep ihatereading.in under $100 a month at 10k visitors. Most of that came from understanding exactly which line items scale with traffic.

Step 1: Read the repo like a bill

You don't need AI to do a first estimate. You need about 30 minutes and four files.

Start with package.json

Every dependency that talks to a paid service is a line on your future bill. Open package.json and sort the dependencies into two groups:

  • Free libraries: React, Tailwind, Radix, date libraries, utility packages. These cost nothing to run.
  • Service SDKs: anything named after a company. @supabase/supabase-js, stripe, posthog-js, resend, @aws-sdk/client-s3, @upstash/redis, openai, @clerk/nextjs, @sentry/nextjs. Each one is a vendor with a pricing page.

Ignore devDependencies for running cost. Test runners and linters don't bill you in production.

In a typical SaaS repo, most packages are free libraries. When we scanned OpenNote, one of our open-source apps, 62 of its 63 packages were free. The cost hides in the handful that aren't.

Then read the env example file

.env.example is the most honest document in any repo. Every key that ends in _API_KEY, _SECRET or _URL points at an external service:

bash
# Key names only. Never open the real .env.
grep -hoE "^[A-Z_]+=" .env.example .env.sample 2>/dev/null | sort -u

DATABASE_URL is a database. RESEND_API_KEY is an email bill. OPENROUTER_API_KEY is an AI bill. S3_ENDPOINT is storage.

Then grep for API calls the manifests don't show

Some services don't have an SDK in package.json at all. They're called with plain fetch. This is the step people skip:

bash
# Every external API the code calls
grep -rhoE "https://[a-z0-9.-]*api[a-z0-9.-]*\.[a-z]+" src lib app --include=*.{js,ts,jsx,tsx} | sort | uniq -c

# Every environment variable the code actually reads
grep -rhoE "process\.env\.[A-Z_]+" src lib app | sort -u

When I ran a dependency scan on OpenNote, it found only one paid service: hosting. But OpenNote calls OpenRouter for its AI features through a plain fetch in lib/ai/openrouter.js. There's no SDK, so nothing in package.json gives it away. If I'd stopped at the manifest, I'd have missed the AI bill entirely.

Finally, check where it deploys

Deploy files tell you which hosting bill you're on:

  • vercel.json means Vercel.
  • wrangler.toml means Cloudflare Workers.
  • fly.toml, Dockerfile or docker-compose.yml means a server or container you pay for by the month.
  • .github/workflows/*.yml shows what runs in CI and where it deploys.

Put it in a table

Now make one row per service with four columns: the unit it bills by (requests, GB, events, emails, seats), the free tier, the price after the free tier, and your expected usage. Estimate usage at three levels, say launch, growth and scale, because the cheapest option at 100 users is often the most expensive at 50,000.

Step 2: Find the hidden costs

The obvious costs are hosting and the database. These are the ones that show up later and surprise people:

  • Per-seat pricing. Vercel Pro is $20 per seat per month, so a team of four pays four times before a single visitor arrives. Many observability and error-tracking tools also price by seat.
  • Server-rendered requests. On Vercel, every server-rendered page uses Active CPU and memory that's billed on top of the plan once you pass the included usage. A mostly static site and a fully server-rendered one can have very different bills at the same traffic.
  • Bandwidth and egress. Vercel Pro includes 1 TB of transfer, then charges $0.15 per GB. AWS S3 charges for data leaving it. Cloudflare R2 charges no egress fees, which is why it matters for anything that serves files.
  • Logs and traces. Logging is free until it isn't. Grafana Cloud's free tier includes 50 GB of logs and 50 GB of traces with 14-day retention, then you pay per GB. Verbose logging in a busy API fills that quickly.
  • Idle compute. Serverless Postgres like Neon bills compute per hour. If background workers keep the database awake, it never scales to zero, and you pay for it running all month.
  • Queue polling. Redis-backed queues poll constantly, even with no jobs. On a per-command plan such as Upstash, those idle polls are billed commands.
  • Analytics events. PostHog is free up to 1M events a month, then charges per event. Autocapture on a busy app burns through that faster than people expect.
  • Free tiers that pause or cap. Supabase's free plan pauses a project after a week without activity. Free tiers are fine for testing, but check the cap before you build a launch plan on one.
  • Preview deployments and builds. Every pull request that creates a preview deployment uses build minutes and sometimes compute.
  • Payment fees. These aren't a monthly line, they're a percentage of revenue. Stripe's standard US card rate is 2.9% + 30¢ per transaction, with extra fees for international cards and currency conversion. Merchant-of-record providers charge more per transaction, because they also handle sales tax for you.
  • AI tokens. Usually the line that grows fastest. Multiply generations per user by tokens per generation by your model's price per million tokens. A cheaper model for simple tasks can cut this by an order of magnitude.
  • Email extras. Sending is cheap. A dedicated IP for better deliverability on Amazon SES is $24.95 a month on top.

Step 3: Swap toward cheaper and open-source options

Once you can see the bill, you can cut it. These are the swaps I look at first, by category. None of them is free of trade-offs, so each comes with what you give up.

CategoryCommon defaultCheaper or open-source optionWhat you give up
HostingVercel ProCloudflare Workers ($5/mo paid plan, static assets free, no egress) or a VPS with CoolifyVercel's polished Next.js integration and preview workflow
FrameworkNext.js with heavy server renderingTanStack Start, Astro, or a Vite SPANext.js ecosystem features; some migration work
DatabaseSupabase, Firebase or ConvexNeon serverless Postgres, or self-hosted PostgresBuilt-in auth, storage and realtime that BaaS platforms bundle
AuthClerk or another hosted auth serviceBetter Auth or Auth.js, running in your own appPrebuilt UI, user dashboards, and someone else handling security
PaymentsStripe with your own tax setupPolar or Dodo Payments as merchant of recordLower per-transaction fees, in exchange for tax handling
AnalyticsPostHog Cloud, uncappedPostHog with a billing cap, or self-hosted UmamiSession replay, feature flags, and other product analytics depth
EmailResendAmazon SESResend's developer experience and React Email tooling
StorageAWS S3Cloudflare R2Some AWS-only integrations
Logs and tracingPaid APMGrafana Cloud free tier, or self-hosted SigNozRetention length and managed alerting
TestingPaid cloud browser gridsPlaywright in GitHub ActionsReal-device coverage across many browsers
Deployment and CIVercel buildsGitHub Actions plus Coolify or Dokploy on a VPSOne-click deploys; you own the server now

A few notes on these:

  • The framework swap is really a rendering swap. Next.js itself is free. The cost comes from server-rendering every request on a platform that bills compute. You can cut a lot of the bill by making more pages static, even if you stay on Next.js. I went deep on this in why our websites are slow.
  • Merchant of record isn't automatically cheaper. Stripe's base card fee is lower. Polar and Dodo cost more per transaction but act as the seller and handle global sales tax. For a solo founder selling worldwide, that trade is often worth it. For a bigger team with a finance person, Stripe usually wins.
  • Self-hosting moves cost, it doesn't delete it. A self-hosted Postgres or Umami needs a server, backups and your time. Count the VPS in the bill. Count your hours too.
  • Free tiers are a launch strategy, not a scale strategy. Plan the paid tier you'll move to before you hit the cap.

If you're starting a new project and want these defaults baked in from day one, my SaaS starter kit and the free Next.js boilerplates list are good places to start.

Step 4: Share the estimate with the people who pay

An estimate that lives in your head doesn't help a client. The format matters as much as the numbers:

  • One file, not a thread. A client should be able to forward a single thing to their CTO or co-founder without you in the loop.
  • Inputs they can change. The first question is always "what if we have 10x the users?" Let them answer it themselves.
  • Every number tied to a reason. "Hosting: $40" means nothing. "Hosting: $40, because Next.js is server-rendering on Vercel Pro" starts a useful conversation.
  • The cheaper path next to the current one. Founders don't only want to know the cost. They want to know how low it could go, and what they'd trade to get there.

This is exactly the part I got tired of doing by hand.

Check your estimated budget with StackBudget

StackBudget is the free, open-source Claude Code skill I built to do all four steps above for any repo.

Point it at a codebase: the folder you're in, a local path, or any GitHub repo, public or private. It returns one interactive HTML calculator of the monthly running cost.

Install it:

bash
git clone --depth 1 https://github.com/shreyvijayvargiya/stackbudget-calculator /tmp/stackbudget \
  && mkdir -p ~/.claude/skills \
  && cp -r /tmp/stackbudget/skills/stack-budget ~/.claude/skills/ \
  && rm -rf /tmp/stackbudget

Run it in Claude Code:

text
/stack-budget                     # the current folder
/stack-budget owner/repo          # any GitHub repo

Or just ask: "What would it cost to run this repo at 50k users?"

What it does:

  • Step 1, automated. It scans every manifest (package.json including workspaces, requirements.txt, pyproject.toml, go.mod, Cargo.toml and more), deploy files and env key names, and maps packages to paid services. Then Claude reviews the scan against how the repo actually deploys, drops dev-only false positives and adds services the rules missed. That review is how it catches cases like OpenNote's fetch-based OpenRouter calls.
  • Step 2, priced. Each line names the packages that cause it, split into frontend and backend, with launch, growth and scale presets. Prices come from vendor pricing pages and are dated in the repo.
  • Step 3, a migration planner. Every service has a "Migrate to" picker: Cloudflare instead of Vercel, self-hosted Postgres instead of Neon, a cheaper model, and so on. "Pick cheapest stack" chooses the lowest option per row and skips free tiers your usage would break. Self-hosted choices add server cost, so the savings shown are net.
  • Step 4, shareable. It's one HTML file, in USD and INR, with light and dark themes, and it works on a phone. Send it to a client, attach it to an issue, or forward it to your CTO.

A real example from the repo: for Reloop, an open-source Resend alternative with 227 packages and 10 paid services, the managed stack at 5,000 users and 1M emails a month comes to about $359 a month. "Pick cheapest stack" brings it to about $96 a month. You can open that report in your browser to see what your clients would get.

What it won't do: it only reads. It never commits, pushes or opens pull requests, and it never opens your real .env files, only the key names in example env files. Remote repos are cloned to a temporary folder and deleted after the report is built.

If you try it, star the repo and open an issue for any vendor it doesn't price yet. Pull requests with new pricing rules are welcome. More open-source tools like this are in the iHateReading open-source projects post, and new ones land in the monthly magazine.

External Links (23)

Explore topics

More in

Weekly letter

Subscribe to iHateReading

Our once-a-week newsletter on programming, jobs, AI, and building products online.

Our once a week newsletter on Programming, Jobs, AI, and Business