Lift-and-Shift to AWS First, Then Modernise: How a B2B SaaS Company Escaped the Data Centre
A 120-engineer B2B SaaS company migrated 47 workloads from ageing on-prem hardware to AWS in 14 months, cutting P99 latency by 60% and infrastructure spend by 34% after a deliberate two-phase approach.
Infrastructure · intermediate · 12 min read · 2358 words · By Sandip Das · Published
Composite scenario: built from common industry patterns; the figures are illustrative.
What this covers
- The Situation
- The Problem
- Constraints
- Options Considered
- The Solution
- Implementation
- Results
- What Went Wrong Along the Way
- Lessons Learned
- Apply It Yourself
Key numbers
| Metric | Before | After |
|---|---|---|
| Monthly uptime (worst month, trailing 6) | 99.6% | 99.97% |
| P99 API latency | 840 ms | 330 ms |
| Monthly infrastructure spend | $148,000 | $97,500 |
| Unplanned outages (trailing 12 months) | 11 | 1 |
| Deployment frequency | 2x per week | 12x per week |
Key components
- AWS Application Migration Service (MGN) — Continuously replicated on-prem VM disk images into AWS, enabling low-RPO migration without application changes.
- AWS Database Migration Service (DMS) — Ran full-load plus change-data-capture replication of PostgreSQL in parallel for three weeks, enabling a low-risk DNS cutover.
- Terraform — Managed all AWS infrastructure as code from day one, providing reproducibility and a clear audit trail for SOC 2.
- SQS and SNS — Replaced a self-hosted RabbitMQ cluster, eliminating two categories of outage and adding native dead-letter-queue support.
- CloudWatch and X-Ray — Provided the team's first end-to-end observability across API and worker tiers, enabling right-sizing and incident diagnosis.
- Route 53 weighted routing — Enabled a gradual, reversible DNS cutover at 5% then 100% traffic, removing the need for a risky big-bang switchover.
The Situation
This is a composite scenario built from patterns common across the industry; the organisation, team structure, and figures are illustrative and do not represent any single company.
The organisation is a 120-engineer B2B SaaS company selling workflow-automation software to mid-market financial services firms. Revenue sits around $28 M ARR and is growing at roughly 30% year-on-year. The engineering team is split across three product squads and a six-person platform team. The platform team owns everything below the application layer: servers, networking, databases, and the deployment pipeline.
The production estate at the start of the project comprised 47 distinct workloads running across two co-located data centres in the same metro area. The primary stack was Python/Django REST APIs backed by PostgreSQL 13, Redis for session caching, and a Celery-based task queue. Front-end assets were served from Nginx on the same VMs. A secondary data-processing pipeline ran on a cluster of bare-metal machines that the team had inherited from an acquisition two years earlier. Hardware was a mix of owned and leased kit, with the oldest servers already past their vendor support window.
At peak, the platform handled around 18,000 authenticated API requests per minute, with background workers processing roughly 400,000 tasks per day. The PostgreSQL primary held about 2.1 TB of customer data. Deployments happened twice a week via a bespoke Fabric-based script that SSH'd into each server in sequence.
The rest of this case study — the trade-offs, the scaling numbers and the build prompt — is available to LearnXops members. Create an account or see membership.
Topics: aws, migration, infrastructure, terraform, lift-and-shift, modernisation
Related case studies
- How 37signals Saved $10M by Leaving AWS for Owned Hardware
- How a 120-Engineer SaaS Company Migrated from One AWS Account to a Multi-Account Landing Zone
- How a B2B SaaS Team Cut CI and Batch Costs by 70% Using Spot Instances Without Losing Jobs
- How a B2B SaaS Team Cut Their AWS Bill by 40% with Rightsizing, Graviton, Savings Plans and S3 Lifecycle Policies
- How a B2B SaaS Team Split a 4,000-Resource Terraform Monolith Into Modules Without Downtime
- The 2017 Amazon S3 Outage: One Mistyped Command and the Cost of a Slow Restart