Skip to main content
GullySystem
A practical guide

Why a cloud database costs more than the app it serves

Ganesh HSStrategy and Technology, GullySystem
Practical advice · 5 min read

In this guide 6 sections
The short answer

Databases are usually sized for the migration weekend and never revisited. Typical causes are an oversized instance class, provisioned storage speed nobody uses, read replicas with no readers, long backup retention and development copies running around the clock. Each can be measured and trimmed without touching the application.

Sized for the migration weekend, never resized

When a plant or a warehouse moves its servers to the cloud, the database gets the biggest instance class on offer. Nobody wants a slow cutover. That is sensible for one weekend. It is wasteful for the next three years.

Look at the monitoring graphs for a normal month. If CPU rarely climbs and memory sits half empty, the instance is too large. Check connection counts too, since an ERP or MES that opens hundreds of idle connections can look busier than it is. Pooling at the application layer, with PgBouncer or RDS Proxy for example, often lets a smaller class carry the same load.

  • Peak and average CPU over thirty days, including month-end
  • Freeable memory and swap activity
  • Connection count against the configured limit
  • Read and write latency at peak

Provisioned storage speed nobody uses

Managed databases let you buy storage throughput in advance. Provisioned IOPS volumes cost more than general-purpose ones, and the charge continues whether the disk is busy or not. A migration team often picks the fastest tier to be safe, and nobody returns to lower it once the cutover succeeds.

Compare the provisioned figure with the peak read and write operations per second from the last month. If the peak is a fraction of what you pay for, move to a general-purpose volume. Test on a restored copy first, because the change can take hours on a large disk. Note that some volume types limit how often you can modify them, so plan one change, not three.

Replicas without readers and failover you never rehearsed

A read replica helps only if something reads from it. Check whether the reporting tool or the application actually points at the replica endpoint. Many replicas were created for a report that was later moved elsewhere.

Multi-zone standby is different. It buys failover and is worth paying for on a production system. It is not worth paying for on a test copy. Keep the standby where an outage would stop shipments or invoicing, and drop it elsewhere. Rehearse a failover once a year so the standby you pay for actually works.

  • Replica endpoint traffic over the last month
  • Which reports or dashboards connect to it
  • Standby settings on non-production copies
  • Cross-region replicas with no recovery plan attached

Backups kept far longer than anyone needs

Automated backups are charged once they exceed the size of the database. Manual snapshots stay until someone deletes them, and they pile up after every upgrade or release. A retention window of several weeks on a development copy buys nothing.

Set retention by system, and write the chosen number into the runbook. Production follows your recovery point and any record-keeping rule the business has. Staging needs a few days. Throwaway copies need none. Delete manual snapshots older than the last verified restore test. Then run a restore into a scratch instance and time it, because a backup you have never restored is a hope, not a plan.

Development copies that run all night

Every developer who asked for a production-sized copy got one, and each is billing around the clock. List every database instance, then sort by name and last connection date. Anything with no connections in a fortnight is a candidate for a final snapshot and a delete. Ask the named developer first; a quick message beats a missed sprint demo.

For copies that stay, stop them out of hours or shrink the class. Finish with a list of what to change, what to test and who signs off.

Database cost audit sheet

Audit table, a line for each database instance. Columns: environment, engine and version, instance class, memory, thirty-day peak CPU. Then storage type, provisioned and peak IOPS, replica count, reader traffic and backup retention days. Last come snapshot count, last connection date and the proposed change.

Open a blank worksheet to print

Questions owners ask

Is the database really the biggest line on most bills?

Often it is the largest or second largest, because it runs around the clock on a large instance with fast storage. Check your own invoice by service rather than assuming. Filter by engine and by instance family, and include the storage and backup lines that sit under the database heading.

Can we shrink a production database safely?

Yes, with care. Measure a full month first, restore a copy at the smaller size, replay realistic load, and schedule the change in a quiet window with a way back.

Do we need read replicas?

Only if something reads from them. A replica serves reporting or spreads read load. If no connection string points at it, it adds cost without helping anyone. Look at the replica’s connection count over a month; zero means it can go.

How long should we keep database backups?

Keep production backups long enough to meet your recovery needs and any record-keeping obligations. For staging and development, a few days is usually enough. Test a restore regularly.

Browse all guidesBack to top ↑
Next step

Have a specific situation to work through?

This article covers the general case. Tell us what you’re actually dealing with and we’ll respond directly.

Share Your Requirements