Journal — December 12, 2025 · 5 min read
Auth — Build vs Buy
A cost model for authentication: what "auth" includes beyond a login form, what building it costs in engineer-weeks, what Auth0, Clerk and WorkOS cost, and the migration trap nobody prices in.
A login form is half a day of work. Authentication is two to four engineer-months, and then it never stops costing you. Almost everyone who scopes the first thing believes they have scoped the second.
So let's do the arithmetic properly. My position is buy by default, and there's one caveat that matters more than any number in the price comparison.
What "auth" actually means
Write out everything that ships inside a real authentication system:
- Password reset with tokens that expire and can't be replayed
- Email verification, and the deliverability problem that arrives with it
- Session management: what lifetime, stored where, invalidated how
- Session invalidation on password change, on "log out everywhere", on role change
- Refresh token rotation with reuse detection
- Rate limiting on login, reset, and verification endpoints separately
- Account lockout, plus the support burden of letting locked-out people back in
- MFA: TOTP, recovery codes, and the "I lost my phone" flow
- Social login per provider, each with its own quirks
- SAML SSO and SCIM provisioning, the first day an enterprise buyer asks
- Audit logs of who signed in from where
- Account recovery when someone loses both password and second factor, which is a policy problem wearing a code problem's clothes
- Breach response: forced rotation, notification, forensics
That list is the actual product. The login form is one bullet.
Pricing the build
Honest ranges from having done most of this:
Core email/password with sessions. One to two weeks to something demoable. Another two to something I'd defend in a security review.
MFA done properly. Two to three weeks. Generating TOTP secrets is an afternoon; recovery codes, rate limits, and the lost-device path are the rest.
SAML SSO and SCIM. Four to eight weeks, and this is the estimate people get most wrong. Okta, Entra, Google Workspace, OneLogin and Ping each interpret the spec differently, and every new enterprise customer is a small integration project forever.
Audit logs, rate limiting, admin tooling. Two to three weeks, and it's the part that gets cut and then rebuilt under deadline when a customer sends a security questionnaire.
Call it three engineer-months before SSO and closer to five with it. Then the recurring cost: dependency patches, provider API changes, incident response, support tickets, pen-test remediation. Ten to twenty percent of one engineer, permanently.
Here's where it gets interesting. If you're paying Indian salaries, three months of engineering is maybe ₹3L (roughly $3,500). At the freelance rates I charge, the same work is $25,000 or more. Build genuinely looks cheaper when your engineering time is cheap, and that's the strongest honest argument for it.
But the maintenance side doesn't scale with your salary band. It scales with attack surface, which costs the same everywhere.
Pricing the buy
Approximate list prices as of late 2025, and these move constantly, so verify before you quote them to anyone:
Clerk. Generous free tier in the several-thousand-MAU range, then per monthly active user. Best developer experience of the group, in my opinion.
Auth0. Small free tier, then B2C tiers that step up sharply. Enterprise connections live near the top of the pricing page.
WorkOS. Core auth free for a large user count, then priced per SSO connection, roughly $100+ per enterprise customer per month. That model is honest about what it's selling.
Cognito. Cheapest per-MAU by a wide margin. Also the one where I've spent the most hours reading forum threads at 1am.
Supabase Auth. Effectively bundled with the Postgres plan you're already paying for, which is why it wins on cost for small products. More on that tradeoff in Supabase vs Firebase.
Two things to price carefully. The first is the MAU cliff: every vendor's curve is trivial at 1,000 users and a real line item at 100,000. A consumer product with a big free tier is the worst possible shape for per-MAU pricing, because you pay per user for users who pay you nothing.
The second is the enterprise upsell. SAML, SCIM, and audit log export are held on the top tier by nearly every vendor, and that tier is where published pricing turns into a sales call. Closing your first $50k enterprise deal will also trigger a five-figure auth invoice. Don't discover that mid-negotiation.
The caveat that beats the price comparison
Migrating off an auth provider is one of the nastiest migrations in software.
Password hashes are the obvious part: some vendors export bcrypt hashes on request, some won't export them at all, and "every user must reset their password" is a churn event, not a migration step. But the worse part is structural. If your orders table has a user_id that is an opaque Auth0 subject string, then the provider owns your data model, and leaving means rewriting foreign keys across your entire schema while the product is live.
So own your user table. Your database has a users row with a primary key you generated. The provider's identifier is a column on that row, not the key. Email, created_at, role, and everything the product cares about live in your Postgres. Let the vendor own credentials, sessions, MFA secrets, and the SAML plumbing, which is exactly the stuff you don't want.
That single discipline turns a catastrophic migration into a merely annoying one, and it costs you nothing at build time.
Where rolling your own is genuinely fine
One internal app, one organisation, session cookie in Postgres, argon2 hashes, no SSO ever. That's a couple of hundred lines and I've written it more than once without regret. It's the same instinct I wrote about in reaching for boring technology: small, understood, no vendor in the path.
I got the boundary wrong once. I built exactly that for an internal tool, felt clever about it, and eleven months later the company standardised on Google Workspace SSO and wanted everything behind it. Retrofitting OIDC onto a hand-rolled session system with live users took three weeks I hadn't budgeted, and one bad afternoon where half the team couldn't log in.
The rule I use now: the moment a second organisation becomes a customer, or the word "Okta" appears in a sales call, you were never in the roll-your-own case.
The judgment
Buy, but treat the vendor as a credential store rather than a system of record. The build-vs-buy spreadsheet almost always understates build by leaving out SSO and maintenance, and almost always understates buy by leaving out the MAU curve. Both errors are survivable. Handing a vendor your primary keys is the one that isn't.