How to Scale an App to 10 Million Users on AWS
Once upon a time…
There were two smart software engineers, James and Robert, who worked at a big tech company called Hooli. Even though they were talented, they never got promoted. This made them feel sad and stuck.
But one day, they had a bright idea: Why not start their own company? So, they decided to build an app together.
Their app started to grow quickly, and soon, they had to figure out how to handle more and more users. They wanted to keep things simple, so they chose to use Amazon Web Services (AWS) to host their app.
Let’s follow James and Robert’s journey as they scaled their app from zero to 10 million users!
1.The Very Beginning: Prelaunch
At first, their app wasn’t ready for the public. They just needed a simple website to tell people about it. So, they built a basic launch page using a static website framework.
To host this page, they used AWS Amplify, which made it easy and cheap to get their site online. Since the page was just static content (like text and images), it cost almost nothing.
For a little bit of backend logic (like handling sign-ups), they used AWS Lambda. This is a “serverless” service, meaning they didn’t have to worry about running or managing servers—just their code.
2.The First Launch
When they launched their app, only a few people signed up. So, they kept things simple by running everything—website, backend, and database—on one EC2 instance (a virtual server on AWS).
They gave this server a special static IP address (called an Elastic IP) and used Amazon Route 53 to point their domain name to it.
But as more users signed up, some needed to store more data. So, they upgraded to a bigger EC2 instance. This is called vertical scaling: making a single server more powerful.
However, they realized this wasn’t perfect. If that one server failed, everything would go down. Plus, there’s a limit to how big a server can get.
3.More Users, More Problems
Soon, their single server ran out of memory. So, they split things up: one EC2 server for the backend, and another, bigger one for the database.
They chose an SQL database (like MySQL or PostgreSQL) because it was reliable and had lots of support.
For a while, things were smooth.
4.Growing to a Thousand Users
But then, disaster struck: a power outage hit the data center where their servers lived.
To prevent this from happening again, James and Robert set up extra servers in a different availability zone (another data center in the same region).
They also set up leader-follower replication for their database. The “leader” handled all the data changes (writes), while the “follower” handled reading data. If the leader failed, the follower could take over automatically.
To balance the load, they used an Elastic Load Balancer (ELB), which spread out users’ requests across their servers and made sure traffic didn’t go to any server that was down.
5.Scaling to Ten Thousand Users
As their app kept growing, their servers started to get overloaded again.
To fix this, they made their backend “stateless.” This means any server could handle any request, because user session data was stored separately in ElasticCache (a fast, managed caching service).
They added more backend servers behind the load balancer, and more database followers to handle the extra load.
But soon, the database was struggling to keep up with all the read requests. So, they used ElasticCache to store (or “cache”) the most popular data, which made things much faster.
They also moved all their static files (like images and scripts) to Amazon S3 (for storage) and CloudFront (a content delivery network, or CDN), which put copies of their files closer to users around the world.
At one point, they noticed their traffic spiked at certain times. To avoid paying for extra servers all the time, they set up autoscaling—servers would automatically start or stop based on how busy things got. They used CloudWatch to monitor everything and trigger autoscaling.
6.Half a Million Users and High Availability
With half a million users, James and Robert wanted to make sure their app was always available—99.99% of the time (which means less than an hour of downtime per year!).
They spread their servers across several availability zones and started using DynamoDB, a managed NoSQL database, for storing session data.
They also switched to a microservices architecture. Instead of one big app, they broke it into smaller pieces (services) that could be scaled independently.
They put load balancers between each layer of their app, so each part could grow as needed.
To make managing all these resources easier, they used CloudFormation, which let them create and update their infrastructure automatically with templates.
7.Ten Million Users: Advanced Scaling
When they reached 10 million users, their database started to slow down because too many people were trying to write data at once.
To solve this, they federated their database—splitting it into several databases based on business areas (like users, products, etc.). This helped them scale, but made it harder to get data from different databases at once.
They also used sharding—splitting one big database into smaller pieces, each on its own server. This made things faster, but required more complex code to put data together when needed.
For data that didn’t need complex relationships, they stored it in NoSQL databases.
Finally, they expanded their app across multiple AWS regions (geographic areas with their own data centers). This gave them even more reliability and let them serve users all over the world quickly.
And They Lived Happily Ever After
Thanks to AWS and smart scaling, James and Robert’s app could handle millions of users from all over the globe. They learned that starting simple and adding complexity only when needed was the best way to grow.
Key Takeaways:
- Start simple: Use basic hosting and serverless tools for your MVP.
- Scale up, then out: Upgrade servers at first, then split your app into pieces and add more servers as you grow.
- Use caching and CDNs: Store popular data and static files closer to users for speed.
- Automate everything: Use autoscaling and infrastructure templates to save time and money.
- Plan for failure: Spread your app across different data centers and regions for high availability.
Want to learn more?
Scroll down to the references for deeper reading!
Share this story with your friends—referrals get rewards!
References: