← Articles

April 4, 2026 · Tim Fraser, Cloud Operations Lead

AWS Migration Cost Surprises and How to Avoid Them

You estimated AWS costs before migrating. You used the pricing calculator, accounted for compute and storage, and arrived at a monthly figure that made the business case work. Then the first real bill arrived 40-60% higher than projected.

This happens with almost every migration. Several significant cost categories are either invisible on-premises or work fundamentally differently in the cloud. Knowing what they are — or catching them early after migration — makes the difference between a surprise and a plan.

Data transfer fees

On-premises, traffic between servers is free. On AWS, traffic between availability zones, regions, and the internet costs money. Data transfer is the most underestimated line item in migration planning.

Cross-AZ traffic costs $0.01/GB each direction. A web server in one AZ talking to a database in another, processing 500GB/month — $10/month for one pair. Multiply across every service. Internet egress costs $0.09/GB for the first 10TB. An application serving 2TB/month pays $180/month in data transfer — a cost that didn't exist on-premises. How to manage it: Review architecture for cross-AZ chattiness. Use CloudFront for content delivery. Check the data transfer section of your bill monthly for the first quarter.

NAT Gateway costs

Private subnets access the internet through NAT Gateways: $0.045/hour (~$32/month just for existing) plus $0.045/GB processed. This gets expensive when applications make frequent calls to AWS API endpoints — every SDK call to S3, DynamoDB, or SQS goes through the NAT Gateway.

How to manage it: Set up VPC endpoints for frequently used services. S3 and DynamoDB have free gateway endpoints. Interface endpoints cost $0.01/hour each but are much cheaper than NAT Gateway processing at volume. One team reduced their NAT Gateway bill from $400/month to $50/month with four VPC endpoints.

Oversized instances from lift-and-shift

Lift-and-shift replicates the source environment. If your server was a 16-core, 64GB machine, the migration plan puts it on a comparable EC2 instance. The problem: most on-premises servers were already oversized for peak loads that happen 2% of the time.

After migration, these instances sit at 10-15% average CPU, costing three or four times what a right-sized instance would.

How to manage it: Wait 2-4 weeks for representative traffic patterns. Check CloudWatch CPU and memory metrics. Anything averaging below 30% CPU is a candidate for downsizing. Go one size at a time and monitor for a week.

Storage class mismatches

Lift-and-shift typically puts everything on gp3 EBS and S3 Standard. Fine for active data, expensive for data that's rarely accessed.

EBS volumes provisioned for peak IOPS waste money when the workload doesn't need them. A gp3 at 10,000 IOPS costs significantly more than the baseline 3,000 IOPS. S3 storage accumulates fast. S3 Standard costs $0.023/GB/month. Glacier Instant Retrieval costs $0.004/GB/month. For 1TB of archival data: $23/month versus $4/month. How to manage it: Review EBS provisioned IOPS — reduce any set high "just in case." For S3, implement lifecycle policies to transition objects to cheaper classes after 30-90 days. Use Intelligent-Tiering for unpredictable access patterns.

Elastic IPs, load balancers, and other fixed costs

Several AWS resources have baseline costs that exist regardless of usage:

How to manage it: Audit for resources that only need to run during business hours. RDS instances can be stopped (up to 7 days at a time) or scheduled to stop/start. Dev and staging environments can use smaller instance types than production. Release any Elastic IPs that aren't essential.

Finding cost surprises early

The best time to catch these surprises is in the first 30 days, when remediation is straightforward. After three months, right-sizing and architectural changes feel like a separate project that never gets prioritised.

plainfra analyses cost data and resource configuration together. Ask "What are my biggest cost drivers since migration?" or "Where am I overspending on data transfer?" and you get specific numbers with specific resources. Weekly reports track trends so you can see whether optimisations are working or new cost creep is replacing the old.

Catching a $200/month NAT Gateway problem in week two is an easy fix. Discovering it in month six means $1,200 already spent.

Try plainfra free → 50K tokens, 7 days, no charge. Or see the interactive demo →.