Road to 100 SaaS products with AI: Part 2

I enjoy building web apps that anyone in the world can use and pay for. There's something special about shipping a product and having someone on the other side of the world sign up for it. That's why I'm building 100 SaaS products: I love building, and I love turning what I build into real revenue.

But building even one SaaS product isn't problem-free. In Part 1 I introduced my first product, Deploy. In this post I'll go through the problems I've run into so far, and how I'm solving them.

Bugs in subscription upgrades

I started building Deploy using Fable, and I chose Paddle as my merchant of record (MOR). A merchant of record handles payments, sales tax, and invoicing on your behalf, which is a huge energy, time and admin saver when you're selling to customers all over the world.

The first version of the app Fable built had a problem with subscription upgrades. When a user upgraded their plan, the app created a second subscription instead of upgrading their existing one. The user would end up with two active subscriptions, and two charges. Thankfully, no real customers were affected, as I caught and fixed the problem early on during development.

The fix was to treat an upgrade as a change to the existing subscription rather than a new checkout: look up the customer's current subscription and update its plan, letting Paddle handle the proration. Billing code is one area where you can't just trust that generated code works. You have to test every path a customer can take: signing up, upgrading, downgrading, and cancelling.

Preventing duplicate transactions

Closely related to the upgrade bug is the problem of duplicate transactions. If a request to the payment provider is sent twice (a user double-clicks a button, or a network request is retried) you can end up charging a customer twice.

The standard solution is an idempotency key: a unique key sent with each request, so that if the same request arrives twice the payment provider only processes it once. At present, Paddle doesn't support idempotency keys, which means I have to guard against duplicates myself in my own code. No users were affected by duplicate transactions.

Polar.sh does support idempotency keys, and I'm considering switching to them as my MOR for future products.

Building a new SaaS is still slow

AI has made building software dramatically faster, but building a complete SaaS product is still slow. It took me weeks to build Deploy.

A real product isn't just the core feature. It's authentication, billing, emails, settings pages, marketing pages, and all the edge cases in between. If I want to reach 100 products, weeks per product isn't fast enough. I need to get each new product from idea to launch much faster, and I'll be writing about how I'm doing that in future posts.

Coming up with new ideas is slow

I enjoy solving my own problems by building my own products, also known as dogfooding. Deploy started as a solution to one of my own problems: I wanted to track my long term goals visually, and I couldn't find a tool that did it the way I wanted.

The catch is that dogfooding depends on having problems to solve. To find inspiration for new products, I need to keep finding new problems, whether they're my own or other people's. Coming up with good ideas is slower than I'd like.

Smaller bugs

Beyond the big problems above, there have been plenty of smaller bugs. Most of them have been easily solvable.

The problem I'm tackling now: Distribution

Building a product is only half the job. The other half is getting it in front of people who need it. Distribution is the problem I'm currently tackling, and it's the reason I'm writing here on my blog.

By sharing what I'm building, the problems I hit, and how I solve them, I hope to reach people who find my products useful.

Follow along

This is just the start. As I work my way towards 100 SaaS products, I'll keep running into new problems, and I'll write about each one here as I attack it. Follow along with this series to see how it goes.